svn merge -r108815:112761 svn+ssh://svn.lindenlab.com/svn/linden/branches/server/server-1.26

The biggest things in this are Scalable Space Servers and Maint-Server-6

QAR-1209 : SSS
QAR-1295 : maint-server-6

Conflicts resolved by prospero:

C    scripts/farm_distribute

C    scripts/automated_build_scripts/build-linux.sh : resolved by
                     prospero, mostly kept the merge-right version in
                     the conflict, but there was one block of repeated
                     code from earlier that I removed.

C    scripts/automated_build_scripts/build-mac.sh : kept merge-right

C    indra/llcommon/llversionserver.h : svn revert

C    indra/newsim/llsimparcel.h : kept *both*... working had "setArea",
                    merge-right had exportStream and importStream

C    indra/newsim/llsimparcel.cpp : see llsimparcel.h

C    indra/newsim/lltask.h : working had LLTask derived also from
                   LLScriptResourceConsumer, merge-right had LLTask
                   dervied also from LLAgentPosition.  To resolve
                   conflict, derive from both.

C    indra/newsim/lllslmanager.h : kept merge-right (had an added comment)

C    indra/llmessage/llhttpnode.h : kept working (added the definition
                   of method LLHTTPNode::extendedResult)

C    indra/lscript/lscript_execute_mono/llscriptexecutemono.cpp
C    indra/lscript/lscript_execute_mono/llscriptexecutemono.h
                  : These two were resolved by si, in consultation with daveh


I also had to add the following stubs to
indra/newsim/tests/llgodkickutils_test.cpp in order to get it to
compile:

  // LLScriptResourceConsumer interface methods in LLTask
  LLScriptResource::LLScriptResource() { }
  LLScriptResourcePool::LLScriptResourcePool() { }
  LLScriptResourcePool LLScriptResourcePool::null;

  LLScriptResourceConsumer::LLScriptResourceConsumer() { }
  LLScriptResourcePool& LLScriptResourceConsumer::getScriptResourcePool() { return LLScriptResourcePool::null; }
  const LLScriptResourcePool& LLScriptResourceConsumer::getScriptResourcePool() const { return LLScriptResourcePool::null; }
  bool LLScriptResourceConsumer::switchScriptResourcePools(LLScriptResourcePool& new_pool) { return false; }
  bool LLScriptResourceConsumer::canUseScriptResourcePool(const LLScriptResourcePool& resource_pool) { return false; }
  bool LLScriptResourceConsumer::isInPool(const LLScriptResourcePool& resource_pool) { return false; }
  void LLScriptResourceConsumer::setScriptResourcePool(LLScriptResourcePool& pool) { }

  S32 LLTask::getUsedPublicURLs() const { return 0; }
  void LLTask::setScriptResourcePool(LLScriptResourcePool& pool) { }
master
Robert Knop 2009-02-25 21:02:17 +00:00
parent 997d24b832
commit c88b470a8a
56 changed files with 2828 additions and 1063 deletions

View File

@ -243,6 +243,24 @@
<key>trusted-sender</key>
<boolean>false</boolean>
</map>
<!-- Simulator to simulator reliable messages -->
<key>GodKickUser</key>
<map>
<key>flavor</key>
<string>llsd</string>
<key>trusted-sender</key>
<boolean>false</boolean>
</map>
<key>RoutedMoneyBalanceReply</key>
<map>
<key>flavor</key>
<string>llsd</string>
<key>trusted-sender</key>
<boolean>false</boolean>
</map>
<!-- Simulator to simulator unreliable messages -->
<key>EdgeDataPacket</key>
<map>
@ -506,6 +524,23 @@
<boolean>false</boolean>
</map>
<key>EstateOwnerMessage</key>
<map>
<key>flavor</key>
<string>llsd</string>
<key>trusted-sender</key>
<boolean>false</boolean>
</map>
<key>RpcScriptRequestInboundForward</key>
<map>
<key>flavor</key>
<string>llsd</string>
<key>trusted-sender</key>
<boolean>false</boolean>
</map>
</map>
<key>capBans</key>
<map>

View File

@ -181,7 +181,7 @@ endif (DARWIN)
if (LINUX OR DARWIN)
set(GCC_WARNINGS "-Wall -Wno-sign-compare -Wno-trigraphs")
set(GCC_WARNINGS "-Wall -Wno-sign-compare -Wno-trigraphs -Wno-non-virtual-dtor")
if (NOT GCC_DISABLE_FATAL_WARNINGS)
set(GCC_WARNINGS "${GCC_WARNINGS} -Werror")

View File

@ -69,8 +69,13 @@ MACRO(ADD_SIMULATOR_BUILD_TEST name parent)
ENDMACRO(ADD_SIMULATOR_BUILD_TEST name parent)
MACRO(ADD_BUILD_TEST_INTERNAL name parent libraries source_files)
ADD_EXECUTABLE(${name}_test ${source_files})
SET(TEST_SOURCE_FILES ${source_files})
SET(HEADER "${name}.h")
set_source_files_properties(${HEADER}
PROPERTIES HEADER_FILE_ONLY TRUE)
LIST(APPEND TEST_SOURCE_FILES ${HEADER})
INCLUDE_DIRECTORIES("${LIBS_OPEN_DIR}/test")
ADD_EXECUTABLE(${name}_test ${TEST_SOURCE_FILES})
TARGET_LINK_LIBRARIES(${name}_test
${libraries}
)
@ -80,11 +85,11 @@ MACRO(ADD_BUILD_TEST_INTERNAL name parent libraries source_files)
ADD_CUSTOM_COMMAND(
OUTPUT ${TEST_OUTPUT}
COMMAND ${TEST_EXE}
ARGS --touch=${TEST_OUTPUT}
ARGS --touch=${TEST_OUTPUT} --sourcedir=${CMAKE_CURRENT_SOURCE_DIR}
DEPENDS ${name}_test
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
)
ADD_CUSTOM_TARGET(${name}_test_ok ALL DEPENDS ${TEST_OUTPUT})
ADD_DEPENDENCIES(${parent} ${name}_test_ok)
ENDMACRO(ADD_BUILD_TEST_INTERNAL name parent libraries)
ENDMACRO(ADD_BUILD_TEST_INTERNAL name parent libraries)

View File

@ -118,6 +118,7 @@ const char* const DEFAULT_AGNI_DATA_SERVER = "63.211.139.100";
const char* const DEFAULT_AGNI_ASSET_SERVER = "http://asset.agni.lindenlab.com:80";
// Information about what ports are for what services is in the wiki Name Space Ports page
// https://wiki.lindenlab.com/wiki/Name_Space_Ports
const char* const DEFAULT_LOCAL_ASSET_SERVER = "http://localhost:12041/asset/tmp";
const char* const LOCAL_ASSET_URL_FORMAT = "http://%s:12041/asset";
@ -138,6 +139,10 @@ const U32 DEFAULT_CAP_PROXY_PORT = 12043;
const U32 DEFAULT_INV_DATA_SERVER_PORT = 12044;
const U32 DEFAULT_CGI_SERVICES_PORT = 12045;
// Mapserver uses ports 12124 - 12139 to allow multiple mapservers to run
// on a single host for map tile generation. JC
const U32 DEFAULT_MAPSERVER_PORT = 12124;
// For automatic port discovery when running multiple viewers on one host
const U32 PORT_DISCOVERY_RANGE_MIN = 13000;
const U32 PORT_DISCOVERY_RANGE_MAX = PORT_DISCOVERY_RANGE_MIN + 50;

View File

@ -33,6 +33,8 @@
#ifndef LL_LLSTRING_H
#define LL_LLSTRING_H
#include <string>
#if LL_LINUX || LL_SOLARIS
#include <wctype.h>
#include <wchar.h>

View File

@ -300,19 +300,22 @@ U32 LLOSInfo::getProcessVirtualSizeKB()
#endif
#if LL_LINUX
LLFILE* status_filep = LLFile::fopen("/proc/self/status", "rb");
S32 numRead = 0;
char buff[STATUS_SIZE]; /* Flawfinder: ignore */
size_t nbytes = fread(buff, 1, STATUS_SIZE-1, status_filep);
buff[nbytes] = '\0';
// All these guys return numbers in KB
char *memp = strstr(buff, "VmSize:");
if (memp)
if (status_filep)
{
numRead += sscanf(memp, "%*s %u", &virtual_size);
S32 numRead = 0;
char buff[STATUS_SIZE]; /* Flawfinder: ignore */
size_t nbytes = fread(buff, 1, STATUS_SIZE-1, status_filep);
buff[nbytes] = '\0';
// All these guys return numbers in KB
char *memp = strstr(buff, "VmSize:");
if (memp)
{
numRead += sscanf(memp, "%*s %u", &virtual_size);
}
fclose(status_filep);
}
fclose(status_filep);
#elif LL_SOLARIS
char proc_ps[LL_MAX_PATH];
sprintf(proc_ps, "/proc/%d/psinfo", (int)getpid());

View File

@ -36,7 +36,7 @@
const S32 LL_VERSION_MAJOR = 1;
const S32 LL_VERSION_MINOR = 27;
const S32 LL_VERSION_PATCH = 0;
const S32 LL_VERSION_BUILD = 109809;
const S32 LL_VERSION_BUILD = 112940;
const char * const LL_CHANNEL = "Second Life Server";

View File

@ -58,26 +58,42 @@ void fallbackDestroyLLImageJ2CImpl(LLImageJ2CImpl* impl)
impl = NULL;
}
// Return string from message, eliminating final \n if present
static std::string chomp(const char* msg)
{
// stomp trailing \n
std::string message = msg;
if (!message.empty())
{
size_t last = message.size() - 1;
if (message[last] == '\n')
{
message.resize( last );
}
}
return message;
}
/**
sample error callback expecting a LLFILE* client object
*/
void error_callback(const char* msg, void*)
{
lldebugs << "LLImageJ2CImpl error_callback: " << msg << llendl;
lldebugs << "LLImageJ2COJ: " << chomp(msg) << llendl;
}
/**
sample warning callback expecting a LLFILE* client object
*/
void warning_callback(const char* msg, void*)
{
lldebugs << "LLImageJ2CImpl warning_callback: " << msg << llendl;
lldebugs << "LLImageJ2COJ: " << chomp(msg) << llendl;
}
/**
sample debug callback expecting no client object
*/
void info_callback(const char* msg, void*)
{
lldebugs << "LLImageJ2CImpl info_callback: " << msg << llendl;
lldebugs << "LLImageJ2COJ: " << chomp(msg) << llendl;
}

View File

