diff options
author | Richard Linden <none@none> | 2013-08-18 22:30:27 -0700 |
---|---|---|
committer | Richard Linden <none@none> | 2013-08-18 22:30:27 -0700 |
commit | 612892b45a3413b16e40c49d3bfde77a4ca927fd (patch) | |
tree | 2272a24c7f0a8354791f74c7485a376abb377f67 /indra/llcommon | |
parent | f8e3a34348ab98ecd56d53360b8f2b6512ad6bba (diff) |
SH-4433 WIP: Interesting: Statistics > Ping Sim is always 0 ms
continued conversion to units system
made units perform type promotion correctly and preserve type in arithmetic
e.g. can now do LLVector3 in units
added typedefs for remaining common unit types, including implicits
Diffstat (limited to 'indra/llcommon')
-rwxr-xr-x | indra/llcommon/llcriticaldamp.cpp | 2 | ||||
-rwxr-xr-x | indra/llcommon/llcriticaldamp.h | 4 | ||||
-rwxr-xr-x | indra/llcommon/lldate.cpp | 2 | ||||
-rwxr-xr-x | indra/llcommon/lldate.h | 2 | ||||
-rwxr-xr-x | indra/llcommon/llframetimer.h | 4 | ||||
-rwxr-xr-x | indra/llcommon/llmemory.cpp | 46 | ||||
-rwxr-xr-x | indra/llcommon/llmemory.h | 18 | ||||
-rwxr-xr-x | indra/llcommon/llprocessor.cpp | 2 | ||||
-rwxr-xr-x | indra/llcommon/llprocessor.h | 2 | ||||
-rwxr-xr-x | indra/llcommon/llsys.cpp | 18 | ||||
-rwxr-xr-x | indra/llcommon/llsys.h | 4 | ||||
-rwxr-xr-x | indra/llcommon/lltimer.cpp | 18 | ||||
-rwxr-xr-x | indra/llcommon/lltimer.h | 20 | ||||
-rw-r--r-- | indra/llcommon/lltraceaccumulators.cpp | 2 | ||||
-rw-r--r-- | indra/llcommon/lltraceaccumulators.h | 20 | ||||
-rw-r--r-- | indra/llcommon/lltracerecording.h | 4 | ||||
-rw-r--r-- | indra/llcommon/llunit.h | 727 | ||||
-rw-r--r-- | indra/llcommon/tests/llunits_test.cpp | 126 |
18 files changed, 659 insertions, 362 deletions
diff --git a/indra/llcommon/llcriticaldamp.cpp b/indra/llcommon/llcriticaldamp.cpp index 5ffad88973..9f4cb09000 100755 --- a/indra/llcommon/llcriticaldamp.cpp +++ b/indra/llcommon/llcriticaldamp.cpp @@ -81,7 +81,7 @@ void LLSmoothInterpolation::updateInterpolants() //----------------------------------------------------------------------------- // getInterpolant() //----------------------------------------------------------------------------- -F32 LLSmoothInterpolation::getInterpolant(LLUnitImplicit<F32, LLUnits::Seconds> time_constant, bool use_cache) +F32 LLSmoothInterpolation::getInterpolant(F32SecondsImplicit time_constant, bool use_cache) { if (time_constant == 0.f) { diff --git a/indra/llcommon/llcriticaldamp.h b/indra/llcommon/llcriticaldamp.h index 7b2a414459..a02a2a0dcf 100755 --- a/indra/llcommon/llcriticaldamp.h +++ b/indra/llcommon/llcriticaldamp.h @@ -42,10 +42,10 @@ public: static void updateInterpolants(); // ACCESSORS - static F32 getInterpolant(LLUnitImplicit<F32, LLUnits::Seconds> time_constant, bool use_cache = true); + static F32 getInterpolant(F32SecondsImplicit time_constant, bool use_cache = true); template<typename T> - static T lerp(T a, T b, LLUnitImplicit<F32, LLUnits::Seconds> time_constant, bool use_cache = true) + static T lerp(T a, T b, F32SecondsImplicit time_constant, bool use_cache = true) { F32 interpolant = getInterpolant(time_constant, use_cache); return ((a * (1.f - interpolant)) diff --git a/indra/llcommon/lldate.cpp b/indra/llcommon/lldate.cpp index cb6f239396..4f2e1304b2 100755 --- a/indra/llcommon/lldate.cpp +++ b/indra/llcommon/lldate.cpp @@ -55,7 +55,7 @@ LLDate::LLDate(const LLDate& date) : mSecondsSinceEpoch(date.mSecondsSinceEpoch) {} -LLDate::LLDate(LLUnitImplicit<F64, LLUnits::Seconds> seconds_since_epoch) : +LLDate::LLDate(F64SecondsImplicit seconds_since_epoch) : mSecondsSinceEpoch(seconds_since_epoch.value()) {} diff --git a/indra/llcommon/lldate.h b/indra/llcommon/lldate.h index 816bc62b14..aecf3b765e 100755 --- a/indra/llcommon/lldate.h +++ b/indra/llcommon/lldate.h @@ -59,7 +59,7 @@ public: * * @param seconds_since_epoch The number of seconds since UTC epoch. */ - LLDate(LLUnitImplicit<F64, LLUnits::Seconds> seconds_since_epoch); + LLDate(F64SecondsImplicit seconds_since_epoch); /** * @brief Construct a date from a string representation diff --git a/indra/llcommon/llframetimer.h b/indra/llcommon/llframetimer.h index d64009440c..81bd5da8a3 100755 --- a/indra/llcommon/llframetimer.h +++ b/indra/llcommon/llframetimer.h @@ -43,7 +43,7 @@ public: // Return the number of seconds since the start of this // application instance. - static F64 getElapsedSeconds() + static F64SecondsImplicit getElapsedSeconds() { // Loses msec precision after ~4.5 hours... return sFrameTime; @@ -52,7 +52,7 @@ public: // Return a low precision usec since epoch static U64 getTotalTime() { - return sTotalTime ? LLUnitImplicit<U64, LLUnits::Microseconds>(sTotalTime) : totalTime(); + return sTotalTime ? U64MicrosecondsImplicit(sTotalTime) : totalTime(); } // Return a low precision seconds since epoch diff --git a/indra/llcommon/llmemory.cpp b/indra/llcommon/llmemory.cpp index c59b61471a..d46e205500 100755 --- a/indra/llcommon/llmemory.cpp +++ b/indra/llcommon/llmemory.cpp @@ -47,11 +47,11 @@ //static char* LLMemory::reserveMem = 0; -U32Kibibytes LLMemory::sAvailPhysicalMemInKB(U32_MAX); -U32Kibibytes LLMemory::sMaxPhysicalMemInKB(0); -U32Kibibytes LLMemory::sAllocatedMemInKB(0); -U32Kibibytes LLMemory::sAllocatedPageSizeInKB(0); -U32Kibibytes LLMemory::sMaxHeapSizeInKB(U32_MAX); +U32Kilobytes LLMemory::sAvailPhysicalMemInKB(U32_MAX); +U32Kilobytes LLMemory::sMaxPhysicalMemInKB(0); +U32Kilobytes LLMemory::sAllocatedMemInKB(0); +U32Kilobytes LLMemory::sAllocatedPageSizeInKB(0); +U32Kilobytes LLMemory::sMaxHeapSizeInKB(U32_MAX); BOOL LLMemory::sEnableMemoryFailurePrevention = FALSE; #if __DEBUG_PRIVATE_MEM__ @@ -94,9 +94,9 @@ void LLMemory::freeReserve() } //static -void LLMemory::initMaxHeapSizeGB(F32 max_heap_size_gb, BOOL prevent_heap_failure) +void LLMemory::initMaxHeapSizeGB(F32Gigabytes max_heap_size, BOOL prevent_heap_failure) { - sMaxHeapSizeInKB = (U32)(max_heap_size_gb * 1024 * 1024) ; + sMaxHeapSizeInKB = max_heap_size; sEnableMemoryFailurePrevention = prevent_heap_failure ; } @@ -113,10 +113,10 @@ void LLMemory::updateMemoryInfo() return ; } - sAllocatedMemInKB = (U32)(counters.WorkingSetSize / 1024) ; - sAllocatedPageSizeInKB = (U32)(counters.PagefileUsage / 1024) ; + sAllocatedMemInKB = (U32Bytes)(counters.WorkingSetSize) ; + sAllocatedPageSizeInKB = (U32Bytes)(counters.PagefileUsage) ; - U32Kibibytes avail_phys, avail_virtual; + U32Kilobytes avail_phys, avail_virtual; LLMemoryInfo::getAvailableMemoryKB(avail_phys, avail_virtual) ; sMaxPhysicalMemInKB = llmin(avail_phys + sAllocatedMemInKB, sMaxHeapSizeInKB); @@ -126,7 +126,7 @@ void LLMemory::updateMemoryInfo() } else { - sAvailPhysicalMemInKB = 0 ; + sAvailPhysicalMemInKB = U32Kilobytes(0); } #else //not valid for other systems for now. @@ -187,8 +187,8 @@ void LLMemory::logMemoryInfo(BOOL update) //static bool LLMemory::isMemoryPoolLow() { - static const U32 LOW_MEMEOY_POOL_THRESHOLD_KB = 64 * 1024 ; //64 MB for emergency use - const static U32 MAX_SIZE_CHECKED_MEMORY_BLOCK = 64 * 1024 * 1024 ; //64 MB + static const U32Megabytes LOW_MEMORY_POOL_THRESHOLD(64); + const static U32Megabytes MAX_SIZE_CHECKED_MEMORY_BLOCK(64); static void* last_reserved_address = NULL ; if(!sEnableMemoryFailurePrevention) @@ -196,32 +196,32 @@ bool LLMemory::isMemoryPoolLow() return false ; //no memory failure prevention. } - if(sAvailPhysicalMemInKB < (LOW_MEMEOY_POOL_THRESHOLD_KB >> 2)) //out of physical memory + if(sAvailPhysicalMemInKB < (LOW_MEMORY_POOL_THRESHOLD / 4)) //out of physical memory { return true ; } - if(sAllocatedPageSizeInKB + (LOW_MEMEOY_POOL_THRESHOLD_KB >> 2) > sMaxHeapSizeInKB) //out of virtual address space. + if(sAllocatedPageSizeInKB + (LOW_MEMORY_POOL_THRESHOLD / 4) > sMaxHeapSizeInKB) //out of virtual address space. { return true ; } - bool is_low = (S32)(sAvailPhysicalMemInKB < LOW_MEMEOY_POOL_THRESHOLD_KB || - sAllocatedPageSizeInKB + LOW_MEMEOY_POOL_THRESHOLD_KB > sMaxHeapSizeInKB) ; + bool is_low = (S32)(sAvailPhysicalMemInKB < LOW_MEMORY_POOL_THRESHOLD || + sAllocatedPageSizeInKB + LOW_MEMORY_POOL_THRESHOLD > sMaxHeapSizeInKB) ; //check the virtual address space fragmentation if(!is_low) { if(!last_reserved_address) { - last_reserved_address = LLMemory::tryToAlloc(last_reserved_address, MAX_SIZE_CHECKED_MEMORY_BLOCK) ; + last_reserved_address = LLMemory::tryToAlloc(last_reserved_address, MAX_SIZE_CHECKED_MEMORY_BLOCK.value()) ; } else { - last_reserved_address = LLMemory::tryToAlloc(last_reserved_address, MAX_SIZE_CHECKED_MEMORY_BLOCK) ; + last_reserved_address = LLMemory::tryToAlloc(last_reserved_address, MAX_SIZE_CHECKED_MEMORY_BLOCK.value()) ; if(!last_reserved_address) //failed, try once more { - last_reserved_address = LLMemory::tryToAlloc(last_reserved_address, MAX_SIZE_CHECKED_MEMORY_BLOCK) ; + last_reserved_address = LLMemory::tryToAlloc(last_reserved_address, MAX_SIZE_CHECKED_MEMORY_BLOCK.value()) ; } } @@ -232,19 +232,19 @@ bool LLMemory::isMemoryPoolLow() } //static -U32Kibibytes LLMemory::getAvailableMemKB() +U32Kilobytes LLMemory::getAvailableMemKB() { return sAvailPhysicalMemInKB ; } //static -U32Kibibytes LLMemory::getMaxMemKB() +U32Kilobytes LLMemory::getMaxMemKB() { return sMaxPhysicalMemInKB ; } //static -U32Kibibytes LLMemory::getAllocatedMemKB() +U32Kilobytes LLMemory::getAllocatedMemKB() { return sAllocatedMemInKB ; } diff --git a/indra/llcommon/llmemory.h b/indra/llcommon/llmemory.h index c45c7ed213..23be1e5b2d 100755 --- a/indra/llcommon/llmemory.h +++ b/indra/llcommon/llmemory.h @@ -166,22 +166,22 @@ public: static U64 getCurrentRSS(); static U32 getWorkingSetSize(); static void* tryToAlloc(void* address, U32 size); - static void initMaxHeapSizeGB(F32 max_heap_size_gb, BOOL prevent_heap_failure); + static void initMaxHeapSizeGB(F32Gigabytes max_heap_size, BOOL prevent_heap_failure); static void updateMemoryInfo() ; static void logMemoryInfo(BOOL update = FALSE); static bool isMemoryPoolLow(); - static U32Kibibytes getAvailableMemKB() ; - static U32Kibibytes getMaxMemKB() ; - static U32Kibibytes getAllocatedMemKB() ; + static U32Kilobytes getAvailableMemKB() ; + static U32Kilobytes getMaxMemKB() ; + static U32Kilobytes getAllocatedMemKB() ; private: static char* reserveMem; - static U32Kibibytes sAvailPhysicalMemInKB ; - static U32Kibibytes sMaxPhysicalMemInKB ; - static U32Kibibytes sAllocatedMemInKB; - static U32Kibibytes sAllocatedPageSizeInKB ; + static U32Kilobytes sAvailPhysicalMemInKB ; + static U32Kilobytes sMaxPhysicalMemInKB ; + static U32Kilobytes sAllocatedMemInKB; + static U32Kilobytes sAllocatedPageSizeInKB ; - static U32Kibibytes sMaxHeapSizeInKB; + static U32Kilobytes sMaxHeapSizeInKB; static BOOL sEnableMemoryFailurePrevention; }; diff --git a/indra/llcommon/llprocessor.cpp b/indra/llcommon/llprocessor.cpp index 80b86153e4..69043dc173 100755 --- a/indra/llcommon/llprocessor.cpp +++ b/indra/llcommon/llprocessor.cpp @@ -875,7 +875,7 @@ LLProcessorInfo::LLProcessorInfo() : mImpl(NULL) LLProcessorInfo::~LLProcessorInfo() {} -LLUnitImplicit<F64, LLUnits::Megahertz> LLProcessorInfo::getCPUFrequency() const { return mImpl->getCPUFrequency(); } +F64MegahertzImplicit LLProcessorInfo::getCPUFrequency() const { return mImpl->getCPUFrequency(); } bool LLProcessorInfo::hasSSE() const { return mImpl->hasSSE(); } bool LLProcessorInfo::hasSSE2() const { return mImpl->hasSSE2(); } bool LLProcessorInfo::hasAltivec() const { return mImpl->hasAltivec(); } diff --git a/indra/llcommon/llprocessor.h b/indra/llcommon/llprocessor.h index 7f220467b0..4956a39700 100755 --- a/indra/llcommon/llprocessor.h +++ b/indra/llcommon/llprocessor.h @@ -37,7 +37,7 @@ public: LLProcessorInfo(); ~LLProcessorInfo(); - LLUnitImplicit<F64, LLUnits::Megahertz> getCPUFrequency() const; + F64MegahertzImplicit getCPUFrequency() const; bool hasSSE() const; bool hasSSE2() const; bool hasAltivec() const; diff --git a/indra/llcommon/llsys.cpp b/indra/llcommon/llsys.cpp index 8f7e60fb68..1ff45d3d90 100755 --- a/indra/llcommon/llsys.cpp +++ b/indra/llcommon/llsys.cpp @@ -832,7 +832,7 @@ LLMemoryInfo::LLMemoryInfo() } #if LL_WINDOWS -static U32Kibibytes LLMemoryAdjustKBResult(U32Kibibytes inKB) +static U32Kilobytes LLMemoryAdjustKBResult(U32Kilobytes inKB) { // Moved this here from llfloaterabout.cpp @@ -843,16 +843,16 @@ static U32Kibibytes LLMemoryAdjustKBResult(U32Kibibytes inKB) // returned from the GetMemoryStatusEx function. Here we keep the // original adjustment from llfoaterabout.cpp until this can be // fixed somehow. - inKB += U32Mibibytes(1); + inKB += U32Megabytes(1); return inKB; } #endif -U32Kibibytes LLMemoryInfo::getPhysicalMemoryKB() const +U32Kilobytes LLMemoryInfo::getPhysicalMemoryKB() const { #if LL_WINDOWS - return LLMemoryAdjustKBResult(U32Kibibytes(mStatsMap["Total Physical KB"].asInteger())); + return LLMemoryAdjustKBResult(U32Kilobytes(mStatsMap["Total Physical KB"].asInteger())); #elif LL_DARWIN // This might work on Linux as well. Someone check... @@ -885,8 +885,8 @@ U32Bytes LLMemoryInfo::getPhysicalMemoryClamped() const // Return the total physical memory in bytes, but clamp it // to no more than U32_MAX - U32Bytes phys_kb = getPhysicalMemoryKB(); - if (phys_kb >= 4194304 /* 4GB in KB */) + U32Kilobytes phys_kb = getPhysicalMemoryKB(); + if (phys_kb >= U32Gigabytes(4)) { return U32Bytes(U32_MAX); } @@ -897,15 +897,15 @@ U32Bytes LLMemoryInfo::getPhysicalMemoryClamped() const } //static -void LLMemoryInfo::getAvailableMemoryKB(U32Kibibytes& avail_physical_mem_kb, U32Kibibytes& avail_virtual_mem_kb) +void LLMemoryInfo::getAvailableMemoryKB(U32Kilobytes& avail_physical_mem_kb, U32Kilobytes& avail_virtual_mem_kb) { #if LL_WINDOWS // Sigh, this shouldn't be a static method, then we wouldn't have to // reload this data separately from refresh() LLSD statsMap(loadStatsMap()); - avail_physical_mem_kb = statsMap["Avail Physical KB"].asInteger(); - avail_virtual_mem_kb = statsMap["Avail Virtual KB"].asInteger(); + avail_physical_mem_kb = (U32Kilobytes)statsMap["Avail Physical KB"].asInteger(); + avail_virtual_mem_kb = (U32Kilobytes)statsMap["Avail Virtual KB"].asInteger(); #elif LL_DARWIN // mStatsMap is derived from vm_stat, look for (e.g.) "kb free": diff --git a/indra/llcommon/llsys.h b/indra/llcommon/llsys.h index ad4f243d05..962367f69f 100755 --- a/indra/llcommon/llsys.h +++ b/indra/llcommon/llsys.h @@ -112,7 +112,7 @@ public: LLMemoryInfo(); ///< Default constructor void stream(std::ostream& s) const; ///< output text info to s - U32Kibibytes getPhysicalMemoryKB() const; + U32Kilobytes getPhysicalMemoryKB() const; /*! Memory size in bytes, if total memory is >= 4GB then U32_MAX will ** be returned. @@ -120,7 +120,7 @@ public: U32Bytes getPhysicalMemoryClamped() const; ///< Memory size in clamped bytes //get the available memory infomation in KiloBytes. - static void getAvailableMemoryKB(U32Kibibytes& avail_physical_mem_kb, U32Kibibytes& avail_virtual_mem_kb); + static void getAvailableMemoryKB(U32Kilobytes& avail_physical_mem_kb, U32Kilobytes& avail_virtual_mem_kb); // Retrieve a map of memory statistics. The keys of the map are platform- // dependent. The values are in kilobytes to try to avoid integer overflow. diff --git a/indra/llcommon/lltimer.cpp b/indra/llcommon/lltimer.cpp index 74f3a7f587..da9d2b646c 100755 --- a/indra/llcommon/lltimer.cpp +++ b/indra/llcommon/lltimer.cpp @@ -225,7 +225,7 @@ void update_clock_frequencies() // returns a U64 number that represents the number of // microseconds since the unix epoch - Jan 1, 1970 -LLUnitImplicit<U64, LLUnits::Microseconds> totalTime() +U64MicrosecondsImplicit totalTime() { U64 current_clock_count = get_clock_count(); if (!gTotalTimeClockCount) @@ -295,14 +295,14 @@ void LLTimer::cleanupClass() } // static -LLUnitImplicit<U64, LLUnits::Microseconds> LLTimer::getTotalTime() +U64MicrosecondsImplicit LLTimer::getTotalTime() { // simply call into the implementation function. return totalTime(); } // static -LLUnitImplicit<F64, LLUnits::Seconds> LLTimer::getTotalSeconds() +F64SecondsImplicit LLTimer::getTotalSeconds() { return U64_to_F64(getTotalTime()) * USEC_TO_SEC_F64; } @@ -351,36 +351,36 @@ U64 getElapsedTimeAndUpdate(U64& lastClockCount) } -LLUnitImplicit<F64, LLUnits::Seconds> LLTimer::getElapsedTimeF64() const +F64SecondsImplicit LLTimer::getElapsedTimeF64() const { U64 last = mLastClockCount; return (F64)getElapsedTimeAndUpdate(last) * gClockFrequencyInv; } -LLUnitImplicit<F32, LLUnits::Seconds> LLTimer::getElapsedTimeF32() const +F32SecondsImplicit LLTimer::getElapsedTimeF32() const { return (F32)getElapsedTimeF64(); } -LLUnitImplicit<F64, LLUnits::Seconds> LLTimer::getElapsedTimeAndResetF64() +F64SecondsImplicit LLTimer::getElapsedTimeAndResetF64() { return (F64)getElapsedTimeAndUpdate(mLastClockCount) * gClockFrequencyInv; } -LLUnitImplicit<F32, LLUnits::Seconds> LLTimer::getElapsedTimeAndResetF32() +F32SecondsImplicit LLTimer::getElapsedTimeAndResetF32() { return (F32)getElapsedTimeAndResetF64(); } /////////////////////////////////////////////////////////////////////////////// -void LLTimer::setTimerExpirySec(LLUnitImplicit<F32, LLUnits::Seconds> expiration) +void LLTimer::setTimerExpirySec(F32SecondsImplicit expiration) { mExpirationTicks = get_clock_count() + (U64)((F32)(expiration * gClockFrequency)); } -LLUnitImplicit<F32, LLUnits::Seconds> LLTimer::getRemainingTimeF32() const +F32SecondsImplicit LLTimer::getRemainingTimeF32() const { U64 cur_ticks = get_clock_count(); if (cur_ticks > mExpirationTicks) diff --git a/indra/llcommon/lltimer.h b/indra/llcommon/lltimer.h index 1f2c56432b..12a453e897 100755 --- a/indra/llcommon/lltimer.h +++ b/indra/llcommon/lltimer.h @@ -67,7 +67,7 @@ public: // Return a high precision number of seconds since the start of // this application instance. - static LLUnitImplicit<F64, LLUnits::Seconds> getElapsedSeconds() + static F64SecondsImplicit getElapsedSeconds() { if (sTimer) { @@ -80,10 +80,10 @@ public: } // Return a high precision usec since epoch - static LLUnitImplicit<U64, LLUnits::Microseconds> getTotalTime(); + static U64MicrosecondsImplicit getTotalTime(); // Return a high precision seconds since epoch - static LLUnitImplicit<F64, LLUnits::Seconds> getTotalSeconds(); + static F64SecondsImplicit getTotalSeconds(); // MANIPULATORS @@ -91,19 +91,19 @@ public: void stop() { mStarted = FALSE; } void reset(); // Resets the timer void setLastClockCount(U64 current_count); // Sets the timer so that the next elapsed call will be relative to this time - void setTimerExpirySec(LLUnitImplicit<F32, LLUnits::Seconds> expiration); + void setTimerExpirySec(F32SecondsImplicit expiration); BOOL checkExpirationAndReset(F32 expiration); BOOL hasExpired() const; - LLUnitImplicit<F32, LLUnits::Seconds> getElapsedTimeAndResetF32(); // Returns elapsed time in seconds with reset - LLUnitImplicit<F64, LLUnits::Seconds> getElapsedTimeAndResetF64(); + F32SecondsImplicit getElapsedTimeAndResetF32(); // Returns elapsed time in seconds with reset + F64SecondsImplicit getElapsedTimeAndResetF64(); - LLUnitImplicit<F32, LLUnits::Seconds> getRemainingTimeF32() const; + F32SecondsImplicit getRemainingTimeF32() const; static BOOL knownBadTimer(); // ACCESSORS - LLUnitImplicit<F32, LLUnits::Seconds> getElapsedTimeF32() const; // Returns elapsed time in seconds - LLUnitImplicit<F64, LLUnits::Seconds> getElapsedTimeF64() const; // Returns elapsed time in seconds + F32SecondsImplicit getElapsedTimeF32() const; // Returns elapsed time in seconds + F64SecondsImplicit getElapsedTimeF64() const; // Returns elapsed time in seconds bool getStarted() const { return mStarted; } @@ -171,6 +171,6 @@ LL_COMMON_API struct tm* utc_to_pacific_time(time_t utc_time, BOOL pacific_dayli LL_COMMON_API void microsecondsToTimecodeString(U64 current_time, std::string& tcstring); LL_COMMON_API void secondsToTimecodeString(F32 current_time, std::string& tcstring); -LLUnitImplicit<U64, LLUnits::Microseconds> LL_COMMON_API totalTime(); // Returns current system time in microseconds +U64MicrosecondsImplicit LL_COMMON_API totalTime(); // Returns current system time in microseconds #endif diff --git a/indra/llcommon/lltraceaccumulators.cpp b/indra/llcommon/lltraceaccumulators.cpp index a632f5634c..1fb68c8158 100644 --- a/indra/llcommon/lltraceaccumulators.cpp +++ b/indra/llcommon/lltraceaccumulators.cpp @@ -114,7 +114,7 @@ void AccumulatorBufferGroup::reset(AccumulatorBufferGroup* other) void AccumulatorBufferGroup::sync() { - LLUnitImplicit<F64, LLUnits::Seconds> time_stamp = LLTimer::getTotalSeconds(); + F64SecondsImplicit time_stamp = LLTimer::getTotalSeconds(); mSamples.sync(time_stamp); mMemStats.sync(time_stamp); diff --git a/indra/llcommon/lltraceaccumulators.h b/indra/llcommon/lltraceaccumulators.h index 73da6bd2d8..f9d223066d 100644 --- a/indra/llcommon/lltraceaccumulators.h +++ b/indra/llcommon/lltraceaccumulators.h @@ -118,7 +118,7 @@ namespace LLTrace } } - void sync(LLUnitImplicit<F64, LLUnits::Seconds> time_stamp) + void sync(F64SecondsImplicit time_stamp) { llassert(mStorageSize >= sNextStorageSlot); for (size_t i = 0; i < sNextStorageSlot; i++) @@ -260,7 +260,7 @@ namespace LLTrace void addSamples(const EventAccumulator& other, EBufferAppendType append_type); void reset(const EventAccumulator* other); - void sync(LLUnitImplicit<F64, LLUnits::Seconds>) {} + void sync(F64SecondsImplicit) {} F64 getSum() const { return mSum; } F64 getMin() const { return mMin; } @@ -305,7 +305,7 @@ namespace LLTrace void sample(F64 value) { - LLUnitImplicit<F64, LLUnits::Seconds> time_stamp = LLTimer::getTotalSeconds(); + F64SecondsImplicit time_stamp = LLTimer::getTotalSeconds(); // store effect of last value sync(time_stamp); @@ -332,11 +332,11 @@ namespace LLTrace void addSamples(const SampleAccumulator& other, EBufferAppendType append_type); void reset(const SampleAccumulator* other); - void sync(LLUnitImplicit<F64, LLUnits::Seconds> time_stamp) + void sync(F64SecondsImplicit time_stamp) { if (mHasValue) { - LLUnitImplicit<F64, LLUnits::Seconds> delta_time = time_stamp - mLastSampleTimeStamp; + F64SecondsImplicit delta_time = time_stamp - mLastSampleTimeStamp; mSum += mLastValue * delta_time; mTotalSamplingTime += delta_time; F64 old_mean = mMean; @@ -353,7 +353,7 @@ namespace LLTrace F64 getMean() const { return mMean; } F64 getStandardDeviation() const { return sqrtf(mSumOfSquares / mTotalSamplingTime); } F64 getSumOfSquares() const { return mSumOfSquares; } - LLUnitImplicit<F64, LLUnits::Seconds> getSamplingTime() { return mTotalSamplingTime; } + F64SecondsImplicit getSamplingTime() { return mTotalSamplingTime; } U32 getSampleCount() const { return mNumSamples; } bool hasValue() const { return mHasValue; } @@ -368,7 +368,7 @@ namespace LLTrace F64 mMean, mSumOfSquares; - LLUnitImplicit<F64, LLUnits::Seconds> + F64SecondsImplicit mLastSampleTimeStamp, mTotalSamplingTime; @@ -403,7 +403,7 @@ namespace LLTrace mSum = 0; } - void sync(LLUnitImplicit<F64, LLUnits::Seconds>) {} + void sync(F64SecondsImplicit) {} F64 getSum() const { return mSum; } @@ -435,7 +435,7 @@ namespace LLTrace TimeBlockAccumulator(); void addSamples(const self_t& other, EBufferAppendType append_type); void reset(const self_t* other); - void sync(LLUnitImplicit<F64, LLUnits::Seconds>) {} + void sync(F64SecondsImplicit) {} // // members @@ -516,7 +516,7 @@ namespace LLTrace mDeallocatedCount = 0; } - void sync(LLUnitImplicit<F64, LLUnits::Seconds> time_stamp) + void sync(F64SecondsImplicit time_stamp) { mSize.sync(time_stamp); mChildSize.sync(time_stamp); diff --git a/indra/llcommon/lltracerecording.h b/indra/llcommon/lltracerecording.h index f5fb2bf561..ea090e6ee1 100644 --- a/indra/llcommon/lltracerecording.h +++ b/indra/llcommon/lltracerecording.h @@ -490,7 +490,7 @@ namespace LLTrace for (S32 i = 1; i <= num_periods; i++) { Recording& recording = getPrevRecording(i); - if (recording.getDuration() > 0.f) + if (recording.getDuration() > (F32Seconds)0.f) { mean += recording.getSum(stat); } @@ -530,7 +530,7 @@ namespace LLTrace for (S32 i = 1; i <= num_periods; i++) { Recording& recording = getPrevRecording(i); - if (recording.getDuration() > 0.f) + if (recording.getDuration() > (F32Seconds)0.f) { mean += recording.getPerSec(stat); } diff --git a/indra/llcommon/llunit.h b/indra/llcommon/llunit.h index b62bebc440..c49c882f23 100644 --- a/indra/llcommon/llunit.h +++ b/indra/llcommon/llunit.h @@ -31,11 +31,29 @@ #include "llpreprocessor.h" #include "llerror.h" +//lightweight replacement of type traits for simple type equality check +template<typename S, typename T> +struct LLIsSameType +{ + static const bool value = false; +}; + +template<typename T> +struct LLIsSameType<T, T> +{ + static const bool value = true; +}; + +template<typename S, typename T> +struct LLPromotedType +{ + typedef decltype(S() + T()) type_t; +}; + template<typename STORAGE_TYPE, typename UNIT_TYPE> struct LLUnit { typedef LLUnit<STORAGE_TYPE, UNIT_TYPE> self_t; - typedef STORAGE_TYPE storage_t; // value initialization @@ -49,18 +67,6 @@ struct LLUnit : mValue(convert(other).mValue) {} - bool operator == (const self_t& other) - { - return mValue = other.mValue; - } - - // value assignment - self_t& operator = (storage_t value) - { - mValue = value; - return *this; - } - // unit assignment template<typename OTHER_STORAGE, typename OTHER_UNIT> self_t& operator = (LLUnit<OTHER_STORAGE, OTHER_UNIT> other) @@ -91,22 +97,12 @@ struct LLUnit *this = LLUnit<storage_t, NEW_UNIT_TYPE>(value); } - void operator += (storage_t value) - { - mValue += value; - } - template<typename OTHER_STORAGE, typename OTHER_UNIT> void operator += (LLUnit<OTHER_STORAGE, OTHER_UNIT> other) { mValue += convert(other).mValue; } - void operator -= (storage_t value) - { - mValue -= value; - } - template<typename OTHER_STORAGE, typename OTHER_UNIT> void operator -= (LLUnit<OTHER_STORAGE, OTHER_UNIT> other) { @@ -161,7 +157,7 @@ std::istream& operator >>(std::istream& s, LLUnit<STORAGE_TYPE, UNIT_TYPE>& unit { STORAGE_TYPE val; s >> val; - unit = val; + unit.value(val); return s; } @@ -181,12 +177,37 @@ struct LLUnitImplicit : public LLUnit<STORAGE_TYPE, UNIT_TYPE> : base_t(convert(other)) {} - // unlike LLUnit, LLUnitImplicit is *implicitly* convertable to a POD scalar (F32, S32, etc) + // unlike LLUnit, LLUnitImplicit is *implicitly* convertable to a POD value (F32, S32, etc) // this allows for interoperability with legacy code operator storage_t() const { return base_t::value(); } + + using base_t::operator +=; + void operator += (storage_t value) + { + mValue += value; + } + + template<typename OTHER_STORAGE, typename OTHER_UNIT> + void operator += (LLUnitImplicit<OTHER_STORAGE, OTHER_UNIT> other) + { + mValue += convert(other).value(); + } + + using base_t::operator -=; + void operator -= (storage_t value) + { + mValue -= value; + } + + template<typename OTHER_STORAGE, typename OTHER_UNIT> + void operator -= (LLUnitImplicit<OTHER_STORAGE, OTHER_UNIT> other) + { + mValue -= convert(other).value(); + } + }; template<typename STORAGE_TYPE, typename UNIT_TYPE> @@ -205,24 +226,12 @@ std::istream& operator >>(std::istream& s, LLUnitImplicit<STORAGE_TYPE, UNIT_TYP return s; } -template<typename S, typename T> -struct LLIsSameType -{ - static const bool value = false; -}; - -template<typename T> -struct LLIsSameType<T, T> -{ - static const bool value = true; -}; - template<typename S1, typename T1, typename S2, typename T2> LL_FORCE_INLINE void ll_convert_units(LLUnit<S1, T1> in, LLUnit<S2, T2>& out, ...) { LL_STATIC_ASSERT((LLIsSameType<T1, T2>::value || !LLIsSameType<T1, typename T1::base_unit_t>::value - || !LLIsSameType<T2, typename T2::base_unit_t>::value), "invalid conversion"); + || !LLIsSameType<T2, typename T2::base_unit_t>::value), "invalid conversion: incompatible units"); if (LLIsSameType<T1, typename T1::base_unit_t>::value) { @@ -253,65 +262,63 @@ LL_FORCE_INLINE void ll_convert_units(LLUnit<S1, T1> in, LLUnit<S2, T2>& out, .. // operator + // template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnit<STORAGE_TYPE1, UNIT_TYPE1> operator + (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> operator + (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> result(first); result += second; return result; } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnit<STORAGE_TYPE, UNIT_TYPE> operator + (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS> +LLUnit<STORAGE_TYPE, UNIT_TYPE> operator + (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS second) { - LLUnit<STORAGE_TYPE, UNIT_TYPE> result(first); - result += second; - return result; + LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "operator + requires compatible unit types"); + return LLUnit<STORAGE_TYPE, UNIT_TYPE>(0); } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnit<STORAGE_TYPE, UNIT_TYPE> operator + (SCALAR_TYPE first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS> +LLUnit<STORAGE_TYPE, UNIT_TYPE> operator + (UNITLESS first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) { - LLUnit<STORAGE_TYPE, UNIT_TYPE> result(first); - result += second; - return result; + LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "operator + requires compatible unit types"); + return LLUnit<STORAGE_TYPE, UNIT_TYPE>(0); } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> operator + (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnitImplicit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> operator + (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> result(first); result += second; return result; } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> operator + (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnitImplicit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> operator + (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> result(first); result += second; return result; } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> operator + (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnitImplicit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> operator + (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE1() + STORAGE_TYPE2()), UNIT_TYPE1> result(first); result += LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1>(second); return result; } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator + (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnitImplicit<decltype(STORAGE_TYPE() + UNITLESS_TYPE()), UNIT_TYPE> operator + (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) { - LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE() + UNITLESS_TYPE()), UNIT_TYPE> result(first); result += second; return result; } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator + (SCALAR_TYPE first, LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnitImplicit<decltype(UNITLESS_TYPE() + STORAGE_TYPE()), UNIT_TYPE> operator + (UNITLESS_TYPE first, LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> second) { - LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> result(first); + LLUnitImplicit<decltype(UNITLESS_TYPE() + STORAGE_TYPE()), UNIT_TYPE> result(first); result += second; return result; } @@ -320,65 +327,63 @@ LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator + (SCALAR_TYPE first, LLUnitImp // operator - // template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnit<STORAGE_TYPE1, UNIT_TYPE1> operator - (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> operator - (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> result(first); result -= second; return result; } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnit<STORAGE_TYPE, UNIT_TYPE> operator - (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS> +LLUnit<STORAGE_TYPE, UNIT_TYPE> operator - (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS second) { - LLUnit<STORAGE_TYPE, UNIT_TYPE> result(first); - result -= second; - return result; + LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "operator - requires compatible unit types"); + return LLUnit<STORAGE_TYPE, UNIT_TYPE>(0); } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnit<STORAGE_TYPE, UNIT_TYPE> operator - (SCALAR_TYPE first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS> +LLUnit<STORAGE_TYPE, UNIT_TYPE> operator - (UNITLESS first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) { - LLUnit<STORAGE_TYPE, UNIT_TYPE> result(first); - result -= second; - return result; + LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "operator - requires compatible unit types"); + return LLUnit<STORAGE_TYPE, UNIT_TYPE>(0); } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> operator - (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnitImplicit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> operator - (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> result(first); result -= second; return result; } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> operator - (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnitImplicit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> operator - (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> result(first); result -= second; return result; } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> operator - (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) +LLUnitImplicit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> operator - (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) { - LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE1() - STORAGE_TYPE2()), UNIT_TYPE1> result(first); result -= LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1>(second); return result; } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator - (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnitImplicit<decltype(STORAGE_TYPE() - UNITLESS_TYPE()), UNIT_TYPE> operator - (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) { - LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> result(first); + LLUnitImplicit<decltype(STORAGE_TYPE() - UNITLESS_TYPE()), UNIT_TYPE> result(first); result -= second; return result; } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator - (SCALAR_TYPE first, LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnitImplicit<decltype(UNITLESS_TYPE() - STORAGE_TYPE()), UNIT_TYPE> operator - (UNITLESS_TYPE first, LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> second) { - LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> result(first); + LLUnitImplicit<decltype(UNITLESS_TYPE() - STORAGE_TYPE()), UNIT_TYPE> result(first); result -= second; return result; } @@ -390,119 +395,144 @@ template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, ty LLUnit<STORAGE_TYPE1, UNIT_TYPE1> operator * (LLUnit<STORAGE_TYPE1, UNIT_TYPE1>, LLUnit<STORAGE_TYPE2, UNIT_TYPE2>) { // spurious use of dependent type to stop gcc from triggering the static assertion before instantiating the template - LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "Multiplication of unit types results in new unit type - not supported."); + LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "multiplication of unit types results in new unit type - not supported."); return LLUnit<STORAGE_TYPE1, UNIT_TYPE1>(); } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnit<STORAGE_TYPE, UNIT_TYPE> operator * (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnit<decltype(STORAGE_TYPE() * UNITLESS_TYPE()), UNIT_TYPE> operator * (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) { - return LLUnit<STORAGE_TYPE, UNIT_TYPE>((STORAGE_TYPE)(first.value() * second)); + return LLUnit<decltype(STORAGE_TYPE() * UNITLESS_TYPE()), UNIT_TYPE>(first.value() * second); } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnit<STORAGE_TYPE, UNIT_TYPE> operator * (SCALAR_TYPE first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnit<decltype(UNITLESS_TYPE() * STORAGE_TYPE()), UNIT_TYPE> operator * (UNITLESS_TYPE first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) { - return LLUnit<STORAGE_TYPE, UNIT_TYPE>((STORAGE_TYPE)(first * second.value())); + return LLUnit<decltype(UNITLESS_TYPE() * STORAGE_TYPE()), UNIT_TYPE>(first * second.value()); } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> operator * (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1>, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2>) { // spurious use of dependent type to stop gcc from triggering the static assertion before instantiating the template - LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "Multiplication of unit types results in new unit type - not supported."); + LL_BAD_TEMPLATE_INSTANTIATION(STORAGE_TYPE1, "multiplication of unit types results in new unit type - not supported."); return LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1>(); } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator * (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnitImplicit<decltype(STORAGE_TYPE() * UNITLESS_TYPE()), UNIT_TYPE> operator * (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) { - return LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE>(first.value() * second); + return LLUnitImplicit<decltype(STORAGE_TYPE() * UNITLESS_TYPE()), UNIT_TYPE>(first.value() * second); } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator * (SCALAR_TYPE first, LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnitImplicit<decltype(UNITLESS_TYPE() * STORAGE_TYPE()), UNIT_TYPE> operator * (UNITLESS_TYPE first, LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> second) { - return LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE>(first * second.value()); + return LLUnitImplicit<decltype(UNITLESS_TYPE() * STORAGE_TYPE()), UNIT_TYPE>(first * second.value()); } // // operator / // -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -SCALAR_TYPE operator / (SCALAR_TYPE first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) -{ - return SCALAR_TYPE(first / second.value()); -} -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnit<STORAGE_TYPE, UNIT_TYPE> operator / (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnit<decltype(STORAGE_TYPE() / UNITLESS_TYPE()), UNIT_TYPE> operator / (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) { - return LLUnit<STORAGE_TYPE, UNIT_TYPE>((STORAGE_TYPE)(first.value() / second)); + return LLUnit<decltype(STORAGE_TYPE() / UNITLESS_TYPE()), UNIT_TYPE>(first.value() / second); } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -STORAGE_TYPE1 operator / (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) +decltype(STORAGE_TYPE1() / STORAGE_TYPE2()) operator / (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) { - return STORAGE_TYPE1(first.value() / first.convert(second)); + return first.value() / first.convert(second).value(); } -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> -LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> operator / (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> +LLUnitImplicit<decltype(STORAGE_TYPE() / UNITLESS_TYPE()), UNIT_TYPE> operator / (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) { - return LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE>((STORAGE_TYPE)(first.value() / second)); + return LLUnitImplicit<decltype(STORAGE_TYPE() / UNITLESS_TYPE()), UNIT_TYPE>(first.value() / second); } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -STORAGE_TYPE1 operator / (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) +decltype(STORAGE_TYPE1() / STORAGE_TYPE2()) operator / (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) { - return STORAGE_TYPE1(first.value() / first.convert(second)); + return (decltype(STORAGE_TYPE1() / STORAGE_TYPE2()))(first.value() / first.convert(second).value()); } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -STORAGE_TYPE1 operator / (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) +decltype(STORAGE_TYPE1() / STORAGE_TYPE2()) operator / (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) { - return STORAGE_TYPE1(first.value() / first.convert(second)); + return (decltype(STORAGE_TYPE1() / STORAGE_TYPE2()))(first.value() / first.convert(second).value()); } template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> -STORAGE_TYPE1 operator / (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) -{ - return STORAGE_TYPE1(first.value() / first.convert(second)); -} - -#define COMPARISON_OPERATORS(op) \ -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> \ -bool operator op (SCALAR_TYPE first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) \ -{ \ - return first op second.value(); \ -} \ - \ -template<typename STORAGE_TYPE, typename UNIT_TYPE, typename SCALAR_TYPE> \ -bool operator op (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, SCALAR_TYPE second) \ -{ \ - return first.value() op second; \ -} \ - \ -template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> \ -bool operator op (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) \ -{ \ - return first.value() op first.convert(second); \ -} \ - \ -template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> \ - bool operator op (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) \ -{ \ - return first.value() op first.convert(second); \ -} - -COMPARISON_OPERATORS(<) -COMPARISON_OPERATORS(<=) -COMPARISON_OPERATORS(>) -COMPARISON_OPERATORS(>=) -COMPARISON_OPERATORS(==) -COMPARISON_OPERATORS(!=) +decltype(STORAGE_TYPE1() / STORAGE_TYPE2()) operator / (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) +{ + return (decltype(STORAGE_TYPE1() / STORAGE_TYPE2()))(first.value() / first.convert(second).value()); +} + +// +// comparison operators +// + +#define LL_UNIT_DECLARE_COMPARISON_OPERATOR(op) \ +template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> \ +bool operator op (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) \ +{ \ + return first.value() op first.convert(second).value(); \ +} \ + \ +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> \ +bool operator op (LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) \ +{ \ + return first.value() op second; \ +} \ + \ +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> \ +bool operator op (UNITLESS_TYPE first, LLUnitImplicit<STORAGE_TYPE, UNIT_TYPE> second) \ +{ \ + return first op second.value(); \ +} \ + \ +template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> \ +bool operator op (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) \ +{ \ + return first.value() op first.convert(second).value(); \ +} \ + \ +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> \ +bool operator op (LLUnit<STORAGE_TYPE, UNIT_TYPE> first, UNITLESS_TYPE second) \ +{ \ + LL_BAD_TEMPLATE_INSTANTIATION(UNITLESS_TYPE, "operator " #op " requires compatible unit types"); \ + return false; \ +} \ + \ +template<typename STORAGE_TYPE, typename UNIT_TYPE, typename UNITLESS_TYPE> \ +bool operator op (UNITLESS_TYPE first, LLUnit<STORAGE_TYPE, UNIT_TYPE> second) \ +{ \ + LL_BAD_TEMPLATE_INSTANTIATION(UNITLESS_TYPE, "operator " #op " requires compatible unit types"); \ + return false; \ +} \ + \ +template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> \ +bool operator op (LLUnit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnitImplicit<STORAGE_TYPE2, UNIT_TYPE2> second) \ +{ \ + return first.value() op first.convert(second).value(); \ +} \ + \ +template<typename STORAGE_TYPE1, typename UNIT_TYPE1, typename STORAGE_TYPE2, typename UNIT_TYPE2> \ +bool operator op (LLUnitImplicit<STORAGE_TYPE1, UNIT_TYPE1> first, LLUnit<STORAGE_TYPE2, UNIT_TYPE2> second) \ +{ \ + return first.value() op first.convert(second).value(); \ +} + +LL_UNIT_DECLARE_COMPARISON_OPERATOR(<); +LL_UNIT_DECLARE_COMPARISON_OPERATOR(<=); +LL_UNIT_DECLARE_COMPARISON_OPERATOR(>); +LL_UNIT_DECLARE_COMPARISON_OPERATOR(>=); +LL_UNIT_DECLARE_COMPARISON_OPERATOR(==); +LL_UNIT_DECLARE_COMPARISON_OPERATOR(!=); template<typename T> @@ -517,8 +547,6 @@ struct LLGetUnitLabel<LLUnit<STORAGE_T, T> > static const char* getUnitLabel() { return T::getUnitLabel(); } }; -#define LL_UNIT_PROMOTE_VALUE(output_type, value) ((true ? (output_type)(1) : (value/value)) * value) - template<typename INPUT_TYPE, typename OUTPUT_TYPE> struct LLUnitLinearOps { @@ -534,25 +562,25 @@ struct LLUnitLinearOps template<typename T> output_t operator * (T other) { - return mInput * other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) * other; } template<typename T> output_t operator / (T other) { - return LL_UNIT_PROMOTE_VALUE(OUTPUT_TYPE, mInput) / other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) / other; } template<typename T> output_t operator + (T other) { - return mInput + other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) + other; } template<typename T> output_t operator - (T other) { - return mInput - other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) - other; } }; @@ -571,25 +599,25 @@ struct LLUnitInverseLinearOps template<typename T> output_t operator * (T other) { - return LL_UNIT_PROMOTE_VALUE(OUTPUT_TYPE, mInput) / other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) / other; } template<typename T> output_t operator / (T other) { - return mInput * other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) * other; } template<typename T> output_t operator + (T other) { - return mInput - other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) - other; } template<typename T> output_t operator - (T other) { - return mInput + other; + return typename LLPromotedType<INPUT_TYPE, OUTPUT_TYPE>::type_t(mInput) + other; } }; @@ -621,13 +649,13 @@ struct unit_name template<typename S1, typename S2> \ void ll_convert_units(LLUnit<S1, unit_name> in, LLUnit<S2, base_unit_name>& out) \ { \ - out = LLUnit<S2, base_unit_name>((S2)(LLUnitLinearOps<S1, S2>(in.value()) conversion_operation)); \ + out = LLUnit<S2, base_unit_name>((S2)(LLUnitLinearOps<S1, S2>(in.value()) conversion_operation)); \ } \ \ template<typename S1, typename S2> \ void ll_convert_units(LLUnit<S1, base_unit_name> in, LLUnit<S2, unit_name>& out) \ { \ - out = LLUnit<S2, unit_name>((S2)(LLUnitInverseLinearOps<S1, S2>(in.value()) conversion_operation)); \ + out = LLUnit<S2, unit_name>((S2)(LLUnitInverseLinearOps<S1, S2>(in.value()) conversion_operation)); \ } // @@ -637,120 +665,140 @@ void ll_convert_units(LLUnit<S1, base_unit_name> in, LLUnit<S2, unit_name>& out) namespace LLUnits { LL_DECLARE_BASE_UNIT(Bytes, "B"); -LL_DECLARE_DERIVED_UNIT(Bytes, * 1000, Kilobytes, "KB"); -LL_DECLARE_DERIVED_UNIT(Kilobytes, * 1000, Megabytes, "MB"); -LL_DECLARE_DERIVED_UNIT(Megabytes, * 1000, Gigabytes, "GB"); -LL_DECLARE_DERIVED_UNIT(Bytes, * 1024, Kibibytes, "KiB"); -LL_DECLARE_DERIVED_UNIT(Kibibytes, * 1024, Mibibytes, "MiB"); -LL_DECLARE_DERIVED_UNIT(Mibibytes, * 1024, Gibibytes, "GiB"); +// technically, these are kibibytes, mibibytes, etc. but we should stick with commonly accepted terminology +LL_DECLARE_DERIVED_UNIT(Bytes, * 1024, Kilobytes, "KB"); +LL_DECLARE_DERIVED_UNIT(Kilobytes, * 1024, Megabytes, "MB"); +LL_DECLARE_DERIVED_UNIT(Megabytes, * 1024, Gigabytes, "GB"); } typedef LLUnit<F32, LLUnits::Bytes> F32Bytes; typedef LLUnit<F32, LLUnits::Kilobytes> F32Kilobytes; typedef LLUnit<F32, LLUnits::Megabytes> F32Megabytes; typedef LLUnit<F32, LLUnits::Gigabytes> F32Gigabytes; -typedef LLUnit<F32, LLUnits::Kibibytes> F32Kibibytes; -typedef LLUnit<F32, LLUnits::Mibibytes> F32Mibibytes; -typedef LLUnit<F32, LLUnits::Gibibytes> F32Gibibytes; + +typedef LLUnitImplicit<F32, LLUnits::Bytes> F32BytesImplicit; +typedef LLUnitImplicit<F32, LLUnits::Kilobytes> F32KilobytesImplicit; +typedef LLUnitImplicit<F32, LLUnits::Megabytes> F32MegabytesImplicit; +typedef LLUnitImplicit<F32, LLUnits::Gigabytes> F32GigabytesImplicit; typedef LLUnit<F64, LLUnits::Bytes> F64Bytes; typedef LLUnit<F64, LLUnits::Kilobytes> F64Kilobytes; typedef LLUnit<F64, LLUnits::Megabytes> F64Megabytes; typedef LLUnit<F64, LLUnits::Gigabytes> F64Gigabytes; -typedef LLUnit<F64, LLUnits::Kibibytes> F64Kibibytes; -typedef LLUnit<F64, LLUnits::Mibibytes> F64Mibibytes; -typedef LLUnit<F64, LLUnits::Gibibytes> F64Gibibytes; + +typedef LLUnitImplicit<F64, LLUnits::Bytes> F64BytesImplicit; +typedef LLUnitImplicit<F64, LLUnits::Kilobytes> F64KilobytesImplicit; +typedef LLUnitImplicit<F64, LLUnits::Megabytes> F64MegabytesImplicit; +typedef LLUnitImplicit<F64, LLUnits::Gigabytes> F64GigabytesImplicit; typedef LLUnit<S32, LLUnits::Bytes> S32Bytes; typedef LLUnit<S32, LLUnits::Kilobytes> S32Kilobytes; typedef LLUnit<S32, LLUnits::Megabytes> S32Megabytes; typedef LLUnit<S32, LLUnits::Gigabytes> S32Gigabytes; -typedef LLUnit<S32, LLUnits::Kibibytes> S32Kibibytes; -typedef LLUnit<S32, LLUnits::Mibibytes> S32Mibibytes; -typedef LLUnit<S32, LLUnits::Gibibytes> S32Gibibytes; -typedef LLUnit<U32, LLUnits::Bytes> U32Bytes; -typedef LLUnit<U32, LLUnits::Kilobytes> U32Kilobytes; -typedef LLUnit<U32, LLUnits::Megabytes> U32Megabytes; -typedef LLUnit<U32, LLUnits::Gigabytes> U32Gigabytes; -typedef LLUnit<U32, LLUnits::Kibibytes> U32Kibibytes; -typedef LLUnit<U32, LLUnits::Mibibytes> U32Mibibytes; -typedef LLUnit<U32, LLUnits::Gibibytes> U32Gibibytes; +typedef LLUnitImplicit<S32, LLUnits::Bytes> S32BytesImplicit; +typedef LLUnitImplicit<S32, LLUnits::Kilobytes> S32KilobytesImplicit; +typedef LLUnitImplicit<S32, LLUnits::Megabytes> S32MegabytesImplicit; +typedef LLUnitImplicit<S32, LLUnits::Gigabytes> S32GigabytesImplicit; typedef LLUnit<S64, LLUnits::Bytes> S64Bytes; typedef LLUnit<S64, LLUnits::Kilobytes> S64Kilobytes; typedef LLUnit<S64, LLUnits::Megabytes> S64Megabytes; typedef LLUnit<S64, LLUnits::Gigabytes> S64Gigabytes; -typedef LLUnit<S64, LLUnits::Kibibytes> S64Kibibytes; -typedef LLUnit<S64, LLUnits::Mibibytes> S64Mibibytes; -typedef LLUnit<S64, LLUnits::Gibibytes> S64Gibibytes; + +typedef LLUnitImplicit<S64, LLUnits::Bytes> S64BytesImplicit; +typedef LLUnitImplicit<S64, LLUnits::Kilobytes> S64KilobytesImplicit; +typedef LLUnitImplicit<S64, LLUnits::Megabytes> S64MegabytesImplicit; +typedef LLUnitImplicit<S64, LLUnits::Gigabytes> S64GigabytesImplicit; + +typedef LLUnit<U32, LLUnits::Bytes> U32Bytes; +typedef LLUnit<U32, LLUnits::Kilobytes> U32Kilobytes; +typedef LLUnit<U32, LLUnits::Megabytes> U32Megabytes; +typedef LLUnit<U32, LLUnits::Gigabytes> U32Gigabytes; + +typedef LLUnitImplicit<U32, LLUnits::Bytes> U32BytesImplicit; +typedef LLUnitImplicit<U32, LLUnits::Kilobytes> U32KilobytesImplicit; +typedef LLUnitImplicit<U32, LLUnits::Megabytes> U32MegabytesImplicit; +typedef LLUnitImplicit<U32, LLUnits::Gigabytes> U32GigabytesImplicit; typedef LLUnit<U64, LLUnits::Bytes> U64Bytes; typedef LLUnit<U64, LLUnits::Kilobytes> U64Kilobytes; typedef LLUnit<U64, LLUnits::Megabytes> U64Megabytes; typedef LLUnit<U64, LLUnits::Gigabytes> U64Gigabytes; -typedef LLUnit<U64, LLUnits::Kibibytes> U64Kibibytes; -typedef LLUnit<U64, LLUnits::Mibibytes> U64Mibibytes; -typedef LLUnit<U64, LLUnits::Gibibytes> U64Gibibytes; + +typedef LLUnitImplicit<U64, LLUnits::Bytes> U64BytesImplicit; +typedef LLUnitImplicit<U64, LLUnits::Kilobytes> U64KilobytesImplicit; +typedef LLUnitImplicit<U64, LLUnits::Megabytes> U64MegabytesImplicit; +typedef LLUnitImplicit<U64, LLUnits::Gigabytes> U64GigabytesImplicit; namespace LLUnits { +// technically, these are kibibits, mibibits, etc. but we should stick with commonly accepted terminology LL_DECLARE_DERIVED_UNIT(Bytes, / 8, Bits, "b"); -LL_DECLARE_DERIVED_UNIT(Bits, * 1000, Kilobits, "Kb"); -LL_DECLARE_DERIVED_UNIT(Kilobits, * 1000, Megabits, "Mb"); -LL_DECLARE_DERIVED_UNIT(Megabits, * 1000, Gigabits, "Gb"); -LL_DECLARE_DERIVED_UNIT(Bits, * 1024, Kibibits, "Kib"); -LL_DECLARE_DERIVED_UNIT(Kibibits, * 1024, Mibibits, "Mib"); -LL_DECLARE_DERIVED_UNIT(Mibibits, * 1024, Gibibits, "Gib"); +LL_DECLARE_DERIVED_UNIT(Bits, * 1024, Kilobits, "Kb"); +LL_DECLARE_DERIVED_UNIT(Kilobits, * 1024, Megabits, "Mb"); +LL_DECLARE_DERIVED_UNIT(Megabits, * 1024, Gigabits, "Gb"); } typedef LLUnit<F32, LLUnits::Bits> F32Bits; typedef LLUnit<F32, LLUnits::Kilobits> F32Kilobits; typedef LLUnit<F32, LLUnits::Megabits> F32Megabits; typedef LLUnit<F32, LLUnits::Gigabits> F32Gigabits; -typedef LLUnit<F32, LLUnits::Kibibits> F32Kibibits; -typedef LLUnit<F32, LLUnits::Mibibits> F32Mibibits; -typedef LLUnit<F32, LLUnits::Gibibits> F32Gibibits; - + +typedef LLUnitImplicit<F32, LLUnits::Bits> F32BitsImplicit; +typedef LLUnitImplicit<F32, LLUnits::Kilobits> F32KilobitsImplicit; +typedef LLUnitImplicit<F32, LLUnits::Megabits> F32MegabitsImplicit; +typedef LLUnitImplicit<F32, LLUnits::Gigabits> F32GigabitsImplicit; + typedef LLUnit<F64, LLUnits::Bits> F64Bits; typedef LLUnit<F64, LLUnits::Kilobits> F64Kilobits; typedef LLUnit<F64, LLUnits::Megabits> F64Megabits; typedef LLUnit<F64, LLUnits::Gigabits> F64Gigabits; -typedef LLUnit<F64, LLUnits::Kibibits> F64Kibibits; -typedef LLUnit<F64, LLUnits::Mibibits> F64Mibibits; -typedef LLUnit<F64, LLUnits::Gibibits> F64Gibibits; + +typedef LLUnitImplicit<F64, LLUnits::Bits> F64BitsImplicit; +typedef LLUnitImplicit<F64, LLUnits::Kilobits> F64KilobitsImplicit; +typedef LLUnitImplicit<F64, LLUnits::Megabits> F64MegabitsImplicit; +typedef LLUnitImplicit<F64, LLUnits::Gigabits> F64GigabitsImplicit; typedef LLUnit<S32, LLUnits::Bits> S32Bits; typedef LLUnit<S32, LLUnits::Kilobits> S32Kilobits; typedef LLUnit<S32, LLUnits::Megabits> S32Megabits; typedef LLUnit<S32, LLUnits::Gigabits> S32Gigabits; -typedef LLUnit<S32, LLUnits::Kibibits> S32Kibibits; -typedef LLUnit<S32, LLUnits::Mibibits> S32Mibibits; -typedef LLUnit<S32, LLUnits::Gibibits> S32Gibibits; -typedef LLUnit<U32, LLUnits::Bits> U32Bits; -typedef LLUnit<U32, LLUnits::Kilobits> U32Kilobits; -typedef LLUnit<U32, LLUnits::Megabits> U32Megabits; -typedef LLUnit<U32, LLUnits::Gigabits> U32Gigabits; -typedef LLUnit<U32, LLUnits::Kibibits> U32Kibibits; -typedef LLUnit<U32, LLUnits::Mibibits> U32Mibibits; -typedef LLUnit<U32, LLUnits::Gibibits> U32Gibibits; +typedef LLUnitImplicit<S32, LLUnits::Bits> S32BitsImplicit; +typedef LLUnitImplicit<S32, LLUnits::Kilobits> S32KilobitsImplicit; +typedef LLUnitImplicit<S32, LLUnits::Megabits> S32MegabitsImplicit; +typedef LLUnitImplicit<S32, LLUnits::Gigabits> S32GigabitsImplicit; typedef LLUnit<S64, LLUnits::Bits> S64Bits; typedef LLUnit<S64, LLUnits::Kilobits> S64Kilobits; typedef LLUnit<S64, LLUnits::Megabits> S64Megabits; typedef LLUnit<S64, LLUnits::Gigabits> S64Gigabits; -typedef LLUnit<S64, LLUnits::Kibibits> S64Kibibits; -typedef LLUnit<S64, LLUnits::Mibibits> S64Mibibits; -typedef LLUnit<S64, LLUnits::Gibibits> S64Gibibits; + +typedef LLUnitImplicit<S64, LLUnits::Bits> S64BitsImplicit; +typedef LLUnitImplicit<S64, LLUnits::Kilobits> S64KilobitsImplicit; +typedef LLUnitImplicit<S64, LLUnits::Megabits> S64MegabitsImplicit; +typedef LLUnitImplicit<S64, LLUnits::Gigabits> S64GigabitsImplicit; + +typedef LLUnit<U32, LLUnits::Bits> U32Bits; +typedef LLUnit<U32, LLUnits::Kilobits> U32Kilobits; +typedef LLUnit<U32, LLUnits::Megabits> U32Megabits; +typedef LLUnit<U32, LLUnits::Gigabits> U32Gigabits; + +typedef LLUnitImplicit<U32, LLUnits::Bits> U32BitsImplicit; +typedef LLUnitImplicit<U32, LLUnits::Kilobits> U32KilobitsImplicit; +typedef LLUnitImplicit<U32, LLUnits::Megabits> U32MegabitsImplicit; +typedef LLUnitImplicit<U32, LLUnits::Gigabits> U32GigabitsImplicit; typedef LLUnit<U64, LLUnits::Bits> U64Bits; typedef LLUnit<U64, LLUnits::Kilobits> U64Kilobits; typedef LLUnit<U64, LLUnits::Megabits> U64Megabits; typedef LLUnit<U64, LLUnits::Gigabits> U64Gigabits; -typedef LLUnit<U64, LLUnits::Kibibits> U64Kibibits; -typedef LLUnit<U64, LLUnits::Mibibits> U64Mibibits; -typedef LLUnit<U64, LLUnits::Gibibits> U64Gibibits; + +typedef LLUnitImplicit<U64, LLUnits::Bits> U64BitsImplicit; +typedef LLUnitImplicit<U64, LLUnits::Kilobits> U64KilobitsImplicit; +typedef LLUnitImplicit<U64, LLUnits::Megabits> U64MegabitsImplicit; +typedef LLUnitImplicit<U64, LLUnits::Gigabits> U64GigabitsImplicit; namespace LLUnits { @@ -771,6 +819,14 @@ typedef LLUnit<F32, LLUnits::Milliseconds> F32Milliseconds; typedef LLUnit<F32, LLUnits::Microseconds> F32Microseconds; typedef LLUnit<F32, LLUnits::Nanoseconds> F32Nanoseconds; +typedef LLUnitImplicit<F32, LLUnits::Seconds> F32SecondsImplicit; +typedef LLUnitImplicit<F32, LLUnits::Minutes> F32MinutesImplicit; +typedef LLUnitImplicit<F32, LLUnits::Hours> F32HoursImplicit; +typedef LLUnitImplicit<F32, LLUnits::Days> F32DaysImplicit; +typedef LLUnitImplicit<F32, LLUnits::Milliseconds> F32MillisecondsImplicit; +typedef LLUnitImplicit<F32, LLUnits::Microseconds> F32MicrosecondsImplicit; +typedef LLUnitImplicit<F32, LLUnits::Nanoseconds> F32NanosecondsImplicit; + typedef LLUnit<F64, LLUnits::Seconds> F64Seconds; typedef LLUnit<F64, LLUnits::Minutes> F64Minutes; typedef LLUnit<F64, LLUnits::Hours> F64Hours; @@ -779,6 +835,14 @@ typedef LLUnit<F64, LLUnits::Milliseconds> F64Milliseconds; typedef LLUnit<F64, LLUnits::Microseconds> F64Microseconds; typedef LLUnit<F64, LLUnits::Nanoseconds> F64Nanoseconds; +typedef LLUnitImplicit<F64, LLUnits::Seconds> F64SecondsImplicit; +typedef LLUnitImplicit<F64, LLUnits::Minutes> F64MinutesImplicit; +typedef LLUnitImplicit<F64, LLUnits::Hours> F64HoursImplicit; +typedef LLUnitImplicit<F64, LLUnits::Days> F64DaysImplicit; +typedef LLUnitImplicit<F64, LLUnits::Milliseconds> F64MillisecondsImplicit; +typedef LLUnitImplicit<F64, LLUnits::Microseconds> F64MicrosecondsImplicit; +typedef LLUnitImplicit<F64, LLUnits::Nanoseconds> F64NanosecondsImplicit; + typedef LLUnit<S32, LLUnits::Seconds> S32Seconds; typedef LLUnit<S32, LLUnits::Minutes> S32Minutes; typedef LLUnit<S32, LLUnits::Hours> S32Hours; @@ -787,13 +851,13 @@ typedef LLUnit<S32, LLUnits::Milliseconds> S32Milliseconds; typedef LLUnit<S32, LLUnits::Microseconds> S32Microseconds; typedef LLUnit<S32, LLUnits::Nanoseconds> S32Nanoseconds; -typedef LLUnit<U32, LLUnits::Seconds> U32Seconds; -typedef LLUnit<U32, LLUnits::Minutes> U32Minutes; -typedef LLUnit<U32, LLUnits::Hours> U32Hours; -typedef LLUnit<U32, LLUnits::Days> U32Days; -typedef LLUnit<U32, LLUnits::Milliseconds> U32Milliseconds; -typedef LLUnit<U32, LLUnits::Microseconds> U32Microseconds; -typedef LLUnit<U32, LLUnits::Nanoseconds> U32Nanoseconds; +typedef LLUnitImplicit<S32, LLUnits::Seconds> S32SecondsImplicit; +typedef LLUnitImplicit<S32, LLUnits::Minutes> S32MinutesImplicit; +typedef LLUnitImplicit<S32, LLUnits::Hours> S32HoursImplicit; +typedef LLUnitImplicit<S32, LLUnits::Days> S32DaysImplicit; +typedef LLUnitImplicit<S32, LLUnits::Milliseconds> S32MillisecondsImplicit; +typedef LLUnitImplicit<S32, LLUnits::Microseconds> S32MicrosecondsImplicit; +typedef LLUnitImplicit<S32, LLUnits::Nanoseconds> S32NanosecondsImplicit; typedef LLUnit<S64, LLUnits::Seconds> S64Seconds; typedef LLUnit<S64, LLUnits::Minutes> S64Minutes; @@ -802,7 +866,31 @@ typedef LLUnit<S64, LLUnits::Days> S64Days; typedef LLUnit<S64, LLUnits::Milliseconds> S64Milliseconds; typedef LLUnit<S64, LLUnits::Microseconds> S64Microseconds; typedef LLUnit<S64, LLUnits::Nanoseconds> S64Nanoseconds; - + +typedef LLUnitImplicit<S64, LLUnits::Seconds> S64SecondsImplicit; +typedef LLUnitImplicit<S64, LLUnits::Minutes> S64MinutesImplicit; +typedef LLUnitImplicit<S64, LLUnits::Hours> S64HoursImplicit; +typedef LLUnitImplicit<S64, LLUnits::Days> S64DaysImplicit; +typedef LLUnitImplicit<S64, LLUnits::Milliseconds> S64MillisecondsImplicit; +typedef LLUnitImplicit<S64, LLUnits::Microseconds> S64MicrosecondsImplicit; +typedef LLUnitImplicit<S64, LLUnits::Nanoseconds> S64NanosecondsImplicit; + +typedef LLUnit<U32, LLUnits::Seconds> U32Seconds; +typedef LLUnit<U32, LLUnits::Minutes> U32Minutes; +typedef LLUnit<U32, LLUnits::Hours> U32Hours; +typedef LLUnit<U32, LLUnits::Days> U32Days; +typedef LLUnit<U32, LLUnits::Milliseconds> U32Milliseconds; +typedef LLUnit<U32, LLUnits::Microseconds> U32Microseconds; +typedef LLUnit<U32, LLUnits::Nanoseconds> U32Nanoseconds; + +typedef LLUnitImplicit<U32, LLUnits::Seconds> U32SecondsImplicit; +typedef LLUnitImplicit<U32, LLUnits::Minutes> U32MinutesImplicit; +typedef LLUnitImplicit<U32, LLUnits::Hours> U32HoursImplicit; +typedef LLUnitImplicit<U32, LLUnits::Days> U32DaysImplicit; +typedef LLUnitImplicit<U32, LLUnits::Milliseconds> U32MillisecondsImplicit; +typedef LLUnitImplicit<U32, LLUnits::Microseconds> U32MicrosecondsImplicit; +typedef LLUnitImplicit<U32, LLUnits::Nanoseconds> U32NanosecondsImplicit; + typedef LLUnit<U64, LLUnits::Seconds> U64Seconds; typedef LLUnit<U64, LLUnits::Minutes> U64Minutes; typedef LLUnit<U64, LLUnits::Hours> U64Hours; @@ -811,6 +899,14 @@ typedef LLUnit<U64, LLUnits::Milliseconds> U64Milliseconds; typedef LLUnit<U64, LLUnits::Microseconds> U64Microseconds; typedef LLUnit<U64, LLUnits::Nanoseconds> U64Nanoseconds; +typedef LLUnitImplicit<U64, LLUnits::Seconds> U64SecondsImplicit; +typedef LLUnitImplicit<U64, LLUnits::Minutes> U64MinutesImplicit; +typedef LLUnitImplicit<U64, LLUnits::Hours> U64HoursImplicit; +typedef LLUnitImplicit<U64, LLUnits::Days> U64DaysImplicit; +typedef LLUnitImplicit<U64, LLUnits::Milliseconds> U64MillisecondsImplicit; +typedef LLUnitImplicit<U64, LLUnits::Microseconds> U64MicrosecondsImplicit; +typedef LLUnitImplicit<U64, LLUnits::Nanoseconds> U64NanosecondsImplicit; + namespace LLUnits { LL_DECLARE_BASE_UNIT(Meters, "m"); @@ -824,31 +920,61 @@ typedef LLUnit<F32, LLUnits::Kilometers> F32Kilometers; typedef LLUnit<F32, LLUnits::Centimeters> F32Centimeters; typedef LLUnit<F32, LLUnits::Millimeters> F32Millimeters; +typedef LLUnitImplicit<F32, LLUnits::Meters> F32MetersImplicit; +typedef LLUnitImplicit<F32, LLUnits::Kilometers> F32KilometersImplicit; +typedef LLUnitImplicit<F32, LLUnits::Centimeters> F32CentimetersImplicit; +typedef LLUnitImplicit<F32, LLUnits::Millimeters> F32MillimetersImplicit; + typedef LLUnit<F64, LLUnits::Meters> F64Meters; typedef LLUnit<F64, LLUnits::Kilometers> F64Kilometers; typedef LLUnit<F64, LLUnits::Centimeters> F64Centimeters; typedef LLUnit<F64, LLUnits::Millimeters> F64Millimeters; +typedef LLUnitImplicit<F64, LLUnits::Meters> F64MetersImplicit; +typedef LLUnitImplicit<F64, LLUnits::Kilometers> F64KilometersImplicit; +typedef LLUnitImplicit<F64, LLUnits::Centimeters> F64CentimetersImplicit; +typedef LLUnitImplicit<F64, LLUnits::Millimeters> F64MillimetersImplicit; + typedef LLUnit<S32, LLUnits::Meters> S32Meters; typedef LLUnit<S32, LLUnits::Kilometers> S32Kilometers; typedef LLUnit<S32, LLUnits::Centimeters> S32Centimeters; typedef LLUnit<S32, LLUnits::Millimeters> S32Millimeters; -typedef LLUnit<U32, LLUnits::Meters> U32Meters; -typedef LLUnit<U32, LLUnits::Kilometers> U32Kilometers; -typedef LLUnit<U32, LLUnits::Centimeters> U32Centimeters; -typedef LLUnit<U32, LLUnits::Millimeters> U32Millimeters; +typedef LLUnitImplicit<S32, LLUnits::Meters> S32MetersImplicit; +typedef LLUnitImplicit<S32, LLUnits::Kilometers> S32KilometersImplicit; +typedef LLUnitImplicit<S32, LLUnits::Centimeters> S32CentimetersImplicit; +typedef LLUnitImplicit<S32, LLUnits::Millimeters> S32MillimetersImplicit; typedef LLUnit<S64, LLUnits::Meters> S64Meters; typedef LLUnit<S64, LLUnits::Kilometers> S64Kilometers; typedef LLUnit<S64, LLUnits::Centimeters> S64Centimeters; typedef LLUnit<S64, LLUnits::Millimeters> S64Millimeters; +typedef LLUnitImplicit<S64, LLUnits::Meters> S64MetersImplicit; +typedef LLUnitImplicit<S64, LLUnits::Kilometers> S64KilometersImplicit; +typedef LLUnitImplicit<S64, LLUnits::Centimeters> S64CentimetersImplicit; +typedef LLUnitImplicit<S64, LLUnits::Millimeters> S64MillimetersImplicit; + +typedef LLUnit<U32, LLUnits::Meters> U32Meters; +typedef LLUnit<U32, LLUnits::Kilometers> U32Kilometers; +typedef LLUnit<U32, LLUnits::Centimeters> U32Centimeters; +typedef LLUnit<U32, LLUnits::Millimeters> U32Millimeters; + +typedef LLUnitImplicit<U32, LLUnits::Meters> U32MetersImplicit; +typedef LLUnitImplicit<U32, LLUnits::Kilometers> U32KilometersImplicit; +typedef LLUnitImplicit<U32, LLUnits::Centimeters> U32CentimetersImplicit; +typedef LLUnitImplicit<U32, LLUnits::Millimeters> U32MillimetersImplicit; + typedef LLUnit<U64, LLUnits::Meters> U64Meters; typedef LLUnit<U64, LLUnits::Kilometers> U64Kilometers; typedef LLUnit<U64, LLUnits::Centimeters> U64Centimeters; typedef LLUnit<U64, LLUnits::Millimeters> U64Millimeters; +typedef LLUnitImplicit<U64, LLUnits::Meters> U64MetersImplicit; +typedef LLUnitImplicit<U64, LLUnits::Kilometers> U64KilometersImplicit; +typedef LLUnitImplicit<U64, LLUnits::Centimeters> U64CentimetersImplicit; +typedef LLUnitImplicit<U64, LLUnits::Millimeters> U64MillimetersImplicit; + namespace LLUnits { // rare units @@ -868,4 +994,137 @@ LL_DECLARE_DERIVED_UNIT(Triangles, * 1000, Kilotriangles, "ktris"); } // namespace LLUnits +// rare units +typedef LLUnit<F32, LLUnits::Hertz> F32Hertz; +typedef LLUnit<F32, LLUnits::Kilohertz> F32Kilohertz; +typedef LLUnit<F32, LLUnits::Megahertz> F32Megahertz; +typedef LLUnit<F32, LLUnits::Gigahertz> F32Gigahertz; +typedef LLUnit<F32, LLUnits::Radians> F32Radians; +typedef LLUnit<F32, LLUnits::Degrees> F32Degrees; +typedef LLUnit<F32, LLUnits::Percent> F32Percent; +typedef LLUnit<F32, LLUnits::Ratio> F32Ratio; +typedef LLUnit<F32, LLUnits::Triangles> F32Triangles; +typedef LLUnit<F32, LLUnits::Kilotriangles> F32KiloTriangles; + +typedef LLUnitImplicit<F32, LLUnits::Hertz> F32HertzImplicit; +typedef LLUnitImplicit<F32, LLUnits::Kilohertz> F32KilohertzImplicit; +typedef LLUnitImplicit<F32, LLUnits::Megahertz> F32MegahertzImplicit; +typedef LLUnitImplicit<F32, LLUnits::Gigahertz> F32GigahertzImplicit; +typedef LLUnitImplicit<F32, LLUnits::Radians> F32RadiansImplicit; +typedef LLUnitImplicit<F32, LLUnits::Degrees> F32DegreesImplicit; +typedef LLUnitImplicit<F32, LLUnits::Percent> F32PercentImplicit; +typedef LLUnitImplicit<F32, LLUnits::Ratio> F32RatioImplicit; +typedef LLUnitImplicit<F32, LLUnits::Triangles> F32TrianglesImplicit; +typedef LLUnitImplicit<F32, LLUnits::Kilotriangles> F32KiloTrianglesImplicit; + +typedef LLUnit<F64, LLUnits::Hertz> F64Hertz; +typedef LLUnit<F64, LLUnits::Kilohertz> F64Kilohertz; +typedef LLUnit<F64, LLUnits::Megahertz> F64Megahertz; +typedef LLUnit<F64, LLUnits::Gigahertz> F64Gigahertz; +typedef LLUnit<F64, LLUnits::Radians> F64Radians; +typedef LLUnit<F64, LLUnits::Degrees> F64Degrees; +typedef LLUnit<F64, LLUnits::Percent> F64Percent; +typedef LLUnit<F64, LLUnits::Ratio> F64Ratio; +typedef LLUnit<F64, LLUnits::Triangles> F64Triangles; +typedef LLUnit<F64, LLUnits::Kilotriangles> F64KiloTriangles; + +typedef LLUnitImplicit<F64, LLUnits::Hertz> F64HertzImplicit; +typedef LLUnitImplicit<F64, LLUnits::Kilohertz> F64KilohertzImplicit; +typedef LLUnitImplicit<F64, LLUnits::Megahertz> F64MegahertzImplicit; +typedef LLUnitImplicit<F64, LLUnits::Gigahertz> F64GigahertzImplicit; +typedef LLUnitImplicit<F64, LLUnits::Radians> F64RadiansImplicit; +typedef LLUnitImplicit<F64, LLUnits::Degrees> F64DegreesImplicit; +typedef LLUnitImplicit<F64, LLUnits::Percent> F64PercentImplicit; +typedef LLUnitImplicit<F64, LLUnits::Ratio> F64RatioImplicit; +typedef LLUnitImplicit<F64, LLUnits::Triangles> F64TrianglesImplicit; +typedef LLUnitImplicit<F64, LLUnits::Kilotriangles> F64KiloTrianglesImplicit; + +typedef LLUnit<S32, LLUnits::Hertz> S32Hertz; +typedef LLUnit<S32, LLUnits::Kilohertz> S32Kilohertz; +typedef LLUnit<S32, LLUnits::Megahertz> S32Megahertz; +typedef LLUnit<S32, LLUnits::Gigahertz> S32Gigahertz; +typedef LLUnit<S32, LLUnits::Radians> S32Radians; +typedef LLUnit<S32, LLUnits::Degrees> S32Degrees; +typedef LLUnit<S32, LLUnits::Percent> S32Percent; +typedef LLUnit<S32, LLUnits::Ratio> S32Ratio; +typedef LLUnit<S32, LLUnits::Triangles> S32Triangles; +typedef LLUnit<S32, LLUnits::Kilotriangles> S32KiloTriangles; + +typedef LLUnitImplicit<S32, LLUnits::Hertz> S32HertzImplicit; +typedef LLUnitImplicit<S32, LLUnits::Kilohertz> S32KilohertzImplicit; +typedef LLUnitImplicit<S32, LLUnits::Megahertz> S32MegahertzImplicit; +typedef LLUnitImplicit<S32, LLUnits::Gigahertz> S32GigahertzImplicit; +typedef LLUnitImplicit<S32, LLUnits::Radians> S32RadiansImplicit; +typedef LLUnitImplicit<S32, LLUnits::Degrees> S32DegreesImplicit; +typedef LLUnitImplicit<S32, LLUnits::Percent> S32PercentImplicit; +typedef LLUnitImplicit<S32, LLUnits::Ratio> S32RatioImplicit; +typedef LLUnitImplicit<S32, LLUnits::Triangles> S32TrianglesImplicit; +typedef LLUnitImplicit<S32, LLUnits::Kilotriangles> S32KiloTrianglesImplicit; + +typedef LLUnit<S64, LLUnits::Hertz> S64Hertz; +typedef LLUnit<S64, LLUnits::Kilohertz> S64Kilohertz; +typedef LLUnit<S64, LLUnits::Megahertz> S64Megahertz; +typedef LLUnit<S64, LLUnits::Gigahertz> S64Gigahertz; +typedef LLUnit<S64, LLUnits::Radians> S64Radians; +typedef LLUnit<S64, LLUnits::Degrees> S64Degrees; +typedef LLUnit<S64, LLUnits::Percent> S64Percent; +typedef LLUnit<S64, LLUnits::Ratio> S64Ratio; +typedef LLUnit<S64, LLUnits::Triangles> S64Triangles; +typedef LLUnit<S64, LLUnits::Kilotriangles> S64KiloTriangles; + +typedef LLUnitImplicit<S64, LLUnits::Hertz> S64HertzImplicit; +typedef LLUnitImplicit<S64, LLUnits::Kilohertz> S64KilohertzImplicit; +typedef LLUnitImplicit<S64, LLUnits::Megahertz> S64MegahertzImplicit; +typedef LLUnitImplicit<S64, LLUnits::Gigahertz> S64GigahertzImplicit; +typedef LLUnitImplicit<S64, LLUnits::Radians> S64RadiansImplicit; +typedef LLUnitImplicit<S64, LLUnits::Degrees> S64DegreesImplicit; +typedef LLUnitImplicit<S64, LLUnits::Percent> S64PercentImplicit; +typedef LLUnitImplicit<S64, LLUnits::Ratio> S64RatioImplicit; +typedef LLUnitImplicit<S64, LLUnits::Triangles> S64TrianglesImplicit; +typedef LLUnitImplicit<S64, LLUnits::Kilotriangles> S64KiloTrianglesImplicit; + +typedef LLUnit<U32, LLUnits::Hertz> U32Hertz; +typedef LLUnit<U32, LLUnits::Kilohertz> U32Kilohertz; +typedef LLUnit<U32, LLUnits::Megahertz> U32Megahertz; +typedef LLUnit<U32, LLUnits::Gigahertz> U32Gigahertz; +typedef LLUnit<U32, LLUnits::Radians> U32Radians; +typedef LLUnit<U32, LLUnits::Degrees> U32Degrees; +typedef LLUnit<U32, LLUnits::Percent> U32Percent; +typedef LLUnit<U32, LLUnits::Ratio> U32Ratio; +typedef LLUnit<U32, LLUnits::Triangles> U32Triangles; +typedef LLUnit<U32, LLUnits::Kilotriangles> U32KiloTriangles; + +typedef LLUnitImplicit<U32, LLUnits::Hertz> U32HertzImplicit; +typedef LLUnitImplicit<U32, LLUnits::Kilohertz> U32KilohertzImplicit; +typedef LLUnitImplicit<U32, LLUnits::Megahertz> U32MegahertzImplicit; +typedef LLUnitImplicit<U32, LLUnits::Gigahertz> U32GigahertzImplicit; +typedef LLUnitImplicit<U32, LLUnits::Radians> U32RadiansImplicit; +typedef LLUnitImplicit<U32, LLUnits::Degrees> U32DegreesImplicit; +typedef LLUnitImplicit<U32, LLUnits::Percent> U32PercentImplicit; +typedef LLUnitImplicit<U32, LLUnits::Ratio> U32RatioImplicit; +typedef LLUnitImplicit<U32, LLUnits::Triangles> U32TrianglesImplicit; +typedef LLUnitImplicit<U32, LLUnits::Kilotriangles> U32KiloTrianglesImplicit; + +typedef LLUnit<U64, LLUnits::Hertz> U64Hertz; +typedef LLUnit<U64, LLUnits::Kilohertz> U64Kilohertz; +typedef LLUnit<U64, LLUnits::Megahertz> U64Megahertz; +typedef LLUnit<U64, LLUnits::Gigahertz> U64Gigahertz; +typedef LLUnit<U64, LLUnits::Radians> U64Radians; +typedef LLUnit<U64, LLUnits::Degrees> U64Degrees; +typedef LLUnit<U64, LLUnits::Percent> U64Percent; +typedef LLUnit<U64, LLUnits::Ratio> U64Ratio; +typedef LLUnit<U64, LLUnits::Triangles> U64Triangles; +typedef LLUnit<U64, LLUnits::Kilotriangles> U64KiloTriangles; + +typedef LLUnitImplicit<U64, LLUnits::Hertz> U64HertzImplicit; +typedef LLUnitImplicit<U64, LLUnits::Kilohertz> U64KilohertzImplicit; +typedef LLUnitImplicit<U64, LLUnits::Megahertz> U64MegahertzImplicit; +typedef LLUnitImplicit<U64, LLUnits::Gigahertz> U64GigahertzImplicit; +typedef LLUnitImplicit<U64, LLUnits::Radians> U64RadiansImplicit; +typedef LLUnitImplicit<U64, LLUnits::Degrees> U64DegreesImplicit; +typedef LLUnitImplicit<U64, LLUnits::Percent> U64PercentImplicit; +typedef LLUnitImplicit<U64, LLUnits::Ratio> U64RatioImplicit; +typedef LLUnitImplicit<U64, LLUnits::Triangles> U64TrianglesImplicit; +typedef LLUnitImplicit<U64, LLUnits::Kilotriangles> U64KiloTrianglesImplicit; + #endif // LL_LLUNIT_H diff --git a/indra/llcommon/tests/llunits_test.cpp b/indra/llcommon/tests/llunits_test.cpp index 8546bcbc54..a8e9be86ca 100644 --- a/indra/llcommon/tests/llunits_test.cpp +++ b/indra/llcommon/tests/llunits_test.cpp @@ -38,6 +38,13 @@ namespace LLUnits LL_DECLARE_DERIVED_UNIT(Latinum, / 16, Solari, "Sol"); } +typedef LLUnit<F32, LLUnits::Quatloos> F32Quatloos; +typedef LLUnit<S32, LLUnits::Quatloos> S32Quatloos; +typedef LLUnit<F32, LLUnits::Latinum> F32Latinum; +typedef LLUnit<S32, LLUnits::Latinum> S32Latinum; +typedef LLUnit<F32, LLUnits::Solari> F32Solari; +typedef LLUnit<S32, LLUnits::Solari> S32Solari; + namespace tut { using namespace LLUnits; @@ -54,28 +61,28 @@ namespace tut void units_object_t::test<1>() { LLUnit<F32, Quatloos> float_quatloos; - ensure("default float unit is zero", float_quatloos == 0.f); + ensure("default float unit is zero", float_quatloos == F32Quatloos(0.f)); LLUnit<F32, Quatloos> float_initialize_quatloos(1); - ensure("non-zero initialized unit", float_initialize_quatloos == 1.f); + ensure("non-zero initialized unit", float_initialize_quatloos == F32Quatloos(1.f)); LLUnit<S32, Quatloos> int_quatloos; - ensure("default int unit is zero", int_quatloos == 0); + ensure("default int unit is zero", int_quatloos == S32Quatloos(0)); - int_quatloos = 42; - ensure("int assignment is preserved", int_quatloos == 42); + int_quatloos = S32Quatloos(42); + ensure("int assignment is preserved", int_quatloos == S32Quatloos(42)); float_quatloos = int_quatloos; - ensure("float assignment from int preserves value", float_quatloos == 42.f); + ensure("float assignment from int preserves value", float_quatloos == F32Quatloos(42.f)); int_quatloos = float_quatloos; - ensure("int assignment from float preserves value", int_quatloos == 42); + ensure("int assignment from float preserves value", int_quatloos == S32Quatloos(42)); - float_quatloos = 42.1f; + float_quatloos = F32Quatloos(42.1f); int_quatloos = float_quatloos; - ensure("int units truncate float units on assignment", int_quatloos == 42); + ensure("int units truncate float units on assignment", int_quatloos == S32Quatloos(42)); LLUnit<U32, Quatloos> unsigned_int_quatloos(float_quatloos); - ensure("unsigned int can be initialized from signed int", unsigned_int_quatloos == 42); + ensure("unsigned int can be initialized from signed int", unsigned_int_quatloos == S32Quatloos(42)); } // conversions to/from base unit @@ -84,15 +91,15 @@ namespace tut { LLUnit<F32, Quatloos> quatloos(1.f); LLUnit<F32, Latinum> latinum_bars(quatloos); - ensure("conversion between units is automatic via initialization", latinum_bars == 1.f / 4.f); + ensure("conversion between units is automatic via initialization", latinum_bars == F32Latinum(1.f / 4.f)); - latinum_bars = 256; + latinum_bars = S32Latinum(256); quatloos = latinum_bars; - ensure("conversion between units is automatic via assignment, and bidirectional", quatloos == 1024); + ensure("conversion between units is automatic via assignment, and bidirectional", quatloos == S32Quatloos(1024)); LLUnit<S32, Quatloos> single_quatloo(1); LLUnit<F32, Latinum> quarter_latinum = single_quatloo; - ensure("division of integer unit preserves fractional values when converted to float unit", quarter_latinum == 0.25f); + ensure("division of integer unit preserves fractional values when converted to float unit", quarter_latinum == F32Latinum(0.25f)); } // conversions across non-base units @@ -101,10 +108,10 @@ namespace tut { LLUnit<F32, Quatloos> quatloos(1024); LLUnit<F32, Solari> solari(quatloos); - ensure("conversions can work between indirectly related units: Quatloos -> Latinum -> Solari", solari == 4096); + ensure("conversions can work between indirectly related units: Quatloos -> Latinum -> Solari", solari == S32Solari(4096)); LLUnit<F32, Latinum> latinum_bars = solari; - ensure("Non base units can be converted between each other", latinum_bars == 256); + ensure("Non base units can be converted between each other", latinum_bars == S32Latinum(256)); } // math operations @@ -114,36 +121,36 @@ namespace tut // exercise math operations LLUnit<F32, Quatloos> quatloos(1.f); quatloos *= 4.f; - ensure(quatloos == 4); + ensure(quatloos == S32Quatloos(4)); quatloos = quatloos * 2; - ensure(quatloos == 8); + ensure(quatloos == S32Quatloos(8)); quatloos = 2.f * quatloos; - ensure(quatloos == 16); - - quatloos += 4.f; - ensure(quatloos == 20); - quatloos += 4; - ensure(quatloos == 24); - quatloos = quatloos + 4; - ensure(quatloos == 28); - quatloos = 4 + quatloos; - ensure(quatloos == 32); + ensure(quatloos == S32Quatloos(16)); + + quatloos += F32Quatloos(4.f); + ensure(quatloos == S32Quatloos(20)); + quatloos += S32Quatloos(4); + ensure(quatloos == S32Quatloos(24)); + quatloos = quatloos + S32Quatloos(4); + ensure(quatloos == S32Quatloos(28)); + quatloos = S32Quatloos(4) + quatloos; + ensure(quatloos == S32Quatloos(32)); quatloos += quatloos * 3; - ensure(quatloos == 128); + ensure(quatloos == S32Quatloos(128)); quatloos -= quatloos / 4 * 3; - ensure(quatloos == 32); - quatloos = quatloos - 8; - ensure(quatloos == 24); - quatloos -= 4; - ensure(quatloos == 20); - quatloos -= 4.f; - ensure(quatloos == 16); + ensure(quatloos == S32Quatloos(32)); + quatloos = quatloos - S32Quatloos(8); + ensure(quatloos == S32Quatloos(24)); + quatloos -= S32Quatloos(4); + ensure(quatloos == S32Quatloos(20)); + quatloos -= F32Quatloos(4.f); + ensure(quatloos == S32Quatloos(16)); quatloos /= 2.f; - ensure(quatloos == 8); + ensure(quatloos == S32Quatloos(8)); quatloos = quatloos / 4; - ensure(quatloos == 2); + ensure(quatloos == S32Quatloos(2)); F32 ratio = quatloos / LLUnit<F32, Quatloos>(2.f); ensure(ratio == 1); @@ -151,23 +158,54 @@ namespace tut ensure(ratio == 1); quatloos += LLUnit<F32, Solari>(8.f); - ensure(quatloos == 4); + ensure(quatloos == S32Quatloos(4)); quatloos -= LLUnit<F32, Latinum>(1.f); - ensure(quatloos == 0); + ensure(quatloos == S32Quatloos(0)); } - // implicit units + // comparison operators template<> template<> void units_object_t::test<5>() { + LLUnit<S32, Quatloos> quatloos(1); + ensure("can perform less than comparison against same type", quatloos < S32Quatloos(2)); + ensure("can perform less than comparison against different storage type", quatloos < F32Quatloos(2.f)); + ensure("can perform less than comparison against different units", quatloos < S32Latinum(5)); + ensure("can perform less than comparison against different storage type and units", quatloos < F32Latinum(5.f)); + + ensure("can perform greater than comparison against same type", quatloos > S32Quatloos(0)); + ensure("can perform greater than comparison against different storage type", quatloos > F32Quatloos(0.f)); + ensure("can perform greater than comparison against different units", quatloos > S32Latinum(0)); + ensure("can perform greater than comparison against different storage type and units", quatloos > F32Latinum(0.f)); + + } + + bool accept_explicit_quatloos(S32Quatloos q) + { + return true; + } + + // signature compatibility + template<> template<> + void units_object_t::test<6>() + { + S32Quatloos quatloos(1); + ensure("can pass unit values as argument", accept_explicit_quatloos(S32Quatloos(1))); + ensure("can pass unit values as argument", accept_explicit_quatloos(quatloos)); + } + + // implicit units + template<> template<> + void units_object_t::test<7>() + { LLUnit<F32, Quatloos> quatloos; - LLUnitImplicit<F32, Quatloos> quatloos_implicit = quatloos + 1; + LLUnitImplicit<F32, Quatloos> quatloos_implicit = quatloos + S32Quatloos(1); ensure("can initialize implicit unit from explicit", quatloos_implicit == 1); quatloos = quatloos_implicit; - ensure("can assign implicit unit to explicit unit", quatloos == 1); + ensure("can assign implicit unit to explicit unit", quatloos == S32Quatloos(1)); quatloos += quatloos_implicit; - ensure("can perform math operation using mixture of implicit and explicit units", quatloos == 2); + ensure("can perform math operation using mixture of implicit and explicit units", quatloos == S32Quatloos(2)); // math operations on implicits quatloos_implicit = 1; |