PageRenderTime 30ms CodeModel.GetById 29ms RepoModel.GetById 0ms app.codeStats 0ms

/kyotocabinet/kcutil.cc

https://github.com/albertz/png-db
C++ | 316 lines | 233 code | 38 blank | 45 comment | 61 complexity | 0fa5e7a0381f8435072da6296e2f1fe5 MD5 | raw file
  1. /*************************************************************************************************
  2. * Utility functions
  3. * Copyright (C) 2009-2011 FAL Labs
  4. * This file is part of Kyoto Cabinet.
  5. * This program is free software: you can redistribute it and/or modify it under the terms of
  6. * the GNU General Public License as published by the Free Software Foundation, either version
  7. * 3 of the License, or any later version.
  8. * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
  9. * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  10. * See the GNU General Public License for more details.
  11. * You should have received a copy of the GNU General Public License along with this program.
  12. * If not, see <http://www.gnu.org/licenses/>.
  13. *************************************************************************************************/
  14. #include "kcutil.h"
  15. #include "myconf.h"
  16. namespace kyotocabinet { // common namespace
  17. /** The package version. */
  18. const char* const VERSION = _KC_VERSION;
  19. /** The library version. */
  20. const int32_t LIBVER = _KC_LIBVER;
  21. /** The library revision. */
  22. const int32_t LIBREV = _KC_LIBREV;
  23. /** The database format version. */
  24. const int32_t FMTVER = _KC_FMTVER;
  25. /** The system name. */
  26. const char* const SYSNAME = _KC_SYSNAME;
  27. /** The flag for big endian environments. */
  28. const bool BIGEND = _KC_BIGEND ? true : false;
  29. /** The clock tick of interruption. */
  30. #if defined(_SYS_MSVC_) || defined(_SYS_MINGW_)
  31. const int32_t CLOCKTICK = 100;
  32. #else
  33. const int32_t CLOCKTICK = sysconf(_SC_CLK_TCK);
  34. #endif
  35. /** The size of a page. */
  36. #if defined(_SYS_MSVC_) || defined(_SYS_MINGW_)
  37. static int32_t win_getpagesize() {
  38. ::SYSTEM_INFO ibuf;
  39. ::GetSystemInfo(&ibuf);
  40. return ibuf.dwPageSize;
  41. }
  42. const int32_t PAGESIZE = win_getpagesize();
  43. #else
  44. const int32_t PAGESIZE = sysconf(_SC_PAGESIZE);
  45. #endif
  46. /** The extra feature list. */
  47. const char* const FEATURES = ""
  48. #if _KC_GCCATOMIC
  49. "(atomic)"
  50. #endif
  51. #if _KC_ZLIB
  52. "(zlib)"
  53. #endif
  54. #if _KC_LZO
  55. "(lzo)"
  56. #endif
  57. #if _KC_LZMA
  58. "(lzma)"
  59. #endif
  60. ;
  61. /**
  62. * Allocate a nullified region on memory.
  63. */
  64. void* mapalloc(size_t size) {
  65. #if defined(_SYS_LINUX_)
  66. _assert_(size > 0 && size <= MEMMAXSIZ);
  67. void* ptr = ::mmap(0, sizeof(size) + size,
  68. PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
  69. if (ptr == MAP_FAILED) throw std::bad_alloc();
  70. *(size_t*)ptr = size;
  71. return (char*)ptr + sizeof(size);
  72. #else
  73. _assert_(size > 0 && size <= MEMMAXSIZ);
  74. void* ptr = std::calloc(size, 1);
  75. if (!ptr) throw std::bad_alloc();
  76. return ptr;
  77. #endif
  78. }
  79. /**
  80. * Free a region on memory.
  81. */
  82. void mapfree(void* ptr) {
  83. #if defined(_SYS_LINUX_)
  84. _assert_(ptr);
  85. size_t size = *((size_t*)ptr - 1);
  86. ::munmap((char*)ptr - sizeof(size), sizeof(size) + size);
  87. #else
  88. _assert_(ptr);
  89. std::free(ptr);
  90. #endif
  91. }
  92. /**
  93. * Get the time of day in seconds.
  94. * @return the time of day in seconds. The accuracy is in microseconds.
  95. */
  96. double time() {
  97. #if defined(_SYS_MSVC_) || defined(_SYS_MINGW_)
  98. _assert_(true);
  99. ::FILETIME ft;
  100. ::GetSystemTimeAsFileTime(&ft);
  101. ::LARGE_INTEGER li;
  102. li.LowPart = ft.dwLowDateTime;
  103. li.HighPart = ft.dwHighDateTime;
  104. return li.QuadPart / 10000000.0;
  105. #else
  106. _assert_(true);
  107. struct ::timeval tv;
  108. if (::gettimeofday(&tv, NULL) != 0) return 0.0;
  109. return tv.tv_sec + tv.tv_usec / 1000000.0;
  110. #endif
  111. }
  112. /**
  113. * Get the process ID.
  114. */
  115. int64_t getpid() {
  116. #if defined(_SYS_MSVC_) || defined(_SYS_MINGW_)
  117. _assert_(true);
  118. return ::GetCurrentProcessId();
  119. #else
  120. _assert_(true);
  121. return ::getpid();
  122. #endif
  123. }
  124. /**
  125. * Get the value of an environment variable.
  126. */
  127. const char* getenv(const char* name) {
  128. _assert_(name);
  129. return ::getenv(name);
  130. }
  131. /**
  132. * Get system information of the environment.
  133. */
  134. void getsysinfo(std::map<std::string, std::string>* strmap) {
  135. #if defined(_SYS_LINUX_)
  136. _assert_(strmap);
  137. struct ::rusage rbuf;
  138. std::memset(&rbuf, 0, sizeof(rbuf));
  139. if (::getrusage(RUSAGE_SELF, &rbuf) == 0) {
  140. (*strmap)["ru_utime"] = strprintf("%0.6f",
  141. rbuf.ru_utime.tv_sec + rbuf.ru_utime.tv_usec / 1000000.0);
  142. (*strmap)["ru_stime"] = strprintf("%0.6f",
  143. rbuf.ru_stime.tv_sec + rbuf.ru_stime.tv_usec / 1000000.0);
  144. if (rbuf.ru_maxrss > 0) {
  145. int64_t size = rbuf.ru_maxrss * 1024LL;
  146. (*strmap)["mem_peak"] = strprintf("%lld", (long long)size);
  147. (*strmap)["mem_size"] = strprintf("%lld", (long long)size);
  148. (*strmap)["mem_rss"] = strprintf("%lld", (long long)size);
  149. }
  150. }
  151. std::ifstream ifs;
  152. ifs.open("/proc/self/status", std::ios_base::in | std::ios_base::binary);
  153. if (ifs) {
  154. std::string line;
  155. while (getline(ifs, line)) {
  156. size_t idx = line.find(':');
  157. if (idx != std::string::npos) {
  158. const std::string& name = line.substr(0, idx);
  159. idx++;
  160. while (idx < line.size() && line[idx] >= '\0' && line[idx] <= ' ') {
  161. idx++;
  162. }
  163. const std::string& value = line.substr(idx);
  164. if (name == "VmPeak") {
  165. int64_t size = atoix(value.c_str());
  166. if (size > 0) (*strmap)["mem_peak"] = strprintf("%lld", (long long)size);
  167. } else if (name == "VmSize") {
  168. int64_t size = atoix(value.c_str());
  169. if (size > 0) (*strmap)["mem_size"] = strprintf("%lld", (long long)size);
  170. } else if (name == "VmRSS") {
  171. int64_t size = atoix(value.c_str());
  172. if (size > 0) (*strmap)["mem_rss"] = strprintf("%lld", (long long)size);
  173. }
  174. }
  175. }
  176. ifs.close();
  177. }
  178. ifs.open("/proc/meminfo", std::ios_base::in | std::ios_base::binary);
  179. if (ifs) {
  180. std::string line;
  181. while (getline(ifs, line)) {
  182. size_t idx = line.find(':');
  183. if (idx != std::string::npos) {
  184. const std::string& name = line.substr(0, idx);
  185. idx++;
  186. while (idx < line.size() && line[idx] >= '\0' && line[idx] <= ' ') {
  187. idx++;
  188. }
  189. const std::string& value = line.substr(idx);
  190. if (name == "MemTotal") {
  191. int64_t size = atoix(value.c_str());
  192. if (size > 0) (*strmap)["mem_total"] = strprintf("%lld", (long long)size);
  193. } else if (name == "MemFree") {
  194. int64_t size = atoix(value.c_str());
  195. if (size > 0) (*strmap)["mem_free"] = strprintf("%lld", (long long)size);
  196. } else if (name == "Cached") {
  197. int64_t size = atoix(value.c_str());
  198. if (size > 0) (*strmap)["mem_cached"] = strprintf("%lld", (long long)size);
  199. }
  200. }
  201. }
  202. ifs.close();
  203. }
  204. #elif defined(_SYS_MACOSX_)
  205. _assert_(strmap);
  206. struct ::rusage rbuf;
  207. std::memset(&rbuf, 0, sizeof(rbuf));
  208. if (::getrusage(RUSAGE_SELF, &rbuf) == 0) {
  209. (*strmap)["ru_utime"] = strprintf("%0.6f",
  210. rbuf.ru_utime.tv_sec + rbuf.ru_utime.tv_usec / 1000000.0);
  211. (*strmap)["ru_stime"] = strprintf("%0.6f",
  212. rbuf.ru_stime.tv_sec + rbuf.ru_stime.tv_usec / 1000000.0);
  213. if (rbuf.ru_maxrss > 0) {
  214. int64_t size = rbuf.ru_maxrss;
  215. (*strmap)["mem_peak"] = strprintf("%lld", (long long)size);
  216. (*strmap)["mem_size"] = strprintf("%lld", (long long)size);
  217. (*strmap)["mem_rss"] = strprintf("%lld", (long long)size);
  218. }
  219. }
  220. #elif defined(_SYS_FREEBSD_) || defined(_SYS_SUNOS_)
  221. _assert_(strmap);
  222. struct ::rusage rbuf;
  223. std::memset(&rbuf, 0, sizeof(rbuf));
  224. if (::getrusage(RUSAGE_SELF, &rbuf) == 0) {
  225. (*strmap)["ru_utime"] = strprintf("%0.6f",
  226. rbuf.ru_utime.tv_sec + rbuf.ru_utime.tv_usec / 1000000.0);
  227. (*strmap)["ru_stime"] = strprintf("%0.6f",
  228. rbuf.ru_stime.tv_sec + rbuf.ru_stime.tv_usec / 1000000.0);
  229. if (rbuf.ru_maxrss > 0) {
  230. int64_t size = rbuf.ru_maxrss * 1024LL;
  231. (*strmap)["mem_peak"] = strprintf("%lld", (long long)size);
  232. (*strmap)["mem_size"] = strprintf("%lld", (long long)size);
  233. (*strmap)["mem_rss"] = strprintf("%lld", (long long)size);
  234. }
  235. }
  236. #elif defined(_SYS_MSVC_) || defined(_SYS_MINGW_)
  237. _assert_(strmap);
  238. ::DWORD pid = ::GetCurrentProcessId();
  239. ::HANDLE ph = ::OpenProcess(PROCESS_QUERY_INFORMATION, false, pid);
  240. if (ph) {
  241. ::FILETIME ct, et, kt, ut;
  242. if (::GetProcessTimes(ph, &ct, &et, &kt, &ut)) {
  243. ::LARGE_INTEGER li;
  244. li.LowPart = ut.dwLowDateTime;
  245. li.HighPart = ut.dwHighDateTime;
  246. (*strmap)["ru_utime"] = strprintf("%0.6f", li.QuadPart / 10000000.0);
  247. li.LowPart = kt.dwLowDateTime;
  248. li.HighPart = kt.dwHighDateTime;
  249. (*strmap)["ru_stime"] = strprintf("%0.6f", li.QuadPart / 10000000.0);
  250. }
  251. ::CloseHandle(ph);
  252. }
  253. ::MEMORYSTATUSEX msbuf;
  254. msbuf.dwLength = sizeof(msbuf);
  255. ::GlobalMemoryStatusEx(&msbuf);
  256. (*strmap)["mem_total"] = strprintf("%lld", (long long)msbuf.ullTotalPhys);
  257. (*strmap)["mem_free"] = strprintf("%lld", (long long)msbuf.ullAvailPhys);
  258. int64_t cached = msbuf.ullTotalPhys - msbuf.ullAvailPhys;
  259. (*strmap)["mem_cached"] = strprintf("%lld", (long long)cached);
  260. #else
  261. _assert_(strmap);
  262. #endif
  263. }
  264. /**
  265. * Set the standard streams into the binary mode.
  266. */
  267. void setstdiobin() {
  268. #if defined(_SYS_MSVC_) || defined(_SYS_MINGW_)
  269. _assert_(true);
  270. _setmode(_fileno(stdin), O_BINARY);
  271. _setmode(_fileno(stdout), O_BINARY);
  272. _setmode(_fileno(stderr), O_BINARY);
  273. #else
  274. _assert_(true);
  275. #endif
  276. }
  277. } // common namespace
  278. // END OF FILE