s3-dbwrap: & is not required when taking a function pointer
[Samba.git] / lib / uid_wrapper / uid_wrapper.c
blob898d1afbb9c5fbedb9ddc7d45a9ba9cc4071e876
1 /*
2 Copyright (C) Andrew Tridgell 2009
3 Copyright (c) 2011 Andreas Schneider <asn@samba.org>
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 3 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>.
19 #ifdef _SAMBA_BUILD_
21 #define UID_WRAPPER_NOT_REPLACE
22 #include "replace.h"
23 #include "system/passwd.h"
24 #include <talloc.h>
26 #else /* _SAMBA_BUILD_ */
28 #error uid_wrapper_only_supported_in_samba_yet
30 #endif
32 #ifndef _PUBLIC_
33 #define _PUBLIC_
34 #endif
37 we keep the virtualised euid/egid/groups information here
39 static struct {
40 bool initialised;
41 bool enabled;
42 uid_t myuid;
43 uid_t euid;
44 uid_t mygid;
45 gid_t egid;
46 gid_t *groups;
47 } uwrap;
49 static void uwrap_init(void)
51 if (uwrap.initialised) return;
52 uwrap.initialised = true;
53 if (getenv("UID_WRAPPER")) {
54 uwrap.enabled = true;
55 /* put us in one group */
56 uwrap.myuid = uwrap.euid = geteuid();
57 uwrap.mygid = uwrap.egid = getegid();
58 uwrap.groups = talloc_array(NULL, gid_t, 1);
59 uwrap.groups[0] = 0;
63 #undef uwrap_enabled
64 _PUBLIC_ int uwrap_enabled(void)
66 uwrap_init();
67 return uwrap.enabled?1:0;
70 #ifdef HAVE_SETEUID
71 _PUBLIC_ int uwrap_seteuid(uid_t euid)
73 uwrap_init();
74 if (!uwrap.enabled) {
75 return seteuid(euid);
77 /* assume for now that the ruid stays as root */
78 if (euid == 0) {
79 uwrap.euid = uwrap.myuid;
80 } else {
81 uwrap.euid = euid;
83 return 0;
85 #endif
87 #ifdef HAVE_SETREUID
88 _PUBLIC_ int uwrap_setreuid(uid_t ruid, uid_t euid)
90 uwrap_init();
91 if (!uwrap.enabled) {
92 return setreuid(ruid, euid);
94 /* assume for now that the ruid stays as root */
95 if (euid == 0) {
96 uwrap.euid = uwrap.myuid;
97 } else {
98 uwrap.euid = euid;
100 return 0;
102 #endif
104 #ifdef HAVE_SETRESUID
105 _PUBLIC_ int uwrap_setresuid(uid_t ruid, uid_t euid, uid_t suid)
107 uwrap_init();
108 if (!uwrap.enabled) {
109 return setresuid(ruid, euid, suid);
111 /* assume for now that the ruid stays as root */
112 if (euid == 0) {
113 uwrap.euid = uwrap.myuid;
114 } else {
115 uwrap.euid = euid;
117 return 0;
119 #endif
121 _PUBLIC_ uid_t uwrap_geteuid(void)
123 uwrap_init();
124 if (!uwrap.enabled) {
125 return geteuid();
127 return uwrap.euid;
130 #ifdef HAVE_SETEGID
131 _PUBLIC_ int uwrap_setegid(gid_t egid)
133 uwrap_init();
134 if (!uwrap.enabled) {
135 return setegid(egid);
137 /* assume for now that the ruid stays as root */
138 if (egid == 0) {
139 uwrap.egid = uwrap.mygid;
140 } else {
141 uwrap.egid = egid;
143 return 0;
145 #endif
147 #ifdef HAVE_SETREGID
148 _PUBLIC_ int uwrap_setregid(gid_t rgid, gid_t egid)
150 uwrap_init();
151 if (!uwrap.enabled) {
152 return setregid(rgid, egid);
154 /* assume for now that the ruid stays as root */
155 if (egid == 0) {
156 uwrap.egid = uwrap.mygid;
157 } else {
158 uwrap.egid = egid;
160 return 0;
162 #endif
164 #ifdef HAVE_SETRESGID
165 _PUBLIC_ int uwrap_setresgid(gid_t rgid, gid_t egid, gid_t sgid)
167 uwrap_init();
168 if (!uwrap.enabled) {
169 return setresgid(rgid, egid, sgid);
171 /* assume for now that the ruid stays as root */
172 if (egid == 0) {
173 uwrap.egid = uwrap.mygid;
174 } else {
175 uwrap.egid = egid;
177 return 0;
179 #endif
181 _PUBLIC_ uid_t uwrap_getegid(void)
183 uwrap_init();
184 if (!uwrap.enabled) {
185 return getegid();
187 return uwrap.egid;
190 _PUBLIC_ int uwrap_setgroups(size_t size, const gid_t *list)
192 uwrap_init();
193 if (!uwrap.enabled) {
194 return setgroups(size, list);
197 talloc_free(uwrap.groups);
198 uwrap.groups = NULL;
200 if (size != 0) {
201 uwrap.groups = talloc_array(NULL, gid_t, size);
202 if (uwrap.groups == NULL) {
203 errno = ENOMEM;
204 return -1;
206 memcpy(uwrap.groups, list, size*sizeof(gid_t));
208 return 0;
211 _PUBLIC_ int uwrap_getgroups(int size, gid_t *list)
213 size_t ngroups;
215 uwrap_init();
216 if (!uwrap.enabled) {
217 return getgroups(size, list);
220 ngroups = talloc_array_length(uwrap.groups);
222 if (size > ngroups) {
223 size = ngroups;
225 if (size == 0) {
226 return ngroups;
228 if (size < ngroups) {
229 errno = EINVAL;
230 return -1;
232 memcpy(list, uwrap.groups, size*sizeof(gid_t));
233 return ngroups;
236 _PUBLIC_ uid_t uwrap_getuid(void)
238 uwrap_init();
239 if (!uwrap.enabled) {
240 return getuid();
242 /* we don't simulate ruid changing */
243 return 0;
246 _PUBLIC_ gid_t uwrap_getgid(void)
248 uwrap_init();
249 if (!uwrap.enabled) {
250 return getgid();
252 /* we don't simulate rgid changing */
253 return 0;