xref: /aosp_15_r20/external/bcc/examples/cgroupid/cgroupid.c (revision 387f9dfdfa2baef462e92476d413c7bc2470293e)
1 #define _GNU_SOURCE
2 #include <stdlib.h>
3 #include <stdio.h>
4 #include <sys/types.h>
5 #include <sys/stat.h>
6 #include <fcntl.h>
7 #include <stdint.h>
8 #include <ctype.h>
9 #include <unistd.h>
10 #include <linux/magic.h>
11 #include <sys/vfs.h>
12 #include <string.h>
13 #include <errno.h>
14 
15 /* 67e9c74b8a873408c27ac9a8e4c1d1c8d72c93ff (4.5) */
16 #ifndef CGROUP2_SUPER_MAGIC
17 #define CGROUP2_SUPER_MAGIC 0x63677270
18 #endif
19 
20 struct cgid_file_handle
21 {
22   //struct file_handle handle;
23   unsigned int handle_bytes;
24   int handle_type;
25   uint64_t cgid;
26 };
27 
get_cgroupid(const char * pathname)28 uint64_t get_cgroupid(const char *pathname) {
29   struct statfs fs;
30   int err;
31   struct cgid_file_handle *h;
32   int mount_id;
33   uint64_t ret;
34 
35   err = statfs(pathname, &fs);
36   if (err != 0) {
37     fprintf (stderr, "statfs on %s failed: %s\n", pathname, strerror(errno));
38     exit(1);
39   }
40 
41   if ((fs.f_type != (typeof(fs.f_type)) CGROUP2_SUPER_MAGIC)) {
42     fprintf (stderr, "File %s is not on a cgroup2 mount.\n", pathname);
43     exit(1);
44   }
45 
46   h = malloc(sizeof(struct cgid_file_handle));
47   if (!h) {
48     fprintf (stderr, "Cannot allocate memory.\n");
49     exit(1);
50   }
51 
52   h->handle_bytes = 8;
53   err = name_to_handle_at(AT_FDCWD, pathname, (struct file_handle *)h, &mount_id, 0);
54   if (err != 0) {
55     fprintf (stderr, "name_to_handle_at failed: %s\n", strerror(errno));
56     exit(1);
57   }
58 
59   if (h->handle_bytes != 8) {
60     fprintf (stderr, "Unexpected handle size: %d. \n", h->handle_bytes);
61     exit(1);
62   }
63 
64   ret = h->cgid;
65   free(h);
66 
67   return ret;
68 }
69 
usage()70 void usage() {
71     fprintf (stderr, "Usage: cgroupid FORMAT FILE\n");
72     fprintf (stderr, "Print the cgroup id of a cgroup2 directory.\n");
73     fprintf (stderr, "Example: cgroupid print-hex /sys/fs/cgroup/unified/system.slice/test.service\n");
74     fprintf (stderr, "\n");
75     fprintf (stderr, "Format:\n");
76     fprintf (stderr, "  number    print the cgroup id as a number\n");
77     fprintf (stderr, "  hex       print the cgroup id as a hexadecimal, suitable for bpftool\n");
78     fprintf (stderr, "\n");
79 }
80 
main(int argc,char ** argv)81 int main(int argc, char **argv) {
82   uint64_t cgroupid;
83   int i;
84 
85   if (argc != 3 || (strcmp(argv[1], "number") != 0 && strcmp(argv[1], "hex"))) {
86     usage();
87     exit(1);
88   }
89 
90   cgroupid = get_cgroupid(argv[2]);
91 
92   if (strcmp(argv[1], "number") == 0)
93     printf("%lu\n", cgroupid);
94 
95   if (strcmp(argv[1], "hex") == 0) {
96     for (i=0; i<8; i++) {
97       printf("%02x%s", ((unsigned char *)&cgroupid)[i], i == 7 ? "\n":" ");
98     }
99   }
100   return 0;
101 }
102