@ -110,37 +110,11 @@ static const std::string PARCEL_ACTION_STRING[LLParcel::A_COUNT + 1] =
"unknown"
};
// Timeouts for parcels
// default is 21 days * 24h/d * 60m/h * 60s/m *1000000 usec/s = 1814400000000
const U64 DEFAULT_USEC_CONVERSION_TIMEOUT = U64L(1814400000000);
// ***** TESTING is 10 minutes
//const U64 DEFAULT_USEC_CONVERSION_TIMEOUT = U64L(600000000);
// group is 60 days * 24h/d * 60m/h * 60s/m *1000000 usec/s = 5184000000000
const U64 GROUP_USEC_CONVERSION_TIMEOUT = U64L(5184000000000);
// ***** TESTING is 10 minutes
//const U64 GROUP_USEC_CONVERSION_TIMEOUT = U64L(600000000);
// default sale timeout is 2 days -> 172800000000
const U64 DEFAULT_USEC_SALE_TIMEOUT = U64L(172800000000);
// ***** TESTING is 10 minutes
//const U64 DEFAULT_USEC_SALE_TIMEOUT = U64L(600000000);
// more grace period extensions.
const U64 SEVEN_DAYS_IN_USEC = U64L(604800000000);
// if more than 100,000s before sale revert, and no extra extension
// has been given, go ahead and extend it more. That's about 1.2 days.
const S32 EXTEND_GRACE_IF_MORE_THAN_SEC = 100000;
const std::string& ownership_status_to_string(LLParcel::EOwnershipStatus status);
LLParcel::EOwnershipStatus ownership_string_to_status(const std::string& s);
//const char* revert_action_to_string(LLParcel::ESaleTimerExpireAction action);
//LLParcel::ESaleTimerExpireAction revert_string_to_action(const char* s);
const std::string& category_to_string(LLParcel::ECategory category);
const std::string& category_to_ui_string(LLParcel::ECategory category);
LLParcel::ECategory category_string_to_category(const std::string& s);
LLParcel::ECategory category_ui_string_to_category(const std::string& s);
LLParcel::LLParcel()
@ -548,500 +522,6 @@ void LLParcel::setDiscountRate(F32 rate)
// File input and output
//-----------------------------------------------------------
// WARNING: Area will be wrong until you calculate it.
BOOL LLParcel::importStream(std::istream& input_stream)
{
U32 setting;
S32 secs_until_revert = 0;
skip_to_end_of_next_keyword("{", input_stream);
if (!input_stream.good())
{
llwarns << "LLParcel::importStream() - bad input_stream" << llendl;
return FALSE;
}
while (input_stream.good())
{
skip_comments_and_emptyspace(input_stream);
std::string line, keyword, value;
get_line(line, input_stream, MAX_STRING);
get_keyword_and_value(keyword, value, line);
if ("}" == keyword)
{
break;
}
else if ("parcel_id" == keyword)
{
mID.set(value);
}
else if ("status" == keyword)
{
mStatus = ownership_string_to_status(value);
}
else if ("category" == keyword)
{
mCategory = category_string_to_category(value);
}
else if ("local_id" == keyword)
{
LLStringUtil::convertToS32(value, mLocalID);
}
else if ("name" == keyword)
{
setName( value );
}
else if ("desc" == keyword)
{
setDesc( value );
}
else if ("music_url" == keyword)
{
setMusicURL( value );
}
else if ("media_url" == keyword)
{
setMediaURL( value );
}
else if ("media_desc" == keyword)
{
setMediaDesc( value );
}
else if ("media_type" == keyword)
{
setMediaType( value );
}
else if ("media_width" == keyword)
{
S32 width;
LLStringUtil::convertToS32(value, width);
setMediaWidth( width );
}
else if ("media_height" == keyword)
{
S32 height;
LLStringUtil::convertToS32(value, height);
setMediaHeight( height );
}
else if ("media_id" == keyword)
{
mMediaID.set( value );
}
else if ("media_auto_scale" == keyword)
{
LLStringUtil::convertToU8(value, mMediaAutoScale);
}
else if ("media_loop" == keyword)
{
LLStringUtil::convertToU8(value, mMediaLoop);
}
else if ("obscure_media" == keyword)
{
LLStringUtil::convertToU8(value, mObscureMedia);
}
else if ("obscure_music" == keyword)
{
LLStringUtil::convertToU8(value, mObscureMusic);
}
else if ("owner_id" == keyword)
{
mOwnerID.set( value );
}
else if ("group_owned" == keyword)
{
LLStringUtil::convertToBOOL(value, mGroupOwned);
}
else if ("clean_other_time" == keyword)
{
S32 time;
LLStringUtil::convertToS32(value, time);
setCleanOtherTime(time);
}
else if ("auth_buyer_id" == keyword)
{
mAuthBuyerID.set(value);
}
else if ("snapshot_id" == keyword)
{
mSnapshotID.set(value);
}
else if ("user_location" == keyword)
{
sscanf(value.c_str(), "%f %f %f",
&mUserLocation.mV[VX],
&mUserLocation.mV[VY],
&mUserLocation.mV[VZ]);
}
else if ("user_look_at" == keyword)
{
sscanf(value.c_str(), "%f %f %f",
&mUserLookAt.mV[VX],
&mUserLookAt.mV[VY],
&mUserLookAt.mV[VZ]);
}
else if ("landing_type" == keyword)
{
S32 landing_type = 0;
LLStringUtil::convertToS32(value, landing_type);
mLandingType = (ELandingType) landing_type;
}
else if ("join_neighbors" == keyword)
{
llinfos << "found deprecated keyword join_neighbors" << llendl;
}
else if ("revert_sale" == keyword)
{
LLStringUtil::convertToS32(value, secs_until_revert);
if (secs_until_revert > 0)
{
mSaleTimerExpires.start();
mSaleTimerExpires.setTimerExpirySec((F32)secs_until_revert);
}
}
else if("extended_grace" == keyword)
{
LLStringUtil::convertToS32(value, mGraceExtension);
}
else if ("user_list_type" == keyword)
{
// deprecated
}
else if("auction_id" == keyword)
{
LLStringUtil::convertToU32(value, mAuctionID);
}
else if ("allow_modify" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_CREATE_OBJECTS, setting);
}
else if ("allow_group_modify" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_CREATE_GROUP_OBJECTS, setting);
}
else if ("allow_all_object_entry" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_ALL_OBJECT_ENTRY, setting);
}
else if ("allow_group_object_entry" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_GROUP_OBJECT_ENTRY, setting);
}
else if ("allow_deed_to_group" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_DEED_TO_GROUP, setting);
}
else if("contribute_with_deed" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_CONTRIBUTE_WITH_DEED, setting);
}
else if ("allow_terraform" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_TERRAFORM, setting);
}
else if ("allow_damage" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_DAMAGE, setting);
}
else if ("allow_fly" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_FLY, setting);
}
else if ("allow_landmark" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_LANDMARK, setting);
}
else if ("sound_local" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_SOUND_LOCAL, setting);
}
else if ("allow_group_scripts" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_GROUP_SCRIPTS, setting);
}
else if ("allow_voice_chat" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_VOICE_CHAT, setting);
}
else if ("use_estate_voice_chan" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_USE_ESTATE_VOICE_CHAN, setting);
}
else if ("allow_scripts" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_OTHER_SCRIPTS, setting);
}
else if ("for_sale" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_FOR_SALE, setting);
}
else if ("sell_w_objects" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_SELL_PARCEL_OBJECTS, setting);
}
else if ("use_pass_list" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_USE_PASS_LIST, setting);
}
else if ("show_directory" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_SHOW_DIRECTORY, setting);
}
else if ("allow_publish" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_ALLOW_PUBLISH, setting);
}
else if ("mature_publish" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_MATURE_PUBLISH, setting);
}
else if ("claim_date" == keyword)
{
// BUG: This will fail when time rolls over in 2038.
S32 time;
LLStringUtil::convertToS32(value, time);
mClaimDate = time;
}
else if ("claim_price" == keyword)
{
LLStringUtil::convertToS32(value, mClaimPricePerMeter);
}
else if ("rent_price" == keyword)
{
LLStringUtil::convertToS32(value, mRentPricePerMeter);
}
else if ("discount_rate" == keyword)
{
LLStringUtil::convertToF32(value, mDiscountRate);
}
else if ("draw_distance" == keyword)
{
LLStringUtil::convertToF32(value, mDrawDistance);
}
else if ("sale_price" == keyword)
{
LLStringUtil::convertToS32(value, mSalePrice);
}
else if ("pass_price" == keyword)
{
LLStringUtil::convertToS32(value, mPassPrice);
}
else if ("pass_hours" == keyword)
{
LLStringUtil::convertToF32(value, mPassHours);
}
else if ("box" == keyword)
{
// deprecated
}
else if ("aabb_min" == keyword)
{
sscanf(value.c_str(), "%f %f %f",
&mAABBMin.mV[VX], &mAABBMin.mV[VY], &mAABBMin.mV[VZ]);
}
else if ("use_access_group" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_USE_ACCESS_GROUP, setting);
}
else if ("use_access_list" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_USE_ACCESS_LIST, setting);
}
else if ("use_ban_list" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_USE_BAN_LIST, setting);
}
else if ("group_name" == keyword)
{
llinfos << "found deprecated keyword group_name" << llendl;
}
else if ("group_id" == keyword)
{
mGroupID.set( value );
}
// TODO: DEPRECATED FLAG
// Flag removed from simstate files in 1.11.1
// Remove at some point where we have guarenteed this flag
// no longer exists anywhere in simstate files.
else if ("require_identified" == keyword)
{
// LLStringUtil::convertToU32(value, setting);
// setParcelFlag(PF_DENY_ANONYMOUS, setting);
}
// TODO: DEPRECATED FLAG
// Flag removed from simstate files in 1.11.1
// Remove at some point where we have guarenteed this flag
// no longer exists anywhere in simstate files.
else if ("require_transacted" == keyword)
{
// LLStringUtil::convertToU32(value, setting);
// setParcelFlag(PF_DENY_ANONYMOUS, setting);
// setParcelFlag(PF_DENY_IDENTIFIED, setting);
}
else if ("restrict_pushobject" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_RESTRICT_PUSHOBJECT, setting);
}
else if ("deny_anonymous" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_DENY_ANONYMOUS, setting);
}
else if ("deny_identified" == keyword)
{
// LLStringUtil::convertToU32(value, setting);
// setParcelFlag(PF_DENY_IDENTIFIED, setting);
}
else if ("deny_transacted" == keyword)
{
// LLStringUtil::convertToU32(value, setting);
// setParcelFlag(PF_DENY_TRANSACTED, setting);
}
else if ("deny_age_unverified" == keyword)
{
LLStringUtil::convertToU32(value, setting);
setParcelFlag(PF_DENY_AGEUNVERIFIED, setting);
}
else if ("access_list" == keyword)
{
S32 entry_count = 0;
LLStringUtil::convertToS32(value, entry_count);
for (S32 i = 0; i < entry_count; i++)
{
LLAccessEntry entry;
if (importAccessEntry(input_stream, &entry))
{
mAccessList[entry.mID] = entry;
}
}
}
else if ("ban_list" == keyword)
{
S32 entry_count = 0;
LLStringUtil::convertToS32(value, entry_count);
for (S32 i = 0; i < entry_count; i++)
{
LLAccessEntry entry;
if (importAccessEntry(input_stream, &entry))
{
mBanList[entry.mID] = entry;
}
}
}
else if ("renter_list" == keyword)
{
/*
S32 entry_count = 0;
LLStringUtil::convertToS32(value, entry_count);
for (S32 i = 0; i < entry_count; i++)
{
LLAccessEntry entry;
if (importAccessEntry(input_stream, &entry))
{
mRenterList.put(entry);
}
}*/
}
else if ("pass_list" == keyword)
{
// legacy - put into access list
S32 entry_count = 0;
LLStringUtil::convertToS32(value, entry_count);
for (S32 i = 0; i < entry_count; i++)
{
LLAccessEntry entry;
if (importAccessEntry(input_stream, &entry))
{
mAccessList[entry.mID] = entry;
}
}
}
else
{
llwarns << "Unknown keyword in parcel section: <"
<< keyword << ">" << llendl;
}
}
// this code block detects if we have loaded a 1.1 simstate file,
// and follows the conversion rules specified in
// design_docs/land/pay_for_parcel.txt.
F32 time_to_expire = 0.0f;
if(mID.isNull())
{
mID.generate();
mStatus = OS_LEASE_PENDING;
//mBuyerID = mOwnerID;
if(getIsGroupOwned())
{
time_to_expire += GROUP_USEC_CONVERSION_TIMEOUT / SEC_TO_MICROSEC;
}
else
{
time_to_expire += DEFAULT_USEC_CONVERSION_TIMEOUT / SEC_TO_MICROSEC;
}
//mExpireAction = STEA_PUBLIC;
mRecordTransaction = TRUE;
}
// this code block deals with giving an extension to pending
// parcels to the midday of 2004-01-19 if they were originally set
// for some time on 2004-01-12.
if((0 == mGraceExtension)
&& (EXTEND_GRACE_IF_MORE_THAN_SEC < secs_until_revert))
{
const S32 NEW_CONVERSION_DATE = 1074538800; // 2004-01-19T11:00:00
time_t now = time(NULL); // now in epoch
secs_until_revert = (S32)(NEW_CONVERSION_DATE - now);
time_to_expire = (F32)secs_until_revert;
mGraceExtension = 1;
}
// This code block adds yet another week to the deadline. :(
if(1 == mGraceExtension)
{
time_to_expire += SEVEN_DAYS_IN_USEC / SEC_TO_MICROSEC;
mGraceExtension = 2;
}
if (time_to_expire > 0)
{
mSaleTimerExpires.setTimerExpirySec(time_to_expire);
mSaleTimerExpires.start();
}
// successful import
return TRUE;
}
BOOL LLParcel::importAccessEntry(std::istream& input_stream, LLAccessEntry* entry)
{
skip_to_end_of_next_keyword("{", input_stream);
@ -1085,230 +565,6 @@ BOOL LLParcel::importAccessEntry(std::istream& input_stream, LLAccessEntry* entr
return input_stream.good();
}
BOOL LLParcel::exportStream(std::ostream& output_stream)
{
S32 setting;
std::string id_string;
std::ios::fmtflags old_flags = output_stream.flags();
output_stream.setf(std::ios::showpoint);
output_stream << "\t{\n";
mID.toString(id_string);
output_stream << "\t\t parcel_id " << id_string << "\n";
output_stream << "\t\t status " << ownership_status_to_string(mStatus) << "\n";
output_stream << "\t\t category " << category_to_string(mCategory) << "\n";
output_stream << "\t\t local_id " << mLocalID << "\n";
const char* name = (mName.empty() ? "" : mName.c_str() );
output_stream << "\t\t name " << name << "\n";
const char* desc = (mDesc.empty() ? "" : mDesc.c_str() );
output_stream << "\t\t desc " << desc << "\n";
const char* music_url = (mMusicURL.empty() ? "" : mMusicURL.c_str() );
output_stream << "\t\t music_url " << music_url << "\n";
const char* media_url = (mMediaURL.empty() ? "" : mMediaURL.c_str() );
output_stream << "\t\t media_url " << media_url << "\n";
const char* media_type = (mMediaType.empty() ? "" : mMediaType.c_str() );
output_stream << "\t\t media_type " << media_type << "\n";
const char* media_desc = (mMediaDesc.empty() ? "" : mMediaDesc.c_str() );
output_stream << "\t\t media_desc " << media_desc << "\n";
output_stream << "\t\t media_auto_scale " << (mMediaAutoScale ? 1 : 0) << "\n";
output_stream << "\t\t media_loop " << (mMediaLoop ? 1 : 0) << "\n";
output_stream << "\t\t obscure_media " << (mObscureMedia ? 1 : 0) << "\n";
output_stream << "\t\t obscure_music " << (mObscureMusic ? 1 : 0) << "\n";
mMediaID.toString(id_string);
output_stream << "\t\t media_id " << id_string << "\n";
output_stream << "\t\t media_width " << mMediaWidth << "\n";
output_stream << "\t\t media_height " << mMediaHeight << "\n";
mOwnerID.toString(id_string);
output_stream << "\t\t owner_id " << id_string << "\n";
output_stream << "\t\t group_owned " << (mGroupOwned ? 1 : 0) << "\n";
output_stream << "\t\t clean_other_time " << getCleanOtherTime() << "\n";
if(!mAuthBuyerID.isNull())
{
mAuthBuyerID.toString(id_string);
output_stream << "\t\t auth_buyer_id " << id_string << "\n";
}
if (!mSnapshotID.isNull())
{
mSnapshotID.toString(id_string);
output_stream << "\t\t snapshot_id " << id_string << "\n";
}
if (!mUserLocation.isExactlyZero())
{
output_stream << "\t\t user_location "
<< (F64)mUserLocation.mV[VX]
<< " " << (F64)mUserLocation.mV[VY]
<< " " << (F64)mUserLocation.mV[VZ] << "\n";
output_stream << "\t\t user_look_at "
<< (F64)mUserLookAt.mV[VX]
<< " " << (F64)mUserLookAt.mV[VY]
<< " " << (F64)mUserLookAt.mV[VZ] << "\n";
}
output_stream << "\t\t landing_type " << mLandingType << "\n";
//if(mJoinNeighbors)
//{
// output_stream << "\t\t join_neighbors " << mJoinNeighbors << "\n";
//}
if(mSaleTimerExpires.getStarted())
{
S32 dt_sec = (S32) mSaleTimerExpires.getRemainingTimeF32()+60; // Add a minute to prevent race conditions
output_stream << "\t\t revert_sale " << dt_sec << "\n";
//output_stream << "\t\t revert_action " << revert_action_to_string(mExpireAction) << "\n";
output_stream << "\t\t extended_grace " << mGraceExtension << "\n";
}
if(0 != mAuctionID)
{
output_stream << "\t\t auction_id " << mAuctionID << "\n";
}
output_stream << "\t\t allow_modify " << getAllowModify() << "\n";
output_stream << "\t\t allow_group_modify " << getAllowGroupModify() << "\n";
output_stream << "\t\t allow_all_object_entry " << getAllowAllObjectEntry() << "\n";
output_stream << "\t\t allow_group_object_entry " << getAllowGroupObjectEntry() << "\n";
output_stream << "\t\t allow_terraform " << getAllowTerraform() << "\n";
output_stream << "\t\t allow_deed_to_group " << getAllowDeedToGroup() << "\n";
output_stream << "\t\t contribute_with_deed " << getContributeWithDeed() << "\n";
output_stream << "\t\t allow_damage " << getAllowDamage() << "\n";
output_stream << "\t\t claim_date " << (S32)mClaimDate << "\n";
output_stream << "\t\t claim_price " << mClaimPricePerMeter << "\n";
output_stream << "\t\t rent_price " << mRentPricePerMeter << "\n";
output_stream << "\t\t discount_rate " << mDiscountRate << "\n";
output_stream << "\t\t allow_fly " << (getAllowFly() ? 1 : 0) << "\n";
output_stream << "\t\t allow_landmark " << (getAllowLandmark() ? 1 : 0) << "\n";
output_stream << "\t\t sound_local " << (getSoundLocal() ? 1 : 0) << "\n";
output_stream << "\t\t allow_scripts " << (getAllowOtherScripts() ? 1 : 0) << "\n";
output_stream << "\t\t allow_group_scripts " << (getAllowGroupScripts() ? 1 : 0) << "\n";
output_stream << "\t\t use_estate_voice_chan " << (getParcelFlagUseEstateVoiceChannel() ? 1 : 0) << "\n";
output_stream << "\t\t allow_voice_chat " << (getParcelFlagAllowVoice() ? 1 : 0) << "\n";
output_stream << "\t\t use_estate_voice_chan " << (getParcelFlagUseEstateVoiceChannel() ? 1 : 0) << "\n";
output_stream << "\t\t for_sale " << (getForSale() ? 1 : 0) << "\n";
output_stream << "\t\t sell_w_objects " << (getSellWithObjects() ? 1 : 0) << "\n";
output_stream << "\t\t draw_distance " << mDrawDistance << "\n";
output_stream << "\t\t sale_price " << mSalePrice << "\n";
setting = (getParcelFlag(PF_USE_ACCESS_GROUP) ? 1 : 0);
output_stream << "\t\t use_access_group " << setting << "\n";
setting = (getParcelFlag(PF_USE_ACCESS_LIST) ? 1 : 0);
output_stream << "\t\t use_access_list " << setting << "\n";
setting = (getParcelFlag(PF_USE_BAN_LIST) ? 1 : 0);
output_stream << "\t\t use_ban_list " << setting << "\n";
mGroupID.toString(id_string);
output_stream << "\t\t group_id " << id_string << "\n";
//const char* group_name
// = (mGroupName.isEmpty() ? "" : mGroupName.c_str() );
//output_stream << "\t\t group_name " << group_name << "\n";
setting = (getParcelFlag(PF_USE_PASS_LIST) ? 1 : 0);
output_stream << "\t\t use_pass_list " << setting << "\n";
output_stream << "\t\t pass_price " << mPassPrice << "\n";
output_stream << "\t\t pass_hours " << mPassHours << "\n";
setting = (getParcelFlag(PF_SHOW_DIRECTORY) ? 1 : 0);
output_stream << "\t\t show_directory " << setting << "\n";
setting = (getParcelFlag(PF_ALLOW_PUBLISH) ? 1 : 0);
output_stream << "\t\t allow_publish " << setting << "\n";
setting = (getParcelFlag(PF_MATURE_PUBLISH) ? 1 : 0);
output_stream << "\t\t mature_publish " << setting << "\n";
setting = (getParcelFlag(PF_DENY_ANONYMOUS) ? 1 : 0);
output_stream << "\t\t deny_anonymous " << setting << "\n";
// setting = (getParcelFlag(PF_DENY_IDENTIFIED) ? 1 : 0);
// output_stream << "\t\t deny_identified " << setting << "\n";
// setting = (getParcelFlag(PF_DENY_TRANSACTED) ? 1 : 0);
// output_stream << "\t\t deny_transacted " << setting << "\n";
setting = (getParcelFlag(PF_DENY_AGEUNVERIFIED) ? 1 : 0);
output_stream << "\t\t deny_age_unverified " << setting << "\n";
setting = (getParcelFlag(PF_RESTRICT_PUSHOBJECT) ? 1 : 0);
output_stream << "\t\t restrict_pushobject " << setting << "\n";
output_stream << "\t\t aabb_min "
<< mAABBMin.mV[VX]
<< " " << mAABBMin.mV[VY]
<< " " << mAABBMin.mV[VZ] << "\n";
if (!mAccessList.empty())
{
output_stream << "\t\t access_list " << mAccessList.size() << "\n";
access_map_const_iterator cit = mAccessList.begin();
access_map_const_iterator end = mAccessList.end();
for ( ; cit != end; ++cit)
{
output_stream << "\t\t{\n";
const LLAccessEntry& entry = (*cit).second;
entry.mID.toString(id_string);
output_stream << "\t\t\tid " << id_string << "\n";
output_stream << "\t\t\ttime " << entry.mTime << "\n";
output_stream << "\t\t\tflags " << entry.mFlags << "\n";
output_stream << "\t\t}\n";
}
}
if (!mBanList.empty())
{
output_stream << "\t\t ban_list " << mBanList.size() << "\n";
access_map_const_iterator cit = mBanList.begin();
access_map_const_iterator end = mBanList.end();
for ( ; cit != end; ++cit)
{
output_stream << "\t\t{\n";
const LLAccessEntry& entry = (*cit).second;
entry.mID.toString(id_string);
output_stream << "\t\t\tid " << id_string << "\n";
output_stream << "\t\t\ttime " << entry.mTime << "\n";
output_stream << "\t\t\tflags " << entry.mFlags << "\n";
output_stream << "\t\t}\n";
}
}
/*if (mRenterList.count() > 0)
{
output_stream << "\t\t renter_list " << mRenterList.count() << "\n";
for (i = 0; i < mRenterList.count(); i++)
{
output_stream << "\t\t{\n";
const LLAccessEntry& entry = mRenterList.get(i);
entry.mID.toString(id_string);
output_stream << "\t\t\tid " << id_string << "\n";
output_stream << "\t\t\ttime " << entry.mTime << "\n";
output_stream << "\t\t\tflags " << entry.mFlags << "\n";
output_stream << "\t\t}\n";
}
}*/
output_stream << "\t}\n";
output_stream.flags(old_flags);
return TRUE;
}
// Assumes we are in a block "ParcelData"
void LLParcel::packMessage(LLMessageSystem* msg)
{

View File

@ -103,6 +103,32 @@ const U32 RT_OTHER = 0x1 << 3;
const U32 RT_LIST = 0x1 << 4;
const U32 RT_SELL = 0x1 << 5;
// Timeouts for parcels
// default is 21 days * 24h/d * 60m/h * 60s/m *1000000 usec/s = 1814400000000
const U64 DEFAULT_USEC_CONVERSION_TIMEOUT = U64L(1814400000000);
// ***** TESTING is 10 minutes
//const U64 DEFAULT_USEC_CONVERSION_TIMEOUT = U64L(600000000);
// group is 60 days * 24h/d * 60m/h * 60s/m *1000000 usec/s = 5184000000000
const U64 GROUP_USEC_CONVERSION_TIMEOUT = U64L(5184000000000);
// ***** TESTING is 10 minutes
//const U64 GROUP_USEC_CONVERSION_TIMEOUT = U64L(600000000);
// default sale timeout is 2 days -> 172800000000
const U64 DEFAULT_USEC_SALE_TIMEOUT = U64L(172800000000);
// ***** TESTING is 10 minutes
//const U64 DEFAULT_USEC_SALE_TIMEOUT = U64L(600000000);
// more grace period extensions.
const U64 SEVEN_DAYS_IN_USEC = U64L(604800000000);
// if more than 100,000s before sale revert, and no extra extension
// has been given, go ahead and extend it more. That's about 1.2 days.
const S32 EXTEND_GRACE_IF_MORE_THAN_SEC = 100000;
class LLMessageSystem;
class LLSD;
@ -271,9 +297,9 @@ public:
void setPassPrice(S32 price) { mPassPrice = price; }
void setPassHours(F32 hours) { mPassHours = hours; }
BOOL importStream(std::istream& input_stream);
// BOOL importStream(std::istream& input_stream);
BOOL importAccessEntry(std::istream& input_stream, LLAccessEntry* entry);
BOOL exportStream(std::ostream& output_stream);
// BOOL exportStream(std::ostream& output_stream);
void packMessage(LLMessageSystem* msg);
void packMessage(LLSD& msg);
@ -633,4 +659,10 @@ public:
};
const std::string& ownership_status_to_string(LLParcel::EOwnershipStatus status);
LLParcel::EOwnershipStatus ownership_string_to_status(const std::string& s);
LLParcel::ECategory category_string_to_category(const std::string& s);
const std::string& category_to_string(LLParcel::ECategory category);
#endif

View File

@ -134,6 +134,7 @@ BOOL LLVector3::clampLength( F32 length_limit )
mV[0] *= length_limit;
mV[1] *= length_limit;
mV[2] *= length_limit;
changed = TRUE;
}
}

