1*2d543d20SAndroid Build Coastguard Worker #include <unistd.h>
2*2d543d20SAndroid Build Coastguard Worker #include <sys/types.h>
3*2d543d20SAndroid Build Coastguard Worker #include <fcntl.h>
4*2d543d20SAndroid Build Coastguard Worker #include <stdlib.h>
5*2d543d20SAndroid Build Coastguard Worker #include <stdio.h>
6*2d543d20SAndroid Build Coastguard Worker #include <errno.h>
7*2d543d20SAndroid Build Coastguard Worker #include <string.h>
8*2d543d20SAndroid Build Coastguard Worker #include "selinux_internal.h"
9*2d543d20SAndroid Build Coastguard Worker #include "policy.h"
10*2d543d20SAndroid Build Coastguard Worker #include <limits.h>
11*2d543d20SAndroid Build Coastguard Worker #include "callbacks.h"
12*2d543d20SAndroid Build Coastguard Worker
security_compute_user_raw(const char * scon,const char * user,char *** con)13*2d543d20SAndroid Build Coastguard Worker int security_compute_user_raw(const char * scon,
14*2d543d20SAndroid Build Coastguard Worker const char *user, char *** con)
15*2d543d20SAndroid Build Coastguard Worker {
16*2d543d20SAndroid Build Coastguard Worker char path[PATH_MAX];
17*2d543d20SAndroid Build Coastguard Worker char **ary;
18*2d543d20SAndroid Build Coastguard Worker char *buf, *ptr;
19*2d543d20SAndroid Build Coastguard Worker size_t size;
20*2d543d20SAndroid Build Coastguard Worker int fd, ret;
21*2d543d20SAndroid Build Coastguard Worker unsigned int i, nel;
22*2d543d20SAndroid Build Coastguard Worker
23*2d543d20SAndroid Build Coastguard Worker if (!selinux_mnt) {
24*2d543d20SAndroid Build Coastguard Worker errno = ENOENT;
25*2d543d20SAndroid Build Coastguard Worker return -1;
26*2d543d20SAndroid Build Coastguard Worker }
27*2d543d20SAndroid Build Coastguard Worker
28*2d543d20SAndroid Build Coastguard Worker selinux_log(SELINUX_WARNING, "Direct use of security_compute_user() is deprecated, switch to get_ordered_context_list()\n");
29*2d543d20SAndroid Build Coastguard Worker
30*2d543d20SAndroid Build Coastguard Worker snprintf(path, sizeof path, "%s/user", selinux_mnt);
31*2d543d20SAndroid Build Coastguard Worker fd = open(path, O_RDWR | O_CLOEXEC);
32*2d543d20SAndroid Build Coastguard Worker if (fd < 0)
33*2d543d20SAndroid Build Coastguard Worker return -1;
34*2d543d20SAndroid Build Coastguard Worker
35*2d543d20SAndroid Build Coastguard Worker size = selinux_page_size;
36*2d543d20SAndroid Build Coastguard Worker buf = malloc(size);
37*2d543d20SAndroid Build Coastguard Worker if (!buf) {
38*2d543d20SAndroid Build Coastguard Worker ret = -1;
39*2d543d20SAndroid Build Coastguard Worker goto out;
40*2d543d20SAndroid Build Coastguard Worker }
41*2d543d20SAndroid Build Coastguard Worker
42*2d543d20SAndroid Build Coastguard Worker ret = snprintf(buf, size, "%s %s", scon, user);
43*2d543d20SAndroid Build Coastguard Worker if (ret < 0 || (size_t)ret >= size) {
44*2d543d20SAndroid Build Coastguard Worker errno = EOVERFLOW;
45*2d543d20SAndroid Build Coastguard Worker ret = -1;
46*2d543d20SAndroid Build Coastguard Worker goto out2;
47*2d543d20SAndroid Build Coastguard Worker }
48*2d543d20SAndroid Build Coastguard Worker
49*2d543d20SAndroid Build Coastguard Worker ret = write(fd, buf, strlen(buf));
50*2d543d20SAndroid Build Coastguard Worker if (ret < 0)
51*2d543d20SAndroid Build Coastguard Worker goto out2;
52*2d543d20SAndroid Build Coastguard Worker
53*2d543d20SAndroid Build Coastguard Worker memset(buf, 0, size);
54*2d543d20SAndroid Build Coastguard Worker ret = read(fd, buf, size - 1);
55*2d543d20SAndroid Build Coastguard Worker if (ret < 0)
56*2d543d20SAndroid Build Coastguard Worker goto out2;
57*2d543d20SAndroid Build Coastguard Worker
58*2d543d20SAndroid Build Coastguard Worker if (sscanf(buf, "%u", &nel) != 1) {
59*2d543d20SAndroid Build Coastguard Worker ret = -1;
60*2d543d20SAndroid Build Coastguard Worker goto out2;
61*2d543d20SAndroid Build Coastguard Worker }
62*2d543d20SAndroid Build Coastguard Worker
63*2d543d20SAndroid Build Coastguard Worker ary = malloc((nel + 1) * sizeof(char *));
64*2d543d20SAndroid Build Coastguard Worker if (!ary) {
65*2d543d20SAndroid Build Coastguard Worker ret = -1;
66*2d543d20SAndroid Build Coastguard Worker goto out2;
67*2d543d20SAndroid Build Coastguard Worker }
68*2d543d20SAndroid Build Coastguard Worker
69*2d543d20SAndroid Build Coastguard Worker ptr = buf + strlen(buf) + 1;
70*2d543d20SAndroid Build Coastguard Worker for (i = 0; i < nel; i++) {
71*2d543d20SAndroid Build Coastguard Worker ary[i] = strdup(ptr);
72*2d543d20SAndroid Build Coastguard Worker if (!ary[i]) {
73*2d543d20SAndroid Build Coastguard Worker freeconary(ary);
74*2d543d20SAndroid Build Coastguard Worker ret = -1;
75*2d543d20SAndroid Build Coastguard Worker goto out2;
76*2d543d20SAndroid Build Coastguard Worker }
77*2d543d20SAndroid Build Coastguard Worker ptr += strlen(ptr) + 1;
78*2d543d20SAndroid Build Coastguard Worker }
79*2d543d20SAndroid Build Coastguard Worker ary[nel] = NULL;
80*2d543d20SAndroid Build Coastguard Worker *con = ary;
81*2d543d20SAndroid Build Coastguard Worker ret = 0;
82*2d543d20SAndroid Build Coastguard Worker out2:
83*2d543d20SAndroid Build Coastguard Worker free(buf);
84*2d543d20SAndroid Build Coastguard Worker out:
85*2d543d20SAndroid Build Coastguard Worker close(fd);
86*2d543d20SAndroid Build Coastguard Worker return ret;
87*2d543d20SAndroid Build Coastguard Worker }
88*2d543d20SAndroid Build Coastguard Worker
89*2d543d20SAndroid Build Coastguard Worker
security_compute_user(const char * scon,const char * user,char *** con)90*2d543d20SAndroid Build Coastguard Worker int security_compute_user(const char * scon,
91*2d543d20SAndroid Build Coastguard Worker const char *user, char *** con)
92*2d543d20SAndroid Build Coastguard Worker {
93*2d543d20SAndroid Build Coastguard Worker int ret;
94*2d543d20SAndroid Build Coastguard Worker char * rscon;
95*2d543d20SAndroid Build Coastguard Worker
96*2d543d20SAndroid Build Coastguard Worker if (selinux_trans_to_raw_context(scon, &rscon))
97*2d543d20SAndroid Build Coastguard Worker return -1;
98*2d543d20SAndroid Build Coastguard Worker
99*2d543d20SAndroid Build Coastguard Worker IGNORE_DEPRECATED_DECLARATION_BEGIN
100*2d543d20SAndroid Build Coastguard Worker ret = security_compute_user_raw(rscon, user, con);
101*2d543d20SAndroid Build Coastguard Worker IGNORE_DEPRECATED_DECLARATION_END
102*2d543d20SAndroid Build Coastguard Worker
103*2d543d20SAndroid Build Coastguard Worker freecon(rscon);
104*2d543d20SAndroid Build Coastguard Worker if (!ret) {
105*2d543d20SAndroid Build Coastguard Worker char **ptr, *tmpcon;
106*2d543d20SAndroid Build Coastguard Worker for (ptr = *con; *ptr; ptr++) {
107*2d543d20SAndroid Build Coastguard Worker if (selinux_raw_to_trans_context(*ptr, &tmpcon)) {
108*2d543d20SAndroid Build Coastguard Worker freeconary(*con);
109*2d543d20SAndroid Build Coastguard Worker *con = NULL;
110*2d543d20SAndroid Build Coastguard Worker return -1;
111*2d543d20SAndroid Build Coastguard Worker }
112*2d543d20SAndroid Build Coastguard Worker freecon(*ptr);
113*2d543d20SAndroid Build Coastguard Worker *ptr = tmpcon;
114*2d543d20SAndroid Build Coastguard Worker }
115*2d543d20SAndroid Build Coastguard Worker }
116*2d543d20SAndroid Build Coastguard Worker
117*2d543d20SAndroid Build Coastguard Worker return ret;
118*2d543d20SAndroid Build Coastguard Worker }
119*2d543d20SAndroid Build Coastguard Worker
120