00001
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 #include "stdmisc.h"
00027
00028 #ifdef NL_OS_WINDOWS
00029 #include <windows.h>
00030 #elif defined NL_OS_UNIX
00031 #include <unistd.h>
00032 #include <string.h>
00033 #include <errno.h>
00034 #endif
00035
00036 #include "nel/misc/command.h"
00037
00038 using namespace std;
00039
00040 #ifdef NL_OS_WINDOWS
00041 # ifdef __STL_DEBUG
00042 # define STL_MODE "debug"
00043 # else
00044 # define STL_MODE "normal"
00045 # endif // __STL_DEBUG
00046 # if(__SGI_STL_PORT < 0x400)
00047 # define STL_STR_VER "< 4.0"
00048 # elif(__SGI_STL_PORT == 0x400)
00049 # define STL_STR_VER "4.0"
00050 # elif(__SGI_STL_PORT == 0x450)
00051 # define STL_STR_VER "4.5"
00052 # elif(__SGI_STL_PORT > 0x450)
00053 # define STL_STR_VER "> 4.5"
00054 # endif // __SGI_STL_PORT
00055 # pragma message("Using STLport version "STL_STR_VER" in "STL_MODE" mode")
00056 #endif // NL_OS_WINDOWS
00057
00058 namespace NLMISC
00059 {
00060
00061
00062
00063
00064
00065 void nlSleep( uint32 ms )
00066 {
00067 #ifdef NL_OS_WINDOWS
00068
00070 #ifdef NL_DEBUG
00071 ms = max(ms, (uint32)1);
00072 #endif
00073
00074 Sleep( ms );
00075
00076 #elif defined NL_OS_UNIX
00077 usleep( ms*1000 );
00078 #endif
00079 }
00080
00081
00082
00083
00084
00085 uint getThreadId()
00086 {
00087 #ifdef NL_OS_WINDOWS
00088 return GetCurrentThreadId();
00089 #elif defined NL_OS_UNIX
00090 return getpid();
00091 #endif
00092
00093 }
00094
00095
00096
00097
00098
00099 string stringFromVector( const vector<uint8>& v, bool limited )
00100 {
00101 string s;
00102
00103 if (!v.empty())
00104 {
00105 int size = v.size ();
00106 if (limited && size > 1000)
00107 {
00108 string middle = "...<buf too big,skip middle part>...";
00109 s.resize (1000 + middle.size());
00110 memcpy (&*s.begin(), &*v.begin(), 500);
00111 memcpy (&*s.begin()+500, &*middle.begin(), middle.size());
00112 memcpy (&*s.begin()+500+middle.size(), &*v.begin()+size-500, 500);
00113 }
00114 else
00115 {
00116 s.resize (size);
00117 memcpy( &*s.begin(), &*v.begin(), v.size() );
00118 }
00119
00120
00121 string::iterator is;
00122 for ( is=s.begin(); is!=s.end(); ++is )
00123 {
00124
00125 if ( ! isprint((uint8)(*is)) || (*is) == '%')
00126 {
00127 (*is) = '?';
00128 }
00129 }
00130 }
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149 return s;
00150 }
00151
00152
00153 sint smprintf( char *buffer, size_t count, const char *format, ... )
00154 {
00155 sint ret;
00156
00157 va_list args;
00158 va_start( args, format );
00159 ret = vsnprintf( buffer, count, format, args );
00160 if ( ret == -1 )
00161 {
00162 buffer[count-1] = '\0';
00163 }
00164 va_end( args );
00165
00166 return( ret );
00167 }
00168
00169
00170 sint64 atoiInt64 (const char *ident, sint64 base)
00171 {
00172 sint64 number = 0;
00173 bool neg = false;
00174
00175
00176 nlassert (ident != NULL);
00177
00178
00179 if (*ident == '\0') goto end;
00180
00181
00182 if (*ident == '+') ident++;
00183
00184
00185 if (*ident == '-') { neg = true; ident++; }
00186
00187 while (*ident != '\0')
00188 {
00189 if (isdigit(*ident))
00190 {
00191 number *= base;
00192 number += (*ident)-'0';
00193 }
00194 else if (base > 10 && islower(*ident))
00195 {
00196 number *= base;
00197 number += (*ident)-'a'+10;
00198 }
00199 else if (base > 10 && isupper(*ident))
00200 {
00201 number *= base;
00202 number += (*ident)-'A'+10;
00203 }
00204 else
00205 {
00206 goto end;
00207 }
00208 ident++;
00209 }
00210 end:
00211 if (neg) number = -number;
00212 return number;
00213
00215
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263
00264
00265
00266
00267
00268
00269
00270
00271
00272
00273
00274
00275
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288
00289
00290
00291
00292
00293
00294
00295
00296
00297
00298 }
00299
00300 void itoaInt64 (sint64 number, char *str, sint64 base)
00301 {
00302 str[0] = '\0';
00303 char b[256];
00304 if(!number)
00305 {
00306 str[0] = '0';
00307 str[1] = '\0';
00308 return;
00309 }
00310 memset(b,'\0',255);
00311 memset(b,'0',64);
00312 sint n;
00313 sint64 x = number;
00314 if (x < 0) x = -x;
00315 char baseTable[] = "0123456789abcdefghijklmnopqrstuvwyz";
00316 for(n = 0; n < 64; n ++)
00317 {
00318 sint num = (sint)(x % base);
00319 b[64 - n] = baseTable[num];
00320 if(!x)
00321 {
00322 int k;
00323 int j = 0;
00324
00325 if (number < 0)
00326 {
00327 str[j++] = '-';
00328 }
00329
00330 for(k = 64 - n + 1; k <= 64; k++)
00331 {
00332 str[j ++] = b[k];
00333 }
00334 str[j] = '\0';
00335 break;
00336 }
00337 x /= base;
00338 }
00339 }
00340
00341 uint raiseToNextPowerOf2(uint v)
00342 {
00343 uint res=1;
00344 while(res<v)
00345 res<<=1;
00346
00347 return res;
00348 }
00349
00350 uint getPowerOf2(uint v)
00351 {
00352 uint res=1;
00353 uint ret=0;
00354 while(res<v)
00355 {
00356 ret++;
00357 res<<=1;
00358 }
00359
00360 return ret;
00361 }
00362
00363 bool isPowerOf2(sint32 v)
00364 {
00365 while(v)
00366 {
00367 if(v&1)
00368 {
00369 v>>=1;
00370 if(v)
00371 return false;
00372 }
00373 else
00374 v>>=1;
00375 }
00376
00377 return true;
00378 }
00379
00380 string bytesToHumanReadable (uint32 bytes)
00381 {
00382 static char *divTable[]= { "b", "kb", "mb", "gb", "tb" };
00383 uint div = 0;
00384 float res = (float)bytes;
00385 float newres = res;
00386 while (true)
00387 {
00388 newres /= 1024;
00389 if(newres < 1.0f || div > 4)
00390 break;
00391 div++;
00392 res = newres;
00393 }
00394 int ires = (int) res;
00395 if (res-(float)ires < .01f)
00396 return toString ("%.0f%s", res, divTable[div]);
00397 else
00398 return toString ("%.2f%s", res, divTable[div]);
00399 }
00400
00401 NLMISC_COMMAND(bthr, "Convert a bytes number into an human readable", "<int>")
00402 {
00403 if (args.size() != 1)
00404 return false;
00405
00406 log.displayNL("%d -> %s", atoi(args[0].c_str()), bytesToHumanReadable(atoi(args[0].c_str())).c_str());
00407
00408 return true;
00409 }
00410
00411 std::string strlwr ( const std::string &str )
00412 {
00413 string res;
00414 res.reserve (str.size());
00415 for (uint i=0; i<str.size(); i++)
00416 {
00417 if ( (str[i] >= 'A') && (str[i] <= 'Z') )
00418 res += str[i] - 'A' + 'a';
00419 else
00420 res += str[i];
00421 }
00422
00423 return res;
00424 }
00425
00426 std::string &strlwr ( std::string &str )
00427 {
00428 for (int i=str.size()-1; i>=0; i--)
00429 {
00430 if ( (str[i] >= 'A') && (str[i] <= 'Z') )
00431 {
00432 str[i] = str[i] - 'A' + 'a';
00433 }
00434 }
00435
00436 return (str);
00437 }
00438
00439 char *strlwr ( char *str )
00440 {
00441 if (str == NULL)
00442 return (NULL);
00443
00444 while (*str != '\0')
00445 {
00446 if ( (*str >= 'A') && (*str <= 'Z') )
00447 {
00448 *str = *str - 'A' + 'a';
00449 }
00450 str++;
00451 }
00452
00453 return (str);
00454 }
00455
00456 std::string &strupr ( std::string &str )
00457 {
00458 for (int i=str.size()-1; i>=0; i--)
00459 {
00460 if ( (str[i] >= 'a') && (str[i] <= 'z') )
00461 {
00462 str[i] = str[i] - 'a' + 'A';
00463 }
00464 }
00465
00466 return (str);
00467 }
00468
00469 char *strupr ( char *str )
00470 {
00471 if (str == NULL)
00472 return (NULL);
00473
00474 while (*str != '\0')
00475 {
00476 if ( (*str >= 'a') && (*str <= 'z') )
00477 {
00478 *str = *str - 'a' + 'A';
00479 }
00480 str++;
00481 }
00482
00483 return (str);
00484 }
00485
00486 sint nlstricmp(const char *lhs,const char *rhs)
00487 {
00488 nlassert(lhs);
00489 nlassert(rhs);
00490 uint lchar, rchar;
00491 while (*lhs != '\0' && *rhs != '\0')
00492 {
00493 lchar = ::toupper(*lhs);
00494 rchar = ::toupper(*rhs);
00495 if (lchar != rchar) return lchar - rchar;
00496 ++lhs;
00497 ++rhs;
00498 }
00499 if (*lhs != 0) return 1;
00500 if (*rhs != 0) return -1;
00501 return 0;
00502 }
00503
00504 sint nlstricmp(const std::string &lhs,const std::string &rhs)
00505 {
00506 return nlstricmp(lhs.c_str(), rhs.c_str());
00507 }
00508
00509
00510
00511
00512
00513
00514
00515 Exception::Exception() : _Reason("Unknown Exception")
00516 {
00517
00518 }
00519
00520 Exception::Exception(const std::string &reason) : _Reason(reason)
00521 {
00522 nlinfo("Exception will be launched: %s", _Reason.c_str());
00523 }
00524
00525 Exception::Exception(const char *format, ...)
00526 {
00527 NLMISC_CONVERT_VARGS (_Reason, format, NLMISC::MaxCStringSize);
00528 nlinfo("Exception will be launched: %s", _Reason.c_str());
00529 }
00530
00531 const char *Exception::what() const throw()
00532 {
00533 return _Reason.c_str();
00534 }
00535
00536 bool launchProgram (const std::string &programName, const std::string &arguments)
00537 {
00538
00539 #ifdef NL_OS_WINDOWS
00540
00541 SECURITY_ATTRIBUTES sa;
00542 sa.nLength = sizeof (sa);
00543 sa.lpSecurityDescriptor = NULL;
00544 sa.bInheritHandle = FALSE;
00545
00546 STARTUPINFO si;
00547 si.cb = sizeof (si);
00548 si.lpReserved = NULL;
00549 si.lpDesktop = NULL;
00550 si.lpTitle = NULL;
00551 si.dwFlags = STARTF_USESHOWWINDOW;
00552 si.cbReserved2 = 0;
00553 si.wShowWindow = SW_MINIMIZE;
00554 si.lpReserved2 = NULL;
00555
00556 PROCESS_INFORMATION pi;
00557
00558 BOOL res = CreateProcess(programName.c_str(), (char*)arguments.c_str(), &sa, &sa, FALSE, 0, NULL, NULL, &si, &pi);
00559
00560 if (res)
00561 {
00562 nldebug("Successful launch '%s' with arg '%s'", programName.c_str(), arguments.c_str());
00563 return true;
00564 }
00565 else
00566 {
00567 LPVOID lpMsgBuf;
00568 FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, GetLastError(), MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR) &lpMsgBuf, 0, NULL);
00569 nlwarning("Failed launched '%s' with arg '%s' err %d: '%s'", programName.c_str(), arguments.c_str(), GetLastError (), lpMsgBuf);
00570 LocalFree(lpMsgBuf);
00571 }
00572
00573 #elif defined(NL_OS_UNIX)
00574
00575 int status = vfork ();
00576 if (status == -1)
00577 {
00578 char *err = strerror (errno);
00579 nlwarning("Failed launched '%s' with arg '%s' err %d: '%s'", programName.c_str(), arguments.c_str(), errno, err);
00580 }
00581 else if (status == 0)
00582 {
00583 status = execlp(programName.c_str(), programName.c_str(), arguments.c_str(), 0);
00584 if (status == -1)
00585 {
00586 perror("Failed launched");
00587 _exit(EXIT_FAILURE);
00588 }
00589 }
00590 else
00591 {
00592 nldebug("Successful launch '%s' with arg '%s'", programName.c_str(), arguments.c_str());
00593 return true;
00594 }
00595 #else
00596 nlwarning ("launchProgram() not implemented");
00597 #endif
00598
00599 return false;
00600
00601 }
00602
00603 }