ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/i-scream/projects/libstatgrab/src/libstatgrab/disk_stats.c
Revision: 1.37
Committed: Sun Oct 19 21:22:09 2003 UTC (20 years, 6 months ago) by ats
Content type: text/plain
Branch: MAIN
CVS Tags: LIBSTATGRAB_0_7
Changes since 1.36: +1 -1 lines
Log Message:
Correct comment about where dk_rbytes is available.

File Contents

# User Rev Content
1 pajs 1.1 /*
2     * i-scream central monitoring system
3 tdb 1.18 * http://www.i-scream.org
4     * Copyright (C) 2000-2003 i-scream
5 pajs 1.1 *
6     * This program is free software; you can redistribute it and/or
7     * modify it under the terms of the GNU General Public License
8     * as published by the Free Software Foundation; either version 2
9     * of the License, or (at your option) any later version.
10     *
11     * This program 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
14     * GNU General Public License for more details.
15     *
16     * You should have received a copy of the GNU General Public License
17     * along with this program; if not, write to the Free Software
18     * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
19     */
20    
21     #ifdef HAVE_CONFIG_H
22     #include "config.h"
23     #endif
24    
25 pajs 1.17 #include <stdio.h>
26 pajs 1.1 #include <stdlib.h>
27     #include <string.h>
28 tdb 1.7 #include "statgrab.h"
29 pajs 1.1
30     #ifdef SOLARIS
31     #include <sys/mnttab.h>
32     #include <sys/statvfs.h>
33 pajs 1.4 #include <kstat.h>
34 pajs 1.1 #define VALID_FS_TYPES {"ufs", "tmpfs"}
35     #endif
36    
37 pajs 1.9 #ifdef LINUX
38 ats 1.30 #include <time.h>
39 pajs 1.9 #include <sys/vfs.h>
40     #include <mntent.h>
41 pajs 1.10 #include "tools.h"
42 ats 1.32 #define VALID_FS_TYPES {"adfs", "affs", "befs", "bfs", "efs", "ext2", \
43     "ext3", "vxfs", "hfs", "hfsplus", "hpfs", "jffs", \
44     "jffs2", "minix", "msdos", "ntfs", "qnx4", "ramfs", \
45     "rootfs", "reiserfs", "sysv", "v7", "udf", "ufs", \
46     "umsdos", "vfat", "xfs", "jfs"}
47 pajs 1.9 #endif
48    
49 ats 1.31 #ifdef ALLBSD
50 pajs 1.16 #include <sys/param.h>
51     #include <sys/ucred.h>
52     #include <sys/mount.h>
53 ats 1.31 #endif
54     #ifdef FREEBSD
55 pajs 1.17 #include <sys/dkstat.h>
56     #include <devstat.h>
57 ats 1.36 #define VALID_FS_TYPES {"hpfs", "msdosfs", "ntfs", "udf", "ext2fs", \
58     "ufs", "mfs"}
59 pajs 1.16 #endif
60 ats 1.34 #ifdef NETBSD
61     #include <sys/param.h>
62     #include <sys/sysctl.h>
63     #include <sys/disk.h>
64 ats 1.35 #define VALID_FS_TYPES {"ffs", "mfs", "msdos", "lfs", "adosfs", "ext2fs", \
65     "ntfs"}
66 ats 1.34 #endif
67 ats 1.31
68 pajs 1.1 #define START_VAL 1
69    
70     char *copy_string(char *orig_ptr, const char *newtext){
71    
72     /* Maybe free if not NULL, and strdup rather than realloc and strcpy? */
73     orig_ptr=realloc(orig_ptr, (1+strlen(newtext)));
74     if(orig_ptr==NULL){
75     return NULL;
76     }
77     strcpy(orig_ptr, newtext);
78    
79     return orig_ptr;
80     }
81    
82    
83     void init_disk_stat(int start, int end, disk_stat_t *disk_stats){
84    
85     for(disk_stats+=start; start<=end; start++){
86     disk_stats->device_name=NULL;
87     disk_stats->fs_type=NULL;
88     disk_stats->mnt_point=NULL;
89    
90     disk_stats++;
91     }
92     }
93    
94     disk_stat_t *get_disk_stats(int *entries){
95    
96     static disk_stat_t *disk_stats;
97     static int watermark=-1;
98    
99     char *fs_types[] = VALID_FS_TYPES;
100     int x, valid_type;
101     int num_disks=0;
102 pajs 1.16 #if defined(LINUX) || defined (SOLARIS)
103 pajs 1.1 FILE *f;
104 pajs 1.16 #endif
105 pajs 1.1
106     disk_stat_t *disk_ptr;
107    
108 pajs 1.9 #ifdef SOLARIS
109 tdb 1.13 struct mnttab mp;
110 pajs 1.9 struct statvfs fs;
111     #endif
112     #ifdef LINUX
113     struct mntent *mp;
114     struct statfs fs;
115     #endif
116 ats 1.31 #ifdef ALLBSD
117 pajs 1.16 int nummnt;
118     struct statfs *mp;
119     #endif
120 pajs 1.9
121 pajs 1.1 if(watermark==-1){
122     disk_stats=malloc(START_VAL * sizeof(disk_stat_t));
123     if(disk_stats==NULL){
124     return NULL;
125     }
126     watermark=START_VAL;
127     init_disk_stat(0, watermark-1, disk_stats);
128     }
129 ats 1.31 #ifdef ALLBSD
130 pajs 1.16 nummnt=getmntinfo(&mp , MNT_LOCAL);
131     if (nummnt<=0){
132     return NULL;
133     }
134     for(;nummnt--; mp++){
135     valid_type=0;
136     for(x=0;x<((sizeof(fs_types))/(sizeof(char*)));x++){
137     if(strcmp(mp->f_fstypename, fs_types[x]) ==0){
138     valid_type=1;
139     break;
140     }
141     }
142     #endif
143    
144 pajs 1.9 #ifdef LINUX
145     if ((f=setmntent("/etc/mtab", "r" ))==NULL){
146     return NULL;
147     }
148 pajs 1.1
149 pajs 1.9 while((mp=getmntent(f))){
150     if((statfs(mp->mnt_dir, &fs)) !=0){
151     continue;
152     }
153 pajs 1.1
154 pajs 1.9 valid_type=0;
155     for(x=0;x<((sizeof(fs_types))/(sizeof(char*)));x++){
156     if(strcmp(mp->mnt_type, fs_types[x]) ==0){
157     valid_type=1;
158     break;
159     }
160     }
161     #endif
162    
163     #ifdef SOLARIS
164 pajs 1.1 if ((f=fopen("/etc/mnttab", "r" ))==NULL){
165     return NULL;
166     }
167     while((getmntent(f, &mp)) == 0){
168     if ((statvfs(mp.mnt_mountp, &fs)) !=0){
169     continue;
170     }
171     valid_type=0;
172     for(x=0;x<((sizeof(fs_types))/(sizeof(char*)));x++){
173     if(strcmp(mp.mnt_fstype, fs_types[x]) ==0){
174     valid_type=1;
175     break;
176     }
177     }
178 pajs 1.9 #endif
179 pajs 1.1
180     if(valid_type){
181     if(num_disks>watermark-1){
182     disk_ptr=disk_stats;
183     if((disk_stats=realloc(disk_stats, (watermark*2 * sizeof(disk_stat_t))))==NULL){
184     disk_stats=disk_ptr;
185     return NULL;
186     }
187    
188     watermark=watermark*2;
189     init_disk_stat(num_disks, watermark-1, disk_stats);
190     }
191    
192     disk_ptr=disk_stats+num_disks;
193 ats 1.31 #ifdef ALLBSD
194 pajs 1.16 if((disk_ptr->device_name=copy_string(disk_ptr->device_name, mp->f_mntfromname))==NULL){
195     return NULL;
196     }
197    
198     if((disk_ptr->fs_type=copy_string(disk_ptr->fs_type, mp->f_fstypename))==NULL){
199     return NULL;
200     }
201    
202     if((disk_ptr->mnt_point=copy_string(disk_ptr->mnt_point, mp->f_mntonname))==NULL){
203     return NULL;
204     }
205    
206     disk_ptr->size = (long long)mp->f_bsize * (long long) mp->f_blocks;
207     disk_ptr->avail = (long long)mp->f_bsize * (long long) mp->f_bavail;
208     disk_ptr->used = (disk_ptr->size) - ((long long)mp->f_bsize * (long long)mp->f_bfree);
209    
210     disk_ptr->total_inodes=(long long)mp->f_files;
211     disk_ptr->free_inodes=(long long)mp->f_ffree;
212     /* Freebsd doesn't have a "available" inodes */
213     disk_ptr->used_inodes=disk_ptr->total_inodes-disk_ptr->free_inodes;
214     #endif
215 pajs 1.9 #ifdef LINUX
216     if((disk_ptr->device_name=copy_string(disk_ptr->device_name, mp->mnt_fsname))==NULL){
217     return NULL;
218     }
219    
220     if((disk_ptr->fs_type=copy_string(disk_ptr->fs_type, mp->mnt_type))==NULL){
221     return NULL;
222     }
223    
224     if((disk_ptr->mnt_point=copy_string(disk_ptr->mnt_point, mp->mnt_dir))==NULL){
225     return NULL;
226     }
227     disk_ptr->size = (long long)fs.f_bsize * (long long)fs.f_blocks;
228     disk_ptr->avail = (long long)fs.f_bsize * (long long)fs.f_bavail;
229     disk_ptr->used = (disk_ptr->size) - ((long long)fs.f_bsize * (long long)fs.f_bfree);
230    
231     disk_ptr->total_inodes=(long long)fs.f_files;
232     disk_ptr->free_inodes=(long long)fs.f_ffree;
233     /* Linux doesn't have a "available" inodes */
234     disk_ptr->used_inodes=disk_ptr->total_inodes-disk_ptr->free_inodes;
235     #endif
236    
237     #ifdef SOLARIS
238 pajs 1.1 /* Memory leak in event of realloc failing */
239     /* Maybe make this char[bigenough] and do strncpy's and put a null in the end?
240 pajs 1.9 * Downside is its a bit hungry for a lot of mounts, as MNT_MAX_SIZE would prob
241     * be upwards of a k each
242     */
243 pajs 1.1 if((disk_ptr->device_name=copy_string(disk_ptr->device_name, mp.mnt_special))==NULL){
244     return NULL;
245     }
246    
247     if((disk_ptr->fs_type=copy_string(disk_ptr->fs_type, mp.mnt_fstype))==NULL){
248     return NULL;
249     }
250    
251     if((disk_ptr->mnt_point=copy_string(disk_ptr->mnt_point, mp.mnt_mountp))==NULL){
252     return NULL;
253     }
254    
255     disk_ptr->size = (long long)fs.f_frsize * (long long)fs.f_blocks;
256     disk_ptr->avail = (long long)fs.f_frsize * (long long)fs.f_bavail;
257     disk_ptr->used = (disk_ptr->size) - ((long long)fs.f_frsize * (long long)fs.f_bfree);
258    
259     disk_ptr->total_inodes=(long long)fs.f_files;
260     disk_ptr->used_inodes=disk_ptr->total_inodes - (long long)fs.f_ffree;
261     disk_ptr->free_inodes=(long long)fs.f_favail;
262 pajs 1.9 #endif
263 pajs 1.1 num_disks++;
264     }
265     }
266    
267     *entries=num_disks;
268    
269     /* If this fails, there is very little i can do about it, so i'll ignore it :) */
270 pajs 1.16 #if defined(LINUX) || defined(SOLARIS)
271 pajs 1.1 fclose(f);
272 pajs 1.16 #endif
273 pajs 1.1
274     return disk_stats;
275    
276     }
277 pajs 1.4 void diskio_stat_init(int start, int end, diskio_stat_t *diskio_stats){
278    
279     for(diskio_stats+=start; start<end; start++){
280     diskio_stats->disk_name=NULL;
281    
282     diskio_stats++;
283     }
284     }
285    
286     diskio_stat_t *diskio_stat_malloc(int needed_entries, int *cur_entries, diskio_stat_t *diskio_stats){
287    
288     if(diskio_stats==NULL){
289    
290     if((diskio_stats=malloc(needed_entries * sizeof(diskio_stat_t)))==NULL){
291     return NULL;
292     }
293     diskio_stat_init(0, needed_entries, diskio_stats);
294     *cur_entries=needed_entries;
295    
296     return diskio_stats;
297     }
298    
299    
300     if(*cur_entries<needed_entries){
301     diskio_stats=realloc(diskio_stats, (sizeof(diskio_stat_t)*needed_entries));
302     if(diskio_stats==NULL){
303     return NULL;
304     }
305     diskio_stat_init(*cur_entries, needed_entries, diskio_stats);
306     *cur_entries=needed_entries;
307     }
308    
309     return diskio_stats;
310     }
311    
312     static diskio_stat_t *diskio_stats=NULL;
313 pajs 1.5 static int num_diskio=0;
314 pajs 1.4
315 ats 1.20 #ifdef LINUX
316     typedef struct {
317     int major;
318     int minor;
319     } partition;
320     #endif
321    
322 tdb 1.3 diskio_stat_t *get_diskio_stats(int *entries){
323 pajs 1.2
324 pajs 1.4 static int sizeof_diskio_stats=0;
325     diskio_stat_t *diskio_stats_ptr;
326    
327 pajs 1.10 #ifdef SOLARIS
328 pajs 1.4 kstat_ctl_t *kc;
329     kstat_t *ksp;
330     kstat_io_t kios;
331 pajs 1.10 #endif
332     #ifdef LINUX
333     FILE *f;
334     char *line_ptr;
335     int major, minor;
336     char dev_letter;
337 ats 1.20 int has_pp_stats = 1;
338     static partition *parts = NULL;
339     static int alloc_parts = 0;
340     int i, n;
341     time_t now;
342 pajs 1.10 #endif
343 pajs 1.17 #ifdef FREEBSD
344 ats 1.21 static struct statinfo stats;
345     static int stats_init = 0;
346 pajs 1.17 int counter;
347     struct device_selection *dev_sel = NULL;
348     int n_selected, n_selections;
349     long sel_gen;
350     struct devstat *dev_ptr;
351 ats 1.31 #endif
352     #ifdef NETBSD
353 ats 1.34 struct disk_sysctl *stats;
354     int num_disks, i;
355     int mib[3];
356     size_t size;
357 pajs 1.17 #endif
358 ats 1.34
359 pajs 1.10 num_diskio=0;
360 ats 1.34
361     #ifdef NETBSD
362     mib[0] = CTL_HW;
363     mib[1] = HW_DISKSTATS;
364     mib[2] = sizeof(struct disk_sysctl);
365    
366     if (sysctl(mib, 3, NULL, &size, NULL, 0) < 0) {
367     return NULL;
368     }
369     num_disks = size / sizeof(struct disk_sysctl);
370    
371     stats = malloc(size);
372     if (stats == NULL) {
373     return NULL;
374     }
375    
376     if (sysctl(mib, 3, stats, &size, NULL, 0) < 0) {
377     return NULL;
378     }
379    
380     for (i = 0; i < num_disks; i++) {
381     u_int64_t rbytes, wbytes;
382    
383     #ifdef HAVE_DK_RBYTES
384     rbytes = stats[i].dk_rbytes;
385     wbytes = stats[i].dk_wbytes;
386     #else
387 ats 1.37 /* Before 1.7, NetBSD merged reads and writes. */
388 ats 1.34 rbytes = wbytes = stats[i].dk_bytes;
389     #endif
390    
391     /* Don't keep stats for disks that have never been used. */
392     if (rbytes == 0 && wbytes == 0) {
393     continue;
394     }
395    
396     diskio_stats = diskio_stat_malloc(num_diskio + 1,
397     &sizeof_diskio_stats,
398     diskio_stats);
399     if (diskio_stats == NULL) {
400     return NULL;
401     }
402     diskio_stats_ptr = diskio_stats + num_diskio;
403    
404     diskio_stats_ptr->read_bytes = rbytes;
405     diskio_stats_ptr->write_bytes = wbytes;
406     if (diskio_stats_ptr->disk_name != NULL) {
407     free(diskio_stats_ptr->disk_name);
408     }
409     diskio_stats_ptr->disk_name = strdup(stats[i].dk_name);
410     diskio_stats_ptr->systime = time(NULL);
411    
412     num_diskio++;
413     }
414    
415     free(stats);
416     #endif
417 pajs 1.4
418 pajs 1.17 #ifdef FREEBSD
419 ats 1.21 if (!stats_init) {
420     stats.dinfo=malloc(sizeof(struct devinfo));
421 ats 1.33 if(stats.dinfo==NULL) return NULL;
422 tdb 1.25 bzero(stats.dinfo, sizeof(struct devinfo));
423 ats 1.21 stats_init = 1;
424     }
425 pajs 1.28 #ifdef FREEBSD5
426     if ((devstat_getdevs(NULL, &stats)) < 0) return NULL;
427 ats 1.29 /* Not aware of a get all devices, so i said 999. If we ever
428     * find a machine with more than 999 disks, then i'll change
429     * this number :)
430     */
431 pajs 1.28 if (devstat_selectdevs(&dev_sel, &n_selected, &n_selections, &sel_gen, stats.dinfo->generation, stats.dinfo->devices, stats.dinfo->numdevs, NULL, 0, NULL, 0, DS_SELECT_ONLY, 999, 1) < 0) return NULL;
432     #else
433 pajs 1.17 if ((getdevs(&stats)) < 0) return NULL;
434     /* Not aware of a get all devices, so i said 999. If we ever
435     * find a machine with more than 999 disks, then i'll change
436     * this number :)
437     */
438     if (selectdevs(&dev_sel, &n_selected, &n_selections, &sel_gen, stats.dinfo->generation, stats.dinfo->devices, stats.dinfo->numdevs, NULL, 0, NULL, 0, DS_SELECT_ONLY, 999, 1) < 0) return NULL;
439 pajs 1.27 #endif
440 pajs 1.17
441     for(counter=0;counter<stats.dinfo->numdevs;counter++){
442     dev_ptr=&stats.dinfo->devices[dev_sel[counter].position];
443    
444     /* Throw away devices that have done nothing, ever.. Eg "odd"
445     * devices.. like mem, proc.. and also doesn't report floppy
446     * drives etc unless they are doing stuff :)
447     */
448 pajs 1.27 #ifdef FREEBSD5
449     if((dev_ptr->bytes[DEVSTAT_READ]==0) && (dev_ptr->bytes[DEVSTAT_WRITE]==0)) continue;
450     #else
451 pajs 1.17 if((dev_ptr->bytes_read==0) && (dev_ptr->bytes_written==0)) continue;
452 pajs 1.27 #endif
453 pajs 1.17 if((diskio_stats=diskio_stat_malloc(num_diskio+1, &sizeof_diskio_stats, diskio_stats))==NULL){
454     return NULL;
455     }
456     diskio_stats_ptr=diskio_stats+num_diskio;
457 pajs 1.27
458     #ifdef FREEBSD5
459     diskio_stats_ptr->read_bytes=dev_ptr->bytes[DEVSTAT_READ];
460     diskio_stats_ptr->write_bytes=dev_ptr->bytes[DEVSTAT_WRITE];
461     #else
462 pajs 1.17 diskio_stats_ptr->read_bytes=dev_ptr->bytes_read;
463     diskio_stats_ptr->write_bytes=dev_ptr->bytes_written;
464 pajs 1.27 #endif
465 pajs 1.17 if(diskio_stats_ptr->disk_name!=NULL) free(diskio_stats_ptr->disk_name);
466     asprintf((&diskio_stats_ptr->disk_name), "%s%d", dev_ptr->device_name, dev_ptr->unit_number);
467     diskio_stats_ptr->systime=time(NULL);
468    
469     num_diskio++;
470     }
471     free(dev_sel);
472    
473     #endif
474 pajs 1.10 #ifdef SOLARIS
475 pajs 1.4 if ((kc = kstat_open()) == NULL) {
476     return NULL;
477     }
478    
479     for (ksp = kc->kc_chain; ksp; ksp = ksp->ks_next) {
480     if (!strcmp(ksp->ks_class, "disk")) {
481    
482     if(ksp->ks_type != KSTAT_TYPE_IO) continue;
483 pajs 1.5 /* We dont want metadevices appearins as num_diskio */
484 pajs 1.4 if(strcmp(ksp->ks_module, "md")==0) continue;
485     if((kstat_read(kc, ksp, &kios))==-1){
486     }
487    
488 pajs 1.5 if((diskio_stats=diskio_stat_malloc(num_diskio+1, &sizeof_diskio_stats, diskio_stats))==NULL){
489 pajs 1.4 kstat_close(kc);
490     return NULL;
491     }
492 pajs 1.5 diskio_stats_ptr=diskio_stats+num_diskio;
493 pajs 1.4
494     diskio_stats_ptr->read_bytes=kios.nread;
495    
496     diskio_stats_ptr->write_bytes=kios.nwritten;
497    
498     if(diskio_stats_ptr->disk_name!=NULL) free(diskio_stats_ptr->disk_name);
499    
500 tdb 1.26 diskio_stats_ptr->disk_name=strdup(ksp->ks_name);
501 pajs 1.14 diskio_stats_ptr->systime=time(NULL);
502 pajs 1.5 num_diskio++;
503 pajs 1.4 }
504     }
505    
506     kstat_close(kc);
507 pajs 1.10 #endif
508 pajs 1.4
509 pajs 1.10 #ifdef LINUX
510 ats 1.20 num_diskio = 0;
511     n = 0;
512 pajs 1.10
513 ats 1.20 /* Read /proc/partitions to find what devices exist. Recent 2.4 kernels
514     have statistics in here too, so we can use those directly. */
515 pajs 1.10
516 ats 1.20 f = fopen("/proc/partitions", "r");
517     if (f == NULL) goto out;
518     now = time(NULL);
519    
520     while ((line_ptr = f_read_line(f, "")) != NULL) {
521     char name[20];
522     char *s;
523     long long rsect, wsect;
524    
525     int nr = sscanf(line_ptr,
526     " %d %d %*d %19s %*d %*d %lld %*d %*d %*d %lld",
527     &major, &minor, name, &rsect, &wsect);
528     if (nr < 3) continue;
529     if (nr < 5) {
530     has_pp_stats = 0;
531     rsect = 0;
532     wsect = 0;
533     }
534    
535     /* Skip device names ending in numbers, since they're
536     partitions. */
537     s = name;
538     while (*s != '\0') s++;
539     --s;
540     if (*s >= '0' && *s <= '9') continue;
541    
542     diskio_stats = diskio_stat_malloc(n + 1, &sizeof_diskio_stats,
543     diskio_stats);
544     if (diskio_stats == NULL) goto out;
545     if (n >= alloc_parts) {
546     alloc_parts += 16;
547     parts = realloc(parts, alloc_parts * sizeof *parts);
548     if (parts == NULL) {
549     alloc_parts = 0;
550     goto out;
551     }
552 pajs 1.11 }
553 pajs 1.12
554 ats 1.20 if (diskio_stats[n].disk_name != NULL)
555     free(diskio_stats[n].disk_name);
556     diskio_stats[n].disk_name = strdup(name);
557     diskio_stats[n].read_bytes = rsect * 512;
558     diskio_stats[n].write_bytes = wsect * 512;
559     diskio_stats[n].systime = now;
560     parts[n].major = major;
561     parts[n].minor = minor;
562 pajs 1.10
563 ats 1.20 n++;
564     }
565 pajs 1.10
566 ats 1.20 if (!has_pp_stats) {
567     /* This is an older kernel without stats in /proc/partitions.
568     Read what we can from /proc/stat instead. */
569    
570     f = fopen("/proc/stat", "r");
571     if (f == NULL) goto out;
572     now = time(NULL);
573    
574     line_ptr = f_read_line(f, "disk_io:");
575     if (line_ptr == NULL) goto out;
576    
577     while((line_ptr=strchr(line_ptr, ' '))!=NULL){
578     long long rsect, wsect;
579    
580     if (*++line_ptr == '\0') break;
581    
582     if((sscanf(line_ptr,
583     "(%d,%d):(%*d, %*d, %lld, %*d, %lld)",
584     &major, &minor, &rsect, &wsect)) != 4) {
585     continue;
586     }
587 pajs 1.10
588 ats 1.20 /* Find the corresponding device from earlier.
589     Just to add to the fun, "minor" is actually the disk
590     number, not the device minor, so we need to figure
591     out the real minor number based on the major!
592     This list is not exhaustive; if you're running
593     an older kernel you probably don't have fancy
594     I2O hardware anyway... */
595     switch (major) {
596     case 3:
597     case 21:
598 pajs 1.10 case 22:
599 ats 1.20 case 33:
600     case 34:
601     case 36:
602     case 56:
603     case 57:
604     case 88:
605     case 89:
606     case 90:
607     case 91:
608     minor *= 64;
609 pajs 1.11 break;
610 ats 1.20 case 9:
611     case 43:
612 pajs 1.11 break;
613 pajs 1.10 default:
614 ats 1.20 minor *= 16;
615 pajs 1.11 break;
616 ats 1.20 }
617     for (i = 0; i < n; i++) {
618     if (major == parts[i].major
619     && minor == parts[i].minor)
620     break;
621     }
622     if (i == n) continue;
623    
624     /* We read the number of blocks. Blocks are stored in
625     512 bytes */
626     diskio_stats[i].read_bytes = rsect * 512;
627     diskio_stats[i].write_bytes = wsect * 512;
628     diskio_stats[i].systime = now;
629 pajs 1.10 }
630     }
631 pajs 1.16
632 ats 1.20 num_diskio = n;
633     out:
634     if (f != NULL) fclose(f);
635 pajs 1.10
636     #endif
637 pajs 1.5 *entries=num_diskio;
638 pajs 1.4
639     return diskio_stats;
640 pajs 1.5 }
641    
642 pajs 1.6 diskio_stat_t *get_diskio_stats_diff(int *entries){
643 pajs 1.5 static diskio_stat_t *diskio_stats_diff=NULL;
644     static int sizeof_diskio_stats_diff=0;
645     diskio_stat_t *diskio_stats_diff_ptr, *diskio_stats_ptr;
646     int disks, x, y;
647    
648     if(diskio_stats==NULL){
649     diskio_stats_ptr=get_diskio_stats(&disks);
650     *entries=disks;
651     return diskio_stats_ptr;
652     }
653    
654     diskio_stats_diff=diskio_stat_malloc(num_diskio, &sizeof_diskio_stats_diff, diskio_stats_diff);
655     if(diskio_stats_diff==NULL){
656     return NULL;
657     }
658    
659     diskio_stats_diff_ptr=diskio_stats_diff;
660     diskio_stats_ptr=diskio_stats;
661    
662     for(disks=0;disks<num_diskio;disks++){
663     if(diskio_stats_diff_ptr->disk_name!=NULL){
664     free(diskio_stats_diff_ptr->disk_name);
665     }
666     diskio_stats_diff_ptr->disk_name=strdup(diskio_stats_ptr->disk_name);
667     diskio_stats_diff_ptr->read_bytes=diskio_stats_ptr->read_bytes;
668     diskio_stats_diff_ptr->write_bytes=diskio_stats_ptr->write_bytes;
669     diskio_stats_diff_ptr->systime=diskio_stats_ptr->systime;
670    
671     diskio_stats_diff_ptr++;
672     diskio_stats_ptr++;
673     }
674    
675     diskio_stats_ptr=get_diskio_stats(&disks);
676     diskio_stats_diff_ptr=diskio_stats_diff;
677    
678     for(x=0;x<sizeof_diskio_stats_diff;x++){
679    
680     if((strcmp(diskio_stats_diff_ptr->disk_name, diskio_stats_ptr->disk_name))==0){
681     diskio_stats_diff_ptr->read_bytes=diskio_stats_ptr->read_bytes-diskio_stats_diff_ptr->read_bytes;
682     diskio_stats_diff_ptr->write_bytes=diskio_stats_ptr->write_bytes-diskio_stats_diff_ptr->write_bytes;
683     diskio_stats_diff_ptr->systime=diskio_stats_ptr->systime-diskio_stats_diff_ptr->systime;
684     }else{
685     diskio_stats_ptr=diskio_stats;
686     for(y=0;y<disks;y++){
687     if((strcmp(diskio_stats_diff_ptr->disk_name, diskio_stats_ptr->disk_name))==0){
688     diskio_stats_diff_ptr->read_bytes=diskio_stats_ptr->read_bytes-diskio_stats_diff_ptr->read_bytes;
689     diskio_stats_diff_ptr->write_bytes=diskio_stats_ptr->write_bytes-diskio_stats_diff_ptr->write_bytes;
690     diskio_stats_diff_ptr->systime=diskio_stats_ptr->systime-diskio_stats_diff_ptr->systime;
691    
692     break;
693     }
694    
695     diskio_stats_ptr++;
696     }
697     }
698    
699     diskio_stats_ptr++;
700     diskio_stats_diff_ptr++;
701    
702     }
703 pajs 1.8
704     *entries=sizeof_diskio_stats_diff;
705 pajs 1.5 return diskio_stats_diff;
706 pajs 1.2 }