View File

@ -7,6 +7,7 @@ include(LLCommon)
include(LLMath)
include(LLMessage)
include(LLVFS)
include(LLAddBuildTest)
include_directories (${CMAKE_CURRENT_SOURCE_DIR})
@ -34,6 +35,7 @@ set(llmessage_SOURCE_FILES
llhost.cpp
llhttpassetstorage.cpp
llhttpclient.cpp
llhttpclientadapter.cpp
llhttpnode.cpp
llhttpsender.cpp
llinstantmessage.cpp
@ -57,6 +59,7 @@ set(llmessage_SOURCE_FILES
llpacketring.cpp
llpartdata.cpp
llpumpio.cpp
llregionpresenceverifier.cpp
llsdappservices.cpp
llsdhttpserver.cpp
llsdmessagebuilder.cpp
@ -65,7 +68,9 @@ set(llmessage_SOURCE_FILES
llsdrpcserver.cpp
llservicebuilder.cpp
llservice.cpp
llstoredmessage.cpp
lltemplatemessagebuilder.cpp
lltemplatemessagedispatcher.cpp
lltemplatemessagereader.cpp
llthrottle.cpp
lltransfermanager.cpp
@ -73,6 +78,7 @@ set(llmessage_SOURCE_FILES
lltransfersourcefile.cpp
lltransfertargetfile.cpp
lltransfertargetvfile.cpp
lltrustedmessageservice.cpp
llurlrequest.cpp
lluseroperation.cpp
llxfer.cpp
@ -85,7 +91,6 @@ set(llmessage_SOURCE_FILES
message_prehash.cpp
message_string_table.cpp
net.cpp
network.cpp
partsyspacket.cpp
patch_code.cpp
patch_dct.cpp
@ -115,7 +120,10 @@ set(llmessage_HEADER_FILES
llhost.h
llhttpassetstorage.h
llhttpclient.h
llhttpclientinterface.h
llhttpclientadapter.h
llhttpnode.h
llhttpnodeadapter.h
llhttpsender.h
llinstantmessage.h
llinvite.h
@ -144,6 +152,7 @@ set(llmessage_HEADER_FILES
llqueryflags.h
llregionflags.h
llregionhandle.h
llregionpresenceverifier.h
llsdappservices.h
llsdhttpserver.h
llsdmessagebuilder.h
@ -152,9 +161,11 @@ set(llmessage_HEADER_FILES
llsdrpcserver.h
llservice.h
llservicebuilder.h
llstoredmessage.h
lltaskname.h
llteleportflags.h
lltemplatemessagebuilder.h
lltemplatemessagedispatcher.h
lltemplatemessagereader.h
llthrottle.h
lltransfermanager.h
@ -162,6 +173,7 @@ set(llmessage_HEADER_FILES
lltransfersourcefile.h
lltransfertargetfile.h
lltransfertargetvfile.h
lltrustedmessageservice.h
llurlrequest.h
lluseroperation.h
llvehicleparams.h
@ -176,7 +188,6 @@ set(llmessage_HEADER_FILES
message.h
message_prehash.h
net.h
network.h
partsyspacket.h
patch_code.h
patch_dct.h
@ -197,3 +208,13 @@ target_link_libraries(
${CRYPTO_LIBRARIES}
${XMLRPCEPI_LIBRARIES}
)
IF (NOT LINUX AND VIEWER)
# When building the viewer the tests links against the shared objects.
# These can not be found when we try to run the tests, so we had to disable them, for the viewer build.
# TODO: Can someone with viewer knowledge figure out how to make these find the correct so.
#ADD_BUILD_TEST(llhttpclientadapter llmessage)
ADD_BUILD_TEST(lltrustedmessageservice llmessage)
ADD_BUILD_TEST(lltemplatemessagedispatcher llmessage)
ENDIF (NOT LINUX AND VIEWER)

View File

@ -111,40 +111,14 @@ bool LLDispatcher::unpackMessage(
LLUUID& invoice,
LLDispatcher::sparam_t& parameters)
{
char buf[MAX_STRING]; /*Flawfinder: ignore*/
msg->getStringFast(_PREHASH_MethodData, _PREHASH_Method, method);
msg->getUUIDFast(_PREHASH_MethodData, _PREHASH_Invoice, invoice);
S32 size;
S32 count = msg->getNumberOfBlocksFast(_PREHASH_ParamList);
for (S32 i = 0; i < count; ++i)
{
// we treat the SParam as binary data (since it might be an
// LLUUID in compressed form which may have embedded \0's,)
size = msg->getSizeFast(_PREHASH_ParamList, i, _PREHASH_Parameter);
msg->getBinaryDataFast(
_PREHASH_ParamList, _PREHASH_Parameter,
buf, size, i, MAX_STRING-1);
// If the last byte of the data is 0x0, this is either a normally
// packed string, or a binary packed UUID (which for these messages
// are packed with a 17th byte 0x0). Unpack into a std::string
// without the trailing \0, so "abc\0" becomes std::string("abc", 3)
// which matches const char* "abc".
if (size > 0
&& buf[size-1] == 0x0)
{
// special char*/size constructor because UUIDs may have embedded
// 0x0 bytes.
std::string binary_data(buf, size-1);
parameters.push_back(binary_data);
}
else
{
// This is either a NULL string, or a string that was packed
// incorrectly as binary data, without the usual trailing '\0'.
std::string string_data(buf, size);
parameters.push_back(string_data);
}
std::string parameter;
msg->getStringFast(_PREHASH_ParamList,_PREHASH_Parameter, parameter, i);
parameters.push_back(parameter);
}
return true;
}

View File

@ -235,6 +235,7 @@ LLSD LLHTTPAssetRequest::getFullDetails() const
void LLHTTPAssetRequest::setupCurlHandle()
{
// *NOTE: Similar code exists in mapserver/llcurlutil.cpp JC
mCurlHandle = curl_easy_init();
curl_easy_setopt(mCurlHandle, CURLOPT_NOSIGNAL, 1);
curl_easy_setopt(mCurlHandle, CURLOPT_NOPROGRESS, 1);

View File

@ -0,0 +1,53 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "llhttpclientadapter.h"
#include "llhttpclient.h"
LLHTTPClientAdapter::~LLHTTPClientAdapter()
{
}
void LLHTTPClientAdapter::get(const std::string& url, LLCurl::ResponderPtr responder)
{
LLHTTPClient::get(url, responder);
}
void LLHTTPClientAdapter::get(const std::string& url, LLCurl::ResponderPtr responder, const LLSD& headers)
{
LLHTTPClient::get(url, responder, headers);
}
void LLHTTPClientAdapter::put(const std::string& url, const LLSD& body, LLCurl::ResponderPtr responder)
{
LLHTTPClient::put(url, body, responder);
}

View File

@ -0,0 +1,48 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=viewergpl$
*
* Copyright (c) 2001-2008, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef LL_HTTPCLIENTADAPTER_H
#define LL_HTTPCLIENTADAPTER_H
#include "llhttpclientinterface.h"
#include "llmemory.h" // LLSingleton<>
class LLHTTPClientAdapter : public LLHTTPClientInterface, public LLSingleton<LLHTTPClientAdapter>
{
public:
virtual ~LLHTTPClientAdapter();
virtual void get(const std::string& url, LLCurl::ResponderPtr responder);
virtual void get(const std::string& url, LLCurl::ResponderPtr responder, const LLSD& headers);
virtual void put(const std::string& url, const LLSD& body, LLCurl::ResponderPtr responder);
};
#endif

View File

@ -0,0 +1,50 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=viewergpl$
*
* Copyright (c) 2001-2008, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef LL_LLHTTPCLIENTINTERFACE_H
#define LL_LLHTTPCLIENTINTERFACE_H
#include "linden_common.h"
#include "llcurl.h"
#include <string>
class LLHTTPClientInterface
{
public:
virtual ~LLHTTPClientInterface() {}
virtual void get(const std::string& url, LLCurl::ResponderPtr responder) = 0;
virtual void get(const std::string& url, LLCurl::ResponderPtr responder, const LLSD& headers) = 0;
virtual void put(const std::string& url, const LLSD& body, LLCurl::ResponderPtr responder) = 0;
};
#endif // LL_LLHTTPCLIENTINTERFACE_H

View File

@ -88,6 +88,9 @@ public:
virtual LLSD post(const LLSD& input) const;
virtual LLSD del(const LLSD& context) const;
/**
* @brief Abstract Base Class declaring Response interface.
*/
class Response : public LLRefCount
{
protected:
@ -95,8 +98,8 @@ public:
public:
/**
* @brief Return the LLSD content and a 200 OK.
*/
* @brief Return the LLSD content and a 200 OK.
*/
virtual void result(const LLSD&) = 0;
/**
@ -111,42 +114,41 @@ public:
virtual void status(S32 code, const std::string& message) = 0;
/**
* @brief Return no body, just status code and 'UNKNOWN ERROR'.
*/
void status(S32 code);
* @brief Return no body, just status code and 'UNKNOWN ERROR'.
*/
virtual void status(S32 code);
void notFound(const std::string& message);
void notFound();
void methodNotAllowed();
virtual void notFound(const std::string& message);
virtual void notFound();
virtual void methodNotAllowed();
/**
* @breif Add a name: value http header.
*
* No effort is made to ensure the response is a valid http
* header.
* The headers are stored as a map of header name : value.
* Though HTTP allows the same header name to be transmitted
* more than once, this implementation only stores a header
* name once.
* @param name The name of the header, eg, "Content-Encoding"
* @param value The value of the header, eg, "gzip"
*/
void addHeader(const std::string& name, const std::string& value);
* @breif Add a name: value http header.
*
* No effort is made to ensure the response is a valid http
* header.
* The headers are stored as a map of header name : value.
* Though HTTP allows the same header name to be transmitted
* more than once, this implementation only stores a header
* name once.
* @param name The name of the header, eg, "Content-Encoding"
* @param value The value of the header, eg, "gzip"
*/
virtual void addHeader(const std::string& name, const std::string& value);
protected:
/**
* @brief Headers to be sent back with the HTTP response.
*
* Protected class membership since derived classes are
* expected to use it and there is no use case yet for other
* uses. If such a use case arises, I suggest making a
* headers() public method, and moving this member data into
* private.
*/
* @brief Headers to be sent back with the HTTP response.
*
* Protected class membership since derived classes are
* expected to use it and there is no use case yet for other
* uses. If such a use case arises, I suggest making a
* headers() public method, and moving this member data into
* private.
*/
LLSD mHeaders;
};
typedef LLPointer<Response> ResponsePtr;
virtual void get(ResponsePtr, const LLSD& context) const;

View File

@ -0,0 +1,57 @@
/**
* @file llhttpnodeadapter.h
* @brief Declaration of llhttpnode adapter classes
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef LL_HTTP_NODE_ADAPTER_H
#define LL_HTTP_NODE_ADAPTER_H
#include "llhttpnode.h"
template<typename T>
class LLHTTPNodeAdapter : public LLHTTPNode
{
public:
virtual bool validate(const std::string& name, LLSD& context) const
{
T node;
return node.validate(name, context);
}
virtual void post(LLHTTPNode::ResponsePtr response,
const LLSD& context,
const LLSD& input) const
{
T node;
return node.post(response, context, input);
}
};
#endif // LL_HTTP_NODE_ADAPTER_H

View File

@ -844,6 +844,7 @@ LLIOPipe::EStatus LLHTTPResponder::process_impl(
= node->getProtocolHandler();
if (protocolHandler)
{
lldebugs << "HTTP context: " << context << llendl;
protocolHandler->build(chain, context);
}
else

View File

@ -0,0 +1,49 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=viewergpl$
*
* Copyright (c) 2001-2008, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef LL_LLMESSAGESENDERINTERFACE_H
#define LL_LLMESSAGESENDERINTERFACE_H
#include "linden_common.h"
#include "llstoredmessage.h"
class LLHost;
class LLSD;
class LLMessageSenderInterface
{
public:
virtual ~LLMessageSenderInterface() {}
virtual S32 sendMessage(const LLHost& host, LLStoredMessagePtr message) = 0;
};
#endif // LL_LLMESSAGESENDERINTERFACE_H

View File

@ -0,0 +1,87 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=internal$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* The following source code is PROPRIETARY AND CONFIDENTIAL. Use of
* this source code is governed by the Linden Lab Source Code Disclosure
* Agreement ("Agreement") previously entered between you and Linden
* Lab. By accessing, using, copying, modifying or distributing this
* software, you acknowledge that you have been informed of your
* obligations under the Agreement and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "llregionpresenceverifier.h"
#include "llhttpclientinterface.h"
#include <sstream>
#include "net.h"
#include "message.h"
LLRegionPresenceVerifier::RegionResponder::RegionResponder(ResponsePtr data) : mSharedData(data)
{
}
void LLRegionPresenceVerifier::RegionResponder::result(const LLSD& content)
{
std::string host = content["private_host"].asString();
U32 port = content["private_port"].asInteger();
LLHost destination(host, port);
LLUUID id = content["region_id"];
llinfos << "Verifying " << destination.getString() << " is region " << id << llendl;
std::stringstream uri;
uri << "http://" << destination.getString() << "/state/basic";
mSharedData->getHttpClient().get(uri.str(), new VerifiedDestinationResponder(mSharedData, content));
}
void LLRegionPresenceVerifier::RegionResponder::completed(
U32 status,
const std::string& reason,
const LLSD& content)
{
LLHTTPClient::Responder::completed(status, reason, content);
mSharedData->onCompletedRegionRequest();
}
LLRegionPresenceVerifier::VerifiedDestinationResponder::VerifiedDestinationResponder(ResponsePtr data, const LLSD& content) : mSharedData(data), mContent(content)
{
}
void LLRegionPresenceVerifier::VerifiedDestinationResponder::result(const LLSD& content)
{
LLUUID actual_region_id = content["region_id"];
LLUUID expected_region_id = mContent["region_id"];
if (mSharedData->checkValidity(content))
{
mSharedData->onRegionVerified(mContent);
}
else if ((mSharedData->shouldRetry()) && (actual_region_id != expected_region_id)) // If the region is correct, then it means we've deliberately changed the data
{
LLSD headers;
headers["Cache-Control"] = "no-cache, max-age=0";
llinfos << "Requesting region information, get uncached for region " << mSharedData->getRegionUri() << llendl;
mSharedData->decrementRetries();
mSharedData->getHttpClient().get(mSharedData->getRegionUri(), new RegionResponder(mSharedData), headers);
}
else
{
llwarns << "Could not correctly look up region from region presence service. Region: " << mSharedData->getRegionUri() << llendl;
}
}

View File

@ -0,0 +1,81 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=internal$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* The following source code is PROPRIETARY AND CONFIDENTIAL. Use of
* this source code is governed by the Linden Lab Source Code Disclosure
* Agreement ("Agreement") previously entered between you and Linden
* Lab. By accessing, using, copying, modifying or distributing this
* software, you acknowledge that you have been informed of your
* obligations under the Agreement and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
/* Macro Definitions */
#ifndef LL_LLREGIONPRESENCEVERIFIER_H
#define LL_LLREGIONPRESENCEVERIFIER_H
#include "llhttpclient.h"
#include <string>
#include "llsd.h"
#include <boost/shared_ptr.hpp>
class LLHTTPClientInterface;
class LLRegionPresenceVerifier
{
public:
class Response
{
public:
virtual ~Response() {}
virtual bool checkValidity(const LLSD& content) const = 0;
virtual void onRegionVerified(const LLSD& region_details) = 0;
virtual void decrementRetries() = 0;
virtual LLHTTPClientInterface& getHttpClient() = 0;
virtual std::string getRegionUri() const = 0;
virtual bool shouldRetry() const = 0;
virtual void onCompletedRegionRequest() {}
};
typedef boost::shared_ptr<Response> ResponsePtr;
class RegionResponder : public LLHTTPClient::Responder
{
public:
RegionResponder(ResponsePtr data);
virtual void result(const LLSD& content);
virtual void completed(
U32 status,
const std::string& reason,
const LLSD& content);
private:
ResponsePtr mSharedData;
};
class VerifiedDestinationResponder : public LLHTTPClient::Responder
{
public:
VerifiedDestinationResponder(ResponsePtr data, const LLSD& content);
virtual void result(const LLSD& content);
private:
ResponsePtr mSharedData;
LLSD mContent;
};
};
#endif //LL_LLREGIONPRESENCEVERIFIER_H

View File

@ -268,10 +268,125 @@ void LLSDMessageBuilder::copyFromMessageData(const LLMsgData& data)
for(; dit != dend; ++dit)
{
//const LLMsgVarData& mvci = *dit;
const LLMsgVarData& mvci = *dit;
const char* varname = mvci.getName();
// TODO: Copy mvci data in to block:
// (*mCurrentBlock)[varname] = v;
switch(mvci.getType())
{
case MVT_FIXED:
addBinaryData(varname, mvci.getData(), mvci.getSize());
break;
case MVT_VARIABLE:
{
const char end = ((const char*)mvci.getData())[mvci.getSize()-1]; // Ensure null terminated
if (mvci.getDataSize() == 1 && end == 0)
{
addString(varname, (const char*)mvci.getData());
}
else
{
addBinaryData(varname, mvci.getData(), mvci.getSize());
}
break;
}
case MVT_U8:
addU8(varname, *(U8*)mvci.getData());
break;
case MVT_U16:
addU16(varname, *(U16*)mvci.getData());
break;
case MVT_U32:
addU32(varname, *(U32*)mvci.getData());
break;
case MVT_U64:
addU64(varname, *(U64*)mvci.getData());
break;
case MVT_S8:
addS8(varname, *(S8*)mvci.getData());
break;
case MVT_S16:
addS16(varname, *(S16*)mvci.getData());
break;
case MVT_S32:
addS32(varname, *(S32*)mvci.getData());
break;
// S64 not supported in LLSD so we just truncate it
case MVT_S64:
addS32(varname, *(S64*)mvci.getData());
break;
case MVT_F32:
addF32(varname, *(F32*)mvci.getData());
break;
case MVT_F64:
addF64(varname, *(F64*)mvci.getData());
break;
case MVT_LLVector3:
addVector3(varname, *(LLVector3*)mvci.getData());
break;
case MVT_LLVector3d:
addVector3d(varname, *(LLVector3d*)mvci.getData());
break;
case MVT_LLVector4:
addVector4(varname, *(LLVector4*)mvci.getData());
break;
case MVT_LLQuaternion:
{
LLVector3 v = *(LLVector3*)mvci.getData();
LLQuaternion q;
q.unpackFromVector3(v);
addQuat(varname, q);
break;
}
case MVT_LLUUID:
addUUID(varname, *(LLUUID*)mvci.getData());
break;
case MVT_BOOL:
addBOOL(varname, *(BOOL*)mvci.getData());
break;
case MVT_IP_ADDR:
addIPAddr(varname, *(U32*)mvci.getData());
break;
case MVT_IP_PORT:
addIPPort(varname, *(U16*)mvci.getData());
break;
case MVT_U16Vec3:
//treated as an array of 6 bytes
addBinaryData(varname, mvci.getData(), 6);
break;
case MVT_U16Quat:
//treated as an array of 8 bytes
addBinaryData(varname, mvci.getData(), 8);
break;
case MVT_S16Array:
addBinaryData(varname, mvci.getData(), mvci.getSize());
break;
default:
llwarns << "Unknown type in conversion of message to LLSD" << llendl;
break;
}
}
}
}

View File

@ -0,0 +1,38 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at
* http://secondlifegrid.net/programs/open_source/licensing/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "llstoredmessage.h"
LLStoredMessage::LLStoredMessage(const std::string& name, const LLSD& message) : mMessage(message), mName(name)
{
}

View File

@ -0,0 +1,58 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at
* http://secondlifegrid.net/programs/open_source/licensing/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef LL_STOREDMESSAGE_H
#define LL_STOREDMESSAGE_H
#include "linden_common.h"
#include "llsd.h"
#include <boost/shared_ptr.hpp>
#include <string>
class LLMessageSystem;
class LLStoredMessage
{
public:
LLStoredMessage(const std::string& name, const LLSD& message);
private:
friend class LLMessageSystem;
LLSD mMessage;
std::string mName;
};
typedef boost::shared_ptr<LLStoredMessage> LLStoredMessagePtr;
#endif // LL_STOREDMESSAGE_H

View File

@ -41,7 +41,7 @@
#include "v3math.h"
#include "v4math.h"
LLTemplateMessageBuilder::LLTemplateMessageBuilder(message_template_name_map_t& name_template_map) :
LLTemplateMessageBuilder::LLTemplateMessageBuilder(const message_template_name_map_t& name_template_map) :
mCurrentSMessageData(NULL),
mCurrentSMessageTemplate(NULL),
mCurrentSDataBlock(NULL),
@ -75,14 +75,14 @@ void LLTemplateMessageBuilder::newMessage(const char *name)
char* namep = (char*)name;
if (mMessageTemplates.count(namep) > 0)
{
mCurrentSMessageTemplate = mMessageTemplates[namep];
mCurrentSMessageTemplate = mMessageTemplates.find(name)->second;
mCurrentSMessageData = new LLMsgData(namep);
mCurrentSMessageName = namep;
mCurrentSDataBlock = NULL;
mCurrentSBlockName = NULL;
// add at one of each block
const LLMessageTemplate* msg_template = mMessageTemplates[namep];
const LLMessageTemplate* msg_template = mMessageTemplates.find(name)->second;
if (msg_template->getDeprecation() != MD_NOTDEPRECATED)
{

View File

@ -49,7 +49,7 @@ public:
typedef std::map<const char* , LLMessageTemplate*> message_template_name_map_t;
LLTemplateMessageBuilder(message_template_name_map_t&);
LLTemplateMessageBuilder(const message_template_name_map_t&);
virtual ~LLTemplateMessageBuilder();
virtual void newMessage(const char* name);
@ -99,6 +99,7 @@ public:
virtual void copyFromMessageData(const LLMsgData& data);
virtual void copyFromLLSD(const LLSD&);
LLMsgData* getCurrentMessage() const { return mCurrentSMessageData; }
private:
void addData(const char* varname, const void* data,
EMsgVariableType type, S32 size);
@ -114,7 +115,7 @@ private:
BOOL mbSBuilt;
BOOL mbSClear;
S32 mCurrentSendTotal;
message_template_name_map_t& mMessageTemplates;
const message_template_name_map_t& mMessageTemplates;
};
#endif // LL_LLTEMPLATEMESSAGEBUILDER_H

View File

@ -0,0 +1,72 @@
/**
* @file lltemplatemessagedispatcher.h
* @brief LLTemplateMessageDispatcher class
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "lltemplatemessagedispatcher.h"
#include "llhttpnode.h"
#include "llhost.h"
#include "message.h"
#include "llsd.h"
#include "lltemplatemessagereader.h"
LLTemplateMessageDispatcher::LLTemplateMessageDispatcher(LLTemplateMessageReader &template_message_reader) :
mTemplateMessageReader(template_message_reader)
{
}
void LLTemplateMessageDispatcher::dispatch(const std::string& msg_name,
const LLSD& message,
LLHTTPNode::ResponsePtr responsep)
{
std::vector<U8> data = message["body"]["binary-template-data"].asBinary();
U32 size = data.size();
if(size == 0)
{
return;
}
LLHost host;
host = gMessageSystem->getSender();
bool validate_message = mTemplateMessageReader.validateMessage(&(data[0]), data.size(), host, true);
if (validate_message)
{
mTemplateMessageReader.readMessage(&(data[0]),host);
}
else
{
gMessageSystem->clearReceiveState();
}
}

View File

@ -0,0 +1,53 @@
/**
* @file lltemplatemessagedispatcher.h
* @brief LLTemplateMessageDispatcher class
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef LLTEMPLATEMESSAGEDISPATCHER_H
#define LLTEMPLATEMESSAGEDISPATCHER_H
#include "linden_common.h"
#include "llsd.h"
#include "llhttpnode.h"
#include "lltemplatemessagereader.h"
class LLTemplateMessageDispatcher
{
public:
LLTemplateMessageDispatcher(LLTemplateMessageReader& template_message_reader);
void dispatch(const std::string& msg_name,
const LLSD& message,
LLHTTPNode::ResponsePtr responsep);
private:
LLTemplateMessageReader &mTemplateMessageReader;
};
#endif // LLTEMPLATEMESSAGEDISPATCHER_H

View File

@ -755,18 +755,38 @@ BOOL LLTemplateMessageReader::decodeData(const U8* buffer, const LLHost& sender
BOOL LLTemplateMessageReader::validateMessage(const U8* buffer,
S32 buffer_size,
const LLHost& sender)
const LLHost& sender,
bool trusted)
{
mReceiveSize = buffer_size;
BOOL result = decodeTemplate(buffer, buffer_size, &mCurrentRMessageTemplate );
if(result)
BOOL valid = decodeTemplate(buffer, buffer_size, &mCurrentRMessageTemplate );
if(valid)
{
mCurrentRMessageTemplate->mReceiveCount++;
//lldebugs << "MessageRecvd:"
//lldebugs << "MessageRecvd:"
// << mCurrentRMessageTemplate->mName
// << " from " << sender << llendl;
}
return result;
if (valid && isBanned(trusted))
{
LL_WARNS("Messaging") << "LLMessageSystem::checkMessages "
<< "received banned message "
<< getMessageName()
<< " from "
<< ((trusted) ? "trusted " : "untrusted ")
<< sender << llendl;
valid = FALSE;
}
if(valid && isUdpBanned())
{
llwarns << "Received UDP black listed message "
<< getMessageName()
<< " from " << sender << llendl;
valid = FALSE;
}
return valid;
}
BOOL LLTemplateMessageReader::readMessage(const U8* buffer,

View File

@ -105,7 +105,7 @@ public:
virtual void copyToBuilder(LLMessageBuilder&) const;
BOOL validateMessage(const U8* buffer, S32 buffer_size,
const LLHost& sender);
const LLHost& sender, bool trusted = false);
BOOL readMessage(const U8* buffer, const LLHost& sender);
bool isTrusted() const;

View File

@ -0,0 +1,89 @@
/**
* @file lltrustedmessageservice.cpp
* @brief LLTrustedMessageService implementation
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "linden_common.h"
#include "lltrustedmessageservice.h"
#include "llhost.h"
#include "llmessageconfig.h"
#include "message.h"
bool LLTrustedMessageService::validate(const std::string& name, LLSD& context)
const
{
return true;
}
void LLTrustedMessageService::post(LLHTTPNode::ResponsePtr response,
const LLSD& context,
const LLSD& input) const
{
std::string name = context["request"]["wildcard"]["message-name"];
std::string senderIP = context["request"]["remote-host"];
std::string senderPort = context["request"]["headers"]
["x-secondlife-udp-listen-port"];
LLSD message_data;
std::string sender = senderIP + ":" + senderPort;
message_data["sender"] = sender;
message_data["body"] = input;
// untrusted senders should not have access to the trusted message
// service, but this can happen in development, so check and warn
LLMessageConfig::SenderTrust trust =
LLMessageConfig::getSenderTrustedness(name);
if ((trust == LLMessageConfig::TRUSTED ||
(trust == LLMessageConfig::NOT_SET &&
gMessageSystem->isTrustedMessage(name)))
&& !gMessageSystem->isTrustedSender(LLHost(sender)))
{
LL_WARNS("Messaging") << "trusted message POST to /trusted-message/"
<< name << " from unknown or untrusted sender "
<< sender << llendl;
response->status(403, "Unknown or untrusted sender");
}
else
{
gMessageSystem->receivedMessageFromTrustedSender();
if (input.has("binary-template-data"))
{
llinfos << "Dispatching template: " << input << llendl;
// try and send this message using udp dispatch
LLMessageSystem::dispatchTemplate(name, message_data, response);
}
else
{
llinfos << "Dispatching without template: " << input << llendl;
LLMessageSystem::dispatch(name, message_data, response);
}
}
}

View File

@ -0,0 +1,51 @@
/**
* @file lltrustedmessageservice.h
* @brief LLTrustedMessageService class
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef LLTRUSTEDMESSAGESERVICE_H
#define LLTRUSTEDMESSAGESERVICE_H
#include "linden_common.h"
#include "llhttpnode.h"
class LLSD;
class LLTrustedMessageService
{
public:
bool validate(const std::string& name, LLSD& context) const;
void post(LLHTTPNode::ResponsePtr response,
const LLSD& context,
const LLSD& input) const;
};
#endif // LLTRUSTEDMESSAGESERVICE_H

View File

@ -59,13 +59,16 @@
#include "llerrorlegacy.h"
#include "llfasttimer.h"
#include "llhttpclient.h"
#include "llhttpnodeadapter.h"
#include "llhttpsender.h"
#include "llmd5.h"
#include "llmessagebuilder.h"
#include "llmessageconfig.h"
#include "lltemplatemessagedispatcher.h"
#include "llpumpio.h"
#include "lltemplatemessagebuilder.h"
#include "lltemplatemessagereader.h"
#include "lltrustedmessageservice.h"
#include "llmessagetemplate.h"
#include "llmessagetemplateparser.h"
#include "llsd.h"
@ -142,52 +145,6 @@ namespace
};
}
class LLTrustedMessageService : public LLHTTPNode
{
virtual bool validate(const std::string& name, LLSD& context) const
{ return true; }
virtual void post(LLHTTPNode::ResponsePtr response,
const LLSD& context,
const LLSD& input) const;
};
//virtual
void LLTrustedMessageService::post(LLHTTPNode::ResponsePtr response,
const LLSD& context,
const LLSD& input) const
{
std::string name = context["request"]["wildcard"]["message-name"];
std::string senderIP = context["request"]["remote-host"];
std::string senderPort = context["request"]["headers"]
["x-secondlife-udp-listen-port"];
LLSD message_data;
std::string sender = senderIP + ":" + senderPort;
message_data["sender"] = sender;
message_data["body"] = input;
// untrusted senders should not have access to the trusted message
// service, but this can happen in development, so check and warn
LLMessageConfig::SenderTrust trust =
LLMessageConfig::getSenderTrustedness(name);
if ((trust == LLMessageConfig::TRUSTED ||
(trust == LLMessageConfig::NOT_SET &&
gMessageSystem->isTrustedMessage(name)))
&& !gMessageSystem->isTrustedSender(LLHost(sender)))
{
LL_WARNS("Messaging") << "trusted message POST to /trusted-message/"
<< name << " from unknown or untrusted sender "
<< sender << llendl;
response->status(403, "Unknown or untrusted sender");
}
else
{
LLMessageSystem::dispatch(name, message_data, response);
}
}
class LLMessageHandlerBridge : public LLHTTPNode
{
virtual bool validate(const std::string& name, LLSD& context) const
@ -223,9 +180,6 @@ void LLMessageHandlerBridge::post(LLHTTPNode::ResponsePtr response,
LLHTTPRegistration<LLMessageHandlerBridge>
gHTTPRegistrationMessageWildcard("/message/<message-name>");
LLHTTPRegistration<LLTrustedMessageService>
gHTTPRegistrationTrustedMessageWildcard("/trusted-message/<message-name>");
//virtual
LLUseCircuitCodeResponder::~LLUseCircuitCodeResponder()
{
@ -293,7 +247,8 @@ LLMessageSystem::LLMessageSystem(const std::string& filename, U32 port,
S32 version_patch,
bool failure_is_fatal,
const F32 circuit_heartbeat_interval, const F32 circuit_timeout) :
mCircuitInfo(circuit_heartbeat_interval, circuit_timeout)
mCircuitInfo(circuit_heartbeat_interval, circuit_timeout),
mLastMessageFromTrustedMessageService(false)
{
init();
@ -445,6 +400,7 @@ void LLMessageSystem::clearReceiveState()
mLastSender.invalidate();
mLastReceivingIF.invalidate();
mMessageReader->clearMessage();
mLastMessageFromTrustedMessageService = false;
}
@ -477,6 +433,17 @@ bool LLMessageSystem::isTrustedSender(const LLHost& host) const
return cdp->getTrusted();
}
void LLMessageSystem::receivedMessageFromTrustedSender()
{
mLastMessageFromTrustedMessageService = true;
}
bool LLMessageSystem::isTrustedSender() const
{
return mLastMessageFromTrustedMessageService ||
isTrustedSender(getSender());
}
static LLMessageSystem::message_template_name_map_t::const_iterator
findTemplate(const LLMessageSystem::message_template_name_map_t& templates,
std::string name)
@ -717,11 +684,16 @@ BOOL LLMessageSystem::checkMessages( S64 frame_count )
// UseCircuitCode can be a valid, off-circuit packet.
// But we don't want to acknowledge UseCircuitCode until the circuit is
// available, which is why the acknowledgement test is done above. JC
bool trusted = cdp && cdp->getTrusted();
valid_packet = mTemplateMessageReader->validateMessage(
buffer,
receive_size,
host);
host,
trusted);
if (!valid_packet)
{
clearReceiveState();
}
// UseCircuitCode is allowed in even from an invalid circuit, so that
// we can toss circuits around.
@ -749,29 +721,6 @@ BOOL LLMessageSystem::checkMessages( S64 frame_count )
valid_packet = FALSE;
}
if (
valid_packet &&
mTemplateMessageReader->isBanned(cdp && cdp->getTrusted()))
{
LL_WARNS("Messaging") << "LLMessageSystem::checkMessages "
<< "received banned message "
<< mTemplateMessageReader->getMessageName()
<< " from "
<< ((cdp && cdp->getTrusted()) ? "trusted " : "untrusted ")
<< host << llendl;
clearReceiveState();
valid_packet = FALSE;
}
if( valid_packet && mTemplateMessageReader->isUdpBanned())
{
llwarns << "Received UDP black listed message "
<< mTemplateMessageReader->getMessageName()
<< " from " << host << llendl;
clearReceiveState();
valid_packet = FALSE;
}
if( valid_packet )
{
logValidMsg(cdp, host, recv_reliable, recv_resent, (BOOL)(acks>0) );
@ -784,94 +733,6 @@ BOOL LLMessageSystem::checkMessages( S64 frame_count )
if (valid_packet)
{
// enable this for output of message names
//LL_INFOS("Messaging") << "< \"" << mTemplateMessageReader->getMessageName()
//<< "\"" << llendl;
/* Code for dumping the complete contents of a message. Keep for future use in optimizing messages.
if( 1 )
{
static char* object_update = LLMessageStringTable::getInstance()->getString("ObjectUpdate");
if(object_update == mTemplateMessageReader->getMessageName() )
{
LL_INFOS("Messaging") << "ObjectUpdate:" << llendl;
U32 i;
LL_INFOS("Messaging") << " Zero Encoded: " << zero_unexpanded_size << llendl;
for( i = 0; i<zero_unexpanded_size; i++ )
{
LL_INFOS("Messaging") << " " << i << ": " << (U32) zero_unexpanded_buffer[i] << llendl;
}
LL_INFOS("Messaging") << "" << llendl;
LL_INFOS("Messaging") << " Zero Unencoded: " << receive_size << llendl;
for( i = 0; i<receive_size; i++ )
{
LL_INFOS("Messaging") << " " << i << ": " << (U32) buffer[i] << llendl;
}
LL_INFOS("Messaging") << "" << llendl;
LL_INFOS("Messaging") << " Blocks and variables: " << llendl;
S32 byte_count = 0;
for (LLMessageTemplate::message_block_map_t::iterator
iter = mCurrentRMessageTemplate->mMemberBlocks.begin(),
end = mCurrentRMessageTemplate->mMemberBlocks.end();
iter != end; iter++)
{
LLMessageBlock* block = iter->second;
const char* block_name = block->mName;
for (LLMsgBlkData::msg_var_data_map_t::iterator
iter = block->mMemberVariables.begin(),
end = block->mMemberVariables.end();
iter != end; iter++)
{
const char* var_name = iter->first;
if( getNumberOfBlocksFast( block_name ) < 1 )
{
LL_INFOS("Messaging") << var_name << " has no blocks" << llendl;
}
for( S32 blocknum = 0; blocknum < getNumberOfBlocksFast( block_name ); blocknum++ )
{
char *bnamep = (char *)block_name + blocknum; // this works because it's just a hash. The bnamep is never derefference
char *vnamep = (char *)var_name;
LLMsgBlkData *msg_block_data = mCurrentRMessageData->mMemberBlocks[bnamep];
if (!msg_block_data)
{
std::string errmsg = llformat("Block %s #%d not in message %s", block_name, blocknum, mCurrentRMessageData->mName);
LL_ERRS("Messaging") << errmsg << llendl;
}
LLMsgVarData vardata = msg_block_data->mMemberVarData[vnamep];
if (!vardata.getName())
{
std::string errmsg = llformat("Variable %s not in message %s block %s", vnamep, mCurrentRMessageData->mName, bnamep);
LL_ERRS("Messaging") << errmsg << llendl;
}
const S32 vardata_size = vardata.getSize();
if( vardata_size )
{
for( i = 0; i < vardata_size; i++ )
{
byte_count++;
LL_INFOS("Messaging") << block_name << " " << var_name << " [" << blocknum << "][" << i << "]= " << (U32)(((U8*)vardata.getData())[i]) << llendl;
}
}
else
{
LL_INFOS("Messaging") << block_name << " " << var_name << " [" << blocknum << "] 0 bytes" << llendl;
}
}
}
}
LL_INFOS("Messaging") << "Byte count =" << byte_count << llendl;
}
}
*/
mPacketsIn++;
mBytesIn += mTrueReceiveSize;
@ -899,9 +760,6 @@ BOOL LLMessageSystem::checkMessages( S64 frame_count )
mInvalidOnCircuitPackets++;
}
}
// Code for dumping the complete contents of a message
// delete [] zero_unexpanded_buffer;
}
} while (!valid_packet && receive_size > 0);
@ -1004,7 +862,7 @@ void LLMessageSystem::processAcks()
}
}
void LLMessageSystem::copyMessageRtoS()
void LLMessageSystem::copyMessageReceivedToSend()
{
// NOTE: babbage: switch builder to match reader to avoid
// converting message format
@ -1021,6 +879,72 @@ void LLMessageSystem::copyMessageRtoS()
mMessageReader->copyToBuilder(*mMessageBuilder);
}
LLSD LLMessageSystem::getReceivedMessageLLSD() const
{
LLSDMessageBuilder builder;
mMessageReader->copyToBuilder(builder);
return builder.getMessage();
}
LLSD LLMessageSystem::getBuiltMessageLLSD() const
{
LLSD result;
if (mLLSDMessageBuilder == mMessageBuilder)
{
result = mLLSDMessageBuilder->getMessage();
}
else
{
// TODO: implement as below?
llerrs << "Message not built as LLSD." << llendl;
}
return result;
}
LLSD LLMessageSystem::wrapReceivedTemplateData() const
{
if(mMessageReader == mTemplateMessageReader)
{
LLTemplateMessageBuilder builder(mMessageTemplates);
builder.newMessage(mMessageReader->getMessageName());
mMessageReader->copyToBuilder(builder);
U8 buffer[MAX_BUFFER_SIZE];
const U8 offset_to_data = 0;
U32 size = builder.buildMessage(buffer, MAX_BUFFER_SIZE,
offset_to_data);
std::vector<U8> binary_data(buffer, buffer+size);
LLSD wrapped_data = LLSD::emptyMap();
wrapped_data["binary-template-data"] = binary_data;
return wrapped_data;
}
else
{
return getReceivedMessageLLSD();
}
}
LLStoredMessagePtr LLMessageSystem::getReceivedMessage() const
{
const std::string& name = mMessageReader->getMessageName();
LLSD message = wrapReceivedTemplateData();
return LLStoredMessagePtr(new LLStoredMessage(name, message));
}
LLStoredMessagePtr LLMessageSystem::getBuiltMessage() const
{
const std::string& name = mMessageBuilder->getMessageName();
LLSD message = getBuiltMessageLLSD();
return LLStoredMessagePtr(new LLStoredMessage(name, message));
}
S32 LLMessageSystem::sendMessage(const LLHost &host, LLStoredMessagePtr message)
{
return sendMessage(host, message->mName.c_str(), message->mMessage);
}
void LLMessageSystem::clearMessage()
{
mSendReliable = FALSE;
@ -1033,6 +957,11 @@ void LLMessageSystem::nextBlockFast(const char *blockname)
mMessageBuilder->nextBlock(blockname);
}
void LLMessageSystem::nextBlock(const char *blockname)
{
nextBlockFast(LLMessageStringTable::getInstance()->getString(blockname));
}
BOOL LLMessageSystem::isSendFull(const char* blockname)
{
char* stringTableName = NULL;
@ -1112,19 +1041,19 @@ S32 LLMessageSystem::sendReliable( const LLHost &host,
void LLMessageSystem::forwardMessage(const LLHost &host)
{
copyMessageRtoS();
copyMessageReceivedToSend();
sendMessage(host);
}
void LLMessageSystem::forwardReliable(const LLHost &host)
{
copyMessageRtoS();
copyMessageReceivedToSend();
sendReliable(host);
}
void LLMessageSystem::forwardReliable(const U32 circuit_code)
{
copyMessageRtoS();
copyMessageReceivedToSend();
sendReliable(findHost(circuit_code));
}
@ -1135,7 +1064,7 @@ S32 LLMessageSystem::forwardReliable( const LLHost &host,
void (*callback)(void **,S32),
void ** callback_data)
{
copyMessageRtoS();
copyMessageReceivedToSend();
return sendReliable(host, retries, ping_based_timeout, timeout, callback, callback_data);
}
@ -1463,13 +1392,6 @@ S32 LLMessageSystem::sendMessage(
LL_WARNS("Messaging") << "trying to send message to invalid host" << llendl;
return 0;
}
newMessage(name);
if (mMessageBuilder != mLLSDMessageBuilder)
{
LL_WARNS("Messaging") << "trying to send llsd message when builder is not LLSD!"
<< llendl;
return 0;
}
const LLHTTPSender& sender = LLHTTPSender::getSender(host);
sender.send(host, name, message, createResponder(name));
@ -2178,6 +2100,15 @@ void LLMessageSystem::dispatch(
handler->post(responsep, context, message);
}
//static
void LLMessageSystem::dispatchTemplate(const std::string& msg_name,
const LLSD& message,
LLHTTPNode::ResponsePtr responsep)
{
LLTemplateMessageDispatcher dispatcher(*(gMessageSystem->mTemplateMessageReader));
dispatcher.dispatch(msg_name, message, responsep);
}
static void check_for_unrecognized_messages(
const char* type,
const LLSD& map,
@ -2730,7 +2661,7 @@ void LLMessageSystem::summarizeLogs(std::ostream& str)
str << "END MESSAGE LOG SUMMARY" << std::endl;
}
void end_messaging_system()
void end_messaging_system(bool print_summary)
{
gTransferManager.cleanup();
LLTransferTargetVFile::updateQueue(true); // shutdown LLTransferTargetVFile
@ -2738,9 +2669,12 @@ void end_messaging_system()
{
gMessageSystem->stopLogging();
std::ostringstream str;
gMessageSystem->summarizeLogs(str);
LL_INFOS("Messaging") << str.str().c_str() << llendl;
if (print_summary)
{
std::ostringstream str;
gMessageSystem->summarizeLogs(str);
LL_INFOS("Messaging") << str.str().c_str() << llendl;
}
delete gMessageSystem;
gMessageSystem = NULL;
@ -4088,3 +4022,11 @@ void LLMessageSystem::banUdpMessage(const std::string& name)
llwarns << "Attempted to ban an unknown message: " << name << "." << llendl;
}
}
const LLHost& LLMessageSystem::getSender() const
{
return mLastSender;
}
LLHTTPRegistration<LLHTTPNodeAdapter<LLTrustedMessageService> >
gHTTPRegistrationTrustedMessageWildcard("/trusted-message/<message-name>");

View File

@ -63,6 +63,9 @@
#include "llstl.h"
#include "llmsgvariabletype.h"
#include "llmsgvariabletype.h"
#include "llmessagesenderinterface.h"
#include "llstoredmessage.h"
const U32 MESSAGE_MAX_STRINGS_LENGTH = 64;
const U32 MESSAGE_NUMBER_OF_HASH_BUCKETS = 8192;
@ -206,7 +209,7 @@ public:
virtual void complete(const LLHost& host, const LLUUID& agent) const = 0;
};
class LLMessageSystem
class LLMessageSystem : public LLMessageSenderInterface
{
private:
U8 mSendBuffer[MAX_BUFFER_SIZE];
@ -373,14 +376,33 @@ public:
void newMessageFast(const char *name);
void newMessage(const char *name);
void copyMessageRtoS();
void clearMessage();
public:
LLStoredMessagePtr getReceivedMessage() const;
LLStoredMessagePtr getBuiltMessage() const;
S32 sendMessage(const LLHost &host, LLStoredMessagePtr message);
private:
LLSD getReceivedMessageLLSD() const;
LLSD getBuiltMessageLLSD() const;
// NOTE: babbage: Only use to support legacy misuse of the
// LLMessageSystem API where values are dangerously written
// as one type and read as another. LLSD does not support
// dangerous conversions and so converting the message to an
// LLSD would result in the reads failing. All code which
// misuses the message system in this way should be made safe
// but while the unsafe code is run in old processes, this
// method should be used to forward unsafe messages.
LLSD wrapReceivedTemplateData() const;
public:
void copyMessageReceivedToSend();
void clearMessage();
void nextBlockFast(const char *blockname);
void nextBlock(const char *blockname)
{
nextBlockFast(LLMessageStringTable::getInstance()->getString(blockname));
}
void nextBlock(const char *blockname);
public:
void addBinaryDataFast(const char *varname, const void *data, S32 size);
@ -461,14 +483,14 @@ public:
void (*callback)(void **,S32), void ** callback_data);
// flush sends a message only if data's been pushed on it.
S32 flushSemiReliable( const LLHost &host,
S32 flushSemiReliable( const LLHost &host,
void (*callback)(void **,S32), void ** callback_data);
S32 flushReliable( const LLHost &host );
S32 flushReliable( const LLHost &host );
void forwardMessage(const LLHost &host);
void forwardReliable(const LLHost &host);
void forwardReliable(const U32 circuit_code);
void forwardMessage(const LLHost &host);
void forwardReliable(const LLHost &host);
void forwardReliable(const U32 circuit_code);
S32 forwardReliable(
const LLHost &host,
S32 retries,
@ -480,9 +502,10 @@ public:
LLHTTPClient::ResponderPtr createResponder(const std::string& name);
S32 sendMessage(const LLHost &host);
S32 sendMessage(const U32 circuit);
private:
S32 sendMessage(const LLHost &host, const char* name,
const LLSD& message);
public:
// BOOL decodeData(const U8 *buffer, const LLHost &host);
void getBinaryDataFast(const char *blockname, const char *varname, void *datap, S32 size, S32 blocknum = 0, S32 max_size = S32_MAX);
@ -561,8 +584,12 @@ public:
void sendDenyTrustedCircuit(const LLHost &host);
/** Return false if host is unknown or untrusted */
// Note:DaveH/Babbage some trusted messages can be received without a circuit
bool isTrustedSender(const LLHost& host) const;
/** Return true if current message is from trusted source */
bool isTrustedSender() const;
/** Return false true if name is unknown or untrusted */
bool isTrustedMessage(const std::string& name) const;
@ -578,6 +605,7 @@ public:
// Change this message to be UDP black listed.
void banUdpMessage(const std::string& name);
private:
// A list of the circuits that need to be sent DenyTrustedCircuit messages.
typedef std::set<LLHost> host_set_t;
@ -594,6 +622,7 @@ public:
void establishBidirectionalTrust(const LLHost &host, S64 frame_count = 0);
// returns whether the given host is on a trusted circuit
// Note:DaveH/Babbage some trusted messages can be received without a circuit
BOOL getCircuitTrust(const LLHost &host);
void setCircuitAllowTimeout(const LLHost &host, BOOL allow);
@ -663,6 +692,12 @@ public:
const LLSD& message,
LLHTTPNode::ResponsePtr responsep);
// this is added to support specific legacy messages and is
// ***not intended for general use*** Si, Gabriel, 2009
static void dispatchTemplate(const std::string& msg_name,
const LLSD& message,
LLHTTPNode::ResponsePtr responsep);
void setMessageBans(const LLSD& trusted, const LLSD& untrusted);
/**
@ -690,9 +725,18 @@ public:
// Check UDP messages and pump http_pump to receive HTTP messages.
bool checkAllMessages(S64 frame_count, LLPumpIO* http_pump);
// Moved to allow access from LLTemplateMessageDispatcher
void clearReceiveState();
// This will cause all trust queries to return true until the next message
// is read: use with caution!
void receivedMessageFromTrustedSender();
private:
bool mLastMessageFromTrustedMessageService;
// The mCircuitCodes is a map from circuit codes to session
// ids. This allows us to verify sessions on connect.
typedef std::map<U32, LLUUID> code_session_map_t;
@ -703,7 +747,6 @@ private:
LLUUID mSessionID;
void addTemplate(LLMessageTemplate *templatep);
void clearReceiveState();
BOOL decodeTemplate( const U8* buffer, S32 buffer_size, LLMessageTemplate** msg_template );
void logMsgFromInvalidCircuit( const LLHost& sender, BOOL recv_reliable );
@ -799,7 +842,7 @@ bool start_messaging_system(
const F32 circuit_heartbeat_interval,
const F32 circuit_timeout);
void end_messaging_system();
void end_messaging_system(bool print_summary = true);
void null_message_callback(LLMessageSystem *msg, void **data);
@ -976,8 +1019,6 @@ inline void *ntohmemcpy(void *s, const void *ct, EMsgVariableType type, size_t n
return(htonmemcpy(s,ct,type, n));
}
inline const LLHost& LLMessageSystem::getSender() const {return mLastSender;}
inline const LLHost& LLMessageSystem::getReceivingInterface() const {return mLastReceivingIF;}
inline U32 LLMessageSystem::getSenderIP() const

View File

@ -51,7 +51,6 @@
#endif
// linden library includes
#include "network.h"
#include "llerror.h"
#include "llhost.h"
#include "lltimer.h"
@ -395,11 +394,30 @@ S32 start_net(S32& socket_out, int& nPort)
return 1;
}
// Don't bind() if we want the operating system to assign our ports for
// us.
if (NET_USE_OS_ASSIGNED_PORT == nPort)
{
// Do nothing; the operating system will do it for us.
// Although bind is not required it will tell us which port we were
// assigned to.
stLclAddr.sin_family = AF_INET;
stLclAddr.sin_addr.s_addr = htonl(INADDR_ANY);
stLclAddr.sin_port = htons(0);
llinfos << "attempting to connect on OS assigned port" << llendl;
nRet = bind(hSocket, (struct sockaddr*) &stLclAddr, sizeof(stLclAddr));
if (nRet < 0)
{
llwarns << "Failed to bind on an OS assigned port error: "
<< nRet << llendl;
}
else
{
sockaddr_in socket_info;
socklen_t len = sizeof(sockaddr_in);
int err = getsockname(hSocket, (sockaddr*)&socket_info, &len);
llinfos << "Get socket returned: " << err << " length " << len << llendl;
nPort = ntohs(socket_info.sin_port);
llinfos << "Assigned port: " << nPort << llendl;
}
}
else
{

View File

@ -0,0 +1,88 @@
/**
* @file llcurl_stub.cpp
* @brief stub class to allow unit testing
*
* $LicenseInfo:firstyear=2008&license=internal$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* The following source code is PROPRIETARY AND CONFIDENTIAL. Use of
* this source code is governed by the Linden Lab Source Code Disclosure
* Agreement ("Agreement") { }
* Lab. By accessing, using, copying, modifying or distributing this
* software, you acknowledge that you have been informed of your
* obligations under the Agreement and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "linden_common.h"
LLCurl::Responder::Responder()
{
}
void LLCurl::Responder::completed(U32 status, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const &reason,
LLSD const& mContent)
{
if (isGoodStatus(status))
{
result(mContent);
}
else
{
error(status, reason, mContent);
}
}
void LLCurl::Responder::completedHeader(unsigned,
std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&,
LLSD const&)
{
}
void LLCurl::Responder::completedRaw(unsigned,
std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&,
LLChannelDescriptors const&,
boost::shared_ptr<LLBufferArray> const&)
{
}
void LLCurl::Responder::error(unsigned,
std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&,
LLSD const&)
{
}
LLCurl::Responder::~Responder ()
{
}
void LLCurl::Responder::error(unsigned,
std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)
{
}
void LLCurl::Responder::result(LLSD const&)
{
}
namespace boost
{
void intrusive_ptr_add_ref(LLCurl::Responder* p)
{
++p->mReferenceCount;
}
void intrusive_ptr_release(LLCurl::Responder* p)
{
if(p && 0 == --p->mReferenceCount)
{
delete p;
}
}
};

View File

@ -0,0 +1,169 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=viewergpl$
*
* Copyright (c) 2001-2008, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "llhttpclientadapter.h"
#include "../test/lltut.h"
#include "llhttpclient.h"
#include "llcurl_stub.cpp"
float const HTTP_REQUEST_EXPIRY_SECS = 1.0F;
std::vector<std::string> get_urls;
std::vector<boost::intrusive_ptr<LLCurl::Responder> > get_responders;
void LLHTTPClient::get(const std::string& url, boost::intrusive_ptr<LLCurl::Responder> responder, const LLSD& headers, const F32 timeout)
{
get_urls.push_back(url);
get_responders.push_back(responder);
}
std::vector<std::string> put_urls;
std::vector<LLSD> put_body;
std::vector<boost::intrusive_ptr<LLCurl::Responder> > put_responders;
void LLHTTPClient::put(std::string const &url, LLSD const &body, boost::intrusive_ptr<LLCurl::Responder> responder,float)
{
put_urls.push_back(url);
put_responders.push_back(responder);
put_body.push_back(body);
}
namespace tut
{
struct LLHTTPClientAdapterData
{
LLHTTPClientAdapterData()
{
get_urls.clear();
get_responders.clear();
put_urls.clear();
put_responders.clear();
put_body.clear();
}
};
typedef test_group<LLHTTPClientAdapterData> factory;
typedef factory::object object;
}
namespace
{
tut::factory tf("LLHTTPClientAdapterData test");
}
namespace tut
{
// Ensure we can create the object
template<> template<>
void object::test<1>()
{
LLHTTPClientAdapter adapter;
}
// Does the get pass the appropriate arguments to the LLHTTPClient
template<> template<>
void object::test<2>()
{
LLHTTPClientAdapter adapter;
boost::intrusive_ptr<LLCurl::Responder> responder = new LLCurl::Responder();
adapter.get("Made up URL", responder);
ensure_equals(get_urls.size(), 1);
ensure_equals(get_urls[0], "Made up URL");
}
// Ensure the responder matches the one passed to get
template<> template<>
void object::test<3>()
{
LLHTTPClientAdapter adapter;
boost::intrusive_ptr<LLCurl::Responder> responder = new LLCurl::Responder();
adapter.get("Made up URL", responder);
ensure_equals(get_responders.size(), 1);
ensure_equals(get_responders[0].get(), responder.get());
}
// Ensure the correct url is used in the put
template<> template<>
void object::test<4>()
{
LLHTTPClientAdapter adapter;
boost::intrusive_ptr<LLCurl::Responder> responder = new LLCurl::Responder();
LLSD body;
body["TestBody"] = "Foobar";
adapter.put("Made up URL", body, responder);
ensure_equals(put_urls.size(), 1);
ensure_equals(put_urls[0], "Made up URL");
}
// Ensure the correct responder is used by put
template<> template<>
void object::test<5>()
{
LLHTTPClientAdapter adapter;
boost::intrusive_ptr<LLCurl::Responder> responder = new LLCurl::Responder();
LLSD body;
body["TestBody"] = "Foobar";
adapter.put("Made up URL", body, responder);
ensure_equals(put_responders.size(), 1);
ensure_equals(put_responders[0].get(), responder.get());
}
// Ensure the message body is passed through the put properly
template<> template<>
void object::test<6>()
{
LLHTTPClientAdapter adapter;
boost::intrusive_ptr<LLCurl::Responder> responder = new LLCurl::Responder();
LLSD body;
body["TestBody"] = "Foobar";
adapter.put("Made up URL", body, responder);
ensure_equals(put_body.size(), 1);
ensure_equals(put_body[0]["TestBody"].asString(), "Foobar");
}
}

View File

@ -0,0 +1,164 @@
/**
* @file lltrustedmessageservice_test.cpp
* @brief LLTrustedMessageService unit tests
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "lltemplatemessagedispatcher.h"
#include "lltut.h"
#include "llhttpnode.h"
#include "llhost.h"
#include "message.h"
#include "llsd.h"
#include "llhost.cpp" // Needed for copy operator
#include "net.cpp" // Needed by LLHost.
LLMessageSystem * gMessageSystem = NULL;
// sensor test doubles
bool gClearRecvWasCalled = false;
void LLMessageSystem::clearReceiveState(void)
{
gClearRecvWasCalled = true;
}
char gUdpDispatchedData[MAX_BUFFER_SIZE];
bool gUdpDispatchWasCalled = false;
BOOL LLTemplateMessageReader::readMessage(const U8* data,class LLHost const &)
{
gUdpDispatchWasCalled = true;
strcpy(gUdpDispatchedData, reinterpret_cast<const char*>(data));
return true;
}
BOOL gValidateMessage = FALSE;
BOOL LLTemplateMessageReader::validateMessage(const U8*, S32 buffer_size, LLHost const &sender, bool trusted)
{
return gValidateMessage;
}
LLHost host;
const LLHost& LLMessageSystem::getSender() const
{
return host;
}
const char* gBinaryTemplateData = "BINARYTEMPLATEDATA";
void fillVector(std::vector<U8>& vector_data, const char* data)
{
vector_data.resize(strlen(data) + 1);
strcpy(reinterpret_cast<char*>(&vector_data[0]), data);
}
namespace tut
{
static LLTemplateMessageReader::message_template_number_map_t numberMap;
struct LLTemplateMessageDispatcherData
{
LLTemplateMessageDispatcherData()
{
mMessageName = "MessageName";
gUdpDispatchWasCalled = false;
gClearRecvWasCalled = false;
gValidateMessage = FALSE;
mMessage["body"]["binary-template-data"] = std::vector<U8>();
}
LLSD mMessage;
LLHTTPNode::ResponsePtr mResponsePtr;
std::string mMessageName;
};
typedef test_group<LLTemplateMessageDispatcherData> factory;
typedef factory::object object;
}
namespace
{
tut::factory tf("LLTemplateMessageDispatcher test");
}
namespace tut
{
// does an empty message stop processing?
template<> template<>
void object::test<1>()
{
LLTemplateMessageReader* pReader = NULL;
LLTemplateMessageDispatcher t(*pReader);
t.dispatch(mMessageName, mMessage, mResponsePtr);
ensure(! gUdpDispatchWasCalled);
ensure(! gClearRecvWasCalled);
}
// does the disaptch invoke the udp send method?
template<> template<>
void object::test<2>()
{
LLTemplateMessageReader* pReader = NULL;
LLTemplateMessageDispatcher t(*pReader);
gValidateMessage = TRUE;
std::vector<U8> vector_data;
fillVector(vector_data, gBinaryTemplateData);
mMessage["body"]["binary-template-data"] = vector_data;
t.dispatch(mMessageName, mMessage, mResponsePtr);
ensure("udp dispatch was called", gUdpDispatchWasCalled);
}
// what if the message wasn't valid? We would hope the message gets cleared!
template<> template<>
void object::test<3>()
{
LLTemplateMessageReader* pReader = NULL;
LLTemplateMessageDispatcher t(*pReader);
std::vector<U8> vector_data;
fillVector(vector_data, gBinaryTemplateData);
mMessage["body"]["binary-template-data"] = vector_data;
gValidateMessage = FALSE;
t.dispatch(mMessageName, mMessage, mResponsePtr);
ensure("clear received message was called", gClearRecvWasCalled);
}
// is the binary data passed through correctly?
template<> template<>
void object::test<4>()
{
LLTemplateMessageReader* pReader = NULL;
LLTemplateMessageDispatcher t(*pReader);
gValidateMessage = TRUE;
std::vector<U8> vector_data;
fillVector(vector_data, gBinaryTemplateData);
mMessage["body"]["binary-template-data"] = vector_data;
t.dispatch(mMessageName, mMessage, mResponsePtr);
ensure("data couriered correctly", strcmp(gBinaryTemplateData, gUdpDispatchedData) == 0);
}
}

View File

@ -0,0 +1,56 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=internal$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* The following source code is PROPRIETARY AND CONFIDENTIAL. Use of
* this source code is governed by the Linden Lab Source Code Disclosure
* Agreement ("Agreement") previously entered between you and Linden
* Lab. By accessing, using, copying, modifying or distributing this
* software, you acknowledge that you have been informed of your
* obligations under the Agreement and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "lltesthttpclientadapter.h"
LLTestHTTPClientAdapter::LLTestHTTPClientAdapter()
{
}
LLTestHTTPClientAdapter::~LLTestHTTPClientAdapter()
{
}
void LLTestHTTPClientAdapter::get(const std::string& url, LLCurl::ResponderPtr responder)
{
mGetUrl.push_back(url);
mGetResponder.push_back(responder);
}
void LLTestHTTPClientAdapter::put(const std::string& url, const LLSD& body, LLCurl::ResponderPtr responder)
{
mPutUrl.push_back(url);
mPutBody.push_back(body);
mPutResponder.push_back(responder);
}
U32 LLTestHTTPClientAdapter::putCalls() const
{
return mPutUrl.size();
}
void LLTestHTTPClientAdapter::get(const std::string& url, LLCurl::ResponderPtr responder, const LLSD& headers)
{
mGetUrl.push_back(url);
mGetHeaders.push_back(headers);
mGetResponder.push_back(responder);
}

View File

@ -0,0 +1,52 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=internal$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* The following source code is PROPRIETARY AND CONFIDENTIAL. Use of
* this source code is governed by the Linden Lab Source Code Disclosure
* Agreement ("Agreement") previously entered between you and Linden
* Lab. By accessing, using, copying, modifying or distributing this
* software, you acknowledge that you have been informed of your
* obligations under the Agreement and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
/* Macro Definitions */
#ifndef LL_LLTESTHTTPCLIENTADAPTER_H
#define LL_LLTESTHTTPCLIENTADAPTER_H
#include "linden_common.h"
#include "llhttpclientinterface.h"
class LLTestHTTPClientAdapter : public LLHTTPClientInterface
{
public:
LLTestHTTPClientAdapter();
virtual ~LLTestHTTPClientAdapter();
virtual void get(const std::string& url, LLCurl::ResponderPtr responder);
virtual void get(const std::string& url, LLCurl::ResponderPtr responder, const LLSD& headers);
virtual void put(const std::string& url, const LLSD& body, LLCurl::ResponderPtr responder);
U32 putCalls() const;
std::vector<LLSD> mPutBody;
std::vector<LLSD> mGetHeaders;
std::vector<std::string> mPutUrl;
std::vector<std::string> mGetUrl;
std::vector<LLCurl::ResponderPtr> mPutResponder;
std::vector<LLCurl::ResponderPtr> mGetResponder;
};
#endif //LL_LLSIMULATORPRESENCESENDER_H

View File

@ -0,0 +1,33 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=internal$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* The following source code is PROPRIETARY AND CONFIDENTIAL. Use of
* this source code is governed by the Linden Lab Source Code Disclosure
* Agreement ("Agreement") previously entered between you and Linden
* Lab. By accessing, using, copying, modifying or distributing this
* software, you acknowledge that you have been informed of your
* obligations under the Agreement and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "lltestmessagesender.h"
LLTestMessageSender::~LLTestMessageSender()
{
}
S32 LLTestMessageSender::sendMessage(const LLHost& host, LLStoredMessagePtr message)
{
mSendHosts.push_back(host);
mSendMessages.push_back(message);
return 0;
}

View File

@ -0,0 +1,46 @@
/**
* @file
* @brief
*
* $LicenseInfo:firstyear=2008&license=internal$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* The following source code is PROPRIETARY AND CONFIDENTIAL. Use of
* this source code is governed by the Linden Lab Source Code Disclosure
* Agreement ("Agreement") previously entered between you and Linden
* Lab. By accessing, using, copying, modifying or distributing this
* software, you acknowledge that you have been informed of your
* obligations under the Agreement and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
/* Macro Definitions */
#ifndef LL_LLTESTMESSAGESENDER_H
#define LL_LLTESTMESSAGESENDER_H
#include "linden_common.h"
#include "llmessagesenderinterface.h"
#include <vector>
class LLTestMessageSender : public LLMessageSenderInterface
{
public:
virtual ~LLTestMessageSender();
virtual S32 sendMessage(const LLHost& host, LLStoredMessagePtr message);
std::vector<LLHost> mSendHosts;
std::vector<LLStoredMessagePtr> mSendMessages;
};
#endif //LL_LLTESTMESSAGESENDER_H

View File

@ -0,0 +1,145 @@
/**
* @file lltrustedmessageservice_test.cpp
* @brief LLTrustedMessageService unit tests
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2001-2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include "lltrustedmessageservice.h"
#include "../test/lltut.h"
#include "llhost.cpp" // LLHost is a value type for test purposes.
#include "net.cpp" // Needed by LLHost.
#include "message.h"
#include "llmessageconfig.h"
LLMessageSystem* gMessageSystem = NULL;
LLMessageConfig::SenderTrust
LLMessageConfig::getSenderTrustedness(const std::string& msg_name)
{
return LLMessageConfig::NOT_SET;
}
void LLMessageSystem::receivedMessageFromTrustedSender()
{
}
bool LLMessageSystem::isTrustedSender(const LLHost& host) const
{
return false;
}
bool LLMessageSystem::isTrustedMessage(const std::string& name) const
{
return false;
}
bool messageDispatched = false;
bool messageDispatchedAsBinary = false;
LLSD lastLLSD;
std::string lastMessageName;
void LLMessageSystem::dispatch(const std::string& msg_name,
const LLSD& message,
LLHTTPNode::ResponsePtr responsep)
{
messageDispatched = true;
lastLLSD = message;
lastMessageName = msg_name;
}
void LLMessageSystem::dispatchTemplate(const std::string& msg_name,
const LLSD& message,
LLHTTPNode::ResponsePtr responsep)
{
lastLLSD = message;
lastMessageName = msg_name;
messageDispatchedAsBinary = true;
}
namespace tut
{
struct LLTrustedMessageServiceData
{
LLTrustedMessageServiceData()
{
LLSD emptyLLSD;
lastLLSD = emptyLLSD;
lastMessageName = "uninitialised message name";
messageDispatched = false;
messageDispatchedAsBinary = false;
}
};
typedef test_group<LLTrustedMessageServiceData> factory;
typedef factory::object object;
}
namespace
{
tut::factory tf("LLTrustedMessageServiceData test");
}
namespace tut
{
// characterisation tests
// 1) test that messages get forwarded with names etc. as current behaviour (something like LLMessageSystem::dispatch(name, data...)
// test llsd messages are sent as normal using LLMessageSystem::dispatch() (eventually)
template<> template<>
void object::test<1>()
{
LLHTTPNode::ResponsePtr response;
LLSD input;
LLSD context;
LLTrustedMessageService adapter;
adapter.post(response, context, input);
// test original ting got called wit nowt, ya get me blood?
ensure_equals(messageDispatched, true);
ensure(lastLLSD.has("body"));
}
// test that llsd wrapped binary-template-data messages are
// sent via LLMessageSystem::binaryDispatch() or similar
template<> template<>
void object::test<2>()
{
LLHTTPNode::ResponsePtr response;
LLSD input;
input["binary-template-data"] = "10001010110"; //make me a message here.
LLSD context;
LLTrustedMessageService adapter;
adapter.post(response, context, input);
ensure("check template-binary-data message was dispatched as binary", messageDispatchedAsBinary);
ensure_equals(lastLLSD["body"]["binary-template-data"].asString(), "10001010110");
// test somit got called with "10001010110" (something like LLMessageSystem::dispatchTemplate(blah))
}
}

View File

@ -50,7 +50,7 @@
const F32 MAX_OBJECT_SPAN = 54.f; // max distance from outside edge of an object to the farthest edge
const F32 OBJECT_SPAN_BONUS = 2.f; // infinitesimally small prims can always link up to this distance
const S32 MAX_PRIMS_PER_OBJECT = 255;
const S32 MAX_PRIMS_PER_OBJECT = 256;
template < typename DATA_TYPE >

View File

@ -1,6 +1,7 @@
/* Localized versions of Info.plist keys */
CFBundleName = "Second Life";
CFBundleShortVersionString = "Second Life version 1.23.0.0";
CFBundleGetInfoString = "Second Life version 1.23.0.0, Copyright 2004-2008 Linden Research, Inc.";

View File

@ -60,6 +60,7 @@ set(test_SOURCE_FILES
llstreamtools_tut.cpp
llstring_tut.cpp
lltemplatemessagebuilder_tut.cpp
lltimestampcache_tut.cpp
lltiming_tut.cpp
lltranscode_tut.cpp
lltut.cpp

View File

@ -94,7 +94,6 @@ namespace tut
template<> template<>
void blowfish_object::test<1>()
{
#if LL_LINUX
LLUUID blank;
LLBlowfishCipher cipher(&blank.mData[0], UUID_BYTES);
@ -107,15 +106,11 @@ namespace tut
dst_len = cipher.requiredEncryptionSpace(8);
ensure("encryption space 8",
(dst_len == 16) );
#else
skip("Blowfish only supported on Linux.");
#endif // LL_LINUX
}
template<> template<>
void blowfish_object::test<2>()
{
#if LL_LINUX
LLUUID blank;
LLBlowfishCipher cipher(&blank.mData[0], UUID_BYTES);
@ -129,15 +124,11 @@ namespace tut
result.resize(count);
ensure("encrypt null key", matchFile("blowfish.1.bin", result));
#else
skip("Blowfish only supported on Linux.");
#endif // LL_LINUX
}
template<> template<>
void blowfish_object::test<3>()
{
#if LL_LINUX
// same as base64 test id
LLUUID id("526a1e07-a19d-baed-84c4-ff08a488d15e");
LLBlowfishCipher cipher(&id.mData[0], UUID_BYTES);
@ -152,8 +143,5 @@ namespace tut
result.resize(count);
ensure("encrypt real key", matchFile("blowfish.2.bin", result));
#else
skip("Blowfish only supported on Linux.");
#endif // LL_LINUX
}
}

View File

@ -35,6 +35,7 @@
#include "linden_common.h"
#include "lltut.h"
#include "llmessagetemplate.h"
#include "llsdmessagebuilder.h"
#include "llsdmessagereader.h"
#include "llsdtraits.h"
@ -43,10 +44,24 @@
#include "v3dmath.h"
#include "v3math.h"
#include "v4math.h"
#include "llsdutil_math.cpp"
#include "lltemplatemessagebuilder.h"
namespace tut
{
static LLTemplateMessageBuilder::message_template_name_map_t templateNameMap;
LLMsgData* messageData = NULL;
LLMsgBlkData* messageBlockData = NULL;
struct LLSDMessageBuilderTestData {
LLSDMessageBuilderTestData()
{
messageData = new LLMsgData("testMessage");
messageBlockData = new LLMsgBlkData("testBlock", 0);
}
static LLSDMessageBuilder defaultBuilder()
{
LLSDMessageBuilder builder;
@ -61,6 +76,43 @@ namespace tut
reader.setMessage("name", builder.getMessage());
return reader;
}
static void addValue(LLMsgBlkData* mbd, char* name, void* v, EMsgVariableType type, int size, int data_size = -1)
{
LLMsgVarData tmp(name, type);
tmp.addData(v, size, type, data_size);
mbd->mMemberVarData[name] = tmp;
}
static LLMessageBlock* defaultTemplateBlock(const EMsgVariableType type = MVT_NULL, const S32 size = 0, EMsgBlockType block = MBT_VARIABLE)
{
return createTemplateBlock(_PREHASH_Test0, type, size, block);
}
static LLMessageBlock* createTemplateBlock(char* name, const EMsgVariableType type = MVT_NULL, const S32 size = 0, EMsgBlockType block = MBT_VARIABLE)
{
LLMessageBlock* result = new LLMessageBlock(name, block);
if(type != MVT_NULL)
{
result->addVariable(_PREHASH_Test0, type, size);
}
return result;
}
static LLTemplateMessageBuilder* defaultTemplateBuilder(LLMessageTemplate& messageTemplate, char* name = _PREHASH_Test0)
{
templateNameMap[_PREHASH_TestMessage] = &messageTemplate;
LLTemplateMessageBuilder* builder = new LLTemplateMessageBuilder(templateNameMap);
builder->newMessage(_PREHASH_TestMessage);
builder->nextBlock(name);
return builder;
}
static LLMessageTemplate defaultTemplate()
{
return LLMessageTemplate(_PREHASH_TestMessage, 1, MFT_HIGH);
}
};
typedef test_group<LLSDMessageBuilderTestData> LLSDMessageBuilderTestGroup;
@ -280,5 +332,509 @@ namespace tut
outValue = buffer;
ensure_equals("Ensure String", inValue, outValue);
}
template<> template<>
void LLSDMessageBuilderTestObject::test<19>()
{
LLMsgBlkData* mbd = new LLMsgBlkData("testBlock", 0);
LLMsgData* md = new LLMsgData("testMessage");
md->addBlock(mbd);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*md);
LLSD output = builder.getMessage();
ensure("Ensure message block created when copied from legacy message to llsd", output["testBlock"].isDefined());
}
// MVT_FIXED
template<> template<>
void LLSDMessageBuilderTestObject::test<20>()
{
char binData[] = "abcdefghijklmnop";
addValue(messageBlockData, "testBinData", &binData, MVT_FIXED, sizeof(binData));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::vector<U8> v = output["testBlock"][0]["testBinData"].asBinary();
ensure("Ensure MVT_S16Array data copied from legacy to llsd give a valid vector", v.size() > 0);
ensure_memory_matches("Ensure fixed binary data works in a message copied from legacy to llsd",
&v[0], sizeof(binData), binData, sizeof(binData));
}
// MVT_VARIABLE data_size 1 (U8's)
template<> template<>
void LLSDMessageBuilderTestObject::test<21>()
{
/* U8 binData[] = "abcdefghijklmnop";
addValue(messageBlockData, "testBinData", &binData, MVT_VARIABLE, sizeof(binData), 1);
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::vector<U8> v = output["testBlock"][0]["testBinData"].asBinary();
ensure("Ensure MVT_S16Array data copied from legacy to llsd give a valid vector", v.size() > 0);
ensure_memory_matches("Ensure MVT_VARIABLE U8 binary data works in a message copied from legacy to llsd",
&v[0], sizeof(binData), binData, sizeof(binData));*/
}
// MVT_VARIABLE data_size 2 (U16's)
template<> template<>
void LLSDMessageBuilderTestObject::test<22>()
{
U16 binData[] = {1,2,3,4,5,6,7,8,9}; //9 shorts
addValue(messageBlockData, "testBinData", &binData, MVT_VARIABLE, sizeof(binData) >> 1, 2);
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::vector<U8> v = output["testBlock"][0]["testBinData"].asBinary();
ensure("Ensure MVT_S16Array data copied from legacy to llsd give a valid vector", v.size() > 0);
ensure_memory_matches("Ensure MVT_VARIABLE U16 binary data works in a message copied from legacy to llsd",
&v[0], sizeof(binData) >> 1, binData, sizeof(binData) >> 1);
}
// MVT_VARIABLE data_size 4 (S32's)
template<> template<>
void LLSDMessageBuilderTestObject::test<23>()
{
U32 binData[] = {9,8,7,6,5,4,3,2,1};
addValue(messageBlockData, "testBinData", &binData, MVT_VARIABLE, sizeof(binData) >> 2, 4);
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::vector<U8> v = output["testBlock"][0]["testBinData"].asBinary();
ensure("Ensure MVT_S16Array data copied from legacy to llsd give a valid vector", v.size() > 0);
ensure_memory_matches("Ensure MVT_VARIABLE S32 binary data works in a message copied from legacy to llsd",
&v[0], sizeof(binData) >> 2, binData, sizeof(binData) >> 2);
}
// MVT_U8
template<> template<>
void LLSDMessageBuilderTestObject::test<24>()
{
U8 data = 0xa5;
addValue(messageBlockData, "testBinData", &data, MVT_U8, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_U8 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asInteger(), data);
}
// MVT_U16
template<> template<>
void LLSDMessageBuilderTestObject::test<25>()
{
U16 data = 0xa55a;
addValue(messageBlockData, "testBinData", &data, MVT_U16, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_U16 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asInteger(), data);
}
// MVT_U32
template<> template<>
void LLSDMessageBuilderTestObject::test<26>()
{
U32 data = 0xa55a7117;
addValue(messageBlockData, "testBinData", &data, MVT_U32, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_U32 data works in a message copied from legacy to llsd",
ll_U32_from_sd(output["testBlock"][0]["testBinData"]), data);
}
// MVT_U64 - crush into an s32: LLSD does not support 64 bit values
template<> template<>
void LLSDMessageBuilderTestObject::test<27>()
{
U64 data = U64L(0xa55a711711223344);
addValue(messageBlockData, "testBinData", &data, MVT_U64, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_U64 data works in a message copied from legacy to llsd",
ll_U64_from_sd(output["testBlock"][0]["testBinData"]), data);
}
// MVT_S8
template<> template<>
void LLSDMessageBuilderTestObject::test<28>()
{
S8 data = -31;
addValue(messageBlockData, "testBinData", &data, MVT_S8, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_S8 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asInteger(), data);
}
// MVT_S16
template<> template<>
void LLSDMessageBuilderTestObject::test<29>()
{
S16 data = -31;
addValue(messageBlockData, "testBinData", &data, MVT_S16, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_S16 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asInteger(), data);
}
// MVT_S32
template<> template<>
void LLSDMessageBuilderTestObject::test<30>()
{
S32 data = -3100;
addValue(messageBlockData, "testBinData", &data, MVT_S32, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_S32 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asInteger(), data);
}
// MVT_S64 - crush into an s32: LLSD does not support 64 bit values
template<> template<>
void LLSDMessageBuilderTestObject::test<31>()
{
S64 data = -31003100;
addValue(messageBlockData, "testBinData", &data, MVT_S64, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_S64 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asInteger(), (S32)data);
}
// MVT_F32
template<> template<>
void LLSDMessageBuilderTestObject::test<32>()
{
F32 data = 1234.1234f;
addValue(messageBlockData, "testBinData", &data, MVT_F32, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_F32 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asReal(), data);
}
// MVT_F64
template<> template<>
void LLSDMessageBuilderTestObject::test<33>()
{
F64 data = 1234.1234;
addValue(messageBlockData, "testBinData", &data, MVT_F64, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_F64 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asReal(), data);
}
// MVT_LLVector3
template<> template<>
void LLSDMessageBuilderTestObject::test<34>()
{
LLVector3 data(1,2,3);
addValue(messageBlockData, "testBinData", &data, MVT_LLVector3, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_LLVector3 data works in a message copied from legacy to llsd",
ll_vector3_from_sd(output["testBlock"][0]["testBinData"]), data);
}
// MVT_LLVector3d
template<> template<>
void LLSDMessageBuilderTestObject::test<35>()
{
LLVector3d data(1,2,3);
addValue(messageBlockData, "testBinData", &data, MVT_LLVector3d, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_LLVector3 data works in a message copied from legacy to llsd",
ll_vector3d_from_sd(output["testBlock"][0]["testBinData"]), data);
}
// MVT_LLVector4
template<> template<>
void LLSDMessageBuilderTestObject::test<36>()
{
LLVector4 data(1,2,3,4);
LLSD v = ll_sd_from_vector4(data);
addValue(messageBlockData, "testBinData", &data, MVT_LLVector4, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_LLVector4 data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"], v);
}
// MVT_LLQuaternion
template<> template<>
void LLSDMessageBuilderTestObject::test<37>()
{
LLQuaternion data(1,2,3,0);
//we send a quaternion packed into a vec3 (w is infered) - so sizeof(vec) == 12 bytes not 16.
LLVector3 vec = data.packToVector3();
addValue(messageBlockData, "testBinData", &vec, MVT_LLQuaternion, sizeof(vec));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_LLQuaternion data works in a message copied from legacy to llsd",
ll_quaternion_from_sd(output["testBlock"][0]["testBinData"]), data);
}
// MVT_LLUUID
template<> template<>
void LLSDMessageBuilderTestObject::test<38>()
{
LLUUID data("01234567-0123-0123-0123-234567abcdef");
addValue(messageBlockData, "testBinData", &data, MVT_LLUUID, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::string v = output["testBlock"][0]["testBinData"].asUUID().asString();
ensure_equals("Ensure MVT_LLUUID data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asUUID(), data);
}
// MVT_BOOL
template<> template<>
void LLSDMessageBuilderTestObject::test<39>()
{
BOOL valueTrue = true;
BOOL valueFalse = false;
LLMsgData* md = new LLMsgData("testMessage");
LLMsgBlkData* mbd = new LLMsgBlkData("testBlock", 0);
addValue(mbd, "testBoolFalse", &valueFalse, MVT_BOOL, sizeof(BOOL));
addValue(mbd, "testBoolTrue", &valueTrue, MVT_BOOL, sizeof(BOOL));
md->addBlock(mbd);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*md);
LLSD output = builder.getMessage();
ensure("Ensure bools work in a message copied from legacy to llsd",
output["testBlock"][0]["testBoolTrue"].asBoolean() && !output["testBlock"][0]["testBoolFalse"].asBoolean());
}
// MVT_IP_ADDR
template<> template<>
void LLSDMessageBuilderTestObject::test<40>()
{
U32 data(0xff887766);
LLSD v = ll_sd_from_ipaddr(data);
addValue(messageBlockData, "testBinData", &data, MVT_IP_ADDR, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_IP_ADDR data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"], v);
}
// MVT_IP_PORT
template<> template<>
void LLSDMessageBuilderTestObject::test<41>()
{
U16 data = 0xff88;
addValue(messageBlockData, "testBinData", &data, MVT_IP_PORT, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
ensure_equals("Ensure MVT_IP_PORT data works in a message copied from legacy to llsd",
output["testBlock"][0]["testBinData"].asInteger(), data);
}
// MVT_U16Vec3
template<> template<>
void LLSDMessageBuilderTestObject::test<42>()
{
U16 data[3] = {0,1,2};
addValue(messageBlockData, "testBinData", &data, MVT_U16Vec3, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::vector<U8> v = output["testBlock"][0]["testBinData"].asBinary();
ensure("Ensure MVT_U16Vec3 data copied from legacy to llsd give a valid vector", v.size() > 0);
ensure_memory_matches("Ensure MVT_U16Vec3 data works in a message copied from legacy to llsd",
(U16*)&v[0], 6, data, 6);
}
// MVT_U16Quat
template<> template<>
void LLSDMessageBuilderTestObject::test<43>()
{
U16 data[4] = {0,1,2,4};
addValue(messageBlockData, "testBinData", &data, MVT_U16Quat, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::vector<U8> v = output["testBlock"][0]["testBinData"].asBinary();
ensure("Ensure MVT_U16Quat data copied from legacy to llsd give a valid vector", v.size() > 0);
ensure_memory_matches("Ensure MVT_U16Quat data works in a message copied from legacy to llsd",
(U16*)&v[0], 8, data, 8);
}
// MVT_S16Array
template<> template<>
void LLSDMessageBuilderTestObject::test<44>()
{
S16 data[19] = {0,-1,2,-4,5,-6,7,-8,9,-10,11,-12,13,-14,15,16,17,18};
addValue(messageBlockData, "testBinData", &data, MVT_S16Array, sizeof(data));
messageData->addBlock(messageBlockData);
LLSDMessageBuilder builder = defaultBuilder();
builder.copyFromMessageData(*messageData);
LLSD output = builder.getMessage();
std::vector<U8> v = output["testBlock"][0]["testBinData"].asBinary();
ensure("Ensure MVT_S16Array data copied from legacy to llsd give a valid vector", v.size() > 0);
ensure_memory_matches("Ensure MVT_S16Array data works in a message copied from legacy to llsd",
(U16*)&v[0], 19, data, 19);
}
template<> template<>
void LLSDMessageBuilderTestObject::test<45>()
{
LLMessageTemplate messageTemplate = defaultTemplate();
messageTemplate.addBlock(defaultTemplateBlock(MVT_U8, 1));
U8 inValue = 2;
LLTemplateMessageBuilder* template_builder = defaultTemplateBuilder(messageTemplate);
template_builder->addU8(_PREHASH_Test0, inValue);
LLSDMessageBuilder builder;
builder.copyFromMessageData(*template_builder->getCurrentMessage());
LLSD output = builder.getMessage();
ensure_equals(output["Test0"][0]["Test0"].asInteger(), 2);
}
template<> template<>
void LLSDMessageBuilderTestObject::test<46>()
{
LLMessageTemplate messageTemplate = defaultTemplate();
messageTemplate.addBlock(defaultTemplateBlock(MVT_VARIABLE, 1));
std::string inValue = "testing";
LLTemplateMessageBuilder* builder = defaultTemplateBuilder(messageTemplate);
builder->addString(_PREHASH_Test0, inValue.c_str());
LLSDMessageBuilder sd_builder;
sd_builder.copyFromMessageData(*builder->getCurrentMessage());
LLSD output = sd_builder.getMessage();
ensure_equals(output["Test0"][0]["Test0"].asString(), std::string("testing"));
}
}

View File

@ -0,0 +1,129 @@
/**
* @file lltimestampcache_tut.cpp
* @author James Tess
* @date 2008-12-03
*
* $LicenseInfo:firstyear=2008&license=viewergpl$
*
* Copyright (c) 2008, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#include <tut/tut.hpp>
#include "linden_common.h"
#include "../mapserver/lltimestampcache.h"
#include "lltut.h"
namespace tut
{
struct LLTimestampCacheTestData
{
};
typedef test_group<LLTimestampCacheTestData> LLTimestampCacheTestGroup;
typedef LLTimestampCacheTestGroup::object LLTimestampCacheTestObject;
LLTimestampCacheTestGroup timestampCacheTestGroup("LLTimestampCache");
// Most common usage
template<> template<>
void LLTimestampCacheTestObject::test<1>()
{
LLTimestampCache<std::string, std::string> cache;
// put in some data
cache.insert("key1", "val1", 1);
cache.insert("key2", "val2", 2);
cache.insert("key3", "val3", 3);
ensure_equals("size is 3", cache.size(), 3);
// check some items
ensure("has key1", cache.has("key1"));
ensure("no invalid key", !cache.has("invalid key"));
// get some items
ensure_equals("get key1", cache.get("key1", 4), "val1");
ensure_equals("get invalid key",
cache.get("invalid key", 4), std::string() );
// timestamps
ensure_equals("key1 timestamp updated", cache.getTimestamp("key1"), 4);
ensure_equals("invalid key timestamp",
cache.getTimestamp("invalid key"), 0);
}
// New empty cache shouldn't have any entries
template<> template<>
void LLTimestampCacheTestObject::test<2>()
{
LLTimestampCache<std::string, std::string> cache;
ensure_equals("starts empty", cache.size(), 0);
ensure_equals("has nothing", cache.has("foo"), false);
ensure_equals("gets nothing", cache.get("foo", 0), std::string() );
U32 max_time = 0xFFFFFFFF;
ensure_equals("erases nothing", cache.eraseBefore(max_time), 0);
}
// Non empty cache
template<> template<>
void LLTimestampCacheTestObject::test<3>()
{
LLTimestampCache<std::string, std::string> cache;
cache.insert("foo", "bar", 123);
ensure_equals("size one", cache.size(), 1);
ensure_equals("has it", cache.has("foo"), true);
ensure_equals("timestamp correct", cache.getTimestamp("foo"), 123);
std::string value = cache.get("foo", 456);
ensure_equals("get value", value, "bar");
ensure_equals("timestamp updated", cache.getTimestamp("foo"), 456);
ensure_equals("erase nothing", cache.eraseBefore(0), 0);
ensure_equals("erase one", cache.eraseBefore(789), 1);
ensure_equals("empty after erase", cache.size(), 0);
}
// Recache of item should update timestamp
template<> template<>
void LLTimestampCacheTestObject::test<4>()
{
LLTimestampCache<std::string, std::string> cache;
cache.insert("foo", "bar", 123);
cache.insert("foo", "bar", 456);
ensure_equals("duplicate suppressed", cache.size(), 1);
ensure_equals("timestamp replaced", cache.getTimestamp("foo"), 456);
}
// Erasing some items
template<> template<>
void LLTimestampCacheTestObject::test<5>()
{
LLTimestampCache<std::string, std::string> cache;
cache.insert("key1", "val1", 1);
cache.insert("key2", "val2", 2);
cache.insert("key3", "val3", 3);
cache.insert("key4", "val4", 4);
size_t erased = cache.eraseBefore(3);
ensure_equals("erase range", erased, 2);
ensure_equals("cache post erase", cache.size(), 2);
ensure_equals("has key3", cache.has("key3"), true);
ensure_equals("not has key2", cache.has("key2"), false);
}
}

View File

@ -33,10 +33,13 @@
*/
#include "linden_common.h"
#include "lltut.h"
#include "lldate.h"
#include "llformat.h"
#include "llsd.h"
#include "lluri.h"
namespace tut
{
@ -74,7 +77,7 @@ namespace tut
void ensure_equals(const char* m, const LLSD& actual,
const LLSD& expected)
{
const std::string& msg = m;
const std::string& msg = m ? m : "";
ensure_equals(msg + " type", actual.type(), expected.type());
switch (actual.type())
@ -196,3 +199,4 @@ namespace tut
}
}
}

View File

@ -35,13 +35,13 @@
#ifndef LL_LLTUT_H
#define LL_LLTUT_H
#include <tut/tut.hpp>
#include "lldate.h"
#include "lluri.h"
#include "llmath.h"
#include <tut/tut.hpp>
class LLDate;
class LLSD;
class LLURI;
namespace tut
{

View File

@ -54,9 +54,10 @@
# include "ctype_workaround.h"
#endif
namespace tut
{
std::string sSourceDir;
test_runner_singleton runner;
}
@ -184,6 +185,7 @@ static const apr_getopt_option_t TEST_CL_OPTIONS[] =
{"verbose", 'v', 0, "Verbose output."},
{"group", 'g', 1, "Run test group specified by option argument."},
{"output", 'o', 1, "Write output to the named file."},
{"sourcedir", 's', 1, "Project source file directory from CMake."},
{"touch", 't', 1, "Touch the given file if all tests succeed"},
{"wait", 'w', 0, "Wait for input before exit."},
{"debug", 'd', 0, "Emit full debug logs."},
@ -302,6 +304,11 @@ int main(int argc, char **argv)
output = new std::ofstream;
output->open(opt_arg);
break;
case 's': // --sourcedir
tut::sSourceDir = opt_arg;
// For convenience, so you can use tut::sSourceDir + "myfile"
tut::sSourceDir += '/';
break;
case 't':
touch = opt_arg;
break;

49
indra/test/test.h Normal file
View File

@ -0,0 +1,49 @@
/**
* @file test.h
* @author James
* @date 2009-01-12
*
* $LicenseInfo:firstyear=2009&license=viewergpl$
*
* Copyright (c) 2009, Linden Research, Inc.
*
* Second Life Viewer Source Code
* The source code in this file ("Source Code") is provided by Linden Lab
* to you under the terms of the GNU General Public License, version 2.0
* ("GPL"), unless you have obtained a separate licensing agreement
* ("Other License"), formally executed by you and Linden Lab. Terms of
* the GPL can be found in doc/GPL-license.txt in this distribution, or
* online at http://secondlife.com/developers/opensource/gplv2
*
* There are special exceptions to the terms and conditions of the GPL as
* it is applied to this Source Code. View the full text of the exception
* in the file doc/FLOSS-exception.txt in this software distribution, or
* online at http://secondlife.com/developers/opensource/flossexception
*
* By copying, modifying or distributing this software, you acknowledge
* that you have read and understood your obligations described above,
* and agree to abide by those obligations.
*
* ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
* WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
* COMPLETENESS OR PERFORMANCE.
* $/LicenseInfo$
*/
#ifndef TEST_H
#define TEST_H
#include <string>
namespace tut
{
// Source code directory from CMake, used for loading test data and
// configuration. For example:
//
// loadMyConfig( sSourceDir + "config.dat" );
//
// Use sparingly, as hitting the file system slows down test execution
// and hence every compile. JC
extern std::string sSourceDir;
}
#endif

View File

@ -8717,7 +8717,7 @@ version 2.0
// spaceserver -> simulator
{
RpcScriptRequestInboundForward Low 416 Trusted Unencoded
RpcScriptRequestInboundForward Low 416 Trusted Unencoded UDPDeprecated
{
DataBlock Single
{ RPCServerIP IPADDR }