Wm4System.cpp

Go to the documentation of this file.
00001 // Wild Magic Source Code
00002 // David Eberly
00003 // http://www.geometrictools.com
00004 // Copyright (c) 1998-2007
00005 //
00006 // This library is free software; you can redistribute it and/or modify it
00007 // under the terms of the GNU Lesser General Public License as published by
00008 // the Free Software Foundation; either version 2.1 of the License, or (at
00009 // your option) any later version.  The license is available for reading at
00010 // either of the locations:
00011 //     http://www.gnu.org/copyleft/lgpl.html
00012 //     http://www.geometrictools.com/License/WildMagicLicense.pdf
00013 // The license applies to versions 0 through 4 of Wild Magic.
00014 //
00015 // Version: 4.0.0 (2006/06/28)
00016 
00017 #include "Wm4FoundationPCH.h"
00018 #include "Wm4System.h"
00019 using namespace Wm4;
00020 
00021 // support for Load
00022 #include <sys/stat.h>
00023 
00024 // support for GetTime
00025 #ifdef __APPLE__
00026 #include <sys/time.h>
00027 static timeval gs_kInitial;
00028 static bool gs_bInitializedTime = false;
00029 #else
00030 #include <sys/timeb.h>
00031 static long gs_lInitialSec = 0;
00032 static long gs_lInitialUSec = 0;
00033 static bool gs_bInitializedTime = false;
00034 #endif
00035 
00036 // support for locating the application directory
00037 #ifdef __APPLE__
00038 #include <Carbon/Carbon.h>
00039 #endif
00040 
00041 char System::ms_acPath[SYSTEM_MAX_PATH];
00042 char System::ms_acEnvVar[SYSTEM_MAX_ENVVAR];
00043 std::vector<std::string>* System::ms_pkDirectories = 0;
00044 char System::WM4_PATH[SYSTEM_MAX_ENVVAR];
00045 
00046 //----------------------------------------------------------------------------
00047 void System::SwapBytes (int iSize, void* pvValue)
00048 {
00049     // size must be even
00050     assert(iSize >= 2 && (iSize & 1) == 0);
00051 
00052     char* acBytes = (char*) pvValue;
00053     for (int i0 = 0, i1 = iSize-1; i0 < iSize/2; i0++, i1--)
00054     {
00055         char cSave = acBytes[i0];
00056         acBytes[i0] = acBytes[i1];
00057         acBytes[i1] = cSave;
00058     }
00059 }
00060 //----------------------------------------------------------------------------
00061 void System::SwapBytes (int iSize, int iQuantity, void* pvValue)
00062 {
00063     // size must be even
00064     assert(iSize >= 2 && (iSize & 1) == 0);
00065 
00066     char* acBytes = (char*) pvValue;
00067     for (int i = 0; i < iQuantity; i++, acBytes += iSize)
00068     {
00069         for (int i0 = 0, i1 = iSize-1; i0 < iSize/2; i0++, i1--)
00070         {
00071             char cSave = acBytes[i0];
00072             acBytes[i0] = acBytes[i1];
00073             acBytes[i1] = cSave;
00074         }
00075     }
00076 }
00077 //----------------------------------------------------------------------------
00078 bool System::IsBigEndian ()
00079 {
00080     int iInt = 1;
00081     char* pcChar = (char*)&iInt;
00082     return !(*pcChar);
00083 }
00084 //----------------------------------------------------------------------------
00085 void System::EndianCopy (int iSize, const void* pvSrc, void* pvDst)
00086 {
00087     size_t uiSize = (size_t)iSize;
00088     Memcpy(pvDst,uiSize,pvSrc,uiSize);
00089 #ifdef WM4_BIG_ENDIAN
00090     SwapBytes(iSize,pvDst);
00091 #endif
00092 }
00093 //----------------------------------------------------------------------------
00094 void System::EndianCopy (int iSize, int iQuantity, const void* pvSrc,
00095     void* pvDst)
00096 {
00097     size_t uiSize = (size_t)(iSize*iQuantity);
00098     Memcpy(pvDst,uiSize,pvSrc,uiSize);
00099 #ifdef WM4_BIG_ENDIAN
00100     SwapBytes(iSize,iQuantity,pvDst);
00101 #endif
00102 }
00103 //----------------------------------------------------------------------------
00104 double System::GetTime ()
00105 {
00106 #ifdef __APPLE__
00107     if (!gs_bInitializedTime)
00108     {
00109         gs_bInitializedTime = true;
00110         gettimeofday(&gs_kInitial, 0);
00111     }
00112 
00113     struct timeval kCurrent;
00114     gettimeofday(&kCurrent,0);
00115     
00116     struct timeval kDelta;
00117     timersub(&kCurrent,&gs_kInitial,&kDelta);
00118 
00119     return 0.001*(double)(1000*kDelta.tv_sec + kDelta.tv_usec/1000);
00120 #else
00121     struct timeb kTB;
00122 
00123     if (!gs_bInitializedTime)
00124     {
00125         gs_bInitializedTime = true;
00126         ftime(&kTB);
00127         gs_lInitialSec = (long)kTB.time;
00128         gs_lInitialUSec = 1000*kTB.millitm;
00129     }
00130 
00131     ftime(&kTB);
00132     long lCurrentSec = (long)kTB.time;
00133     long lCurrentUSec = 1000*kTB.millitm;
00134     long lDeltaSec = lCurrentSec - gs_lInitialSec;
00135     long lDeltaUSec = lCurrentUSec -gs_lInitialUSec;
00136     if (lDeltaUSec < 0)
00137     {
00138         lDeltaUSec += 1000000;
00139         lDeltaSec--;
00140     }
00141 
00142     return 0.001*(double)(1000*lDeltaSec + lDeltaUSec/1000);
00143 #endif
00144 }
00145 //----------------------------------------------------------------------------
00146 bool System::Load (const char* acFilename, char*& racBuffer, int& riSize)
00147 {
00148     struct stat kStat;
00149     if (stat(acFilename,&kStat) != 0)
00150     {
00151         // file does not exist
00152         racBuffer = 0;
00153         riSize = 0;
00154         return false;
00155     }
00156 
00157     FILE* pkFile = System::Fopen(acFilename,"rb");
00158     assert(pkFile);
00159     if (!pkFile)
00160     {
00161         racBuffer = 0;
00162         riSize = 0;
00163         return false;
00164     }
00165 
00166     riSize = kStat.st_size;
00167     racBuffer = WM4_NEW char[riSize];
00168     int iRead = (int)fread(racBuffer,sizeof(char),riSize,pkFile);
00169     if (System::Fclose(pkFile) != 0 || iRead != riSize)
00170     {
00171         assert(false);
00172         WM4_DELETE[] racBuffer;
00173         racBuffer = 0;
00174         riSize = 0;
00175         return false;
00176     }
00177 
00178     return true;
00179 }
00180 //----------------------------------------------------------------------------
00181 bool System::Save (const char* acFilename, const char* acBuffer, int iSize)
00182 {
00183     if (!acBuffer || iSize <= 0)
00184     {
00185         // The input buffer must exist.  It is not possible to verify that
00186         // the buffer has the specified number of bytes.
00187         assert(false);
00188         return false;
00189     }
00190 
00191     FILE* pkFile = System::Fopen(acFilename,"wb");
00192     if (!pkFile)
00193     {
00194         return false;
00195     }
00196 
00197     int iWrite = (int)fwrite(acBuffer,sizeof(char),iSize,pkFile);
00198     if (System::Fclose(pkFile) != 0 || iWrite != iSize)
00199     {
00200         assert( false );
00201         return false;
00202     }
00203 
00204     return true;
00205 }
00206 //----------------------------------------------------------------------------
00207 bool System::Append (const char* acFilename, char* acBuffer, int iSize)
00208 {
00209     if (!acBuffer || iSize <= 0)
00210     {
00211         // The input buffer must exist.  It is not possible to verify that
00212         // the buffer has the specified number of bytes.
00213         assert(false);
00214         return false;
00215     }
00216 
00217     FILE* pkFile = System::Fopen(acFilename,"ab");
00218     if (!pkFile)
00219     {
00220         return false;
00221     }
00222 
00223     int iWrite = (int)fwrite(acBuffer,sizeof(char),iSize,pkFile);
00224     if (System::Fclose(pkFile) != 0 || iWrite != iSize)
00225     {
00226         assert( false );
00227         return false;
00228     }
00229 
00230     return true;
00231 }
00232 //----------------------------------------------------------------------------
00233 int System::Read1 (const char* acBuffer, int iQuantity, void* pvData)
00234 {
00235     assert(acBuffer && iQuantity > 0 && pvData);
00236     size_t uiSize = (size_t)iQuantity;
00237     Memcpy(pvData,uiSize,acBuffer,uiSize);
00238     return iQuantity;
00239 }
00240 //----------------------------------------------------------------------------
00241 int System::Write1 (char* acBuffer, int iQuantity, const void* pvData)
00242 {
00243     assert(acBuffer && iQuantity > 0 && pvData);
00244     size_t uiSize = (size_t)iQuantity;
00245     Memcpy(acBuffer,uiSize,pvData,uiSize);
00246     return iQuantity;
00247 }
00248 //----------------------------------------------------------------------------
00249 int System::Read1 (FILE* pkFile, int iQuantity, void* pvData)
00250 {
00251     assert(pkFile && iQuantity > 0 && pvData);
00252     fread(pvData,1,iQuantity,pkFile);
00253     return iQuantity;
00254 }
00255 //----------------------------------------------------------------------------
00256 int System::Write1 (FILE* pkFile, int iQuantity, const void* pvData)
00257 {
00258     assert(pkFile && iQuantity > 0 && pvData);
00259     fwrite(pvData,1,iQuantity,pkFile);
00260     return iQuantity;
00261 }
00262 //----------------------------------------------------------------------------
00263 int System::Read2le (const char* acBuffer, int iQuantity, void* pvData)
00264 {
00265     assert(acBuffer && iQuantity > 0 && pvData);
00266     int iNumBytes = 2*iQuantity;
00267     size_t uiSize = (size_t)iNumBytes;
00268     Memcpy(pvData,uiSize,acBuffer,uiSize);
00269 #ifdef WM4_BIG_ENDIAN
00270     SwapBytes(2,iQuantity,pvData);
00271 #endif
00272     return iNumBytes;
00273 }
00274 //----------------------------------------------------------------------------
00275 int System::Read4le (const char* acBuffer, int iQuantity, void* pvData)
00276 {
00277     assert(acBuffer && iQuantity > 0 && pvData);
00278     int iNumBytes = 4*iQuantity;
00279     size_t uiSize = (size_t)iNumBytes;
00280     Memcpy(pvData,uiSize,acBuffer,uiSize);
00281 #ifdef WM4_BIG_ENDIAN
00282     SwapBytes(4,iQuantity,pvData);
00283 #endif
00284     return iNumBytes;
00285 }
00286 //----------------------------------------------------------------------------
00287 int System::Read8le (const char* acBuffer, int iQuantity, void* pvData)
00288 {
00289     assert(acBuffer && iQuantity > 0 && pvData);
00290     int iNumBytes = 8*iQuantity;
00291     size_t uiSize = (size_t)iNumBytes;
00292     Memcpy(pvData,uiSize,acBuffer,uiSize);
00293 #ifdef WM4_BIG_ENDIAN
00294     SwapBytes(8,iQuantity,pvData);
00295 #endif
00296     return iNumBytes;
00297 }
00298 //----------------------------------------------------------------------------
00299 int System::Write2le (char* acBuffer, int iQuantity, const void* pvData)
00300 {
00301     assert(acBuffer && iQuantity > 0 && pvData);
00302     int iNumBytes = 2*iQuantity;
00303     size_t uiSize = (size_t)iNumBytes;
00304     Memcpy(acBuffer,uiSize,pvData,uiSize);
00305 #ifdef WM4_BIG_ENDIAN
00306     SwapBytes(2,iQuantity,acBuffer);
00307 #endif
00308     return iNumBytes;
00309 }
00310 //----------------------------------------------------------------------------
00311 int System::Write4le (char* acBuffer, int iQuantity, const void* pvData)
00312 {
00313     assert(acBuffer && iQuantity > 0 && pvData);
00314     int iNumBytes = 4*iQuantity;
00315     size_t uiSize = (size_t)iNumBytes;
00316     Memcpy(acBuffer,uiSize,pvData,uiSize);
00317 #ifdef WM4_BIG_ENDIAN
00318     SwapBytes(4,iQuantity,acBuffer);
00319 #endif
00320     return iNumBytes;
00321 }
00322 //----------------------------------------------------------------------------
00323 int System::Write8le (char* acBuffer, int iQuantity, const void* pvData)
00324 {
00325     assert(acBuffer && iQuantity > 0 && pvData);
00326     int iNumBytes = 8*iQuantity;
00327     size_t uiSize = (size_t)iNumBytes;
00328     Memcpy(acBuffer,uiSize,pvData,uiSize);
00329 #ifdef WM4_BIG_ENDIAN
00330     SwapBytes(8,iQuantity,acBuffer);
00331 #endif
00332     return iNumBytes;
00333 }
00334 //----------------------------------------------------------------------------
00335 int System::Read2le (FILE* pkFile, int iQuantity, void* pvData)
00336 {
00337     assert(pkFile && iQuantity > 0 && pvData);
00338     fread(pvData,2,iQuantity,pkFile);
00339 #ifdef WM4_BIG_ENDIAN
00340     SwapBytes(2,iQuantity,pvData);
00341 #endif
00342     return 2*iQuantity;
00343 }
00344 //----------------------------------------------------------------------------
00345 int System::Read4le (FILE* pkFile, int iQuantity, void* pvData)
00346 {
00347     assert(pkFile && iQuantity > 0 && pvData);
00348     fread(pvData,4,iQuantity,pkFile);
00349 #ifdef WM4_BIG_ENDIAN
00350     SwapBytes(4,iQuantity,pvData);
00351 #endif
00352     return 4*iQuantity;
00353 }
00354 //----------------------------------------------------------------------------
00355 int System::Read8le (FILE* pkFile, int iQuantity, void* pvData)
00356 {
00357     assert(pkFile && iQuantity > 0 && pvData);
00358     fread(pvData,8,iQuantity,pkFile);
00359 #ifdef WM4_BIG_ENDIAN
00360     SwapBytes(8,iQuantity,pvData);
00361 #endif
00362     return 8*iQuantity;
00363 }
00364 //----------------------------------------------------------------------------
00365 int System::Write2le (FILE* pkFile, int iQuantity, const void* pvData)
00366 {
00367     assert(pkFile && iQuantity > 0 && pvData);
00368 #ifdef WM4_BIG_ENDIAN
00369     const short* psData = (const short*)pvData;
00370     for (int i = 0; i < iQuantity; i++)
00371     {
00372         short sTemp = *psData++;
00373         SwapBytes(2,&sTemp);
00374         fwrite(&sTemp,2,1,pkFile);
00375     }
00376 #else
00377     fwrite(pvData,2,iQuantity,pkFile);
00378 #endif
00379     return 2*iQuantity;
00380 }
00381 //----------------------------------------------------------------------------
00382 int System::Write4le (FILE* pkFile, int iQuantity, const void* pvData)
00383 {
00384     assert(pkFile && iQuantity > 0 && pvData);
00385 #ifdef WM4_BIG_ENDIAN
00386     const int* piData = (const int*)pvData;
00387     for (int i = 0; i < iQuantity; i++)
00388     {
00389         int iTemp = *piData++;
00390         SwapBytes(4,&iTemp);
00391         fwrite(&iTemp,4,1,pkFile);
00392     }
00393 #else
00394     fwrite(pvData,4,iQuantity,pkFile);
00395 #endif
00396     return 4*iQuantity;
00397 }
00398 //----------------------------------------------------------------------------
00399 int System::Write8le (FILE* pkFile, int iQuantity, const void* pvData)
00400 {
00401     assert(pkFile && iQuantity > 0 && pvData);
00402 #ifdef WM4_BIG_ENDIAN
00403     const double* pdData = (const double*)pvData;
00404     for (int i = 0; i < iQuantity; i++)
00405     {
00406         double dTemp = *pdData++;
00407         SwapBytes(8,&dTemp);
00408         fwrite(&dTemp,8,1,pkFile);
00409     }
00410 #else
00411     fwrite(pvData,8,iQuantity,pkFile);
00412 #endif
00413     return 8*iQuantity;
00414 }
00415 //----------------------------------------------------------------------------
00416 int System::Read2be (const char* acBuffer, int iQuantity, void* pvData)
00417 {
00418     assert(acBuffer && iQuantity > 0 && pvData);
00419     int iNumBytes = 2*iQuantity;
00420     size_t uiSize = (size_t)iNumBytes;
00421     Memcpy(pvData,uiSize,acBuffer,uiSize);
00422 #ifndef WM4_BIG_ENDIAN
00423     SwapBytes(2,iQuantity,pvData);
00424 #endif
00425     return iNumBytes;
00426 }
00427 //----------------------------------------------------------------------------
00428 int System::Read4be (const char* acBuffer, int iQuantity, void* pvData)
00429 {
00430     assert(acBuffer && iQuantity > 0 && pvData);
00431     int iNumBytes = 4*iQuantity;
00432     size_t uiSize = (size_t)iNumBytes;
00433     Memcpy(pvData,uiSize,acBuffer,uiSize);
00434 #ifndef WM4_BIG_ENDIAN
00435     SwapBytes(4,iQuantity,pvData);
00436 #endif
00437     return iNumBytes;
00438 }
00439 //----------------------------------------------------------------------------
00440 int System::Read8be (const char* acBuffer, int iQuantity, void* pvData)
00441 {
00442     assert(acBuffer && iQuantity > 0 && pvData);
00443     int iNumBytes = 8*iQuantity;
00444     size_t uiSize = (size_t)iNumBytes;
00445     Memcpy(pvData,uiSize,acBuffer,uiSize);
00446 #ifndef WM4_BIG_ENDIAN
00447     SwapBytes(8,iQuantity,pvData);
00448 #endif
00449     return iNumBytes;
00450 }
00451 //----------------------------------------------------------------------------
00452 int System::Write2be (char* acBuffer, int iQuantity, const void* pvData)
00453 {
00454     assert(acBuffer && iQuantity > 0 && pvData);
00455     int iNumBytes = 2*iQuantity;
00456     size_t uiSize = (size_t)iNumBytes;
00457     Memcpy(acBuffer,uiSize,pvData,uiSize);
00458 #ifndef WM4_BIG_ENDIAN
00459     SwapBytes(2,iQuantity,acBuffer);
00460 #endif
00461     return iNumBytes;
00462 }
00463 //----------------------------------------------------------------------------
00464 int System::Write4be (char* acBuffer, int iQuantity, const void* pvData)
00465 {
00466     assert(acBuffer && iQuantity > 0 && pvData);
00467     int iNumBytes = 4*iQuantity;
00468     size_t uiSize = (size_t)iNumBytes;
00469     Memcpy(acBuffer,uiSize,pvData,uiSize);
00470 #ifndef WM4_BIG_ENDIAN
00471     SwapBytes(4,iQuantity,acBuffer);
00472 #endif
00473     return iNumBytes;
00474 }
00475 //----------------------------------------------------------------------------
00476 int System::Write8be (char* acBuffer, int iQuantity, const void* pvData)
00477 {
00478     assert(acBuffer && iQuantity > 0 && pvData);
00479     int iNumBytes = 8*iQuantity;
00480     size_t uiSize = (size_t)iNumBytes;
00481     Memcpy(acBuffer,uiSize,pvData,uiSize);
00482 #ifndef WM4_BIG_ENDIAN
00483     SwapBytes(8,iQuantity,acBuffer);
00484 #endif
00485     return iNumBytes;
00486 }
00487 //----------------------------------------------------------------------------
00488 int System::Read2be (FILE* pkFile, int iQuantity, void* pvData)
00489 {
00490     assert(pkFile && iQuantity > 0 && pvData);
00491     fread(pvData,2,iQuantity,pkFile);
00492 #ifndef WM4_BIG_ENDIAN
00493     SwapBytes(2,iQuantity,pvData);
00494 #endif
00495     return 2*iQuantity;
00496 }
00497 //----------------------------------------------------------------------------
00498 int System::Read4be (FILE* pkFile, int iQuantity, void* pvData)
00499 {
00500     assert(pkFile && iQuantity > 0 && pvData);
00501     fread(pvData,4,iQuantity,pkFile);
00502 #ifndef WM4_BIG_ENDIAN
00503     SwapBytes(4,iQuantity,pvData);
00504 #endif
00505     return 4*iQuantity;
00506 }
00507 //----------------------------------------------------------------------------
00508 int System::Read8be (FILE* pkFile, int iQuantity, void* pvData)
00509 {
00510     assert(pkFile && iQuantity > 0 && pvData);
00511     fread(pvData,8,iQuantity,pkFile);
00512 #ifndef WM4_BIG_ENDIAN
00513     SwapBytes(8,iQuantity,pvData);
00514 #endif
00515     return 8*iQuantity;
00516 }
00517 //----------------------------------------------------------------------------
00518 int System::Write2be (FILE* pkFile, int iQuantity, const void* pvData)
00519 {
00520     assert(pkFile && iQuantity > 0 && pvData);
00521 #ifndef WM4_BIG_ENDIAN
00522     const short* psData = (const short*)pvData;
00523     for (int i = 0; i < iQuantity; i++)
00524     {
00525         short sTemp = *psData++;
00526         SwapBytes(2,&sTemp);
00527         fwrite(&sTemp,2,1,pkFile);
00528     }
00529 #else
00530     fwrite(pvData,2,iQuantity,pkFile);
00531 #endif
00532     return 2*iQuantity;
00533 }
00534 //----------------------------------------------------------------------------
00535 int System::Write4be (FILE* pkFile, int iQuantity, const void* pvData)
00536 {
00537     assert(pkFile && iQuantity > 0 && pvData);
00538 #ifndef WM4_BIG_ENDIAN
00539     const int* piData = (const int*)pvData;
00540     for (int i = 0; i < iQuantity; i++)
00541     {
00542         int iTemp = *piData++;
00543         SwapBytes(4,&iTemp);
00544         fwrite(&iTemp,4,1,pkFile);
00545     }
00546 #else
00547     fwrite(pvData,4,iQuantity,pkFile);
00548 #endif
00549     return 4*iQuantity;
00550 }
00551 //----------------------------------------------------------------------------
00552 int System::Write8be (FILE* pkFile, int iQuantity, const void* pvData)
00553 {
00554     assert(pkFile && iQuantity > 0 && pvData);
00555 #ifndef WM4_BIG_ENDIAN
00556     const double* pdData = (const double*)pvData;
00557     for (int i = 0; i < iQuantity; i++)
00558     {
00559         double dTemp = *pdData++;
00560         SwapBytes(8,&dTemp);
00561         fwrite(&dTemp,8,1,pkFile);
00562     }
00563 #else
00564     fwrite(pvData,8,iQuantity,pkFile);
00565 #endif
00566     return 8*iQuantity;
00567 }
00568 //----------------------------------------------------------------------------
00569 const char* System::GetPath (const char* acDirectory, const char* acFilename)
00570 {
00571 #ifdef __APPLE__
00572     // An application-relative path is needed for the applications to be able
00573     // to find the input data sets.  Unfortunately, there is no exact way to
00574     // predict which directory the application is run from, since this depends
00575     // on whether it was launched by the Finder, Xcode, gdb, the console, etc.
00576     // To work around this, the following code switches to the application
00577     // directory.  Beware of your applications themselves changing directory,
00578     // which could cause the input data sets not to be found.
00579 
00580     // WARNING.  The engine supports XCode 2.x, but not XCode 1.x.  The
00581     // directory structure assumed here is based on the default Xcode 2.x
00582     // preferences:
00583     //     "Put build products in project directory"
00584     //     "Put intermediate build files with build products"
00585     // If you change the Xcode preferences, you will need to modify this code
00586     // to correctly locate the application directory.
00587 
00588     OSStatus eError;
00589     FSRef kExeRef;    // ${ApplicationPath}/build/WildMagic/executableFile
00590     FSRef kWMRef;     // ${ApplicationPath}/build/WildMagic
00591     FSRef kBuildRef;  // ${ApplicationPath}/build
00592     FSRef kAppRef;    // ${ApplicationPath}
00593     ProcessSerialNumber kPSN;
00594 
00595     MacGetCurrentProcess(&kPSN);
00596     eError = GetProcessBundleLocation(&kPSN,&kExeRef);
00597     eError = FSGetCatalogInfo(&kExeRef,0,0,0,0,&kWMRef);
00598     eError = FSGetCatalogInfo(&kWMRef,0,0,0,0,&kBuildRef);
00599     eError = FSGetCatalogInfo(&kBuildRef,0,0,0,0,&kAppRef);
00600     eError = FSRefMakePath(&kAppRef,(UInt8*)ms_acPath,SYSTEM_MAX_PATH);
00601     eError = chdir(ms_acPath);
00602 
00603 #if 0
00604     // If you really must use Xcode version 1.x, then the path searching
00605     // code must be the following.
00606     OSStatus eError;
00607     FSRef kExeRef;    // ${ApplicationPath}/build/executableFile
00608     FSRef kBuildRef;  // ${ApplicationPath}/build
00609     FSRef kAppRef;    // ${ApplicationPath}
00610     ProcessSerialNumber kPSN;
00611 
00612     MacGetCurrentProcess(&kPSN);
00613     eError = GetProcessBundleLocation(&kPSN,&kExeRef);
00614     eError = FSGetCatalogInfo(&kExeRef,0,0,0,0,&kBuildRef);
00615     eError = FSGetCatalogInfo(&kBuildRef,0,0,0,0,&kAppRef);
00616     eError = FSRefMakePath(&kAppRef,(UInt8*)ms_acPath,SYSTEM_MAX_PATH);
00617     eError = chdir(ms_acPath);
00618 #endif
00619 #endif
00620 
00621     size_t uiDLength = strlen(acDirectory);
00622     size_t uiFLength = strlen(acFilename);
00623     if (uiDLength + uiFLength + 1 <= SYSTEM_MAX_PATH)
00624     {
00625         System::Strcpy(ms_acPath,SYSTEM_MAX_PATH,acDirectory);
00626         System::Strcat(ms_acPath,SYSTEM_MAX_PATH,acFilename);
00627         return ms_acPath;
00628     }
00629     return 0;
00630 }
00631 //----------------------------------------------------------------------------
00632 void System::Initialize ()
00633 {
00634     assert(ms_pkDirectories == 0);
00635     ms_pkDirectories = WM4_NEW std::vector<std::string>;
00636 
00637     const char* acWm4Path = GetEnv("WM4_PATH");
00638     if (acWm4Path)
00639     {
00640         Strcpy(WM4_PATH,SYSTEM_MAX_ENVVAR,acWm4Path);
00641     }
00642     else
00643     {
00644         WM4_PATH[0] = 0;
00645     }
00646 }
00647 //----------------------------------------------------------------------------
00648 void System::Terminate ()
00649 {
00650     WM4_DELETE ms_pkDirectories;
00651     ms_pkDirectories = 0;
00652 }
00653 //----------------------------------------------------------------------------
00654 int System::GetDirectoryQuantity ()
00655 {
00656     if (!ms_pkDirectories)
00657     {
00658         Initialize();
00659     }
00660 
00661     return (int)ms_pkDirectories->size();
00662 }
00663 //----------------------------------------------------------------------------
00664 const char* System::GetDirectory (int i)
00665 {
00666     if (!ms_pkDirectories)
00667     {
00668         Initialize();
00669     }
00670 
00671     if (0 <= i && i < (int)ms_pkDirectories->size())
00672     {
00673         return (*ms_pkDirectories)[i].c_str();
00674     }
00675     return 0;
00676 }
00677 //----------------------------------------------------------------------------
00678 bool System::InsertDirectory (const char* acDirectory)
00679 {
00680     if (!ms_pkDirectories)
00681     {
00682         Initialize();
00683     }
00684 
00685     std::string kDirectory = std::string(acDirectory) + std::string("/");
00686     for (int i = 0; i < (int)ms_pkDirectories->size(); i++)
00687     {
00688         if (kDirectory == (*ms_pkDirectories)[i])
00689         {
00690             return false;
00691         }
00692     }
00693     ms_pkDirectories->push_back(kDirectory);
00694     return true;
00695 }
00696 //----------------------------------------------------------------------------
00697 bool System::RemoveDirectory (const char* acDirectory)
00698 {
00699     if (!ms_pkDirectories)
00700     {
00701         Initialize();
00702     }
00703 
00704     std::string kDirectory = std::string(acDirectory) + std::string("/");
00705     std::vector<std::string>::iterator pkIter = ms_pkDirectories->begin();
00706     for (; pkIter != ms_pkDirectories->end(); pkIter++)
00707     {
00708         if (kDirectory == *pkIter)
00709         {
00710             ms_pkDirectories->erase(pkIter);
00711             return true;
00712         }
00713     }
00714     return false;
00715 }
00716 //----------------------------------------------------------------------------
00717 void System::RemoveAllDirectories ()
00718 {
00719     if (!ms_pkDirectories)
00720     {
00721         Initialize();
00722     }
00723 
00724     ms_pkDirectories->clear();
00725 }
00726 //----------------------------------------------------------------------------
00727 const char* System::GetPath (const char* acFilename, int eMode)
00728 {
00729     if (!ms_pkDirectories)
00730     {
00731         Initialize();
00732     }
00733 
00734     for (int i = 0; i < (int)ms_pkDirectories->size(); i++)
00735     {
00736         const char* acDecorated = System::GetPath(
00737             (*ms_pkDirectories)[i].c_str(),acFilename);
00738         if (!acDecorated)
00739         {
00740             return 0;
00741         }
00742 
00743         FILE* pkFile;
00744         if (eMode == SM_READ)
00745         {
00746             pkFile = System::Fopen(acDecorated,"r");
00747         }
00748         else if (eMode == SM_WRITE)
00749         {
00750             pkFile = System::Fopen(acDecorated,"w");
00751         }
00752         else // eMode == SM_READ_WRITE
00753         {
00754             pkFile = System::Fopen(acDecorated,"r+");
00755         }
00756 
00757         if (pkFile)
00758         {
00759             System::Fclose(pkFile);
00760             return acDecorated;
00761         }
00762     }
00763     return 0;
00764 }
00765 //----------------------------------------------------------------------------
00766 unsigned int System::MakeRGB (unsigned char ucR, unsigned char ucG,
00767     unsigned char ucB)
00768 {
00769 #ifdef WM4_BIG_ENDIAN
00770     return (0xFF | (ucB << 8) | (ucG << 16) | (ucR << 24));
00771 #else
00772     return (ucR | (ucG << 8) | (ucB << 16) | (0xFF << 24));
00773 #endif
00774 }
00775 //----------------------------------------------------------------------------
00776 unsigned int System::MakeRGBA (unsigned char ucR, unsigned char ucG,
00777     unsigned char ucB, unsigned char ucA)
00778 {
00779 #ifdef WM4_BIG_ENDIAN
00780     return (ucA | (ucB << 8) | (ucG << 16) | (ucR << 24));
00781 #else
00782     return (ucR | (ucG << 8) | (ucB << 16) | (ucA << 24));
00783 #endif
00784 }
00785 //----------------------------------------------------------------------------
00786 FILE* System::Fopen (const char* acFilename, const char* acMode)
00787 {
00788 #ifdef WM4_USING_VC80
00789     FILE* pkFile;
00790     errno_t uiError = fopen_s(&pkFile,acFilename,acMode);
00791     if (uiError == 0)
00792     {
00793         return pkFile;
00794     }
00795     else
00796     {
00797         return 0;
00798     }
00799 #else
00800     return fopen(acFilename,acMode);
00801 #endif
00802 }
00803 //----------------------------------------------------------------------------
00804 int System::Fprintf (FILE* pkFile, const char* acFormat, ...)
00805 {
00806     if (!pkFile || !acFormat)
00807     {
00808         return -1;
00809     }
00810 
00811     va_list acArgs;
00812     va_start(acArgs,acFormat);
00813 
00814 #ifdef WM4_USING_VC80
00815     int iNumWritten = vfprintf_s(pkFile,acFormat,acArgs);
00816 #else
00817     int iNumWritten = vfprintf(pkFile,acFormat,acArgs);
00818 #endif
00819 
00820     va_end(acArgs);
00821     return iNumWritten;
00822 }
00823 //----------------------------------------------------------------------------
00824 int System::Fclose (FILE* pkFile)
00825 {
00826     return fclose(pkFile);
00827 }
00828 //----------------------------------------------------------------------------
00829 const char* System::GetEnv (const char* acEnvVarName)
00830 {
00831 #ifdef WM4_USING_VC80
00832    size_t uiRequiredSize;
00833    errno_t uiError = getenv_s(&uiRequiredSize,0,0,acEnvVarName);
00834    if (uiError > 0)
00835    {
00836        return 0;
00837    }
00838    getenv_s(&uiRequiredSize,ms_acEnvVar,SYSTEM_MAX_ENVVAR,acEnvVarName);
00839 #else
00840     char* acEnvVar = getenv(acEnvVarName);
00841     if (acEnvVar == 0)
00842     {
00843         return 0;
00844     }
00845     System::Strcpy(ms_acEnvVar,SYSTEM_MAX_ENVVAR,getenv(acEnvVarName));
00846 #endif
00847     return ms_acEnvVar;
00848 }
00849 //----------------------------------------------------------------------------
00850 void* System::Memcpy (void* pvDst, size_t uiDstSize, const void* pvSrc,
00851     size_t uiSrcSize)
00852 {
00853 #ifdef WM4_USING_VC80
00854     errno_t uiError = memcpy_s(pvDst,uiDstSize,pvSrc,uiSrcSize);
00855     if (uiError == 0)
00856     {
00857         return pvDst;
00858     }
00859     else
00860     {
00861         return 0;
00862     }
00863 #else
00864     if (!pvDst || uiDstSize == 0 || !pvSrc || uiSrcSize == 0)
00865     {
00866         // Be consistent with the behavior of memcpy_s.
00867         return 0;
00868     }
00869 
00870     if (uiSrcSize > uiDstSize)
00871     {
00872         // The source memory is too large to copy to the destination.  To
00873         // be consistent with memcpy_s, return null as an indication that the
00874         // copy failed.
00875         return 0;
00876     }
00877     memcpy(pvDst,pvSrc,uiSrcSize);
00878     return pvDst;
00879 #endif
00880 }
00881 //----------------------------------------------------------------------------
00882 int System::Sprintf (char* acDst, size_t uiDstSize, const char* acFormat, ...)
00883 {
00884     if (!acDst || uiDstSize == 0 || !acFormat)
00885     {
00886         return -1;
00887     }
00888 
00889     va_list acArgs;
00890     va_start(acArgs,acFormat);
00891 
00892 #ifdef WM4_USING_VC80
00893     int iNumWritten = vsprintf_s(acDst,uiDstSize,acFormat,acArgs);
00894 #else
00895     int iNumWritten = vsprintf(acDst,acFormat,acArgs);
00896 #endif
00897 
00898     va_end(acArgs);
00899     return iNumWritten;
00900 }
00901 //----------------------------------------------------------------------------
00902 char* System::Strcpy (char* acDst, size_t uiDstSize, const char* acSrc)
00903 {
00904 #ifdef WM4_USING_VC80
00905     errno_t uiError = strcpy_s(acDst,uiDstSize,acSrc);
00906     if (uiError == 0)
00907     {
00908         return acDst;
00909     }
00910     else
00911     {
00912         return 0;
00913     }
00914 #else
00915     if (!acDst || uiDstSize == 0 || !acSrc)
00916     {
00917         // Be consistent with the behavior of strcpy_s.
00918         return 0;
00919     }
00920 
00921     size_t uiSrcLen = strlen(acSrc);
00922     if (uiSrcLen + 1 > uiDstSize)
00923     {
00924         // The source string is too large to copy to the destination.  To
00925         // be consistent with strcpy_s, return null as an indication that the
00926         // copy failed.
00927         return 0;
00928     }
00929     strncpy(acDst,acSrc,uiSrcLen);
00930     acDst[uiSrcLen] = 0;
00931     return acDst;
00932 #endif
00933 }
00934 //----------------------------------------------------------------------------
00935 char* System::Strcat (char* acDst, size_t uiDstSize, const char* acSrc)
00936 {
00937 #ifdef WM4_USING_VC80
00938     errno_t uiError = strcat_s(acDst,uiDstSize,acSrc);
00939     if (uiError == 0)
00940     {
00941         return acDst;
00942     }
00943     else
00944     {
00945         return 0;
00946     }
00947 #else
00948     if (!acDst || uiDstSize == 0 || !acSrc)
00949     {
00950         // Be consistent with the behavior of strcat_s.
00951         return 0;
00952     }
00953 
00954     size_t uiSrcLen = strlen(acSrc);
00955     size_t uiDstLen = strlen(acDst);
00956     size_t uiSumLen = uiSrcLen + uiDstLen;
00957     if (uiSumLen + 1 > uiDstSize)
00958     {
00959         // The source string is too large to append to the destination.  To
00960         // be consistent with strcat_s, return null as an indication that
00961         // the concatenation failed.
00962         return 0;
00963     }
00964     strncat(acDst,acSrc,uiSrcLen);
00965     acDst[uiSumLen] = 0;
00966     return acDst;
00967 #endif
00968 }
00969 //----------------------------------------------------------------------------
00970 char* System::Strncpy (char* acDst, size_t uiDstSize, const char* acSrc,
00971     size_t uiSrcSize)
00972 {
00973 #ifdef WM4_USING_VC80
00974     errno_t uiError = strncpy_s(acDst,uiDstSize,acSrc,uiSrcSize);
00975     if (uiError == 0)
00976     {
00977         return acDst;
00978     }
00979     else
00980     {
00981         return 0;
00982     }
00983 #else
00984     if (!acDst || uiDstSize == 0 || !acSrc || uiSrcSize == 0)
00985     {
00986         // Be consistent with the behavior of strncpy_s.
00987         return 0;
00988     }
00989 
00990     if (uiSrcSize + 1 > uiDstSize)
00991     {
00992         // The source string is too large to copy to the destination.  To
00993         // be consistent with strncpy_s, return null as an indication that
00994         // the copy failed.
00995         return 0;
00996     }
00997     strncpy(acDst,acSrc,uiSrcSize);
00998     return acDst;
00999 #endif
01000 }
01001 //----------------------------------------------------------------------------
01002 char* System::Strtok (char* acToken, const char* acDelimiters,
01003     char*& racNextToken)
01004 {
01005 #ifdef WM4_USING_VC80
01006     return strtok_s(acToken,acDelimiters,&racNextToken);
01007 #else
01008     (void)racNextToken;  // avoid warning in release build
01009     return strtok(acToken,acDelimiters);
01010 #endif
01011 }
01012 //----------------------------------------------------------------------------

Generated on Wed Nov 23 19:01:08 2011 for FreeCAD by  doxygen 1.6.1