File indexing completed on 2024-04-28 15:14:03
0001 /* 0002 * Author: David Robert Nadeau 0003 * Site: http://NadeauSoftware.com/ 0004 * License: Creative Commons Attribution 3.0 Unported License 0005 * http://creativecommons.org/licenses/by/3.0/deed.en_US 0006 */ 0007 0008 //http://nadeausoftware.com/articles/2012/07/c_c_tip_how_get_process_resident_set_size_physical_memory_use 0009 0010 #if defined(_WIN32) 0011 #include <windows.h> 0012 #include <psapi.h> 0013 0014 #elif defined(__unix__) || defined(__unix) || defined(unix) || (defined(__APPLE__) && defined(__MACH__)) 0015 #include <unistd.h> 0016 #include <sys/resource.h> 0017 0018 #if defined(__APPLE__) && defined(__MACH__) 0019 #include <mach/mach.h> 0020 0021 #elif (defined(_AIX) || defined(__TOS__AIX__)) || (defined(__sun__) || defined(__sun) || defined(sun) && (defined(__SVR4) || defined(__svr4__))) 0022 #include <fcntl.h> 0023 #include <procfs.h> 0024 0025 #elif defined(__linux__) || defined(__linux) || defined(linux) || defined(__gnu_linux__) 0026 #include <stdio.h> 0027 0028 #endif 0029 0030 #else 0031 #error "Cannot define getPeakRSS( ) or getCurrentRSS( ) for an unknown OS." 0032 #endif 0033 0034 0035 0036 0037 0038 /** 0039 * Returns the peak (maximum so far) resident set size (physical 0040 * memory use) measured in bytes, or zero if the value cannot be 0041 * determined on this OS. 0042 */ 0043 size_t getPeakRSS( ) 0044 { 0045 #if defined(_WIN32) 0046 /* Windows -------------------------------------------------- */ 0047 PROCESS_MEMORY_COUNTERS info; 0048 GetProcessMemoryInfo( GetCurrentProcess( ), &info, sizeof(info) ); 0049 return (size_t)info.PeakWorkingSetSize; 0050 0051 #elif (defined(_AIX) || defined(__TOS__AIX__)) || (defined(__sun__) || defined(__sun) || defined(sun) && (defined(__SVR4) || defined(__svr4__))) 0052 /* AIX and Solaris ------------------------------------------ */ 0053 struct psinfo psinfo; 0054 int fd = -1; 0055 if ( (fd = open( "/proc/self/psinfo", O_RDONLY )) == -1 ) 0056 return (size_t)0L; /* Can't open? */ 0057 if ( read( fd, &psinfo, sizeof(psinfo) ) != sizeof(psinfo) ) 0058 { 0059 close( fd ); 0060 return (size_t)0L; /* Can't read? */ 0061 } 0062 close( fd ); 0063 return (size_t)(psinfo.pr_rssize * 1024L); 0064 0065 #elif defined(__unix__) || defined(__unix) || defined(unix) || (defined(__APPLE__) && defined(__MACH__)) 0066 /* BSD, Linux, and OSX -------------------------------------- */ 0067 struct rusage rusage; 0068 getrusage( RUSAGE_SELF, &rusage ); 0069 #if defined(__APPLE__) && defined(__MACH__) 0070 return (size_t)rusage.ru_maxrss; 0071 #else 0072 return (size_t)(rusage.ru_maxrss * 1024L); 0073 #endif 0074 0075 #else 0076 /* Unknown OS ----------------------------------------------- */ 0077 return (size_t)0L; /* Unsupported. */ 0078 #endif 0079 } 0080 0081 0082 0083 0084 0085 /** 0086 * Returns the current resident set size (physical memory use) measured 0087 * in bytes, or zero if the value cannot be determined on this OS. 0088 */ 0089 size_t getCurrentRSS( ) 0090 { 0091 #if defined(_WIN32) 0092 /* Windows -------------------------------------------------- */ 0093 PROCESS_MEMORY_COUNTERS info; 0094 GetProcessMemoryInfo( GetCurrentProcess( ), &info, sizeof(info) ); 0095 return (size_t)info.WorkingSetSize; 0096 0097 #elif defined(__APPLE__) && defined(__MACH__) 0098 /* OSX ------------------------------------------------------ */ 0099 struct mach_task_basic_info info; 0100 mach_msg_type_number_t infoCount = MACH_TASK_BASIC_INFO_COUNT; 0101 if ( task_info( mach_task_self( ), MACH_TASK_BASIC_INFO, 0102 (task_info_t)&info, &infoCount ) != KERN_SUCCESS ) 0103 return (size_t)0L; /* Can't access? */ 0104 return (size_t)info.resident_size; 0105 0106 #elif defined(__linux__) || defined(__linux) || defined(linux) || defined(__gnu_linux__) 0107 /* Linux ---------------------------------------------------- */ 0108 long rss = 0L; 0109 FILE* fp = NULL; 0110 if ( (fp = fopen( "/proc/self/statm", "r" )) == NULL ) 0111 return (size_t)0L; /* Can't open? */ 0112 if ( fscanf( fp, "%*s%ld", &rss ) != 1 ) 0113 { 0114 fclose( fp ); 0115 return (size_t)0L; /* Can't read? */ 0116 } 0117 fclose( fp ); 0118 0119 if ((size_t)rss > std::numeric_limits<size_t>::max()/(size_t)sysconf( _SC_PAGESIZE)) 0120 return std::numeric_limits<size_t>::max(); 0121 else 0122 return (size_t)rss * (size_t)sysconf( _SC_PAGESIZE); 0123 0124 #else 0125 /* AIX, BSD, Solaris, and Unknown OS ------------------------ */ 0126 return (size_t)0L; /* Unsupported. */ 0127 #endif 0128 }