1 #include <stdio.h>
2 #include <inttypes.h>
3 #include <stdint.h>
4 #include <stdlib.h>
5 #include <getopt.h>
6 #include <string.h>
7 #include <errno.h>
8 
9 const char* smaps_file = "smaps";
10 bool verbose = false;
11 int iterations = 1;
12 int bufsz = -1;
13 
14 int64_t
get_pss(int pid)15 get_pss(int pid)
16 {
17   char filename[64];
18   snprintf(filename, sizeof(filename), "/proc/%" PRId32 "/%s", pid,
19            smaps_file);
20   if (verbose)
21     fprintf(stderr, "smaps:[%s]\n", filename);
22 
23   FILE * file = fopen(filename, "r");
24   if (!file) {
25     return (int64_t) -1;
26   }
27 
28   if (bufsz >= 0) {
29     if (setvbuf(file, NULL, _IOFBF, bufsz)) {
30       fprintf(stderr, "setvbuf failed: %s\n", strerror(errno));
31       exit(1);
32     }
33   }
34 
35   // Tally up all of the Pss from the various maps
36   char line[256];
37   int64_t pss = 0;
38   while (fgets(line, sizeof(line), file)) {
39     int64_t v;
40     if (sscanf(line, "Pss: %" SCNd64 " kB", &v) == 1) {
41       if (verbose)
42         fprintf(stderr, "pss line: %llu\n", (unsigned long long) v);
43       pss += v;
44     }
45   }
46 
47   fclose(file);
48 
49   // Return the Pss value in bytes, not kilobytes
50   return pss * 1024;
51 }
52 
53 int
main(int argc,char ** argv)54 main(int argc, char** argv)
55 {
56   int c;
57   while ((c = getopt(argc, argv, "n:rvb:")) != -1) {
58     switch (c) {
59       case 'r':
60         smaps_file = "smaps_rollup";
61         break;
62       case 'v':
63         verbose = true;
64         break;
65       case 'n':
66         iterations = atoi(optarg);
67         break;
68       case 'b':
69         bufsz = atoi(optarg);
70         break;
71       default:
72         return 1;
73     }
74   }
75 
76   if (argv[optind] == NULL) {
77     fprintf(stderr, "pssbench: no PID given\n");
78     return 1;
79   }
80   int pid = atoi(argv[optind]);
81   int64_t pss = 0;
82   for (int i = 0; i < iterations; ++i)
83     pss = get_pss(pid);
84   fflush(NULL);
85 
86   printf("iterations:%d pid:%d pss:%lld\n", iterations, pid, (long long)pss);
87   return 0;
88 }
89