24#ifndef CASA_HOSTINFOLINUX_H
25#define CASA_HOSTINFOLINUX_H
27# if defined(HOSTINFO_DO_IMPLEMENT)
58#include <sys/resource.h>
82#include <linux/proc_fs.h>
84#define PROC_SUPER_MAGIC 0x9fa0
88#define CPUINFO "/proc/cpuinfo"
89#define MEMINFO "/proc/meminfo"
91#define bytetok(x) (((x) + 512) >> 10)
95class HostMachineInfo {
104 ptrdiff_t memory_total;
105 ptrdiff_t memory_used;
106 ptrdiff_t memory_free;
108 ptrdiff_t swap_total;
117skip_ws(
const char *p)
119 while (isspace(*p)) p++;
124skip_token(
const char *p)
126 while (isspace(*p)) p++;
127 while (*p && !isspace(*p)) p++;
138get_cgroup_limit(std::string group, std::string
value, std::string sub_value=
"")
140 uInt64 result = std::numeric_limits<uInt64>::max();
142 const std::string cgroup = std::string(
"/sys/fs/cgroup/") + group +
"/";
146 std::ifstream ifs(
"/proc/self/cgroup", std::ifstream::in);
147 std::string hierarchy;
148 while (getline(ifs, line)) {
149 std::stringstream ss(line);
151 std::vector<std::string> fields;
152 while (getline(ss, token,
':')) {
153 fields.push_back(token);
155 if (fields.size() % 3 != 0) {
158 for (std::vector<std::string>::size_type i=1; i < fields.size(); i+=3) {
159 if (fields[i].find(group) != std::string::npos) {
160 hierarchy = fields[i + 1] +
"/";
164 if (hierarchy.size() == 0) {
168 std::ifstream flimit((cgroup + hierarchy +
value).c_str(), std::ifstream::in);
170 if (!flimit.is_open()) {
171 flimit.open((cgroup +
value).c_str(), std::ifstream::in);
173 if (flimit.is_open()) {
174 if (!sub_value.empty()) {
176 while (getline(flimit, line)) {
177 std::stringstream ss(line);
180 if (token == sub_value) {
193HostMachineInfo::HostMachineInfo( ) : valid(1)
200 if (sched_getaffinity(0,
sizeof(cpuset), &cpuset) == 0) {
202 cpus = CPU_COUNT(&cpuset);
204 for (
int i = 0; i < CPU_SETSIZE; i++) {
205 if (CPU_ISSET(i, &cpuset)) {
216 if (statfs(PROCFS, &sb) < 0 || sb.f_type != PROC_SUPER_MAGIC)
218 fprintf( stderr,
"proc filesystem not mounted on " PROCFS
"\n" );
228 FILE *fptr = fopen(CPUINFO,
"r");
229 while ( (p = fgets( buffer,
sizeof(buffer), fptr )) ) {
230 if ( ! strncmp( p,
"processor", 9 ) ) ++cpus;
239void HostMachineInfo::update_info( )
247 unsigned long sys_mem_total, sys_mem_free, sys_mem_cached,
248 sys_mem_avail, sys_swap_total, sys_swap_free;
250 fd = open(MEMINFO, O_RDONLY);
251 len = ::read(fd, buffer,
sizeof(buffer)-1);
255 p = strstr(buffer,
"MemTotal:");
257 if (sscanf (p,
"MemTotal: %lu kB\nMemFree: %lu kB\n",
258 &sys_mem_total, &sys_mem_free) != 2)
259 cerr <<
"Error parsing MemTotal and MemFree in /proc/meminfo\n";
261 p = strstr (buffer,
"Cached:");
262 if (sscanf (p,
"Cached: %lu kB\n", &sys_mem_cached) != 1)
263 cerr <<
"Error parsing Cached in /proc/meminfo\n";
267 p = strstr (buffer,
"MemAvailable:");
268 if (!p || sscanf (p,
"MemAvailable: %lu kB\n", &sys_mem_avail) != 1) {
270 sys_mem_avail = sys_mem_cached + sys_mem_free;
275 if (getrlimit(RLIMIT_RSS, &rlim) == 0 && rlim.rlim_cur > 0) {
276 sys_mem_total = std::min(rlim.rlim_cur / 1024, (rlim_t)sys_mem_total);
278 sys_mem_avail = std::min(sys_mem_total, sys_mem_avail);
282 uInt64 proc_mem_max = get_cgroup_limit(
"memory",
"memory.limit_in_bytes") / 1024;
284 uInt64 proc_mem_used = get_cgroup_limit(
"memory",
"memory.stat",
"total_rss") / 1024;
287 memory_total = std::min((uInt64)sys_mem_total, proc_mem_max);
290 if (proc_mem_max <= sys_mem_total && proc_mem_used <= proc_mem_max) {
291 memory_free = proc_mem_max - proc_mem_used;
295 memory_free = std::min((uInt64)sys_mem_avail, (uInt64)memory_total);
297 memory_used = memory_total - memory_free;
299 p = strstr (buffer,
"SwapTotal:");
300 if (sscanf (p,
"SwapTotal: %lu kB\nSwapFree: %lu kB\n",
301 &sys_swap_total, &sys_swap_free) != 2)
302 cerr <<
"Error parsing SwapTotal and SwapFree in /proc/meminfo\n";
305 uInt64 proc_swap_max = get_cgroup_limit(
"memory",
"memory.memsw.limit_in_bytes") / 1024;
306 uInt64 proc_swap_used = get_cgroup_limit(
"memory",
"memory.stat",
"total_swap") / 1024;
308 if (proc_mem_max <= sys_mem_total && proc_mem_max <= proc_swap_max) {
309 proc_swap_max = proc_swap_max - proc_mem_max;
313 swap_total = std::min((uInt64)sys_swap_total, proc_swap_max);
315 if (proc_swap_max <= (uInt64)swap_total && proc_swap_used <= proc_swap_max) {
316 swap_free = proc_swap_max - proc_swap_used;
319 swap_free = sys_swap_free;
321 swap_used = swap_total - swap_free;
this file contains all the compiler specific defines
void close() override
Flush and close the file.
LatticeExprNode value(const LatticeExprNode &expr)
This function returns the value of the expression without a mask.
unsigned long long uInt64