diff options
author | Monty Brandenberg <monty@lindenlab.com> | 2012-06-16 15:50:48 -0400 |
---|---|---|
committer | Monty Brandenberg <monty@lindenlab.com> | 2012-06-16 15:50:48 -0400 |
commit | 6193ee6a331e3dfd562400a32a961bad0b8bed12 (patch) | |
tree | e80c47af3030e3322809fa1a392c555b8e2e8a8a /indra/llcorehttp | |
parent | 57575339bb7dd4f67c5e4dc1c1ccc9eda6a2f8f5 (diff) |
First round of basic tuning work (shorter sleeps, larger BufferArray blocks).
Beefed up the metrics gathering in http_texture_load to get memory sizes and
cpu consumption on windows (still need to implement that on Mac & linux).
Ran runs with various idle loops with sleeps from 20 ms down to pure spinning,
varied Block allocation size from 1504 to 2^20 bytes. 2ms/2ms/65540 appears
to be a good spot under the test conditions (Win7, danu grid, client in Boston).
Diffstat (limited to 'indra/llcorehttp')
-rw-r--r-- | indra/llcorehttp/_httpservice.cpp | 2 | ||||
-rw-r--r-- | indra/llcorehttp/bufferarray.h | 2 | ||||
-rw-r--r-- | indra/llcorehttp/examples/http_texture_load.cpp | 249 |
3 files changed, 244 insertions, 9 deletions
diff --git a/indra/llcorehttp/_httpservice.cpp b/indra/llcorehttp/_httpservice.cpp index beba8f08f4..87a78820f5 100644 --- a/indra/llcorehttp/_httpservice.cpp +++ b/indra/llcorehttp/_httpservice.cpp @@ -40,7 +40,7 @@ // Tuning parameters -static const int LOOP_SLEEP_NORMAL_MS = 10; // Normal per-loop sleep in milliseconds +static const int LOOP_SLEEP_NORMAL_MS = 2; // Normal per-loop sleep in milliseconds namespace LLCore diff --git a/indra/llcorehttp/bufferarray.h b/indra/llcorehttp/bufferarray.h index 72c3e1c669..d3862b45e1 100644 --- a/indra/llcorehttp/bufferarray.h +++ b/indra/llcorehttp/bufferarray.h @@ -74,7 +74,7 @@ private: public: // Internal magic number, may be used by unit tests. - static const size_t BLOCK_ALLOC_SIZE = 1504; + static const size_t BLOCK_ALLOC_SIZE = 65540; /// Appends the indicated data to the BufferArray /// modifying current position and total size. New diff --git a/indra/llcorehttp/examples/http_texture_load.cpp b/indra/llcorehttp/examples/http_texture_load.cpp index 6f79833cf6..1277dd3353 100644 --- a/indra/llcorehttp/examples/http_texture_load.cpp +++ b/indra/llcorehttp/examples/http_texture_load.cpp @@ -33,6 +33,8 @@ #include <pthread.h> #endif +#include "linden_common.h" + #include "httpcommon.h" #include "httprequest.h" #include "httphandler.h" @@ -43,6 +45,8 @@ #include <curl/curl.h> #include <openssl/crypto.h> +#include "lltimer.h" + void init_curl(); void term_curl(); @@ -65,6 +69,9 @@ int optind(1); #endif + +// Mostly just a container for the texture IDs and fetch +// parameters.... class WorkingSet : public LLCore::HttpHandler { public: @@ -98,11 +105,46 @@ public: texture_list_t mTextures; int mErrorsApi; int mErrorsHttp; + int mErrorsHttp404; + int mErrorsHttp416; + int mErrorsHttp500; + int mErrorsHttp503; int mSuccesses; long mByteCount; }; +// Gather process information while we run. Process +// size, cpu consumed, wallclock time. + +class Metrics +{ +public: + class MetricsImpl; + +public: + Metrics(); + ~Metrics(); + + void init(); + void sample(); + void term(); + +protected: + MetricsImpl * mImpl; + +public: + U64 mMaxVSZ; + U64 mMinVSZ; + U64 mStartWallTime; + U64 mEndWallTime; + U64 mStartUTime; + U64 mEndUTime; + U64 mStartSTime; + U64 mEndSTime; +}; + + // // // @@ -191,22 +233,38 @@ int main(int argc, char** argv) return 1; } + // Setup metrics + Metrics metrics; + metrics.init(); + // Run it + int passes(0); while (! ws.reload(hr)) { - hr->update(1000); -#if defined(WIN32) - Sleep(5); -#else - usleep(5000); -#endif + hr->update(5000); + ms_sleep(2); + if (0 == (++passes % 200)) + { + metrics.sample(); + } } + metrics.sample(); + metrics.term(); // Report std::cout << "HTTP errors: " << ws.mErrorsHttp << " API errors: " << ws.mErrorsApi << " Successes: " << ws.mSuccesses << " Byte count: " << ws.mByteCount << std::endl; - + std::cout << "HTTP 404 errors: " << ws.mErrorsHttp404 << " HTTP 416 errors: " << ws.mErrorsHttp416 + << " HTTP 500 errors: " << ws.mErrorsHttp500 << " HTTP 503 errors: " << ws.mErrorsHttp503 + << std::endl; + std::cout << "User CPU: " << (metrics.mEndUTime - metrics.mStartUTime) + << " uS System CPU: " << (metrics.mEndSTime - metrics.mStartSTime) + << " uS Wall Time: " << (metrics.mEndWallTime - metrics.mStartWallTime) + << " uS Maximum VSZ: " << metrics.mMaxVSZ + << " Bytes Minimum VSZ: " << metrics.mMinVSZ << " Bytes" + << std::endl; + // Clean up delete hr; term_curl(); @@ -250,6 +308,10 @@ WorkingSet::WorkingSet() mAt(0), mErrorsApi(0), mErrorsHttp(0), + mErrorsHttp404(0), + mErrorsHttp416(0), + mErrorsHttp500(0), + mErrorsHttp503(0), mSuccesses(0), mByteCount(0L) { @@ -333,7 +395,28 @@ void WorkingSet::onCompleted(LLCore::HttpHandle handle, LLCore::HttpResponse * r // Something in this library or libcurl if (status.isHttpStatus()) { + static const LLCore::HttpStatus hs404(404); + static const LLCore::HttpStatus hs416(416); + static const LLCore::HttpStatus hs500(500); + static const LLCore::HttpStatus hs503(503); + ++mErrorsHttp; + if (hs404 == status) + { + ++mErrorsHttp404; + } + else if (hs416 == status) + { + ++mErrorsHttp416; + } + else if (hs500 == status) + { + ++mErrorsHttp500; + } + else if (hs503 == status) + { + ++mErrorsHttp503; + } } else { @@ -492,3 +575,155 @@ int getopt(int argc, char * const argv[], const char *optstring) #endif + + +#if defined(WIN32) + +#define PSAPI_VERSION 1 +#include "windows.h" +#include "psapi.h" + +class Metrics::MetricsImpl +{ +public: + MetricsImpl() + {} + + ~MetricsImpl() + {} + + void MetricsImpl::init(Metrics * metrics) + { + HANDLE self(GetCurrentProcess()); // Does not have to be closed + FILETIME ft_dummy, ft_system, ft_user; + GetProcessTimes(self, &ft_dummy, &ft_dummy, &ft_system, &ft_user); + ULARGE_INTEGER uli; + uli.u.LowPart = ft_system.dwLowDateTime; + uli.u.HighPart = ft_system.dwHighDateTime; + metrics->mStartSTime = uli.QuadPart / U64L(10); // Convert to uS + uli.u.LowPart = ft_user.dwLowDateTime; + uli.u.HighPart = ft_user.dwHighDateTime; + metrics->mStartUTime = uli.QuadPart / U64L(10); + metrics->mStartWallTime = totalTime(); + } + + void MetricsImpl::sample(Metrics * metrics) + { + PROCESS_MEMORY_COUNTERS_EX counters; + + GetProcessMemoryInfo(GetCurrentProcess(), + (PROCESS_MEMORY_COUNTERS *) &counters, + sizeof(counters)); + // Okay, PrivateUsage isn't truly VSZ but it will be + // a good tracker for leaks and fragmentation. Work on + // a better estimator later... + SIZE_T vsz(counters.PrivateUsage); + metrics->mMaxVSZ = (std::max)(metrics->mMaxVSZ, U64(vsz)); + metrics->mMinVSZ = (std::min)(metrics->mMinVSZ, U64(vsz)); + } + + void MetricsImpl::term(Metrics * metrics) + { + HANDLE self(GetCurrentProcess()); // Does not have to be closed + FILETIME ft_dummy, ft_system, ft_user; + GetProcessTimes(self, &ft_dummy, &ft_dummy, &ft_system, &ft_user); + ULARGE_INTEGER uli; + uli.u.LowPart = ft_system.dwLowDateTime; + uli.u.HighPart = ft_system.dwHighDateTime; + metrics->mEndSTime = uli.QuadPart / U64L(10); + uli.u.LowPart = ft_user.dwLowDateTime; + uli.u.HighPart = ft_user.dwHighDateTime; + metrics->mEndUTime = uli.QuadPart / U64L(10); + metrics->mEndWallTime = totalTime(); + } + +protected: +}; + +#elif defined(DARWIN) + + +class Metrics::MetricsImpl +{ +public: + MetricsImpl() + {} + + ~MetricsImpl() + {} + + void MetricsImpl::init(Metrics *) + {} + + void MetricsImpl::sample(Metrics *) + {} + + void MetricsImpl::term(Metrics *) + {} +}; + +#else + +class Metrics::MetricsImpl +{ +public: + MetricsImpl() + {} + + + ~MetricsImpl() + {} + + void MetricsImpl::init(Metrics *) + {} + + + void MetricsImpl::sample(Metrics *) + {} + + + void MetricsImpl::term(Metrics *) + {} +}; + +#endif // defined(WIN32) + +Metrics::Metrics() + : mMaxVSZ(U64(0)), + mMinVSZ(U64L(0xffffffffffffffff)), + mStartWallTime(U64(0)), + mEndWallTime(U64(0)), + mStartUTime(U64(0)), + mEndUTime(U64(0)), + mStartSTime(U64(0)), + mEndSTime(U64(0)) +{ + mImpl = new MetricsImpl(); +} + + +Metrics::~Metrics() +{ + delete mImpl; + mImpl = NULL; +} + + +void Metrics::init() +{ + mImpl->init(this); +} + + +void Metrics::sample() +{ + mImpl->sample(this); +} + + +void Metrics::term() +{ + mImpl->term(this); +} + + |