MachineSpecs.cpp
1 /*********************************************************************
2 * Software License Agreement (BSD License)
3 *
4 * Copyright (c) 2010, Rice University
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 *
11 * * Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above
14 * copyright notice, this list of conditions and the following
15 * disclaimer in the documentation and/or other materials provided
16 * with the distribution.
17 * * Neither the name of the Rice University nor the names of its
18 * contributors may be used to endorse or promote products derived
19 * from this software without specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
25 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
27 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
29 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
31 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32 * POSSIBILITY OF SUCH DAMAGE.
33 *********************************************************************/
34 
35 /* Author: The Internet */
36 
37 #include "ompl/tools/benchmark/MachineSpecs.h"
38 #include "ompl/util/Console.h"
39 #include <sstream>
40 
42 
43 #if defined _WIN32
44 
45 // Windows 2000 or newer
46 #include <winsock2.h>
47 #include <windows.h>
48 #include <stdio.h>
49 #include <psapi.h>
50 
51 ompl::machine::MemUsage_t getProcessMemoryUsageAux()
52 {
53  HANDLE hProcess;
54  PROCESS_MEMORY_COUNTERS pmc;
55 
56  hProcess = OpenProcess( PROCESS_QUERY_INFORMATION |
57  PROCESS_VM_READ,
58  false,
59  GetCurrentProcessId() );
60 
61  ompl::machine::MemUsage_t result = 0;
62 
63  if (NULL != hProcess)
64  {
65  if ( GetProcessMemoryInfo( hProcess, &pmc, sizeof(pmc)) )
66  result = pmc.WorkingSetSize;
67  CloseHandle( hProcess );
68  }
69 
70  return result;
71 }
72 
73 std::string getCPUInfoAux()
74 {
75  static const int BUF_SIZE = 256;
76  char buffer[BUF_SIZE];
77  std::stringstream result;
78  FILE *cmdPipe = _popen("wmic cpu list full", "rt");
79  if (cmdPipe != NULL)
80  {
81  while (fgets(buffer, BUF_SIZE, cmdPipe))
82  result << buffer;
83  if (feof(cmdPipe))
84  _pclose(cmdPipe);
85  }
86  return result.str();
87 }
88 
89 
90 #else
91 #if defined __APPLE__
92 
93 // Mac OS 10.2 or newer
94 #include <mach/mach_init.h>
95 #include <mach/task.h>
96 #include <sys/time.h>
97 #include <sys/resource.h>
98 #include <stdint.h>
99 #include <cstring>
100 #include <unistd.h>
101 
102 ompl::machine::MemUsage_t getProcessMemoryUsageAux()
103 {
104 
105  task_basic_info info;
106  kern_return_t rval = 0;
107  mach_port_t task = mach_task_self();
108  mach_msg_type_number_t tcnt = TASK_BASIC_INFO_COUNT;
109  task_info_t tptr = (task_info_t) &info;
110 
111  memset(&info, 0, sizeof(info));
112 
113  rval = task_info(task, TASK_BASIC_INFO, tptr, &tcnt);
114  if (!(rval == KERN_SUCCESS)) return 0;
115  return info.resident_size;
116 }
117 
118 std::string getCPUInfoAux()
119 {
120  static const int BUF_SIZE = 256;
121  char buffer[BUF_SIZE];
122  std::stringstream result;
123  FILE *cmdPipe = popen("sysctl hw", "r");
124  if (cmdPipe != NULL)
125  {
126  while (fgets(buffer, BUF_SIZE, cmdPipe))
127  result << buffer;
128  if (feof(cmdPipe))
129  pclose(cmdPipe);
130  }
131  return result.str();
132 }
133 
134 #else
135 #if defined _POSIX_VERSION || defined _POSIX2_VERSION || defined __linux__
136 // we need a posix compliant os that exposes /proc/self/stat
137 
138 #include <unistd.h>
139 #include <ios>
140 #include <iostream>
141 #include <fstream>
142 
143 ompl::machine::MemUsage_t getProcessMemoryUsageAux()
144 {
145  using std::ios_base;
146  using std::ifstream;
147  using std::string;
148 
149  // 'file' stat seems to give the most reliable results
150  //
151  ifstream stat_stream("/proc/self/stat",ios_base::in);
152 
153  if (stat_stream.good() && !stat_stream.eof())
154  {
155  // dummy vars for leading entries in stat that we don't care about
156  //
157  string pid, comm, state, ppid, pgrp, session, tty_nr;
158  string tpgid, flags, minflt, cminflt, majflt, cmajflt;
159  string utime, stime, cutime, cstime, priority, nice;
160  string O, itrealvalue, starttime;
161 
162 
163  // the two fields we want
164  //
165  unsigned long vsize;
166  long rss;
167 
168  stat_stream >> pid >> comm >> state >> ppid >> pgrp >> session >> tty_nr
169  >> tpgid >> flags >> minflt >> cminflt >> majflt >> cmajflt
170  >> utime >> stime >> cutime >> cstime >> priority >> nice
171  >> O >> itrealvalue >> starttime >> vsize >> rss; // don't care about the rest
172 
173  ompl::machine::MemUsage_t page_size = sysconf(_SC_PAGE_SIZE);
174  return rss * page_size;
175  }
176  return 0;
177 }
178 
179 std::string getCPUInfoAux()
180 {
181  static const int BUF_SIZE = 4096;
182  char buffer[BUF_SIZE];
183  std::stringstream result;
184  FILE *cmdPipe = popen("lscpu", "r");
185  if (cmdPipe != NULL)
186  {
187  while (fgets(buffer, BUF_SIZE, cmdPipe))
188  result << buffer;
189  if (feof(cmdPipe))
190  pclose(cmdPipe);
191  }
192  return result.str();
193 }
194 
195 #else
196 // if we have no idea what to do, we return 0
197 ompl::machine::MemUsage_t getProcessMemoryUsageAux()
198 {
199  return 0;
200 }
201 // if we have no idea what to do, we return an empty string
202 std::string getCPUInfoAux()
203 {
204  return std::string();
205 }
206 
207 #endif // posix
208 #endif // apple
209 #endif // windows
210 
212 {
213  MemUsage_t result = getProcessMemoryUsageAux();
214  if (result == 0)
215  {
216  OMPL_WARN("Unable to get memory usage");
217  }
218  return result;
219 }
220 
221 std::string ompl::machine::getCPUInfo()
222 {
223  std::string result = getCPUInfoAux();
224  if (result.size() == 0)
225  {
226  OMPL_WARN("Unable to get CPU information");
227  }
228  return result;
229 }
230 
231 std::string ompl::machine::getHostname()
232 {
233  static const int BUF_SIZE = 1024;
234  char buffer[BUF_SIZE];
235  int len = gethostname(buffer, sizeof(buffer));
236  if (len != 0)
237  return std::string();
238  else
239  {
240  buffer[BUF_SIZE - 1] = '\0';
241  return std::string(buffer);
242  }
243 }
244 
std::string getCPUInfo()
Get information about the CPU of the machine in use.
#define OMPL_WARN(fmt,...)
Log a formatted warning string.
Definition: Console.h:66
MemUsage_t getProcessMemoryUsage()
Get the amount of memory the current process is using. This should work on major platforms (Windows...
unsigned long long MemUsage_t
Amount of memory used, in bytes.
Definition: MachineSpecs.h:50
std::string getHostname()
Get the hostname of the machine in use.