Merge pull request #1907 from elfprince13/osxDedeprecation

OSX de-deprecation (profiler and macFileIO)
This commit is contained in:
Areloch 2017-01-31 09:46:44 -06:00 committed by GitHub
commit 87c9fce380
5 changed files with 223 additions and 199 deletions

View file

@ -491,10 +491,11 @@ template<class T> T ReservedSocketList<T>::resolve(NetSocket socketToResolve)
EntryType &entry = mSocketList[socketToResolve.getHandle()]; EntryType &entry = mSocketList[socketToResolve.getHandle()];
return entry.used ? entry.value : -1; return entry.used ? entry.value : -1;
} }
ConnectionNotifyEvent* Net::smConnectionNotify = NULL;
ConnectionAcceptedEvent* Net::smConnectionAccept = NULL; static ConnectionNotifyEvent* smConnectionNotify = NULL;
ConnectionReceiveEvent* Net::smConnectionReceive = NULL; static ConnectionAcceptedEvent* smConnectionAccept = NULL;
PacketReceiveEvent* Net::smPacketReceive = NULL; static ConnectionReceiveEvent* smConnectionReceive = NULL;
static PacketReceiveEvent* smPacketReceive = NULL;
ConnectionNotifyEvent& Net::getConnectionNotifyEvent() ConnectionNotifyEvent& Net::getConnectionNotifyEvent()
{ {

View file

@ -214,13 +214,12 @@ struct Net
static bool smMulticastEnabled; static bool smMulticastEnabled;
static bool smIpv4Enabled; static bool smIpv4Enabled;
static bool smIpv6Enabled; static bool smIpv6Enabled;
static ConnectionNotifyEvent* smConnectionNotify; static ConnectionNotifyEvent* smConnectionNotify;
static ConnectionAcceptedEvent* smConnectionAccept; static ConnectionAcceptedEvent* smConnectionAccept;
static ConnectionReceiveEvent* smConnectionReceive; static ConnectionReceiveEvent* smConnectionReceive;
static PacketReceiveEvent* smPacketReceive; static PacketReceiveEvent* smPacketReceive;
static bool init(); static bool init();
static void shutdown(); static void shutdown();

View file

@ -27,7 +27,7 @@
#endif #endif
#if defined(TORQUE_OS_MAC) #if defined(TORQUE_OS_MAC)
#include <CoreServices/CoreServices.h> // For high resolution timer #include <mach/mach_time.h>
#endif #endif
#include "core/stream/fileStream.h" #include "core/stream/fileStream.h"
@ -48,15 +48,15 @@ Profiler *gProfiler = NULL;
//#define TORQUE_PROFILER_DEBUG //#define TORQUE_PROFILER_DEBUG
// Machinery to record the stack of node names, as a debugging aid to find // Machinery to record the stack of node names, as a debugging aid to find
// mismatched PROFILE_START and PROFILE_END blocks. We profile from the // mismatched PROFILE_START and PROFILE_END blocks. We profile from the
// beginning to catch profile block errors that occur when torque is starting up. // beginning to catch profile block errors that occur when torque is starting up.
#ifdef TORQUE_PROFILER_DEBUG #ifdef TORQUE_PROFILER_DEBUG
Vector<StringTableEntry> gProfilerNodeStack; Vector<StringTableEntry> gProfilerNodeStack;
#define TORQUE_PROFILE_AT_ENGINE_START true #define TORQUE_PROFILE_AT_ENGINE_START true
#define PROFILER_DEBUG_PUSH_NODE( nodename ) \ #define PROFILER_DEBUG_PUSH_NODE( nodename ) \
gProfilerNodeStack.push_back( nodename ); gProfilerNodeStack.push_back( nodename );
#define PROFILER_DEBUG_POP_NODE() \ #define PROFILER_DEBUG_POP_NODE() \
gProfilerNodeStack.pop_back(); gProfilerNodeStack.pop_back();
#else #else
#define TORQUE_PROFILE_AT_ENGINE_START false #define TORQUE_PROFILE_AT_ENGINE_START false
#define PROFILER_DEBUG_PUSH_NODE( nodename ) ; #define PROFILER_DEBUG_PUSH_NODE( nodename ) ;
@ -68,7 +68,7 @@ Vector<StringTableEntry> gProfilerNodeStack;
void startHighResolutionTimer(U32 time[2]) void startHighResolutionTimer(U32 time[2])
{ {
//time[0] = Platform::getRealMilliseconds(); //time[0] = Platform::getRealMilliseconds();
__asm __asm
{ {
push eax push eax
@ -89,7 +89,7 @@ U32 endHighResolutionTimer(U32 time[2])
U32 ticks; U32 ticks;
//ticks = Platform::getRealMilliseconds() - time[0]; //ticks = Platform::getRealMilliseconds() - time[0];
//return ticks; //return ticks;
__asm __asm
{ {
push eax push eax
@ -135,20 +135,26 @@ U32 endHighResolutionTimer(U32 time[2])
void startHighResolutionTimer(U32 time[2]) { void startHighResolutionTimer(U32 time[2]) {
UnsignedWide t; U64 now = mach_absolute_time();
Microseconds(&t); AssertFatal(sizeof(U32[2]) == sizeof(U64), "Can't pack mach_absolute_time into U32[2]");
time[0] = t.lo; memcpy(time, &now, sizeof(U64));
time[1] = t.hi;
} }
U32 endHighResolutionTimer(U32 time[2]) { U32 endHighResolutionTimer(U32 time[2]) {
UnsignedWide t; static mach_timebase_info_data_t sTimebaseInfo = {0, 0};
Microseconds(&t);
return t.lo - time[0]; U64 now = mach_absolute_time();
// given that we're returning a 32 bit integer, and this is unsigned subtraction... AssertFatal(sizeof(U32[2]) == sizeof(U64), "Can't pack mach_absolute_time into U32[2]");
// it will just wrap around, we don't need the upper word of the time. U64 then;
// NOTE: the code assumes that more than 3 hrs will not go by between calls to startHighResolutionTimer() and endHighResolutionTimer(). memcpy(&then, time, sizeof(U64));
// I mean... that damn well better not happen anyway.
if(sTimebaseInfo.denom == 0){
mach_timebase_info(&sTimebaseInfo);
}
// Handle the micros/nanos conversion first, because shedding a few bits is better than overflowing.
U64 elapsedMicros = ((now - then) / 1000) * sTimebaseInfo.numer / sTimebaseInfo.denom;
return (U32)elapsedMicros; // Just truncate, and hope we didn't overflow
} }
#else #else
@ -170,7 +176,7 @@ Profiler::Profiler()
{ {
mMaxStackDepth = MaxStackDepth; mMaxStackDepth = MaxStackDepth;
mCurrentHash = 0; mCurrentHash = 0;
mCurrentProfilerData = (ProfilerData *) malloc(sizeof(ProfilerData)); mCurrentProfilerData = (ProfilerData *) malloc(sizeof(ProfilerData));
mCurrentProfilerData->mRoot = NULL; mCurrentProfilerData->mRoot = NULL;
mCurrentProfilerData->mNextForRoot = NULL; mCurrentProfilerData->mNextForRoot = NULL;
@ -185,17 +191,17 @@ Profiler::Profiler()
mCurrentProfilerData->mInvokeCount = 0; mCurrentProfilerData->mInvokeCount = 0;
mCurrentProfilerData->mTotalTime = 0; mCurrentProfilerData->mTotalTime = 0;
mCurrentProfilerData->mSubTime = 0; mCurrentProfilerData->mSubTime = 0;
#ifdef TORQUE_ENABLE_PROFILE_PATH #ifdef TORQUE_ENABLE_PROFILE_PATH
mCurrentProfilerData->mPath = ""; mCurrentProfilerData->mPath = "";
#endif #endif
mRootProfilerData = mCurrentProfilerData; mRootProfilerData = mCurrentProfilerData;
for(U32 i = 0; i < ProfilerData::HashTableSize; i++) for(U32 i = 0; i < ProfilerData::HashTableSize; i++)
mCurrentProfilerData->mChildHash[i] = 0; mCurrentProfilerData->mChildHash[i] = 0;
mProfileList = NULL; mProfileList = NULL;
mEnabled = TORQUE_PROFILE_AT_ENGINE_START; mEnabled = TORQUE_PROFILE_AT_ENGINE_START;
mNextEnable = TORQUE_PROFILE_AT_ENGINE_START; mNextEnable = TORQUE_PROFILE_AT_ENGINE_START;
mStackDepth = 0; mStackDepth = 0;
gProfiler = this; gProfiler = this;
@ -216,20 +222,20 @@ void Profiler::reset()
mEnabled = false; // in case we're in a profiler call. mEnabled = false; // in case we're in a profiler call.
ProfilerData * head = mProfileList; ProfilerData * head = mProfileList;
ProfilerData * curr = head; ProfilerData * curr = head;
while ( curr ) while ( curr )
{ {
head = curr->mNextProfilerData; head = curr->mNextProfilerData;
free( curr ); free( curr );
if ( head ) if ( head )
curr = head; curr = head;
else else
curr = NULL; curr = NULL;
} }
mProfileList = NULL; mProfileList = NULL;
for(ProfilerRootData *walk = ProfilerRootData::sRootList; walk; walk = walk->mNextRoot) for(ProfilerRootData *walk = ProfilerRootData::sRootList; walk; walk = walk->mNextRoot)
{ {
walk->mFirstProfilerData = 0; walk->mFirstProfilerData = 0;
@ -256,7 +262,7 @@ ProfilerRootData::ProfilerRootData(const char *name)
for(ProfilerRootData *walk = sRootList; walk; walk = walk->mNextRoot) for(ProfilerRootData *walk = sRootList; walk; walk = walk->mNextRoot)
if(!dStrcmp(walk->mName, name)) if(!dStrcmp(walk->mName, name))
AssertFatal( false, avar( "Duplicate profile name: %s", name ) ); AssertFatal( false, avar( "Duplicate profile name: %s", name ) );
mName = name; mName = name;
mNameHash = _StringTable::hashString(name); mNameHash = _StringTable::hashString(name);
mNextRoot = sRootList; mNextRoot = sRootList;
@ -283,7 +289,7 @@ void Profiler::validate()
if(!wk) if(!wk)
Platform::debugBreak(); Platform::debugBreak();
for(wk = dp->mParent->mChildHash[walk->mNameHash & (ProfilerData::HashTableSize - 1)] ; for(wk = dp->mParent->mChildHash[walk->mNameHash & (ProfilerData::HashTableSize - 1)] ;
wk; wk = wk->mNextHash) wk; wk = wk->mNextHash)
if(wk == dp) if(wk == dp)
break; break;
if(!wk) if(!wk)
@ -300,7 +306,7 @@ const char * Profiler::getProfilePath()
if( !ThreadManager::isMainThread() ) if( !ThreadManager::isMainThread() )
return "[non-main thread]"; return "[non-main thread]";
#endif #endif
return (mEnabled && mCurrentProfilerData) ? mCurrentProfilerData->mPath : "na"; return (mEnabled && mCurrentProfilerData) ? mCurrentProfilerData->mPath : "na";
} }
#endif #endif
@ -312,14 +318,14 @@ const char * Profiler::constructProfilePath(ProfilerData * pd)
{ {
const bool saveEnable = gProfiler->mEnabled; const bool saveEnable = gProfiler->mEnabled;
gProfiler->mEnabled = false; gProfiler->mEnabled = false;
const char * connector = " -> "; const char * connector = " -> ";
U32 len = dStrlen(pd->mParent->mPath); U32 len = dStrlen(pd->mParent->mPath);
if (!len) if (!len)
connector = ""; connector = "";
len += dStrlen(connector); len += dStrlen(connector);
len += dStrlen(pd->mRoot->mName); len += dStrlen(pd->mRoot->mName);
U32 mark = FrameAllocator::getWaterMark(); U32 mark = FrameAllocator::getWaterMark();
char * buf = (char*)FrameAllocator::alloc(len+1); char * buf = (char*)FrameAllocator::alloc(len+1);
dStrcpy(buf,pd->mParent->mPath); dStrcpy(buf,pd->mParent->mPath);
@ -342,25 +348,25 @@ void Profiler::hashPush(ProfilerRootData *root)
if( !ThreadManager::isMainThread() ) if( !ThreadManager::isMainThread() )
return; return;
#endif #endif
mStackDepth++; mStackDepth++;
PROFILER_DEBUG_PUSH_NODE(root->mName); PROFILER_DEBUG_PUSH_NODE(root->mName);
AssertFatal(mStackDepth <= mMaxStackDepth, AssertFatal(mStackDepth <= mMaxStackDepth,
"Stack overflow in profiler. You may have mismatched PROFILE_START and PROFILE_ENDs"); "Stack overflow in profiler. You may have mismatched PROFILE_START and PROFILE_ENDs");
if(!mEnabled) if(!mEnabled)
return; return;
ProfilerData *nextProfiler = NULL; ProfilerData *nextProfiler = NULL;
if(!root->mEnabled || mCurrentProfilerData->mRoot == root) if(!root->mEnabled || mCurrentProfilerData->mRoot == root)
{ {
mCurrentProfilerData->mSubDepth++; mCurrentProfilerData->mSubDepth++;
return; return;
} }
if(mCurrentProfilerData->mLastSeenProfiler && if(mCurrentProfilerData->mLastSeenProfiler &&
mCurrentProfilerData->mLastSeenProfiler->mRoot == root) mCurrentProfilerData->mLastSeenProfiler->mRoot == root)
nextProfiler = mCurrentProfilerData->mLastSeenProfiler; nextProfiler = mCurrentProfilerData->mLastSeenProfiler;
if(!nextProfiler) if(!nextProfiler)
{ {
// first see if it's in the hash table... // first see if it's in the hash table...
@ -377,17 +383,17 @@ void Profiler::hashPush(ProfilerRootData *root)
nextProfiler = (ProfilerData *) malloc(sizeof(ProfilerData)); nextProfiler = (ProfilerData *) malloc(sizeof(ProfilerData));
for(U32 i = 0; i < ProfilerData::HashTableSize; i++) for(U32 i = 0; i < ProfilerData::HashTableSize; i++)
nextProfiler->mChildHash[i] = 0; nextProfiler->mChildHash[i] = 0;
nextProfiler->mRoot = root; nextProfiler->mRoot = root;
nextProfiler->mNextForRoot = root->mFirstProfilerData; nextProfiler->mNextForRoot = root->mFirstProfilerData;
root->mFirstProfilerData = nextProfiler; root->mFirstProfilerData = nextProfiler;
nextProfiler->mNextProfilerData = mProfileList; nextProfiler->mNextProfilerData = mProfileList;
mProfileList = nextProfiler; mProfileList = nextProfiler;
nextProfiler->mNextHash = mCurrentProfilerData->mChildHash[index]; nextProfiler->mNextHash = mCurrentProfilerData->mChildHash[index];
mCurrentProfilerData->mChildHash[index] = nextProfiler; mCurrentProfilerData->mChildHash[index] = nextProfiler;
nextProfiler->mParent = mCurrentProfilerData; nextProfiler->mParent = mCurrentProfilerData;
nextProfiler->mNextSibling = mCurrentProfilerData->mFirstChild; nextProfiler->mNextSibling = mCurrentProfilerData->mFirstChild;
mCurrentProfilerData->mFirstChild = nextProfiler; mCurrentProfilerData->mFirstChild = nextProfiler;
@ -437,7 +443,7 @@ void Profiler::hashPop(ProfilerRootData *expected)
if( !ThreadManager::isMainThread() ) if( !ThreadManager::isMainThread() )
return; return;
#endif #endif
mStackDepth--; mStackDepth--;
PROFILER_DEBUG_POP_NODE(); PROFILER_DEBUG_POP_NODE();
AssertFatal(mStackDepth >= 0, "Stack underflow in profiler. You may have mismatched PROFILE_START and PROFILE_ENDs"); AssertFatal(mStackDepth >= 0, "Stack underflow in profiler. You may have mismatched PROFILE_START and PROFILE_ENDs");
@ -453,15 +459,15 @@ void Profiler::hashPop(ProfilerRootData *expected)
{ {
AssertISV(expected == mCurrentProfilerData->mRoot, "Profiler::hashPop - didn't get expected ProfilerRoot!"); AssertISV(expected == mCurrentProfilerData->mRoot, "Profiler::hashPop - didn't get expected ProfilerRoot!");
} }
F64 fElapsed = endHighResolutionTimer(mCurrentProfilerData->mStartTime); F64 fElapsed = endHighResolutionTimer(mCurrentProfilerData->mStartTime);
mCurrentProfilerData->mTotalTime += fElapsed; mCurrentProfilerData->mTotalTime += fElapsed;
mCurrentProfilerData->mParent->mSubTime += fElapsed; // mark it in the parent as well... mCurrentProfilerData->mParent->mSubTime += fElapsed; // mark it in the parent as well...
mCurrentProfilerData->mRoot->mTotalTime += fElapsed; mCurrentProfilerData->mRoot->mTotalTime += fElapsed;
if(mCurrentProfilerData->mParent->mRoot) if(mCurrentProfilerData->mParent->mRoot)
mCurrentProfilerData->mParent->mRoot->mSubTime += fElapsed; // mark it in the parent as well... mCurrentProfilerData->mParent->mRoot->mSubTime += fElapsed; // mark it in the parent as well...
mCurrentProfilerData = mCurrentProfilerData->mParent; mCurrentProfilerData = mCurrentProfilerData->mParent;
} }
if(mStackDepth == 0) if(mStackDepth == 0)
@ -474,13 +480,13 @@ void Profiler::hashPop(ProfilerRootData *expected)
} }
if(!mEnabled && mNextEnable) if(!mEnabled && mNextEnable)
startHighResolutionTimer(mCurrentProfilerData->mStartTime); startHighResolutionTimer(mCurrentProfilerData->mStartTime);
#if defined(TORQUE_OS_WIN) #if defined(TORQUE_OS_WIN)
// The high performance counters under win32 are unreliable when running on multiple // The high performance counters under win32 are unreliable when running on multiple
// processors. When the profiler is enabled, we restrict Torque to a single processor. // processors. When the profiler is enabled, we restrict Torque to a single processor.
if(mNextEnable != mEnabled) if(mNextEnable != mEnabled)
{ {
if(mNextEnable) if(mNextEnable)
{ {
Con::warnf("Warning: forcing the Torque profiler thread to run only on cpu 1."); Con::warnf("Warning: forcing the Torque profiler thread to run only on cpu 1.");
@ -496,7 +502,7 @@ void Profiler::hashPop(ProfilerRootData *expected)
} }
} }
#endif #endif
mEnabled = mNextEnable; mEnabled = mNextEnable;
} }
} }
@ -514,15 +520,15 @@ static void profilerDataDumpRecurse(ProfilerData *data, char *buffer, U32 buffer
{ {
// dump out this one: // dump out this one:
Con::printf("%7.3f %7.3f %8d %s%s", Con::printf("%7.3f %7.3f %8d %s%s",
100 * data->mTotalTime / totalTime, 100 * data->mTotalTime / totalTime,
100 * (data->mTotalTime - data->mSubTime) / totalTime, 100 * (data->mTotalTime - data->mSubTime) / totalTime,
data->mInvokeCount, data->mInvokeCount,
buffer, buffer,
data->mRoot ? data->mRoot->mName : "ROOT" ); data->mRoot ? data->mRoot->mName : "ROOT" );
data->mTotalTime = 0; data->mTotalTime = 0;
data->mSubTime = 0; data->mSubTime = 0;
data->mInvokeCount = 0; data->mInvokeCount = 0;
buffer[bufferLen] = ' '; buffer[bufferLen] = ' ';
buffer[bufferLen+1] = ' '; buffer[bufferLen+1] = ' ';
buffer[bufferLen+2] = 0; buffer[bufferLen+2] = 0;
@ -552,16 +558,16 @@ static void profilerDataDumpRecurseFile(ProfilerData *data, char *buffer, U32 bu
{ {
char pbuffer[256]; char pbuffer[256];
dSprintf(pbuffer, 255, "%7.3f %7.3f %8d %s%s\n", dSprintf(pbuffer, 255, "%7.3f %7.3f %8d %s%s\n",
100 * data->mTotalTime / totalTime, 100 * data->mTotalTime / totalTime,
100 * (data->mTotalTime - data->mSubTime) / totalTime, 100 * (data->mTotalTime - data->mSubTime) / totalTime,
data->mInvokeCount, data->mInvokeCount,
buffer, buffer,
data->mRoot ? data->mRoot->mName : "ROOT" ); data->mRoot ? data->mRoot->mName : "ROOT" );
fws.write(dStrlen(pbuffer), pbuffer); fws.write(dStrlen(pbuffer), pbuffer);
data->mTotalTime = 0; data->mTotalTime = 0;
data->mSubTime = 0; data->mSubTime = 0;
data->mInvokeCount = 0; data->mInvokeCount = 0;
buffer[bufferLen] = ' '; buffer[bufferLen] = ' ';
buffer[bufferLen+1] = ' '; buffer[bufferLen+1] = ' ';
buffer[bufferLen+2] = 0; buffer[bufferLen+2] = 0;
@ -593,7 +599,7 @@ void Profiler::dump()
mEnabled = false; mEnabled = false;
mStackDepth++; mStackDepth++;
// may have some profiled calls... gotta turn em off. // may have some profiled calls... gotta turn em off.
Vector<ProfilerRootData *> rootVector; Vector<ProfilerRootData *> rootVector;
F64 totalTime = 0; F64 totalTime = 0;
for(ProfilerRootData *walk = ProfilerRootData::sRootList; walk; walk = walk->mNextRoot) for(ProfilerRootData *walk = ProfilerRootData::sRootList; walk; walk = walk->mNextRoot)
@ -602,8 +608,8 @@ void Profiler::dump()
rootVector.push_back(walk); rootVector.push_back(walk);
} }
dQsort((void *) &rootVector[0], rootVector.size(), sizeof(ProfilerRootData *), rootDataCompare); dQsort((void *) &rootVector[0], rootVector.size(), sizeof(ProfilerRootData *), rootDataCompare);
if (mDumpToConsole == true) if (mDumpToConsole == true)
{ {
Con::printf("Profiler Data Dump:"); Con::printf("Profiler Data Dump:");
@ -612,10 +618,10 @@ void Profiler::dump()
for(U32 i = 0; i < rootVector.size(); i++) for(U32 i = 0; i < rootVector.size(); i++)
{ {
Con::printf("%7.3f %7.3f %8d %s", Con::printf("%7.3f %7.3f %8d %s",
100 * (rootVector[i]->mTotalTime - rootVector[i]->mSubTime) / totalTime, 100 * (rootVector[i]->mTotalTime - rootVector[i]->mSubTime) / totalTime,
100 * rootVector[i]->mTotalTime / totalTime, 100 * rootVector[i]->mTotalTime / totalTime,
rootVector[i]->mTotalInvokeCount, rootVector[i]->mTotalInvokeCount,
rootVector[i]->mName); rootVector[i]->mName);
rootVector[i]->mTotalInvokeCount = 0; rootVector[i]->mTotalInvokeCount = 0;
rootVector[i]->mTotalTime = 0; rootVector[i]->mTotalTime = 0;
rootVector[i]->mSubTime = 0; rootVector[i]->mSubTime = 0;
@ -623,9 +629,9 @@ void Profiler::dump()
Con::printf(""); Con::printf("");
Con::printf("Ordered by stack trace total time -"); Con::printf("Ordered by stack trace total time -");
Con::printf("%% Time %% NSTime Invoke # Name"); Con::printf("%% Time %% NSTime Invoke # Name");
mCurrentProfilerData->mTotalTime = endHighResolutionTimer(mCurrentProfilerData->mStartTime); mCurrentProfilerData->mTotalTime = endHighResolutionTimer(mCurrentProfilerData->mStartTime);
char depthBuffer[MaxStackDepth * 2 + 1]; char depthBuffer[MaxStackDepth * 2 + 1];
depthBuffer[0] = 0; depthBuffer[0] = 0;
profilerDataDumpRecurse(mCurrentProfilerData, depthBuffer, 0, totalTime); profilerDataDumpRecurse(mCurrentProfilerData, depthBuffer, 0, totalTime);
@ -637,44 +643,44 @@ void Profiler::dump()
FileStream fws; FileStream fws;
bool success = fws.open(mDumpFileName, Torque::FS::File::Write); bool success = fws.open(mDumpFileName, Torque::FS::File::Write);
AssertFatal(success, "Cannot write profile dump to specified file!"); AssertFatal(success, "Cannot write profile dump to specified file!");
char buffer[1024]; char buffer[1024];
dStrcpy(buffer, "Profiler Data Dump:\n"); dStrcpy(buffer, "Profiler Data Dump:\n");
fws.write(dStrlen(buffer), buffer);
dStrcpy(buffer, "Ordered by non-sub total time -\n");
fws.write(dStrlen(buffer), buffer);
dStrcpy(buffer, "%%NSTime %% Time Invoke # Name\n");
fws.write(dStrlen(buffer), buffer);
for(U32 i = 0; i < rootVector.size(); i++)
{
dSprintf(buffer, 1023, "%7.3f %7.3f %8d %s\n",
100 * (rootVector[i]->mTotalTime - rootVector[i]->mSubTime) / totalTime,
100 * rootVector[i]->mTotalTime / totalTime,
rootVector[i]->mTotalInvokeCount,
rootVector[i]->mName);
fws.write(dStrlen(buffer), buffer); fws.write(dStrlen(buffer), buffer);
dStrcpy(buffer, "Ordered by non-sub total time -\n");
fws.write(dStrlen(buffer), buffer); rootVector[i]->mTotalInvokeCount = 0;
dStrcpy(buffer, "%%NSTime %% Time Invoke # Name\n"); rootVector[i]->mTotalTime = 0;
fws.write(dStrlen(buffer), buffer); rootVector[i]->mSubTime = 0;
}
for(U32 i = 0; i < rootVector.size(); i++) dStrcpy(buffer, "\nOrdered by non-sub total time -\n");
{ fws.write(dStrlen(buffer), buffer);
dSprintf(buffer, 1023, "%7.3f %7.3f %8d %s\n", dStrcpy(buffer, "%%NSTime %% Time Invoke # Name\n");
100 * (rootVector[i]->mTotalTime - rootVector[i]->mSubTime) / totalTime, fws.write(dStrlen(buffer), buffer);
100 * rootVector[i]->mTotalTime / totalTime,
rootVector[i]->mTotalInvokeCount,
rootVector[i]->mName);
fws.write(dStrlen(buffer), buffer);
rootVector[i]->mTotalInvokeCount = 0;
rootVector[i]->mTotalTime = 0;
rootVector[i]->mSubTime = 0;
}
dStrcpy(buffer, "\nOrdered by non-sub total time -\n");
fws.write(dStrlen(buffer), buffer);
dStrcpy(buffer, "%%NSTime %% Time Invoke # Name\n");
fws.write(dStrlen(buffer), buffer);
mCurrentProfilerData->mTotalTime = endHighResolutionTimer(mCurrentProfilerData->mStartTime); mCurrentProfilerData->mTotalTime = endHighResolutionTimer(mCurrentProfilerData->mStartTime);
char depthBuffer[MaxStackDepth * 2 + 1]; char depthBuffer[MaxStackDepth * 2 + 1];
depthBuffer[0] = 0; depthBuffer[0] = 0;
profilerDataDumpRecurseFile(mCurrentProfilerData, depthBuffer, 0, totalTime, fws); profilerDataDumpRecurseFile(mCurrentProfilerData, depthBuffer, 0, totalTime, fws);
mEnabled = enableSave; mEnabled = enableSave;
mStackDepth--; mStackDepth--;
fws.close(); fws.close();
} }
mDumpToConsole = false; mDumpToConsole = false;
mDumpToFile = false; mDumpToFile = false;
mDumpFileName[0] = '\0'; mDumpFileName[0] = '\0';
@ -709,13 +715,13 @@ void Profiler::enableMarker(const char *marker, bool enable)
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
DefineEngineFunction( profilerMarkerEnable, void, ( const char* markerName, bool enable ), ( true ), DefineEngineFunction( profilerMarkerEnable, void, ( const char* markerName, bool enable ), ( true ),
"@brief Enable or disable a specific profile.\n\n" "@brief Enable or disable a specific profile.\n\n"
"@param enable Optional paramater to enable or disable the profile.\n" "@param enable Optional paramater to enable or disable the profile.\n"
"@param markerName Name of a specific marker to enable or disable.\n" "@param markerName Name of a specific marker to enable or disable.\n"
"@note Calling this function will first call profilerReset(), clearing all data from profiler. " "@note Calling this function will first call profilerReset(), clearing all data from profiler. "
"All profile markers are enabled by default.\n\n" "All profile markers are enabled by default.\n\n"
"@ingroup Debugging") "@ingroup Debugging")
{ {
if( gProfiler ) if( gProfiler )
gProfiler->enableMarker( markerName, enable ); gProfiler->enableMarker( markerName, enable );
@ -724,37 +730,37 @@ DefineEngineFunction( profilerMarkerEnable, void, ( const char* markerName, bool
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
DefineEngineFunction( profilerEnable, void, ( bool enable ),, DefineEngineFunction( profilerEnable, void, ( bool enable ),,
"@brief Enables or disables the profiler.\n\n" "@brief Enables or disables the profiler.\n\n"
"Data is only gathered while the profiler is enabled.\n\n" "Data is only gathered while the profiler is enabled.\n\n"
"@note Profiler is not available in shipping builds.\n" "@note Profiler is not available in shipping builds.\n"
"T3D has predefined profiling areas surrounded by markers, " "T3D has predefined profiling areas surrounded by markers, "
"but you may need to define additional markers (in C++) around areas you wish to profile," "but you may need to define additional markers (in C++) around areas you wish to profile,"
" by using the PROFILE_START( markerName ); and PROFILE_END(); macros.\n\n" " by using the PROFILE_START( markerName ); and PROFILE_END(); macros.\n\n"
"@ingroup Debugging\n" ) "@ingroup Debugging\n" )
{ {
if(gProfiler) if(gProfiler)
gProfiler->enable(enable); gProfiler->enable(enable);
} }
DefineEngineFunction(profilerDump, void, (),, DefineEngineFunction(profilerDump, void, (),,
"@brief Dumps current profiling stats to the console window.\n\n" "@brief Dumps current profiling stats to the console window.\n\n"
"@note Markers disabled with profilerMarkerEnable() will be skipped over. " "@note Markers disabled with profilerMarkerEnable() will be skipped over. "
"If the profiler is currently running, it will be disabled.\n" "If the profiler is currently running, it will be disabled.\n"
"@ingroup Debugging") "@ingroup Debugging")
{ {
if(gProfiler) if(gProfiler)
gProfiler->dumpToConsole(); gProfiler->dumpToConsole();
} }
DefineEngineFunction( profilerDumpToFile, void, ( const char* fileName ),, DefineEngineFunction( profilerDumpToFile, void, ( const char* fileName ),,
"@brief Dumps current profiling stats to a file.\n\n" "@brief Dumps current profiling stats to a file.\n\n"
"@note If the profiler is currently running, it will be disabled.\n" "@note If the profiler is currently running, it will be disabled.\n"
"@param fileName Name and path of file to save profiling stats to. Must use forward slashes (/). " "@param fileName Name and path of file to save profiling stats to. Must use forward slashes (/). "
"Will attempt to create the file if it does not already exist.\n" "Will attempt to create the file if it does not already exist.\n"
"@tsexample\n" "@tsexample\n"
"profilerDumpToFile( \"C:/Torque/log1.txt\" );\n" "profilerDumpToFile( \"C:/Torque/log1.txt\" );\n"
"@endtsexample\n\n" "@endtsexample\n\n"
"@ingroup Debugging" ) "@ingroup Debugging" )
{ {
if(gProfiler) if(gProfiler)
gProfiler->dumpToFile(fileName); gProfiler->dumpToFile(fileName);
@ -762,9 +768,9 @@ DefineEngineFunction( profilerDumpToFile, void, ( const char* fileName ),,
DefineEngineFunction( profilerReset, void, (),, DefineEngineFunction( profilerReset, void, (),,
"@brief Resets the profiler, clearing it of all its data.\n\n" "@brief Resets the profiler, clearing it of all its data.\n\n"
"If the profiler is currently running, it will first be disabled. " "If the profiler is currently running, it will first be disabled. "
"All markers will retain their current enabled/disabled status.\n\n" "All markers will retain their current enabled/disabled status.\n\n"
"@ingroup Debugging" ) "@ingroup Debugging" )
{ {
if(gProfiler) if(gProfiler)
gProfiler->reset(); gProfiler->reset();

View file

@ -76,8 +76,8 @@ TEST(Net, TCPRequest)
handler.mDataReceived = 0; handler.mDataReceived = 0;
// Hook into the signals. // Hook into the signals.
Net::smConnectionNotify ->notify(&handler, &TcpHandle::notify); Net::smConnectionNotify .notify(&handler, &TcpHandle::notify);
Net::smConnectionReceive->notify(&handler, &TcpHandle::receive); Net::smConnectionReceive.notify(&handler, &TcpHandle::receive);
// Open a TCP connection to garagegames.com // Open a TCP connection to garagegames.com
handler.mSocket = Net::openConnectTo("72.246.107.193:80"); handler.mSocket = Net::openConnectTo("72.246.107.193:80");
@ -85,8 +85,8 @@ TEST(Net, TCPRequest)
while(Process::processEvents() && (Platform::getRealMilliseconds() < limit) ) {} while(Process::processEvents() && (Platform::getRealMilliseconds() < limit) ) {}
// Unhook from the signals. // Unhook from the signals.
Net::smConnectionNotify ->remove(&handler, &TcpHandle::notify); Net::smConnectionNotify .remove(&handler, &TcpHandle::notify);
Net::smConnectionReceive->remove(&handler, &TcpHandle::receive); Net::smConnectionReceive.remove(&handler, &TcpHandle::receive);
EXPECT_GT(handler.mDataReceived, 0) EXPECT_GT(handler.mDataReceived, 0)
<< "Didn't get any data back!"; << "Didn't get any data back!";
@ -139,8 +139,8 @@ struct JournalHandle
mDataReceived = 0; mDataReceived = 0;
// Hook into the signals. // Hook into the signals.
Net::smConnectionNotify ->notify(this, &JournalHandle::notify); Net::smConnectionNotify .notify(this, &JournalHandle::notify);
Net::smConnectionReceive->notify(this, &JournalHandle::receive); Net::smConnectionReceive.notify(this, &JournalHandle::receive);
// Open a TCP connection to garagegames.com // Open a TCP connection to garagegames.com
mSocket = Net::openConnectTo("72.246.107.193:80"); mSocket = Net::openConnectTo("72.246.107.193:80");
@ -149,8 +149,8 @@ struct JournalHandle
while(Process::processEvents()) {} while(Process::processEvents()) {}
// Unhook from the signals. // Unhook from the signals.
Net::smConnectionNotify ->remove(this, &JournalHandle::notify); Net::smConnectionNotify .remove(this, &JournalHandle::notify);
Net::smConnectionReceive->remove(this, &JournalHandle::receive); Net::smConnectionReceive.remove(this, &JournalHandle::receive);
EXPECT_GT(mDataReceived, 0) EXPECT_GT(mDataReceived, 0)
<< "Didn't get any data back!"; << "Didn't get any data back!";

View file

@ -68,46 +68,54 @@ bool dFileTouch(const char *path)
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
bool dPathCopy(const char* source, const char* dest, bool nooverwrite) bool dPathCopy(const char* source, const char* dest, bool nooverwrite)
{ {
NSFileManager *manager = [NSFileManager defaultManager]; if(source == NULL || dest == NULL)
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSString *nsource = [[NSString stringWithUTF8String:source] stringByStandardizingPath];
NSString *ndest = [[NSString stringWithUTF8String:dest] stringByStandardizingPath];
NSString *ndestFolder = [ndest stringByDeletingLastPathComponent];
if(! [manager fileExistsAtPath:nsource])
{
Con::errorf("dPathCopy: no file exists at %s",source);
return false; return false;
}
if( [manager fileExistsAtPath:ndest] ) @autoreleasepool {
{ NSFileManager *manager = [NSFileManager defaultManager];
if(nooverwrite)
NSString *nsource = [manager stringWithFileSystemRepresentation:source length:dStrlen(source)];
NSString *ndest = [manager stringWithFileSystemRepresentation:dest length:dStrlen(dest)];
NSString *ndestFolder = [ndest stringByDeletingLastPathComponent];
if(! [manager fileExistsAtPath:nsource])
{ {
Con::errorf("dPathCopy: file already exists at %s",dest); Con::errorf("dPathCopy: no file exists at %s",source);
return false; return false;
} }
Con::warnf("Deleting files at path: %s", dest);
bool deleted = [manager removeFileAtPath:ndest handler:nil]; if( [manager fileExistsAtPath:ndest] )
if(!deleted)
{ {
Con::errorf("Copy failed! Could not delete files at path: %s", dest); if(nooverwrite)
return false; {
Con::errorf("dPathCopy: file already exists at %s",dest);
return false;
}
Con::warnf("Deleting files at path: %s", dest);
if(![manager removeItemAtPath:ndest error:nil] || [manager fileExistsAtPath:ndest])
{
Con::errorf("Copy failed! Could not delete files at path: %s", dest);
return false;
}
} }
if([manager fileExistsAtPath:ndestFolder] == NO)
{
ndestFolder = [ndestFolder stringByAppendingString:@"/"]; // createpath requires a trailing slash
Platform::createPath([ndestFolder UTF8String]);
}
bool ret = [manager copyItemAtPath:nsource toPath:ndest error:nil];
// n.b.: The "success" semantics don't guarantee a copy actually took place, so we'll verify
// because this is surprising behavior for a method called copy.
if( ![manager fileExistsAtPath:ndest] )
{
Con::warnf("The filemanager returned success, but the file was not copied. Something strange is happening");
ret = false;
}
return ret;
} }
if([manager fileExistsAtPath:ndestFolder] == NO)
{
ndestFolder = [ndestFolder stringByAppendingString:@"/"]; // createpath requires a trailing slash
Platform::createPath([ndestFolder UTF8String]);
}
bool ret = [manager copyPath:nsource toPath:ndest handler:nil];
[pool release];
return ret;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -117,25 +125,35 @@ bool dFileRename(const char *source, const char *dest)
if(source == NULL || dest == NULL) if(source == NULL || dest == NULL)
return false; return false;
NSFileManager *manager = [NSFileManager defaultManager]; @autoreleasepool {
NSFileManager *manager = [NSFileManager defaultManager];
NSString *nsource = [manager stringWithFileSystemRepresentation:source length:dStrlen(source)];
NSString *ndest = [manager stringWithFileSystemRepresentation:dest length:dStrlen(dest)]; NSString *nsource = [manager stringWithFileSystemRepresentation:source length:dStrlen(source)];
NSString *ndest = [manager stringWithFileSystemRepresentation:dest length:dStrlen(dest)];
if(! [manager fileExistsAtPath:nsource])
{ if(! [manager fileExistsAtPath:nsource])
Con::errorf("dFileRename: no file exists at %s",source); {
return false; Con::errorf("dFileRename: no file exists at %s",source);
return false;
}
if( [manager fileExistsAtPath:ndest] )
{
Con::warnf("dFileRename: Deleting files at path: %s", dest);
}
bool ret = [manager moveItemAtPath:nsource toPath:ndest error:nil];
// n.b.: The "success" semantics don't guarantee a move actually took place, so we'll verify
// because this is surprising behavior for a method called rename.
if( ![manager fileExistsAtPath:ndest] )
{
Con::warnf("The filemanager returned success, but the file was not moved. Something strange is happening");
ret = false;
}
return ret;
} }
if( [manager fileExistsAtPath:ndest] )
{
Con::warnf("dFileRename: Deleting files at path: %s", dest);
}
bool ret = [manager movePath:nsource toPath:ndest handler:nil];
return ret;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -722,9 +740,9 @@ bool Platform::isSubDirectory(const char *pathParent, const char *pathSub)
inline bool isGoodDirectory(dirent* entry) inline bool isGoodDirectory(dirent* entry)
{ {
return (entry->d_type == DT_DIR // is a dir return (entry->d_type == DT_DIR // is a dir
&& dStrcmp(entry->d_name,".") != 0 // not here && dStrcmp(entry->d_name,".") != 0 // not here
&& dStrcmp(entry->d_name,"..") != 0 // not parent && dStrcmp(entry->d_name,"..") != 0 // not parent
&& !Platform::isExcludedDirectory(entry->d_name)); // not excluded && !Platform::isExcludedDirectory(entry->d_name)); // not excluded
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -856,7 +874,7 @@ static bool recurseDumpDirectories(const char *basePath, const char *subPath, Ve
if ( isDir ) if ( isDir )
{ {
if (dStrcmp(d->d_name, ".") == 0 || if (dStrcmp(d->d_name, ".") == 0 ||
dStrcmp(d->d_name, "..") == 0) dStrcmp(d->d_name, "..") == 0)
continue; continue;
if (Platform::isExcludedDirectory(d->d_name)) if (Platform::isExcludedDirectory(d->d_name))
continue; continue;
@ -869,8 +887,8 @@ static bool recurseDumpDirectories(const char *basePath, const char *subPath, Ve
dSprintf(child, 1024, "%s/%s", subPath, d->d_name); dSprintf(child, 1024, "%s/%s", subPath, d->d_name);
if (currentDepth < recurseDepth || recurseDepth == -1 ) if (currentDepth < recurseDepth || recurseDepth == -1 )
recurseDumpDirectories(basePath, child, directoryVector, recurseDumpDirectories(basePath, child, directoryVector,
currentDepth + 1, recurseDepth, currentDepth + 1, recurseDepth,
noBasePath); noBasePath);
} }
else else
{ {
@ -881,8 +899,8 @@ static bool recurseDumpDirectories(const char *basePath, const char *subPath, Ve
dSprintf(child, 1024, "/%s", d->d_name); dSprintf(child, 1024, "/%s", d->d_name);
if (currentDepth < recurseDepth || recurseDepth == -1) if (currentDepth < recurseDepth || recurseDepth == -1)
recurseDumpDirectories(basePath, child, directoryVector, recurseDumpDirectories(basePath, child, directoryVector,
currentDepth + 1, recurseDepth, currentDepth + 1, recurseDepth,
noBasePath); noBasePath);
} }
} }
} }