Xinqi Bao's Git

d9bd0188249a4e19be22a8c0753f9deef3591b39
[slstatus.git] / components / cpu.c
1 /* See LICENSE file for copyright and license details. */
2 #include <stdint.h>
3 #include <stdio.h>
4 #include <string.h>
5
6 #include "../util.h"
7
8 #if defined(__linux__)
9 const char *
10 cpu_freq(void)
11 {
12 uintmax_t freq;
13
14 /* in kHz */
15 if (pscanf("/sys/devices/system/cpu/cpu0/cpufreq/"
16 "scaling_cur_freq", "%ju", &freq) != 1) {
17 return NULL;
18 }
19
20 return fmt_human(freq * 1000, 1000);
21 }
22
23 const char *
24 cpu_perc(void)
25 {
26 static long double a[7];
27 long double b[7];
28
29 memcpy(b, a, sizeof(b));
30 /* cpu user nice system idle iowait irq softirq */
31 if (pscanf("/proc/stat", "%*s %Lf %Lf %Lf %Lf %Lf %Lf %Lf",
32 &a[0], &a[1], &a[2], &a[3], &a[4], &a[5], &a[6])
33 != 7) {
34 return NULL;
35 }
36 if (b[0] == 0) {
37 return NULL;
38 }
39
40 return bprintf("%d", (int)(100 *
41 ((b[0] + b[1] + b[2] + b[5] + b[6]) -
42 (a[0] + a[1] + a[2] + a[5] + a[6])) /
43 ((b[0] + b[1] + b[2] + b[3] + b[4] + b[5] +
44 b[6]) -
45 (a[0] + a[1] + a[2] + a[3] + a[4] + a[5] +
46 a[6]))));
47 }
48 #elif defined(__OpenBSD__)
49 #include <sys/param.h>
50 #include <sys/sched.h>
51 #include <sys/sysctl.h>
52
53 const char *
54 cpu_freq(void)
55 {
56 int freq, mib[2];
57 size_t size;
58
59 mib[0] = CTL_HW;
60 mib[1] = HW_CPUSPEED;
61
62 size = sizeof(freq);
63
64 /* in MHz */
65 if (sysctl(mib, 2, &freq, &size, NULL, 0) < 0) {
66 warn("sysctl 'HW_CPUSPEED':");
67 return NULL;
68 }
69
70 return fmt_human(freq * 1E6, 1000);
71 }
72
73 const char *
74 cpu_perc(void)
75 {
76 int mib[2];
77 static uintmax_t a[CPUSTATES];
78 uintmax_t b[CPUSTATES];
79 size_t size;
80
81 mib[0] = CTL_KERN;
82 mib[1] = KERN_CPTIME;
83
84 size = sizeof(a);
85
86 memcpy(b, a, sizeof(b));
87 if (sysctl(mib, 2, &a, &size, NULL, 0) < 0) {
88 warn("sysctl 'KERN_CPTIME':");
89 return NULL;
90 }
91 if (b[0] == 0) {
92 return NULL;
93 }
94
95 return bprintf("%d", 100 *
96 ((a[CP_USER] + a[CP_NICE] + a[CP_SYS] +
97 a[CP_INTR]) -
98 (b[CP_USER] + b[CP_NICE] + b[CP_SYS] +
99 b[CP_INTR])) /
100 ((a[CP_USER] + a[CP_NICE] + a[CP_SYS] +
101 a[CP_INTR] + a[CP_IDLE]) -
102 (b[CP_USER] + b[CP_NICE] + b[CP_SYS] +
103 b[CP_INTR] + b[CP_IDLE])));
104 }
105 #elif defined(__FreeBSD__)
106 #include <sys/param.h>
107 #include <sys/sysctl.h>
108 #include <devstat.h>
109
110 const char *
111 cpu_freq(void)
112 {
113 int freq;
114 size_t size;
115
116 size = sizeof(freq);
117 /* in MHz */
118 if (sysctlbyname("hw.clockrate", &freq, &size, NULL, 0) == -1
119 || !size) {
120 warn("sysctlbyname 'hw.clockrate':");
121 return NULL;
122 }
123
124 return fmt_human(freq * 1E6, 1000);
125 }
126
127 const char *
128 cpu_perc(void)
129 {
130 size_t size;
131 static long a[CPUSTATES];
132 long b[CPUSTATES];
133
134 size = sizeof(a);
135 memcpy(b, a, sizeof(b));
136 if (sysctlbyname("kern.cp_time", &a, &size, NULL, 0) == -1
137 || !size) {
138 warn("sysctlbyname 'kern.cp_time':");
139 return NULL;
140 }
141 if (b[0] == 0) {
142 return NULL;
143 }
144
145 return bprintf("%d", 100 *
146 ((a[CP_USER] + a[CP_NICE] + a[CP_SYS] +
147 a[CP_INTR]) -
148 (b[CP_USER] + b[CP_NICE] + b[CP_SYS] +
149 b[CP_INTR])) /
150 ((a[CP_USER] + a[CP_NICE] + a[CP_SYS] +
151 a[CP_INTR] + a[CP_IDLE]) -
152 (b[CP_USER] + b[CP_NICE] + b[CP_SYS] +
153 b[CP_INTR] + b[CP_IDLE])));
154 }
155 #endif