1#include <unistd.h>
2#include <stdlib.h>
3#include <stdio.h>
4#include <getopt.h>
5#include <errno.h>
6#include <string.h>
7#include <selinux/selinux.h>
8
9static void usage(const char *progname)
10{
11    fprintf(stderr, "usage:  %s -a or %s boolean...\n", progname, progname);
12    exit(1);
13}
14
15int getsebool_main(int argc, char **argv)
16{
17    int i, get_all = 0, rc = 0, active, pending, len = 0, opt;
18    char **names;
19
20    while ((opt = getopt(argc, argv, "a")) > 0) {
21        switch (opt) {
22        case 'a':
23            if (argc > 2)
24                usage(argv[0]);
25            if (is_selinux_enabled() <= 0) {
26                fprintf(stderr, "%s:  SELinux is disabled\n",
27                        argv[0]);
28                return 1;
29            }
30            errno = 0;
31            rc = security_get_boolean_names(&names, &len);
32            if (rc) {
33                fprintf(stderr,
34                        "%s:  Unable to get boolean names:  %s\n",
35                        argv[0], strerror(errno));
36                return 1;
37            }
38            if (!len) {
39                printf("No booleans\n");
40                return 0;
41            }
42            get_all = 1;
43            break;
44        default:
45            usage(argv[0]);
46        }
47    }
48
49    if (is_selinux_enabled() <= 0) {
50        fprintf(stderr, "%s:  SELinux is disabled\n", argv[0]);
51        return 1;
52    }
53    if (!len) {
54        if (argc < 2)
55            usage(argv[0]);
56        len = argc - 1;
57        names = malloc(sizeof(char *) * len);
58        if (!names) {
59            fprintf(stderr, "%s:  out of memory\n", argv[0]);
60            return 2;
61        }
62        for (i = 0; i < len; i++) {
63            names[i] = strdup(argv[i + 1]);
64            if (!names[i]) {
65                fprintf(stderr, "%s:  out of memory\n",
66                        argv[0]);
67                return 2;
68            }
69        }
70    }
71
72    for (i = 0; i < len; i++) {
73        active = security_get_boolean_active(names[i]);
74        if (active < 0) {
75            if (get_all && errno == EACCES)
76                continue;
77            fprintf(stderr, "Error getting active value for %s\n",
78                    names[i]);
79            rc = -1;
80            goto out;
81        }
82        pending = security_get_boolean_pending(names[i]);
83        if (pending < 0) {
84            fprintf(stderr, "Error getting pending value for %s\n",
85                    names[i]);
86            rc = -1;
87            goto out;
88        }
89        if (pending != active) {
90            printf("%s --> %s pending: %s\n", names[i],
91                   (active ? "on" : "off"),
92                   (pending ? "on" : "off"));
93        } else {
94            printf("%s --> %s\n", names[i],
95                   (active ? "on" : "off"));
96        }
97    }
98
99out:
100    for (i = 0; i < len; i++)
101        free(names[i]);
102    free(names);
103    return rc;
104}
105