ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/i-scream/projects/libstatgrab/src/libstatgrab/os_info.c
Revision: 1.25
Committed: Sun Oct 3 18:35:58 2010 UTC (13 years, 6 months ago) by tdb
Content type: text/plain
Branch: MAIN
CVS Tags: HEAD
Changes since 1.24: +24 -1 lines
Log Message:
Add support for AIX 5.x - 9.x.

Many thanks to Jens Rehsack <rehsack@googlemail.com> for providing the
patch for this work. Thanks!

File Contents

# Content
1 /*
2 * i-scream libstatgrab
3 * http://www.i-scream.org
4 * Copyright (C) 2000-2004 i-scream
5 *
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
19 * 02111-1307 USA
20 *
21 * $Id: os_info.c,v 1.24 2006/10/09 14:09:38 tdb Exp $
22 */
23
24 #ifdef HAVE_CONFIG_H
25 #include "config.h"
26 #endif
27
28 #ifndef WIN32
29 #include <sys/utsname.h>
30 #endif
31 #include "statgrab.h"
32 #include <stdlib.h>
33 #ifdef SOLARIS
34 #include <kstat.h>
35 #include <time.h>
36 #endif
37 #if defined(LINUX) || defined(CYGWIN)
38 #include <stdio.h>
39 #endif
40 #ifdef ALLBSD
41 #if defined(FREEBSD) || defined(DFBSD)
42 #include <sys/types.h>
43 #include <sys/sysctl.h>
44 #else
45 #include <sys/param.h>
46 #include <sys/sysctl.h>
47 #endif
48 #include <time.h>
49 #include <sys/time.h>
50 #endif
51 #ifdef HPUX
52 #include <sys/param.h>
53 #include <sys/pstat.h>
54 #include <time.h>
55 #endif
56 #ifdef AIX
57 #include <utmp.h>
58 #include <libperfstat.h>
59 #endif
60 #ifdef WIN32
61 #include <windows.h>
62 #include "win32.h"
63 #define WINDOWS2000 "Windows 2000"
64 #define WINDOWSXP "Windows XP"
65 #define WINDOWS2003 "Windows Server 2003"
66 #define BUFSIZE 12
67 static int runonce = 0;
68 #endif
69
70 #include "tools.h"
71
72 #ifdef WIN32
73 static int home_or_pro(const OSVERSIONINFOEX osinfo, char **name)
74 {
75 int r;
76
77 if (osinfo.wSuiteMask & VER_SUITE_PERSONAL) {
78 r = sg_concat_string(name, " Home Edition");
79 } else {
80 r = sg_concat_string(name, " Professional");
81 }
82 return r;
83 }
84
85 static char *get_os_name(const OSVERSIONINFOEX osinfo)
86 {
87 char *name;
88 char tmp[10];
89 int r = 0;
90
91 /* we only compile on 2k or newer, which is version 5
92 * Covers 2000, XP and 2003 */
93 if (osinfo.dwMajorVersion != 5) {
94 return "Unknown";
95 }
96 switch(osinfo.dwMinorVersion) {
97 case 0: /* Windows 2000 */
98 name = strdup(WINDOWS2000);
99 if(name == NULL) {
100 goto out;
101 }
102 if (osinfo.wProductType == VER_NT_WORKSTATION) {
103 r = home_or_pro(osinfo, &name);
104 } else if (osinfo.wSuiteMask & VER_SUITE_DATACENTER) {
105 r = sg_concat_string(&name, " Datacenter Server");
106 } else if (osinfo.wSuiteMask & VER_SUITE_ENTERPRISE) {
107 r = sg_concat_string(&name, " Advanced Server");
108 } else {
109 r = sg_concat_string(&name, " Server");
110 }
111 break;
112 case 1: /* Windows XP */
113 name = strdup(WINDOWSXP);
114 if(name == NULL) {
115 goto out;
116 }
117 r = home_or_pro(osinfo, &name);
118 break;
119 case 2: /* Windows 2003 */
120 name = strdup(WINDOWS2003);
121 if(name == NULL) {
122 goto out;
123 }
124 if (osinfo.wSuiteMask & VER_SUITE_DATACENTER) {
125 r = sg_concat_string(&name, " Datacenter Edition");
126 } else if (osinfo.wSuiteMask & VER_SUITE_ENTERPRISE) {
127 r = sg_concat_string(&name, " Enterprise Edition");
128 } else if (osinfo.wSuiteMask & VER_SUITE_BLADE) {
129 r = sg_concat_string(&name, " Web Edition");
130 } else {
131 r = sg_concat_string(&name, " Standard Edition");
132 }
133 break;
134 default:
135 name = strdup("Windows 2000 based");
136 break;
137 }
138 if(r != 0) {
139 free (name);
140 return NULL;
141 }
142 /* Add on service pack version */
143 if (osinfo.wServicePackMajor != 0) {
144 if(osinfo.wServicePackMinor == 0) {
145 if(snprintf(tmp, sizeof(tmp), " SP%d", osinfo.wServicePackMajor) != -1) {
146 r = sg_concat_string(&name, tmp);
147 }
148 } else {
149 if(snprintf(tmp, sizeof(tmp), " SP%d.%d", osinfo.wServicePackMajor,
150 osinfo.wServicePackMinor) != -1) {
151 r = sg_concat_string(&name, tmp);
152 }
153 }
154 if(r) {
155 free(name);
156 return NULL;
157 }
158 }
159 return name;
160
161 out:
162 /* strdup failed */
163 sg_set_error_with_errno(SG_ERROR_MALLOC, NULL);
164 return NULL;
165 }
166 #endif
167
168 sg_host_info *sg_get_host_info()
169 {
170 static sg_host_info general_stat;
171 #ifndef WIN32
172 static struct utsname os;
173 #endif
174
175 #ifdef HPUX
176 struct pst_static *pstat_static;
177 time_t currtime;
178 long boottime;
179 #endif
180 #ifdef SOLARIS
181 time_t boottime,curtime;
182 kstat_ctl_t *kc;
183 kstat_t *ksp;
184 kstat_named_t *kn;
185 #endif
186 #if defined(LINUX) || defined(CYGWIN)
187 FILE *f;
188 #endif
189 #ifdef ALLBSD
190 int mib[2];
191 struct timeval boottime;
192 time_t curtime;
193 size_t size;
194 #endif
195 #ifdef WIN32
196 unsigned long nameln;
197 char *name;
198 long long result;
199 OSVERSIONINFOEX osinfo;
200 SYSTEM_INFO sysinfo;
201 char *tmp_name;
202 char tmp[10];
203 #endif
204 #ifdef AIX
205 static perfstat_cpu_total_t cpu_total;
206 struct utmp *ut;
207 #endif
208
209 #ifndef WIN32 /* Trust windows to be different */
210 if((uname(&os)) < 0){
211 sg_set_error_with_errno(SG_ERROR_UNAME, NULL);
212 return NULL;
213 }
214
215 general_stat.os_name = os.sysname;
216 general_stat.os_release = os.release;
217 general_stat.os_version = os.version;
218 general_stat.platform = os.machine;
219 general_stat.hostname = os.nodename;
220 #else /* WIN32 */
221 if (!runonce) {
222 /* these settings are static after boot, so why get them
223 * constantly? */
224
225 /* get system name */
226 nameln = MAX_COMPUTERNAME_LENGTH + 1;
227 name = sg_malloc(nameln);
228 if(name == NULL) {
229 return NULL;
230 }
231 if(GetComputerName(name, &nameln) == 0) {
232 free(name);
233 sg_set_error(SG_ERROR_HOST, "GetComputerName");
234 return NULL;
235 }
236 if(sg_update_string(&general_stat.hostname, name)) {
237 free(name);
238 return NULL;
239 }
240 free(name);
241
242 /* get OS name, version and build */
243 ZeroMemory(&osinfo, sizeof(OSVERSIONINFOEX));
244 osinfo.dwOSVersionInfoSize = sizeof(osinfo);
245 if(!GetVersionEx(&osinfo)) {
246 sg_set_error(SG_ERROR_HOST, "GetVersionEx");
247 return NULL;
248 }
249
250 /* Release - single number */
251 if(snprintf(tmp, sizeof(tmp), "%ld", osinfo.dwBuildNumber) == -1) {
252 free(tmp);
253 return NULL;
254 }
255 if(sg_update_string(&general_stat.os_release, tmp)) {
256 free(tmp);
257 return NULL;
258 }
259
260 /* Version */
261 /* usually a single digit . single digit, eg 5.0 */
262 if(snprintf(tmp, sizeof(tmp), "%ld.%ld", osinfo.dwMajorVersion,
263 osinfo.dwMinorVersion) == -1) {
264 free(tmp);
265 return NULL;
266 }
267 if(sg_update_string(&general_stat.os_version, tmp)) {
268 free(tmp);
269 return NULL;
270 }
271
272 /* OS name */
273 tmp_name = get_os_name(osinfo);
274 if(tmp_name == NULL) {
275 return NULL;
276 }
277 if(sg_update_string(&general_stat.os_name, tmp_name)) {
278 free(tmp_name);
279 return NULL;
280 }
281 free(tmp_name);
282 runonce = 1;
283
284 /* Platform */
285 GetSystemInfo(&sysinfo);
286 switch(sysinfo.wProcessorArchitecture) {
287 case PROCESSOR_ARCHITECTURE_INTEL:
288 if(sg_update_string(&general_stat.platform,
289 "Intel")) {
290 return NULL;
291 }
292 break;
293 case PROCESSOR_ARCHITECTURE_IA64:
294 if(sg_update_string(&general_stat.platform,
295 "IA64")) {
296 return NULL;
297 }
298 break;
299 case PROCESSOR_ARCHITECTURE_AMD64:
300 if(sg_update_string(&general_stat.platform,
301 "AMD64")) {
302 return NULL;
303 }
304 break;
305 default:
306 if(sg_update_string(&general_stat.platform,
307 "Unknown")){
308 return NULL;
309 }
310 break;
311 }
312 }
313 #endif /* WIN32 */
314
315 /* get uptime */
316 #ifdef HPUX
317 pstat_static = sg_get_pstat_static();
318 if (pstat_static == NULL) {
319 return NULL;
320 }
321
322 currtime = time(NULL);
323
324 boottime = pstat_static->boot_time;
325
326 general_stat.uptime = currtime - boottime;
327 #endif
328 #ifdef SOLARIS
329 if ((kc = kstat_open()) == NULL) {
330 sg_set_error(SG_ERROR_KSTAT_OPEN, NULL);
331 return NULL;
332 }
333 if((ksp=kstat_lookup(kc, "unix", -1, "system_misc"))==NULL){
334 sg_set_error(SG_ERROR_KSTAT_LOOKUP, "unix,-1,system_misc");
335 kstat_close(kc);
336 return NULL;
337 }
338 if (kstat_read(kc, ksp, 0) == -1) {
339 sg_set_error(SG_ERROR_KSTAT_READ, NULL);
340 kstat_close(kc);
341 return NULL;
342 }
343 if((kn=kstat_data_lookup(ksp, "boot_time")) == NULL){
344 sg_set_error(SG_ERROR_KSTAT_DATA_LOOKUP, "boot_time");
345 kstat_close(kc);
346 return NULL;
347 }
348 boottime=(kn->value.ui32);
349
350 kstat_close(kc);
351
352 time(&curtime);
353 general_stat.uptime = curtime - boottime;
354 #endif
355 #if defined(LINUX) || defined(CYGWIN)
356 if ((f=fopen("/proc/uptime", "r")) == NULL) {
357 sg_set_error_with_errno(SG_ERROR_OPEN, "/proc/uptime");
358 return NULL;
359 }
360 if((fscanf(f,"%lu %*d",&general_stat.uptime)) != 1){
361 sg_set_error(SG_ERROR_PARSE, NULL);
362 return NULL;
363 }
364 fclose(f);
365 #endif
366 #ifdef ALLBSD
367 mib[0] = CTL_KERN;
368 mib[1] = KERN_BOOTTIME;
369 size = sizeof boottime;
370 if (sysctl(mib, 2, &boottime, &size, NULL, 0) < 0){
371 sg_set_error_with_errno(SG_ERROR_SYSCTL,
372 "CTL_KERN.KERN_BOOTTIME");
373 return NULL;
374 }
375 time(&curtime);
376 general_stat.uptime=curtime-boottime.tv_sec;
377 #endif
378 #ifdef WIN32
379 if(read_counter_large(SG_WIN32_UPTIME, &result)) {
380 sg_set_error(SG_ERROR_PDHREAD, PDH_UPTIME);
381 return NULL;
382 }
383 general_stat.uptime = (time_t) result;
384 #endif
385 #ifdef AIX
386 if(perfstat_cpu_total(NULL, &cpu_total, sizeof(cpu_total), 1) != 1) {
387 sg_set_error_with_errno(SG_ERROR_SYSCTL, "perfstat_cpu_total");
388 return NULL;
389 }
390 general_stat.platform = cpu_total.description;
391
392 while( ut = getutent() ) {
393 if( ut->ut_type == BOOT_TIME ) {
394 general_stat.uptime = time(NULL) - ut->ut_time;
395 break;
396 }
397 }
398
399 #endif
400
401 return &general_stat;
402
403 }