summaryrefslogtreecommitdiff
path: root/indra/llcommon
diff options
context:
space:
mode:
Diffstat (limited to 'indra/llcommon')
-rw-r--r--indra/llcommon/CMakeLists.txt1
-rw-r--r--indra/llcommon/fix_macros.h25
-rw-r--r--indra/llcommon/llapp.cpp3
-rw-r--r--indra/llcommon/llapr.h2
-rw-r--r--indra/llcommon/llmemory.cpp31
-rw-r--r--indra/llcommon/llmemory.h37
-rw-r--r--indra/llcommon/llqueuedthread.cpp4
-rw-r--r--indra/llcommon/llstring.cpp3
-rw-r--r--indra/llcommon/llsys.cpp34
-rw-r--r--indra/llcommon/llthread.cpp42
-rw-r--r--indra/llcommon/llthread.h36
-rw-r--r--indra/llcommon/lluri.cpp36
-rw-r--r--indra/llcommon/llversionviewer.h2
-rw-r--r--indra/llcommon/tests/bitpack_test.cpp1
-rw-r--r--indra/llcommon/tests/lluri_test.cpp94
15 files changed, 241 insertions, 110 deletions
diff --git a/indra/llcommon/CMakeLists.txt b/indra/llcommon/CMakeLists.txt
index 36a8319189..66e2bc9095 100644
--- a/indra/llcommon/CMakeLists.txt
+++ b/indra/llcommon/CMakeLists.txt
@@ -116,6 +116,7 @@ set(llcommon_HEADER_FILES
bitpack.h
ctype_workaround.h
doublelinkedlist.h
+ fix_macros.h
imageids.h
indra_constants.h
linden_common.h
diff --git a/indra/llcommon/fix_macros.h b/indra/llcommon/fix_macros.h
new file mode 100644
index 0000000000..ef959decff
--- /dev/null
+++ b/indra/llcommon/fix_macros.h
@@ -0,0 +1,25 @@
+/**
+ * @file fix_macros.h
+ * @author Nat Goodspeed
+ * @date 2012-11-16
+ * @brief The Mac system headers seem to #define macros with obnoxiously
+ * generic names, preventing any library from using those names. We've
+ * had to fix these in so many places that it's worth making a header
+ * file to handle it.
+ *
+ * $LicenseInfo:firstyear=2012&license=viewerlgpl$
+ * Copyright (c) 2012, Linden Research, Inc.
+ * $/LicenseInfo$
+ */
+
+// DON'T use an #include guard: every time we encounter this header, #undef
+// these macros all over again.
+
+// who injects MACROS with such generic names?! Grr.
+#ifdef equivalent
+#undef equivalent
+#endif
+
+#ifdef check
+#undef check
+#endif
diff --git a/indra/llcommon/llapp.cpp b/indra/llcommon/llapp.cpp
index ed192a9975..ca258900c7 100644
--- a/indra/llcommon/llapp.cpp
+++ b/indra/llcommon/llapp.cpp
@@ -289,6 +289,7 @@ void LLApp::setupErrorHandling()
// occasionally checks to see if the app is in an error state, and sees if it needs to be run.
#if LL_WINDOWS
+#if LL_SEND_CRASH_REPORTS
// This sets a callback to handle w32 signals to the console window.
// The viewer shouldn't be affected, sicne its a windowed app.
SetConsoleCtrlHandler( (PHANDLER_ROUTINE) ConsoleCtrlHandler, TRUE);
@@ -300,7 +301,7 @@ void LLApp::setupErrorHandling()
mExceptionHandler = new google_breakpad::ExceptionHandler(
L"C:\\Temp\\", 0, windows_post_minidump_callback, 0, google_breakpad::ExceptionHandler::HANDLER_ALL);
}
-
+#endif
#else
//
// Start up signal handling.
diff --git a/indra/llcommon/llapr.h b/indra/llcommon/llapr.h
index af33ce666f..034546c3f3 100644
--- a/indra/llcommon/llapr.h
+++ b/indra/llcommon/llapr.h
@@ -168,7 +168,7 @@ public:
void operator -=(Type x) { apr_atomic_sub32(&mData, apr_uint32_t(x)); }
void operator +=(Type x) { apr_atomic_add32(&mData, apr_uint32_t(x)); }
Type operator ++(int) { return apr_atomic_inc32(&mData); } // Type++
- Type operator --(int) { return apr_atomic_dec32(&mData); } // Type--
+ Type operator --(int) { return apr_atomic_dec32(&mData); } // approximately --Type (0 if final is 0, non-zero otherwise)
private:
apr_uint32_t mData;
diff --git a/indra/llcommon/llmemory.cpp b/indra/llcommon/llmemory.cpp
index afaf366668..70ad10ad55 100644
--- a/indra/llcommon/llmemory.cpp
+++ b/indra/llcommon/llmemory.cpp
@@ -252,21 +252,6 @@ U32 LLMemory::getAllocatedMemKB()
return sAllocatedMemInKB ;
}
-void* ll_allocate (size_t size)
-{
- if (size == 0)
- {
- llwarns << "Null allocation" << llendl;
- }
- void *p = malloc(size);
- if (p == NULL)
- {
- LLMemory::freeReserve();
- llerrs << "Out of memory Error" << llendl;
- }
- return p;
-}
-
//----------------------------------------------------------------------------
#if defined(LL_WINDOWS)
@@ -1365,7 +1350,7 @@ char* LLPrivateMemoryPool::allocate(U32 size)
//if the asked size larger than MAX_BLOCK_SIZE, fetch from heap directly, the pool does not manage it
if(size >= CHUNK_SIZE)
{
- return (char*)malloc(size) ;
+ return (char*)ll_aligned_malloc_16(size) ;
}
char* p = NULL ;
@@ -1422,7 +1407,7 @@ char* LLPrivateMemoryPool::allocate(U32 size)
to_log = false ;
}
- return (char*)malloc(size) ;
+ return (char*)ll_aligned_malloc_16(size) ;
}
return p ;
@@ -1441,7 +1426,7 @@ void LLPrivateMemoryPool::freeMem(void* addr)
if(!chunk)
{
- free(addr) ; //release from heap
+ ll_aligned_free_16(addr) ; //release from heap
}
else
{
@@ -1565,7 +1550,7 @@ LLPrivateMemoryPool::LLMemoryChunk* LLPrivateMemoryPool::addChunk(S32 chunk_inde
mReservedPoolSize += preferred_size + overhead ;
- char* buffer = (char*)malloc(preferred_size + overhead) ;
+ char* buffer = (char*)ll_aligned_malloc_16(preferred_size + overhead) ;
if(!buffer)
{
return NULL ;
@@ -1633,7 +1618,7 @@ void LLPrivateMemoryPool::removeChunk(LLMemoryChunk* chunk)
mReservedPoolSize -= chunk->getBufferSize() ;
//release memory
- free(chunk->getBuffer()) ;
+ ll_aligned_free_16(chunk->getBuffer()) ;
}
U16 LLPrivateMemoryPool::findHashKey(const char* addr)
@@ -1977,7 +1962,7 @@ char* LLPrivateMemoryPoolManager::allocate(LLPrivateMemoryPool* poolp, U32 size,
if(!poolp)
{
- p = (char*)malloc(size) ;
+ p = (char*)ll_aligned_malloc_16(size) ;
}
else
{
@@ -2006,7 +1991,7 @@ char* LLPrivateMemoryPoolManager::allocate(LLPrivateMemoryPool* poolp, U32 size)
}
else
{
- return (char*)malloc(size) ;
+ return (char*)ll_aligned_malloc_16(size) ;
}
}
#endif
@@ -2031,7 +2016,7 @@ void LLPrivateMemoryPoolManager::freeMem(LLPrivateMemoryPool* poolp, void* addr
{
if(!sPrivatePoolEnabled)
{
- free(addr) ; //private pool is disabled.
+ ll_aligned_free_16(addr) ; //private pool is disabled.
}
else if(!sInstance) //the private memory manager is destroyed, try the dangling list
{
diff --git a/indra/llcommon/llmemory.h b/indra/llcommon/llmemory.h
index 9dd776ff57..10013e0f92 100644
--- a/indra/llcommon/llmemory.h
+++ b/indra/llcommon/llmemory.h
@@ -27,6 +27,13 @@
#define LLMEMORY_H
#include "llmemtype.h"
+
+#if LL_WINDOWS && LL_DEBUG
+#define LL_CHECK_MEMORY llassert(_CrtCheckMemory());
+#else
+#define LL_CHECK_MEMORY
+#endif
+
inline void* ll_aligned_malloc( size_t size, int align )
{
void* mem = malloc( size + (align - 1) + sizeof(void*) );
@@ -58,31 +65,43 @@ inline void* ll_aligned_malloc_16(size_t size) // returned hunk MUST be freed wi
#endif
}
-inline void* ll_aligned_realloc_16(void* ptr, size_t size) // returned hunk MUST be freed with ll_aligned_free_16().
+inline void ll_aligned_free_16(void *p)
{
#if defined(LL_WINDOWS)
- return _aligned_realloc(ptr, size, 16);
+ _aligned_free(p);
#elif defined(LL_DARWIN)
- return realloc(ptr,size); // default osx malloc is 16 byte aligned.
+ return free(p);
#else
- return realloc(ptr,size); // FIXME not guaranteed to be aligned.
+ free(p); // posix_memalign() is compatible with heap deallocator
#endif
}
-inline void ll_aligned_free_16(void *p)
+inline void* ll_aligned_realloc_16(void* ptr, size_t size, size_t old_size) // returned hunk MUST be freed with ll_aligned_free_16().
{
#if defined(LL_WINDOWS)
- _aligned_free(p);
+ return _aligned_realloc(ptr, size, 16);
#elif defined(LL_DARWIN)
- return free(p);
+ return realloc(ptr,size); // default osx malloc is 16 byte aligned.
#else
- free(p); // posix_memalign() is compatible with heap deallocator
+ //FIXME: memcpy is SLOW
+ void* ret = ll_aligned_malloc_16(size);
+ if (ptr)
+ {
+ if (ret)
+ {
+ // Only copy the size of the smallest memory block to avoid memory corruption.
+ memcpy(ret, ptr, llmin(old_size, size));
+ }
+ ll_aligned_free_16(ptr);
+ }
+ return ret;
#endif
}
+
#else // USE_TCMALLOC
// ll_aligned_foo_16 are not needed with tcmalloc
#define ll_aligned_malloc_16 malloc
-#define ll_aligned_realloc_16 realloc
+#define ll_aligned_realloc_16(a,b,c) realloc(a,b)
#define ll_aligned_free_16 free
#endif // USE_TCMALLOC
diff --git a/indra/llcommon/llqueuedthread.cpp b/indra/llcommon/llqueuedthread.cpp
index 1738c16dea..abf47a0f57 100644
--- a/indra/llcommon/llqueuedthread.cpp
+++ b/indra/llcommon/llqueuedthread.cpp
@@ -134,8 +134,8 @@ S32 LLQueuedThread::updateQueue(F32 max_time_ms)
pending = getPending();
if(pending > 0)
{
- unpause();
- }
+ unpause();
+ }
}
else
{
diff --git a/indra/llcommon/llstring.cpp b/indra/llcommon/llstring.cpp
index fa0eb9f72c..0c32679744 100644
--- a/indra/llcommon/llstring.cpp
+++ b/indra/llcommon/llstring.cpp
@@ -47,7 +47,8 @@ std::string ll_safe_string(const char* in)
std::string ll_safe_string(const char* in, S32 maxlen)
{
- if(in) return std::string(in, maxlen);
+ if(in && maxlen > 0 ) return std::string(in, maxlen);
+
return std::string();
}
diff --git a/indra/llcommon/llsys.cpp b/indra/llcommon/llsys.cpp
index 6073bcd0a6..c96f2191f3 100644
--- a/indra/llcommon/llsys.cpp
+++ b/indra/llcommon/llsys.cpp
@@ -944,13 +944,15 @@ LLSD LLMemoryInfo::loadStatsMap()
state.dwLength = sizeof(state);
GlobalMemoryStatusEx(&state);
- stats.add("Percent Memory use", state.dwMemoryLoad);
- stats.add("Total Physical KB", state.ullTotalPhys/1024);
- stats.add("Avail Physical KB", state.ullAvailPhys/1024);
- stats.add("Total page KB", state.ullTotalPageFile/1024);
- stats.add("Avail page KB", state.ullAvailPageFile/1024);
- stats.add("Total Virtual KB", state.ullTotalVirtual/1024);
- stats.add("Avail Virtual KB", state.ullAvailVirtual/1024);
+ DWORDLONG div = 1024;
+
+ stats.add("Percent Memory use", state.dwMemoryLoad/div);
+ stats.add("Total Physical KB", state.ullTotalPhys/div);
+ stats.add("Avail Physical KB", state.ullAvailPhys/div);
+ stats.add("Total page KB", state.ullTotalPageFile/div);
+ stats.add("Avail page KB", state.ullAvailPageFile/div);
+ stats.add("Total Virtual KB", state.ullTotalVirtual/div);
+ stats.add("Avail Virtual KB", state.ullAvailVirtual/div);
PERFORMANCE_INFORMATION perf;
perf.cb = sizeof(perf);
@@ -982,15 +984,15 @@ LLSD LLMemoryInfo::loadStatsMap()
GetProcessMemoryInfo(GetCurrentProcess(), PPROCESS_MEMORY_COUNTERS(&pmem), sizeof(pmem));
stats.add("Page Fault Count", pmem.PageFaultCount);
- stats.add("PeakWorkingSetSize KB", pmem.PeakWorkingSetSize/1024);
- stats.add("WorkingSetSize KB", pmem.WorkingSetSize/1024);
- stats.add("QutaPeakPagedPoolUsage KB", pmem.QuotaPeakPagedPoolUsage/1024);
- stats.add("QuotaPagedPoolUsage KB", pmem.QuotaPagedPoolUsage/1024);
- stats.add("QuotaPeakNonPagedPoolUsage KB", pmem.QuotaPeakNonPagedPoolUsage/1024);
- stats.add("QuotaNonPagedPoolUsage KB", pmem.QuotaNonPagedPoolUsage/1024);
- stats.add("PagefileUsage KB", pmem.PagefileUsage/1024);
- stats.add("PeakPagefileUsage KB", pmem.PeakPagefileUsage/1024);
- stats.add("PrivateUsage KB", pmem.PrivateUsage/1024);
+ stats.add("PeakWorkingSetSize KB", pmem.PeakWorkingSetSize/div);
+ stats.add("WorkingSetSize KB", pmem.WorkingSetSize/div);
+ stats.add("QutaPeakPagedPoolUsage KB", pmem.QuotaPeakPagedPoolUsage/div);
+ stats.add("QuotaPagedPoolUsage KB", pmem.QuotaPagedPoolUsage/div);
+ stats.add("QuotaPeakNonPagedPoolUsage KB", pmem.QuotaPeakNonPagedPoolUsage/div);
+ stats.add("QuotaNonPagedPoolUsage KB", pmem.QuotaNonPagedPoolUsage/div);
+ stats.add("PagefileUsage KB", pmem.PagefileUsage/div);
+ stats.add("PeakPagefileUsage KB", pmem.PeakPagefileUsage/div);
+ stats.add("PrivateUsage KB", pmem.PrivateUsage/div);
#elif LL_DARWIN
diff --git a/indra/llcommon/llthread.cpp b/indra/llcommon/llthread.cpp
index a6ad6b125c..1d56a52c32 100644
--- a/indra/llcommon/llthread.cpp
+++ b/indra/llcommon/llthread.cpp
@@ -71,6 +71,13 @@ LL_COMMON_API void assert_main_thread()
}
}
+void LLThread::registerThreadID()
+{
+#if !LL_DARWIN
+ sThreadID = ++sIDIter;
+#endif
+}
+
//
// Handed to the APR thread creation function
//
@@ -114,7 +121,7 @@ LLThread::LLThread(const std::string& name, apr_pool_t *poolp) :
apr_pool_create(&mAPRPoolp, NULL); // Create a subpool for this thread
}
mRunCondition = new LLCondition(mAPRPoolp);
-
+ mDataLock = new LLMutex(mAPRPoolp);
mLocalAPRFilePoolp = NULL ;
}
@@ -173,7 +180,10 @@ void LLThread::shutdown()
}
delete mRunCondition;
- mRunCondition = 0;
+ mRunCondition = NULL;
+
+ delete mDataLock;
+ mDataLock = NULL;
if (mIsLocalPool && mAPRPoolp)
{
@@ -242,28 +252,30 @@ bool LLThread::runCondition(void)
// Stop thread execution if requested until unpaused.
void LLThread::checkPause()
{
- mRunCondition->lock();
+ mDataLock->lock();
// This is in a while loop because the pthread API allows for spurious wakeups.
while(shouldSleep())
{
+ mDataLock->unlock();
mRunCondition->wait(); // unlocks mRunCondition
+ mDataLock->lock();
// mRunCondition is locked when the thread wakes up
}
- mRunCondition->unlock();
+ mDataLock->unlock();
}
//============================================================================
void LLThread::setQuitting()
{
- mRunCondition->lock();
+ mDataLock->lock();
if (mStatus == RUNNING)
{
mStatus = QUITTING;
}
- mRunCondition->unlock();
+ mDataLock->unlock();
wake();
}
@@ -285,12 +297,12 @@ void LLThread::yield()
void LLThread::wake()
{
- mRunCondition->lock();
+ mDataLock->lock();
if(!shouldSleep())
{
mRunCondition->signal();
}
- mRunCondition->unlock();
+ mDataLock->unlock();
}
void LLThread::wakeLocked()
@@ -481,6 +493,19 @@ LLThreadSafeRefCount::LLThreadSafeRefCount() :
{
}
+LLThreadSafeRefCount::LLThreadSafeRefCount(const LLThreadSafeRefCount& src)
+{
+ if (sMutex)
+ {
+ sMutex->lock();
+ }
+ mRef = 0;
+ if (sMutex)
+ {
+ sMutex->unlock();
+ }
+}
+
LLThreadSafeRefCount::~LLThreadSafeRefCount()
{
if (mRef != 0)
@@ -489,6 +514,7 @@ LLThreadSafeRefCount::~LLThreadSafeRefCount()
}
}
+
//============================================================================
LLResponder::~LLResponder()
diff --git a/indra/llcommon/llthread.h b/indra/llcommon/llthread.h
index b52e70ab2e..5c8bbca2ca 100644
--- a/indra/llcommon/llthread.h
+++ b/indra/llcommon/llthread.h
@@ -88,6 +88,11 @@ public:
U32 getID() const { return mID; }
+ // Called by threads *not* created via LLThread to register some
+ // internal state used by LLMutex. You must call this once early
+ // in the running thread to prevent collisions with the main thread.
+ static void registerThreadID();
+
private:
BOOL mPaused;
@@ -97,6 +102,7 @@ private:
protected:
std::string mName;
LLCondition* mRunCondition;
+ LLMutex* mDataLock;
apr_thread_t *mAPRThreadp;
apr_pool_t *mAPRPoolp;
@@ -122,15 +128,15 @@ protected:
inline void unlockData();
// This is the predicate that decides whether the thread should sleep.
- // It should only be called with mRunCondition locked, since the virtual runCondition() function may need to access
+ // It should only be called with mDataLock locked, since the virtual runCondition() function may need to access
// data structures that are thread-unsafe.
bool shouldSleep(void) { return (mStatus == RUNNING) && (isPaused() || (!runCondition())); }
// To avoid spurious signals (and the associated context switches) when the condition may or may not have changed, you can do the following:
- // mRunCondition->lock();
+ // mDataLock->lock();
// if(!shouldSleep())
// mRunCondition->signal();
- // mRunCondition->unlock();
+ // mDataLock->unlock();
};
//============================================================================
@@ -205,12 +211,12 @@ private:
void LLThread::lockData()
{
- mRunCondition->lock();
+ mDataLock->lock();
}
void LLThread::unlockData()
{
- mRunCondition->unlock();
+ mDataLock->unlock();
}
@@ -227,15 +233,27 @@ public:
private:
static LLMutex* sMutex;
-private:
- LLThreadSafeRefCount(const LLThreadSafeRefCount&); // not implemented
- LLThreadSafeRefCount&operator=(const LLThreadSafeRefCount&); // not implemented
-
protected:
virtual ~LLThreadSafeRefCount(); // use unref()
public:
LLThreadSafeRefCount();
+ LLThreadSafeRefCount(const LLThreadSafeRefCount&);
+ LLThreadSafeRefCount& operator=(const LLThreadSafeRefCount& ref)
+ {
+ if (sMutex)
+ {
+ sMutex->lock();
+ }
+ mRef = 0;
+ if (sMutex)
+ {
+ sMutex->unlock();
+ }
+ return *this;
+ }
+
+
void ref()
{
diff --git a/indra/llcommon/lluri.cpp b/indra/llcommon/lluri.cpp
index b39ea0c6f2..21456a599b 100644
--- a/indra/llcommon/lluri.cpp
+++ b/indra/llcommon/lluri.cpp
@@ -37,6 +37,8 @@
// system includes
#include <boost/tokenizer.hpp>
+#include <boost/algorithm/string/find_iterator.hpp>
+#include <boost/algorithm/string/finder.hpp>
void encode_character(std::ostream& ostr, std::string::value_type val)
{
@@ -317,7 +319,7 @@ LLURI LLURI::buildHTTP(const std::string& prefix,
const LLSD& path)
{
LLURI result;
-
+
// TODO: deal with '/' '?' '#' in host_port
if (prefix.find("://") != prefix.npos)
{
@@ -342,15 +344,41 @@ LLURI LLURI::buildHTTP(const std::string& prefix,
result.mEscapedPath += "/" + escapePathComponent(it->asString());
}
}
- else if(path.isString())
+ else if (path.isString())
{
- result.mEscapedPath += "/" + escapePathComponent(path.asString());
+ std::string pathstr(path);
+ // Trailing slash is significant in HTTP land. If caller specified,
+ // make a point of preserving.
+ std::string last_slash;
+ std::string::size_type len(pathstr.length());
+ if (len && pathstr[len-1] == '/')
+ {
+ last_slash = "/";
+ }
+
+ // Escape every individual path component, recombining with slashes.
+ for (boost::split_iterator<std::string::const_iterator>
+ ti(pathstr, boost::first_finder("/")), tend;
+ ti != tend; ++ti)
+ {
+ // Eliminate a leading slash or duplicate slashes anywhere. (Extra
+ // slashes show up here as empty components.) This test also
+ // eliminates a trailing slash, hence last_slash above.
+ if (! ti->empty())
+ {
+ result.mEscapedPath
+ += "/" + escapePathComponent(std::string(ti->begin(), ti->end()));
+ }
+ }
+
+ // Reinstate trailing slash, if any.
+ result.mEscapedPath += last_slash;
}
else if(path.isUndefined())
{
// do nothing
}
- else
+ else
{
llwarns << "Valid path arguments to buildHTTP are array, string, or undef, you passed type"
<< path.type() << llendl;
diff --git a/indra/llcommon/llversionviewer.h b/indra/llcommon/llversionviewer.h
index 295fed3c4b..a254fa4467 100644
--- a/indra/llcommon/llversionviewer.h
+++ b/indra/llcommon/llversionviewer.h
@@ -29,7 +29,7 @@
const S32 LL_VERSION_MAJOR = 3;
const S32 LL_VERSION_MINOR = 4;
-const S32 LL_VERSION_PATCH = 1;
+const S32 LL_VERSION_PATCH = 4;
const S32 LL_VERSION_BUILD = 264760;
const char * const LL_CHANNEL = "Second Life Developer";
diff --git a/indra/llcommon/tests/bitpack_test.cpp b/indra/llcommon/tests/bitpack_test.cpp
index afc0c18cd0..49cae16400 100644
--- a/indra/llcommon/tests/bitpack_test.cpp
+++ b/indra/llcommon/tests/bitpack_test.cpp
@@ -94,6 +94,7 @@ namespace tut
ensure("bitPack: individual unpack: 5", unpackbuffer[0] == (U8) str[5]);
bitunpack.bitUnpack(unpackbuffer, 8*4); // Life
ensure_memory_matches("bitPack: 4 bytes unpack:", unpackbuffer, 4, str+6, 4);
+ ensure("keep compiler quiet", unpack_bufsize == unpack_bufsize);
}
// U32 packing
diff --git a/indra/llcommon/tests/lluri_test.cpp b/indra/llcommon/tests/lluri_test.cpp
index f6d4221256..4c64f15ca7 100644
--- a/indra/llcommon/tests/lluri_test.cpp
+++ b/indra/llcommon/tests/lluri_test.cpp
@@ -58,12 +58,12 @@ namespace tut
ensure_equals("escape/unescape escaped", uri_esc_2, uri_esc_1);
}
};
-
+
typedef test_group<URITestData> URITestGroup;
typedef URITestGroup::object URITestObject;
URITestGroup uriTestGroup("LLURI");
-
+
template<> template<>
void URITestObject::test<1>()
{
@@ -89,14 +89,14 @@ namespace tut
template<> template<>
void URITestObject::test<2>()
{
- // empty string
+ set_test_name("empty string");
checkParts(LLURI(""), "", "", "", "");
}
-
+
template<> template<>
void URITestObject::test<3>()
{
- // no scheme
+ set_test_name("no scheme");
checkParts(LLURI("foo"), "", "foo", "", "");
checkParts(LLURI("foo%3A"), "", "foo:", "", "");
}
@@ -104,7 +104,7 @@ namespace tut
template<> template<>
void URITestObject::test<4>()
{
- // scheme w/o paths
+ set_test_name("scheme w/o paths");
checkParts(LLURI("mailto:zero@ll.com"),
"mailto", "zero@ll.com", "", "");
checkParts(LLURI("silly://abc/def?foo"),
@@ -114,16 +114,16 @@ namespace tut
template<> template<>
void URITestObject::test<5>()
{
- // authority section
+ set_test_name("authority section");
checkParts(LLURI("http:///"),
"http", "///", "", "/");
-
+
checkParts(LLURI("http://abc"),
"http", "//abc", "abc", "");
-
+
checkParts(LLURI("http://a%2Fb/cd"),
"http", "//a/b/cd", "a/b", "/cd");
-
+
checkParts(LLURI("http://host?"),
"http", "//host?", "host", "");
}
@@ -131,13 +131,13 @@ namespace tut
template<> template<>
void URITestObject::test<6>()
{
- // path section
+ set_test_name("path section");
checkParts(LLURI("http://host/a/b/"),
"http", "//host/a/b/", "host", "/a/b/");
-
+
checkParts(LLURI("http://host/a%3Fb/"),
"http", "//host/a?b/", "host", "/a?b/");
-
+
checkParts(LLURI("http://host/a:b/"),
"http", "//host/a:b/", "host", "/a:b/");
}
@@ -145,16 +145,16 @@ namespace tut
template<> template<>
void URITestObject::test<7>()
{
- // query string
+ set_test_name("query string");
checkParts(LLURI("http://host/?"),
"http", "//host/?", "host", "/", "");
-
+
checkParts(LLURI("http://host/?x"),
"http", "//host/?x", "host", "/", "x");
-
+
checkParts(LLURI("http://host/??"),
"http", "//host/??", "host", "/", "?");
-
+
checkParts(LLURI("http://host/?%3F"),
"http", "//host/??", "host", "/", "?");
}
@@ -167,19 +167,44 @@ namespace tut
path.append("123");
checkParts(LLURI::buildHTTP("host", path),
"http", "//host/x/123", "host", "/x/123");
-
+
LLSD query;
query["123"] = "12";
query["abcd"] = "abc";
checkParts(LLURI::buildHTTP("host", path, query),
"http", "//host/x/123?123=12&abcd=abc",
"host", "/x/123", "123=12&abcd=abc");
+
+ ensure_equals(LLURI::buildHTTP("host", "").asString(),
+ "http://host");
+ ensure_equals(LLURI::buildHTTP("host", "/").asString(),
+ "http://host/");
+ ensure_equals(LLURI::buildHTTP("host", "//").asString(),
+ "http://host/");
+ ensure_equals(LLURI::buildHTTP("host", "dir name").asString(),
+ "http://host/dir%20name");
+ ensure_equals(LLURI::buildHTTP("host", "dir name/").asString(),
+ "http://host/dir%20name/");
+ ensure_equals(LLURI::buildHTTP("host", "/dir name").asString(),
+ "http://host/dir%20name");
+ ensure_equals(LLURI::buildHTTP("host", "/dir name/").asString(),
+ "http://host/dir%20name/");
+ ensure_equals(LLURI::buildHTTP("host", "dir name/subdir name").asString(),
+ "http://host/dir%20name/subdir%20name");
+ ensure_equals(LLURI::buildHTTP("host", "dir name/subdir name/").asString(),
+ "http://host/dir%20name/subdir%20name/");
+ ensure_equals(LLURI::buildHTTP("host", "/dir name/subdir name").asString(),
+ "http://host/dir%20name/subdir%20name");
+ ensure_equals(LLURI::buildHTTP("host", "/dir name/subdir name/").asString(),
+ "http://host/dir%20name/subdir%20name/");
+ ensure_equals(LLURI::buildHTTP("host", "//dir name//subdir name//").asString(),
+ "http://host/dir%20name/subdir%20name/");
}
template<> template<>
void URITestObject::test<9>()
{
- // test unescaped path components
+ set_test_name("test unescaped path components");
LLSD path;
path.append("x@*//*$&^");
path.append("123");
@@ -190,7 +215,7 @@ namespace tut
template<> template<>
void URITestObject::test<10>()
{
- // test unescaped query components
+ set_test_name("test unescaped query components");
LLSD path;
path.append("x");
path.append("123");
@@ -205,7 +230,7 @@ namespace tut
template<> template<>
void URITestObject::test<11>()
{
- // test unescaped host components
+ set_test_name("test unescaped host components");
LLSD path;
path.append("x");
path.append("123");
@@ -216,16 +241,16 @@ namespace tut
"http", "//hi123*33--}{:portstuffs/x/123?123=12&abcd=abc",
"hi123*33--}{:portstuffs", "/x/123", "123=12&abcd=abc");
}
-
+
template<> template<>
void URITestObject::test<12>()
{
- // test funky host_port values that are actually prefixes
-
+ set_test_name("test funky host_port values that are actually prefixes");
+
checkParts(LLURI::buildHTTP("http://example.com:8080", LLSD()),
"http", "//example.com:8080",
"example.com:8080", "");
-
+
checkParts(LLURI::buildHTTP("http://example.com:8080/", LLSD()),
"http", "//example.com:8080/",
"example.com:8080", "/");
@@ -242,7 +267,7 @@ namespace tut
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
"0123456789"
"-._~";
- // test escape
+ set_test_name("test escape");
ensure_equals("escaping", LLURI::escape("abcdefg", "abcdef"), "abcdef%67");
ensure_equals("escaping", LLURI::escape("|/&\\+-_!@", ""), "%7C%2F%26%5C%2B%2D%5F%21%40");
ensure_equals("escaping as query variable",
@@ -259,13 +284,12 @@ namespace tut
cedilla.push_back( (char)0xA7 );
ensure_equals("escape UTF8", LLURI::escape( cedilla, unreserved), "%C3%A7");
}
-
+
template<> template<>
void URITestObject::test<14>()
{
- // make sure escape and unescape of empty strings return empty
- // strings.
+ set_test_name("make sure escape and unescape of empty strings return empty strings.");
std::string uri_esc(LLURI::escape(""));
ensure("escape string empty", uri_esc.empty());
std::string uri_raw(LLURI::unescape(""));
@@ -275,7 +299,7 @@ namespace tut
template<> template<>
void URITestObject::test<15>()
{
- // do some round-trip tests
+ set_test_name("do some round-trip tests");
escapeRoundTrip("http://secondlife.com");
escapeRoundTrip("http://secondlife.com/url with spaces");
escapeRoundTrip("http://bad[domain]name.com/");
@@ -286,7 +310,7 @@ namespace tut
template<> template<>
void URITestObject::test<16>()
{
- // Test the default escaping
+ set_test_name("Test the default escaping");
// yes -- this mangles the url. This is expected behavior
std::string simple("http://secondlife.com");
ensure_equals(
@@ -302,7 +326,7 @@ namespace tut
template<> template<>
void URITestObject::test<17>()
{
- // do some round-trip tests with very long strings.
+ set_test_name("do some round-trip tests with very long strings.");
escapeRoundTrip("Welcome to Second Life.We hope you'll have a richly rewarding experience, filled with creativity, self expression and fun.The goals of the Community Standards are simple: treat each other with respect and without harassment, adhere to local standards as indicated by simulator ratings, and refrain from any hate activity which slurs a real-world individual or real-world community. Behavioral Guidelines - The Big Six");
escapeRoundTrip(
"'asset_data':b(12100){'task_id':ucc706f2d-0b68-68f8-11a4-f1043ff35ca0}\n{\n\tname\tObject|\n\tpermissions 0\n\t{\n\t\tbase_mask\t7fffffff\n\t\towner_mask\t7fffffff\n\t\tgroup_mask\t00000000\n\t\teveryone_mask\t00000000\n\t\tnext_owner_mask\t7fffffff\n\t\tcreator_id\t13fd9595-a47b-4d64-a5fb-6da645f038e0\n\t\towner_id\t3c115e51-04f4-523c-9fa6-98aff1034730\n\t\tlast_owner_id\t3c115e51-04f4-523c-9fa6-98aff1034730\n\t\tgroup_id\t00000000-0000-0000-0000-000000000000\n\t}\n\tlocal_id\t217444921\n\ttotal_crc\t323\n\ttype\t2\n\ttask_valid\t2\n\ttravel_access\t13\n\tdisplayopts\t2\n\tdisplaytype\tv\n\tpos\t-0.368634403\t0.00781063363\t-0.569040775\n\toldpos\t150.117996\t25.8658009\t8.19664001\n\trotation\t-0.06293071806430816650390625\t-0.6995697021484375\t-0.7002241611480712890625\t0.1277817934751510620117188\n\tchildpos\t-0.00499999989\t-0.0359999985\t0.307999998\n\tchildrot\t-0.515492737293243408203125\t-0.46601200103759765625\t0.529055416584014892578125\t0.4870323240756988525390625\n\tscale"
@@ -322,7 +346,7 @@ namespace tut
"D STRING RW SV 20f36c3a-b44b-9bc7-87f3-018bfdfc8cda\n\tscratchpad\t0\n\t{\n\t\n\t}\n\tsale_info\t0\n\t{\n\t\tsale_type\tnot\n\t\tsale_price\t10\n\t}\n\torig_asset_id\t8747acbc-d391-1e59-69f1-41d06830e6c0\n\torig_item_id\t20f36c3a-b44b-9bc7-87f3-018bfdfc8cda\n\tfrom_task_id\t3c115e51-04f4-523c-9fa6-98aff1034730\n\tcorrect_family_id\t00000000-0000-0000-0000-000000000000\n\thas_rezzed\t0\n\tpre_link_base_mask\t7fffffff\n\tlinked \tlinked\n\tdefault_pay_price\t-2\t1\t5\t10\t20\n}\n");
}
-
+
template<> template<>
void URITestObject::test<18>()
{
@@ -335,7 +359,7 @@ namespace tut
ensure_equals("pathmap", u.pathArray()[1].asString(), "login");
ensure_equals("query", u.query(), "first_name=Testert4&last_name=Tester&web_login_key=test");
ensure_equals("query map element", u.queryMap()["last_name"].asString(), "Tester");
-
+
u = LLURI("secondlife://Da Boom/128/128/128");
// if secondlife is the scheme, LLURI should parse /128/128/128 as path, with Da Boom as authority
ensure_equals("scheme", u.scheme(), "secondlife");
@@ -350,7 +374,7 @@ namespace tut
template<> template<>
void URITestObject::test<19>()
{
- // Parse about: schemes
+ set_test_name("Parse about: schemes");
LLURI u("about:blank?redirect-http-hack=secondlife%3A%2F%2F%2Fapp%2Flogin%3Ffirst_name%3DCallum%26last_name%3DLinden%26location%3Dspecify%26grid%3Dvaak%26region%3D%2FMorris%2F128%2F128%26web_login_key%3Defaa4795-c2aa-4c58-8966-763c27931e78");
ensure_equals("scheme", u.scheme(), "about");
ensure_equals("authority", u.authority(), "");