1 // SPDX-License-Identifier: LGPL-2.1
2 /*
3 *
4 * Copyright (C) International Business Machines Corp., 2007,2008
5 * Author(s): Steve French (sfrench@us.ibm.com)
6 *
7 * Contains the routines for mapping CIFS/NTFS ACLs
8 *
9 */
10
11 #include <linux/fs.h>
12 #include <linux/slab.h>
13 #include <linux/string.h>
14 #include <linux/keyctl.h>
15 #include <linux/key-type.h>
16 #include <keys/user-type.h>
17 #include "cifspdu.h"
18 #include "cifsglob.h"
19 #include "cifsacl.h"
20 #include "cifsproto.h"
21 #include "cifs_debug.h"
22 #include "fs_context.h"
23
24 /* security id for everyone/world system group */
25 static const struct cifs_sid sid_everyone = {
26 1, 1, {0, 0, 0, 0, 0, 1}, {0} };
27 /* security id for Authenticated Users system group */
28 static const struct cifs_sid sid_authusers = {
29 1, 1, {0, 0, 0, 0, 0, 5}, {cpu_to_le32(11)} };
30
31 /* S-1-22-1 Unmapped Unix users */
32 static const struct cifs_sid sid_unix_users = {1, 1, {0, 0, 0, 0, 0, 22},
33 {cpu_to_le32(1), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
34
35 /* S-1-22-2 Unmapped Unix groups */
36 static const struct cifs_sid sid_unix_groups = { 1, 1, {0, 0, 0, 0, 0, 22},
37 {cpu_to_le32(2), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
38
39 /*
40 * See https://technet.microsoft.com/en-us/library/hh509017(v=ws.10).aspx
41 */
42
43 /* S-1-5-88 MS NFS and Apple style UID/GID/mode */
44
45 /* S-1-5-88-1 Unix uid */
46 static const struct cifs_sid sid_unix_NFS_users = { 1, 2, {0, 0, 0, 0, 0, 5},
47 {cpu_to_le32(88),
48 cpu_to_le32(1), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
49
50 /* S-1-5-88-2 Unix gid */
51 static const struct cifs_sid sid_unix_NFS_groups = { 1, 2, {0, 0, 0, 0, 0, 5},
52 {cpu_to_le32(88),
53 cpu_to_le32(2), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
54
55 /* S-1-5-88-3 Unix mode */
56 static const struct cifs_sid sid_unix_NFS_mode = { 1, 2, {0, 0, 0, 0, 0, 5},
57 {cpu_to_le32(88),
58 cpu_to_le32(3), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
59
60 static const struct cred *root_cred;
61
62 static int
cifs_idmap_key_instantiate(struct key * key,struct key_preparsed_payload * prep)63 cifs_idmap_key_instantiate(struct key *key, struct key_preparsed_payload *prep)
64 {
65 char *payload;
66
67 /*
68 * If the payload is less than or equal to the size of a pointer, then
69 * an allocation here is wasteful. Just copy the data directly to the
70 * payload.value union member instead.
71 *
72 * With this however, you must check the datalen before trying to
73 * dereference payload.data!
74 */
75 if (prep->datalen <= sizeof(key->payload)) {
76 key->payload.data[0] = NULL;
77 memcpy(&key->payload, prep->data, prep->datalen);
78 } else {
79 payload = kmemdup(prep->data, prep->datalen, GFP_KERNEL);
80 if (!payload)
81 return -ENOMEM;
82 key->payload.data[0] = payload;
83 }
84
85 key->datalen = prep->datalen;
86 return 0;
87 }
88
89 static inline void
cifs_idmap_key_destroy(struct key * key)90 cifs_idmap_key_destroy(struct key *key)
91 {
92 if (key->datalen > sizeof(key->payload))
93 kfree(key->payload.data[0]);
94 }
95
96 static struct key_type cifs_idmap_key_type = {
97 .name = "cifs.idmap",
98 .instantiate = cifs_idmap_key_instantiate,
99 .destroy = cifs_idmap_key_destroy,
100 .describe = user_describe,
101 };
102
103 static char *
sid_to_key_str(struct cifs_sid * sidptr,unsigned int type)104 sid_to_key_str(struct cifs_sid *sidptr, unsigned int type)
105 {
106 int i, len;
107 unsigned int saval;
108 char *sidstr, *strptr;
109 unsigned long long id_auth_val;
110
111 /* 3 bytes for prefix */
112 sidstr = kmalloc(3 + SID_STRING_BASE_SIZE +
113 (SID_STRING_SUBAUTH_SIZE * sidptr->num_subauth),
114 GFP_KERNEL);
115 if (!sidstr)
116 return sidstr;
117
118 strptr = sidstr;
119 len = sprintf(strptr, "%cs:S-%hhu", type == SIDOWNER ? 'o' : 'g',
120 sidptr->revision);
121 strptr += len;
122
123 /* The authority field is a single 48-bit number */
124 id_auth_val = (unsigned long long)sidptr->authority[5];
125 id_auth_val |= (unsigned long long)sidptr->authority[4] << 8;
126 id_auth_val |= (unsigned long long)sidptr->authority[3] << 16;
127 id_auth_val |= (unsigned long long)sidptr->authority[2] << 24;
128 id_auth_val |= (unsigned long long)sidptr->authority[1] << 32;
129 id_auth_val |= (unsigned long long)sidptr->authority[0] << 48;
130
131 /*
132 * MS-DTYP states that if the authority is >= 2^32, then it should be
133 * expressed as a hex value.
134 */
135 if (id_auth_val <= UINT_MAX)
136 len = sprintf(strptr, "-%llu", id_auth_val);
137 else
138 len = sprintf(strptr, "-0x%llx", id_auth_val);
139
140 strptr += len;
141
142 for (i = 0; i < sidptr->num_subauth; ++i) {
143 saval = le32_to_cpu(sidptr->sub_auth[i]);
144 len = sprintf(strptr, "-%u", saval);
145 strptr += len;
146 }
147
148 return sidstr;
149 }
150
151 /*
152 * if the two SIDs (roughly equivalent to a UUID for a user or group) are
153 * the same returns zero, if they do not match returns non-zero.
154 */
155 static int
compare_sids(const struct cifs_sid * ctsid,const struct cifs_sid * cwsid)156 compare_sids(const struct cifs_sid *ctsid, const struct cifs_sid *cwsid)
157 {
158 int i;
159 int num_subauth, num_sat, num_saw;
160
161 if ((!ctsid) || (!cwsid))
162 return 1;
163
164 /* compare the revision */
165 if (ctsid->revision != cwsid->revision) {
166 if (ctsid->revision > cwsid->revision)
167 return 1;
168 else
169 return -1;
170 }
171
172 /* compare all of the six auth values */
173 for (i = 0; i < NUM_AUTHS; ++i) {
174 if (ctsid->authority[i] != cwsid->authority[i]) {
175 if (ctsid->authority[i] > cwsid->authority[i])
176 return 1;
177 else
178 return -1;
179 }
180 }
181
182 /* compare all of the subauth values if any */
183 num_sat = ctsid->num_subauth;
184 num_saw = cwsid->num_subauth;
185 num_subauth = num_sat < num_saw ? num_sat : num_saw;
186 if (num_subauth) {
187 for (i = 0; i < num_subauth; ++i) {
188 if (ctsid->sub_auth[i] != cwsid->sub_auth[i]) {
189 if (le32_to_cpu(ctsid->sub_auth[i]) >
190 le32_to_cpu(cwsid->sub_auth[i]))
191 return 1;
192 else
193 return -1;
194 }
195 }
196 }
197
198 return 0; /* sids compare/match */
199 }
200
201 static bool
is_well_known_sid(const struct cifs_sid * psid,uint32_t * puid,bool is_group)202 is_well_known_sid(const struct cifs_sid *psid, uint32_t *puid, bool is_group)
203 {
204 int i;
205 int num_subauth;
206 const struct cifs_sid *pwell_known_sid;
207
208 if (!psid || (puid == NULL))
209 return false;
210
211 num_subauth = psid->num_subauth;
212
213 /* check if Mac (or Windows NFS) vs. Samba format for Unix owner SID */
214 if (num_subauth == 2) {
215 if (is_group)
216 pwell_known_sid = &sid_unix_groups;
217 else
218 pwell_known_sid = &sid_unix_users;
219 } else if (num_subauth == 3) {
220 if (is_group)
221 pwell_known_sid = &sid_unix_NFS_groups;
222 else
223 pwell_known_sid = &sid_unix_NFS_users;
224 } else
225 return false;
226
227 /* compare the revision */
228 if (psid->revision != pwell_known_sid->revision)
229 return false;
230
231 /* compare all of the six auth values */
232 for (i = 0; i < NUM_AUTHS; ++i) {
233 if (psid->authority[i] != pwell_known_sid->authority[i]) {
234 cifs_dbg(FYI, "auth %d did not match\n", i);
235 return false;
236 }
237 }
238
239 if (num_subauth == 2) {
240 if (psid->sub_auth[0] != pwell_known_sid->sub_auth[0])
241 return false;
242
243 *puid = le32_to_cpu(psid->sub_auth[1]);
244 } else /* 3 subauths, ie Windows/Mac style */ {
245 *puid = le32_to_cpu(psid->sub_auth[0]);
246 if ((psid->sub_auth[0] != pwell_known_sid->sub_auth[0]) ||
247 (psid->sub_auth[1] != pwell_known_sid->sub_auth[1]))
248 return false;
249
250 *puid = le32_to_cpu(psid->sub_auth[2]);
251 }
252
253 cifs_dbg(FYI, "Unix UID %d returned from SID\n", *puid);
254 return true; /* well known sid found, uid returned */
255 }
256
257 static __u16
cifs_copy_sid(struct cifs_sid * dst,const struct cifs_sid * src)258 cifs_copy_sid(struct cifs_sid *dst, const struct cifs_sid *src)
259 {
260 int i;
261 __u16 size = 1 + 1 + 6;
262
263 dst->revision = src->revision;
264 dst->num_subauth = min_t(u8, src->num_subauth, SID_MAX_SUB_AUTHORITIES);
265 for (i = 0; i < NUM_AUTHS; ++i)
266 dst->authority[i] = src->authority[i];
267 for (i = 0; i < dst->num_subauth; ++i)
268 dst->sub_auth[i] = src->sub_auth[i];
269 size += (dst->num_subauth * 4);
270
271 return size;
272 }
273
274 static int
id_to_sid(unsigned int cid,uint sidtype,struct cifs_sid * ssid)275 id_to_sid(unsigned int cid, uint sidtype, struct cifs_sid *ssid)
276 {
277 int rc;
278 struct key *sidkey;
279 struct cifs_sid *ksid;
280 unsigned int ksid_size;
281 char desc[3 + 10 + 1]; /* 3 byte prefix + 10 bytes for value + NULL */
282 const struct cred *saved_cred;
283
284 rc = snprintf(desc, sizeof(desc), "%ci:%u",
285 sidtype == SIDOWNER ? 'o' : 'g', cid);
286 if (rc >= sizeof(desc))
287 return -EINVAL;
288
289 rc = 0;
290 saved_cred = override_creds(root_cred);
291 sidkey = request_key(&cifs_idmap_key_type, desc, "");
292 if (IS_ERR(sidkey)) {
293 rc = -EINVAL;
294 cifs_dbg(FYI, "%s: Can't map %cid %u to a SID\n",
295 __func__, sidtype == SIDOWNER ? 'u' : 'g', cid);
296 goto out_revert_creds;
297 } else if (sidkey->datalen < CIFS_SID_BASE_SIZE) {
298 rc = -EIO;
299 cifs_dbg(FYI, "%s: Downcall contained malformed key (datalen=%hu)\n",
300 __func__, sidkey->datalen);
301 goto invalidate_key;
302 }
303
304 /*
305 * A sid is usually too large to be embedded in payload.value, but if
306 * there are no subauthorities and the host has 8-byte pointers, then
307 * it could be.
308 */
309 ksid = sidkey->datalen <= sizeof(sidkey->payload) ?
310 (struct cifs_sid *)&sidkey->payload :
311 (struct cifs_sid *)sidkey->payload.data[0];
312
313 ksid_size = CIFS_SID_BASE_SIZE + (ksid->num_subauth * sizeof(__le32));
314 if (ksid_size > sidkey->datalen) {
315 rc = -EIO;
316 cifs_dbg(FYI, "%s: Downcall contained malformed key (datalen=%hu, ksid_size=%u)\n",
317 __func__, sidkey->datalen, ksid_size);
318 goto invalidate_key;
319 }
320
321 cifs_copy_sid(ssid, ksid);
322 out_key_put:
323 key_put(sidkey);
324 out_revert_creds:
325 revert_creds(saved_cred);
326 return rc;
327
328 invalidate_key:
329 key_invalidate(sidkey);
330 goto out_key_put;
331 }
332
333 int
sid_to_id(struct cifs_sb_info * cifs_sb,struct cifs_sid * psid,struct cifs_fattr * fattr,uint sidtype)334 sid_to_id(struct cifs_sb_info *cifs_sb, struct cifs_sid *psid,
335 struct cifs_fattr *fattr, uint sidtype)
336 {
337 int rc = 0;
338 struct key *sidkey;
339 char *sidstr;
340 const struct cred *saved_cred;
341 kuid_t fuid = cifs_sb->ctx->linux_uid;
342 kgid_t fgid = cifs_sb->ctx->linux_gid;
343
344 /*
345 * If we have too many subauthorities, then something is really wrong.
346 * Just return an error.
347 */
348 if (unlikely(psid->num_subauth > SID_MAX_SUB_AUTHORITIES)) {
349 cifs_dbg(FYI, "%s: %u subauthorities is too many!\n",
350 __func__, psid->num_subauth);
351 return -EIO;
352 }
353
354 if ((cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UID_FROM_ACL) ||
355 (cifs_sb_master_tcon(cifs_sb)->posix_extensions)) {
356 uint32_t unix_id;
357 bool is_group;
358
359 if (sidtype != SIDOWNER)
360 is_group = true;
361 else
362 is_group = false;
363
364 if (is_well_known_sid(psid, &unix_id, is_group) == false)
365 goto try_upcall_to_get_id;
366
367 if (is_group) {
368 kgid_t gid;
369 gid_t id;
370
371 id = (gid_t)unix_id;
372 gid = make_kgid(&init_user_ns, id);
373 if (gid_valid(gid)) {
374 fgid = gid;
375 goto got_valid_id;
376 }
377 } else {
378 kuid_t uid;
379 uid_t id;
380
381 id = (uid_t)unix_id;
382 uid = make_kuid(&init_user_ns, id);
383 if (uid_valid(uid)) {
384 fuid = uid;
385 goto got_valid_id;
386 }
387 }
388 /* If unable to find uid/gid easily from SID try via upcall */
389 }
390
391 try_upcall_to_get_id:
392 sidstr = sid_to_key_str(psid, sidtype);
393 if (!sidstr)
394 return -ENOMEM;
395
396 saved_cred = override_creds(root_cred);
397 sidkey = request_key(&cifs_idmap_key_type, sidstr, "");
398 if (IS_ERR(sidkey)) {
399 cifs_dbg(FYI, "%s: Can't map SID %s to a %cid\n",
400 __func__, sidstr, sidtype == SIDOWNER ? 'u' : 'g');
401 goto out_revert_creds;
402 }
403
404 /*
405 * FIXME: Here we assume that uid_t and gid_t are same size. It's
406 * probably a safe assumption but might be better to check based on
407 * sidtype.
408 */
409 BUILD_BUG_ON(sizeof(uid_t) != sizeof(gid_t));
410 if (sidkey->datalen != sizeof(uid_t)) {
411 cifs_dbg(FYI, "%s: Downcall contained malformed key (datalen=%hu)\n",
412 __func__, sidkey->datalen);
413 key_invalidate(sidkey);
414 goto out_key_put;
415 }
416
417 if (sidtype == SIDOWNER) {
418 kuid_t uid;
419 uid_t id;
420 memcpy(&id, &sidkey->payload.data[0], sizeof(uid_t));
421 uid = make_kuid(&init_user_ns, id);
422 if (uid_valid(uid))
423 fuid = uid;
424 } else {
425 kgid_t gid;
426 gid_t id;
427 memcpy(&id, &sidkey->payload.data[0], sizeof(gid_t));
428 gid = make_kgid(&init_user_ns, id);
429 if (gid_valid(gid))
430 fgid = gid;
431 }
432
433 out_key_put:
434 key_put(sidkey);
435 out_revert_creds:
436 revert_creds(saved_cred);
437 kfree(sidstr);
438
439 /*
440 * Note that we return 0 here unconditionally. If the mapping
441 * fails then we just fall back to using the ctx->linux_uid/linux_gid.
442 */
443 got_valid_id:
444 rc = 0;
445 if (sidtype == SIDOWNER)
446 fattr->cf_uid = fuid;
447 else
448 fattr->cf_gid = fgid;
449 return rc;
450 }
451
452 int
init_cifs_idmap(void)453 init_cifs_idmap(void)
454 {
455 struct cred *cred;
456 struct key *keyring;
457 int ret;
458
459 cifs_dbg(FYI, "Registering the %s key type\n",
460 cifs_idmap_key_type.name);
461
462 /* create an override credential set with a special thread keyring in
463 * which requests are cached
464 *
465 * this is used to prevent malicious redirections from being installed
466 * with add_key().
467 */
468 cred = prepare_kernel_cred(NULL);
469 if (!cred)
470 return -ENOMEM;
471
472 keyring = keyring_alloc(".cifs_idmap",
473 GLOBAL_ROOT_UID, GLOBAL_ROOT_GID, cred,
474 (KEY_POS_ALL & ~KEY_POS_SETATTR) |
475 KEY_USR_VIEW | KEY_USR_READ,
476 KEY_ALLOC_NOT_IN_QUOTA, NULL, NULL);
477 if (IS_ERR(keyring)) {
478 ret = PTR_ERR(keyring);
479 goto failed_put_cred;
480 }
481
482 ret = register_key_type(&cifs_idmap_key_type);
483 if (ret < 0)
484 goto failed_put_key;
485
486 /* instruct request_key() to use this special keyring as a cache for
487 * the results it looks up */
488 set_bit(KEY_FLAG_ROOT_CAN_CLEAR, &keyring->flags);
489 cred->thread_keyring = keyring;
490 cred->jit_keyring = KEY_REQKEY_DEFL_THREAD_KEYRING;
491 root_cred = cred;
492
493 cifs_dbg(FYI, "cifs idmap keyring: %d\n", key_serial(keyring));
494 return 0;
495
496 failed_put_key:
497 key_put(keyring);
498 failed_put_cred:
499 put_cred(cred);
500 return ret;
501 }
502
503 void
exit_cifs_idmap(void)504 exit_cifs_idmap(void)
505 {
506 key_revoke(root_cred->thread_keyring);
507 unregister_key_type(&cifs_idmap_key_type);
508 put_cred(root_cred);
509 cifs_dbg(FYI, "Unregistered %s key type\n", cifs_idmap_key_type.name);
510 }
511
512 /* copy ntsd, owner sid, and group sid from a security descriptor to another */
copy_sec_desc(const struct cifs_ntsd * pntsd,struct cifs_ntsd * pnntsd,__u32 sidsoffset,struct cifs_sid * pownersid,struct cifs_sid * pgrpsid)513 static __u32 copy_sec_desc(const struct cifs_ntsd *pntsd,
514 struct cifs_ntsd *pnntsd,
515 __u32 sidsoffset,
516 struct cifs_sid *pownersid,
517 struct cifs_sid *pgrpsid)
518 {
519 struct cifs_sid *owner_sid_ptr, *group_sid_ptr;
520 struct cifs_sid *nowner_sid_ptr, *ngroup_sid_ptr;
521
522 /* copy security descriptor control portion */
523 pnntsd->revision = pntsd->revision;
524 pnntsd->type = pntsd->type;
525 pnntsd->dacloffset = cpu_to_le32(sizeof(struct cifs_ntsd));
526 pnntsd->sacloffset = 0;
527 pnntsd->osidoffset = cpu_to_le32(sidsoffset);
528 pnntsd->gsidoffset = cpu_to_le32(sidsoffset + sizeof(struct cifs_sid));
529
530 /* copy owner sid */
531 if (pownersid)
532 owner_sid_ptr = pownersid;
533 else
534 owner_sid_ptr = (struct cifs_sid *)((char *)pntsd +
535 le32_to_cpu(pntsd->osidoffset));
536 nowner_sid_ptr = (struct cifs_sid *)((char *)pnntsd + sidsoffset);
537 cifs_copy_sid(nowner_sid_ptr, owner_sid_ptr);
538
539 /* copy group sid */
540 if (pgrpsid)
541 group_sid_ptr = pgrpsid;
542 else
543 group_sid_ptr = (struct cifs_sid *)((char *)pntsd +
544 le32_to_cpu(pntsd->gsidoffset));
545 ngroup_sid_ptr = (struct cifs_sid *)((char *)pnntsd + sidsoffset +
546 sizeof(struct cifs_sid));
547 cifs_copy_sid(ngroup_sid_ptr, group_sid_ptr);
548
549 return sidsoffset + (2 * sizeof(struct cifs_sid));
550 }
551
552
553 /*
554 change posix mode to reflect permissions
555 pmode is the existing mode (we only want to overwrite part of this
556 bits to set can be: S_IRWXU, S_IRWXG or S_IRWXO ie 00700 or 00070 or 00007
557 */
access_flags_to_mode(__le32 ace_flags,int type,umode_t * pmode,umode_t * pdenied,umode_t mask)558 static void access_flags_to_mode(__le32 ace_flags, int type, umode_t *pmode,
559 umode_t *pdenied, umode_t mask)
560 {
561 __u32 flags = le32_to_cpu(ace_flags);
562 /*
563 * Do not assume "preferred" or "canonical" order.
564 * The first DENY or ALLOW ACE which matches perfectly is
565 * the permission to be used. Once allowed or denied, same
566 * permission in later ACEs do not matter.
567 */
568
569 /* If not already allowed, deny these bits */
570 if (type == ACCESS_DENIED) {
571 if (flags & GENERIC_ALL &&
572 !(*pmode & mask & 0777))
573 *pdenied |= mask & 0777;
574
575 if (((flags & GENERIC_WRITE) ||
576 ((flags & FILE_WRITE_RIGHTS) == FILE_WRITE_RIGHTS)) &&
577 !(*pmode & mask & 0222))
578 *pdenied |= mask & 0222;
579
580 if (((flags & GENERIC_READ) ||
581 ((flags & FILE_READ_RIGHTS) == FILE_READ_RIGHTS)) &&
582 !(*pmode & mask & 0444))
583 *pdenied |= mask & 0444;
584
585 if (((flags & GENERIC_EXECUTE) ||
586 ((flags & FILE_EXEC_RIGHTS) == FILE_EXEC_RIGHTS)) &&
587 !(*pmode & mask & 0111))
588 *pdenied |= mask & 0111;
589
590 return;
591 } else if (type != ACCESS_ALLOWED) {
592 cifs_dbg(VFS, "unknown access control type %d\n", type);
593 return;
594 }
595 /* else ACCESS_ALLOWED type */
596
597 if ((flags & GENERIC_ALL) &&
598 !(*pdenied & mask & 0777)) {
599 *pmode |= mask & 0777;
600 cifs_dbg(NOISY, "all perms\n");
601 return;
602 }
603
604 if (((flags & GENERIC_WRITE) ||
605 ((flags & FILE_WRITE_RIGHTS) == FILE_WRITE_RIGHTS)) &&
606 !(*pdenied & mask & 0222))
607 *pmode |= mask & 0222;
608
609 if (((flags & GENERIC_READ) ||
610 ((flags & FILE_READ_RIGHTS) == FILE_READ_RIGHTS)) &&
611 !(*pdenied & mask & 0444))
612 *pmode |= mask & 0444;
613
614 if (((flags & GENERIC_EXECUTE) ||
615 ((flags & FILE_EXEC_RIGHTS) == FILE_EXEC_RIGHTS)) &&
616 !(*pdenied & mask & 0111))
617 *pmode |= mask & 0111;
618
619 /* If DELETE_CHILD is set only on an owner ACE, set sticky bit */
620 if (flags & FILE_DELETE_CHILD) {
621 if (mask == ACL_OWNER_MASK) {
622 if (!(*pdenied & 01000))
623 *pmode |= 01000;
624 } else if (!(*pdenied & 01000)) {
625 *pmode &= ~01000;
626 *pdenied |= 01000;
627 }
628 }
629
630 cifs_dbg(NOISY, "access flags 0x%x mode now %04o\n", flags, *pmode);
631 return;
632 }
633
634 /*
635 Generate access flags to reflect permissions mode is the existing mode.
636 This function is called for every ACE in the DACL whose SID matches
637 with either owner or group or everyone.
638 */
639
mode_to_access_flags(umode_t mode,umode_t bits_to_use,__u32 * pace_flags)640 static void mode_to_access_flags(umode_t mode, umode_t bits_to_use,
641 __u32 *pace_flags)
642 {
643 /* reset access mask */
644 *pace_flags = 0x0;
645
646 /* bits to use are either S_IRWXU or S_IRWXG or S_IRWXO */
647 mode &= bits_to_use;
648
649 /* check for R/W/X UGO since we do not know whose flags
650 is this but we have cleared all the bits sans RWX for
651 either user or group or other as per bits_to_use */
652 if (mode & S_IRUGO)
653 *pace_flags |= SET_FILE_READ_RIGHTS;
654 if (mode & S_IWUGO)
655 *pace_flags |= SET_FILE_WRITE_RIGHTS;
656 if (mode & S_IXUGO)
657 *pace_flags |= SET_FILE_EXEC_RIGHTS;
658
659 cifs_dbg(NOISY, "mode: %04o, access flags now 0x%x\n",
660 mode, *pace_flags);
661 return;
662 }
663
cifs_copy_ace(struct cifs_ace * dst,struct cifs_ace * src,struct cifs_sid * psid)664 static __u16 cifs_copy_ace(struct cifs_ace *dst, struct cifs_ace *src, struct cifs_sid *psid)
665 {
666 __u16 size = 1 + 1 + 2 + 4;
667
668 dst->type = src->type;
669 dst->flags = src->flags;
670 dst->access_req = src->access_req;
671
672 /* Check if there's a replacement sid specified */
673 if (psid)
674 size += cifs_copy_sid(&dst->sid, psid);
675 else
676 size += cifs_copy_sid(&dst->sid, &src->sid);
677
678 dst->size = cpu_to_le16(size);
679
680 return size;
681 }
682
fill_ace_for_sid(struct cifs_ace * pntace,const struct cifs_sid * psid,__u64 nmode,umode_t bits,__u8 access_type,bool allow_delete_child)683 static __u16 fill_ace_for_sid(struct cifs_ace *pntace,
684 const struct cifs_sid *psid, __u64 nmode,
685 umode_t bits, __u8 access_type,
686 bool allow_delete_child)
687 {
688 int i;
689 __u16 size = 0;
690 __u32 access_req = 0;
691
692 pntace->type = access_type;
693 pntace->flags = 0x0;
694 mode_to_access_flags(nmode, bits, &access_req);
695
696 if (access_type == ACCESS_ALLOWED && allow_delete_child)
697 access_req |= FILE_DELETE_CHILD;
698
699 if (access_type == ACCESS_ALLOWED && !access_req)
700 access_req = SET_MINIMUM_RIGHTS;
701 else if (access_type == ACCESS_DENIED)
702 access_req &= ~SET_MINIMUM_RIGHTS;
703
704 pntace->access_req = cpu_to_le32(access_req);
705
706 pntace->sid.revision = psid->revision;
707 pntace->sid.num_subauth = psid->num_subauth;
708 for (i = 0; i < NUM_AUTHS; i++)
709 pntace->sid.authority[i] = psid->authority[i];
710 for (i = 0; i < psid->num_subauth; i++)
711 pntace->sid.sub_auth[i] = psid->sub_auth[i];
712
713 size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth * 4);
714 pntace->size = cpu_to_le16(size);
715
716 return size;
717 }
718
719
720 #ifdef CONFIG_CIFS_DEBUG2
dump_ace(struct cifs_ace * pace,char * end_of_acl)721 static void dump_ace(struct cifs_ace *pace, char *end_of_acl)
722 {
723 int num_subauth;
724
725 /* validate that we do not go past end of acl */
726
727 if (le16_to_cpu(pace->size) < 16) {
728 cifs_dbg(VFS, "ACE too small %d\n", le16_to_cpu(pace->size));
729 return;
730 }
731
732 if (end_of_acl < (char *)pace + le16_to_cpu(pace->size)) {
733 cifs_dbg(VFS, "ACL too small to parse ACE\n");
734 return;
735 }
736
737 num_subauth = pace->sid.num_subauth;
738 if (num_subauth) {
739 int i;
740 cifs_dbg(FYI, "ACE revision %d num_auth %d type %d flags %d size %d\n",
741 pace->sid.revision, pace->sid.num_subauth, pace->type,
742 pace->flags, le16_to_cpu(pace->size));
743 for (i = 0; i < num_subauth; ++i) {
744 cifs_dbg(FYI, "ACE sub_auth[%d]: 0x%x\n",
745 i, le32_to_cpu(pace->sid.sub_auth[i]));
746 }
747
748 /* BB add length check to make sure that we do not have huge
749 num auths and therefore go off the end */
750 }
751
752 return;
753 }
754 #endif
755
parse_dacl(struct cifs_acl * pdacl,char * end_of_acl,struct cifs_sid * pownersid,struct cifs_sid * pgrpsid,struct cifs_fattr * fattr,bool mode_from_special_sid)756 static void parse_dacl(struct cifs_acl *pdacl, char *end_of_acl,
757 struct cifs_sid *pownersid, struct cifs_sid *pgrpsid,
758 struct cifs_fattr *fattr, bool mode_from_special_sid)
759 {
760 int i;
761 int num_aces = 0;
762 int acl_size;
763 char *acl_base;
764 struct cifs_ace **ppace;
765
766 /* BB need to add parm so we can store the SID BB */
767
768 if (!pdacl) {
769 /* no DACL in the security descriptor, set
770 all the permissions for user/group/other */
771 fattr->cf_mode |= 0777;
772 return;
773 }
774
775 /* validate that we do not go past end of acl */
776 if (end_of_acl < (char *)pdacl + le16_to_cpu(pdacl->size)) {
777 cifs_dbg(VFS, "ACL too small to parse DACL\n");
778 return;
779 }
780
781 cifs_dbg(NOISY, "DACL revision %d size %d num aces %d\n",
782 le16_to_cpu(pdacl->revision), le16_to_cpu(pdacl->size),
783 le32_to_cpu(pdacl->num_aces));
784
785 /* reset rwx permissions for user/group/other.
786 Also, if num_aces is 0 i.e. DACL has no ACEs,
787 user/group/other have no permissions */
788 fattr->cf_mode &= ~(0777);
789
790 acl_base = (char *)pdacl;
791 acl_size = sizeof(struct cifs_acl);
792
793 num_aces = le32_to_cpu(pdacl->num_aces);
794 if (num_aces > 0) {
795 umode_t denied_mode = 0;
796
797 if (num_aces > ULONG_MAX / sizeof(struct cifs_ace *))
798 return;
799 ppace = kmalloc_array(num_aces, sizeof(struct cifs_ace *),
800 GFP_KERNEL);
801 if (!ppace)
802 return;
803
804 for (i = 0; i < num_aces; ++i) {
805 ppace[i] = (struct cifs_ace *) (acl_base + acl_size);
806 #ifdef CONFIG_CIFS_DEBUG2
807 dump_ace(ppace[i], end_of_acl);
808 #endif
809 if (mode_from_special_sid &&
810 (compare_sids(&(ppace[i]->sid),
811 &sid_unix_NFS_mode) == 0)) {
812 /*
813 * Full permissions are:
814 * 07777 = S_ISUID | S_ISGID | S_ISVTX |
815 * S_IRWXU | S_IRWXG | S_IRWXO
816 */
817 fattr->cf_mode &= ~07777;
818 fattr->cf_mode |=
819 le32_to_cpu(ppace[i]->sid.sub_auth[2]);
820 break;
821 } else {
822 if (compare_sids(&(ppace[i]->sid), pownersid) == 0) {
823 access_flags_to_mode(ppace[i]->access_req,
824 ppace[i]->type,
825 &fattr->cf_mode,
826 &denied_mode,
827 ACL_OWNER_MASK);
828 } else if (compare_sids(&(ppace[i]->sid), pgrpsid) == 0) {
829 access_flags_to_mode(ppace[i]->access_req,
830 ppace[i]->type,
831 &fattr->cf_mode,
832 &denied_mode,
833 ACL_GROUP_MASK);
834 } else if ((compare_sids(&(ppace[i]->sid), &sid_everyone) == 0) ||
835 (compare_sids(&(ppace[i]->sid), &sid_authusers) == 0)) {
836 access_flags_to_mode(ppace[i]->access_req,
837 ppace[i]->type,
838 &fattr->cf_mode,
839 &denied_mode,
840 ACL_EVERYONE_MASK);
841 }
842 }
843
844
845 /* memcpy((void *)(&(cifscred->aces[i])),
846 (void *)ppace[i],
847 sizeof(struct cifs_ace)); */
848
849 acl_base = (char *)ppace[i];
850 acl_size = le16_to_cpu(ppace[i]->size);
851 }
852
853 kfree(ppace);
854 }
855
856 return;
857 }
858
setup_authusers_ACE(struct cifs_ace * pntace)859 unsigned int setup_authusers_ACE(struct cifs_ace *pntace)
860 {
861 int i;
862 unsigned int ace_size = 20;
863
864 pntace->type = ACCESS_ALLOWED_ACE_TYPE;
865 pntace->flags = 0x0;
866 pntace->access_req = cpu_to_le32(GENERIC_ALL);
867 pntace->sid.num_subauth = 1;
868 pntace->sid.revision = 1;
869 for (i = 0; i < NUM_AUTHS; i++)
870 pntace->sid.authority[i] = sid_authusers.authority[i];
871
872 pntace->sid.sub_auth[0] = sid_authusers.sub_auth[0];
873
874 /* size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth*4) */
875 pntace->size = cpu_to_le16(ace_size);
876 return ace_size;
877 }
878
879 /*
880 * Fill in the special SID based on the mode. See
881 * https://technet.microsoft.com/en-us/library/hh509017(v=ws.10).aspx
882 */
setup_special_mode_ACE(struct cifs_ace * pntace,__u64 nmode)883 unsigned int setup_special_mode_ACE(struct cifs_ace *pntace, __u64 nmode)
884 {
885 int i;
886 unsigned int ace_size = 28;
887
888 pntace->type = ACCESS_DENIED_ACE_TYPE;
889 pntace->flags = 0x0;
890 pntace->access_req = 0;
891 pntace->sid.num_subauth = 3;
892 pntace->sid.revision = 1;
893 for (i = 0; i < NUM_AUTHS; i++)
894 pntace->sid.authority[i] = sid_unix_NFS_mode.authority[i];
895
896 pntace->sid.sub_auth[0] = sid_unix_NFS_mode.sub_auth[0];
897 pntace->sid.sub_auth[1] = sid_unix_NFS_mode.sub_auth[1];
898 pntace->sid.sub_auth[2] = cpu_to_le32(nmode & 07777);
899
900 /* size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth*4) */
901 pntace->size = cpu_to_le16(ace_size);
902 return ace_size;
903 }
904
setup_special_user_owner_ACE(struct cifs_ace * pntace)905 unsigned int setup_special_user_owner_ACE(struct cifs_ace *pntace)
906 {
907 int i;
908 unsigned int ace_size = 28;
909
910 pntace->type = ACCESS_ALLOWED_ACE_TYPE;
911 pntace->flags = 0x0;
912 pntace->access_req = cpu_to_le32(GENERIC_ALL);
913 pntace->sid.num_subauth = 3;
914 pntace->sid.revision = 1;
915 for (i = 0; i < NUM_AUTHS; i++)
916 pntace->sid.authority[i] = sid_unix_NFS_users.authority[i];
917
918 pntace->sid.sub_auth[0] = sid_unix_NFS_users.sub_auth[0];
919 pntace->sid.sub_auth[1] = sid_unix_NFS_users.sub_auth[1];
920 pntace->sid.sub_auth[2] = cpu_to_le32(current_fsgid().val);
921
922 /* size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth*4) */
923 pntace->size = cpu_to_le16(ace_size);
924 return ace_size;
925 }
926
populate_new_aces(char * nacl_base,struct cifs_sid * pownersid,struct cifs_sid * pgrpsid,__u64 * pnmode,u32 * pnum_aces,u16 * pnsize,bool modefromsid)927 static void populate_new_aces(char *nacl_base,
928 struct cifs_sid *pownersid,
929 struct cifs_sid *pgrpsid,
930 __u64 *pnmode, u32 *pnum_aces, u16 *pnsize,
931 bool modefromsid)
932 {
933 __u64 nmode;
934 u32 num_aces = 0;
935 u16 nsize = 0;
936 __u64 user_mode;
937 __u64 group_mode;
938 __u64 other_mode;
939 __u64 deny_user_mode = 0;
940 __u64 deny_group_mode = 0;
941 bool sticky_set = false;
942 struct cifs_ace *pnntace = NULL;
943
944 nmode = *pnmode;
945 num_aces = *pnum_aces;
946 nsize = *pnsize;
947
948 if (modefromsid) {
949 pnntace = (struct cifs_ace *) (nacl_base + nsize);
950 nsize += setup_special_mode_ACE(pnntace, nmode);
951 num_aces++;
952 goto set_size;
953 }
954
955 /*
956 * We'll try to keep the mode as requested by the user.
957 * But in cases where we cannot meaningfully convert that
958 * into ACL, return back the updated mode, so that it is
959 * updated in the inode.
960 */
961
962 if (!memcmp(pownersid, pgrpsid, sizeof(struct cifs_sid))) {
963 /*
964 * Case when owner and group SIDs are the same.
965 * Set the more restrictive of the two modes.
966 */
967 user_mode = nmode & (nmode << 3) & 0700;
968 group_mode = nmode & (nmode >> 3) & 0070;
969 } else {
970 user_mode = nmode & 0700;
971 group_mode = nmode & 0070;
972 }
973
974 other_mode = nmode & 0007;
975
976 /* We need DENY ACE when the perm is more restrictive than the next sets. */
977 deny_user_mode = ~(user_mode) & ((group_mode << 3) | (other_mode << 6)) & 0700;
978 deny_group_mode = ~(group_mode) & (other_mode << 3) & 0070;
979
980 *pnmode = user_mode | group_mode | other_mode | (nmode & ~0777);
981
982 /* This tells if we should allow delete child for group and everyone. */
983 if (nmode & 01000)
984 sticky_set = true;
985
986 if (deny_user_mode) {
987 pnntace = (struct cifs_ace *) (nacl_base + nsize);
988 nsize += fill_ace_for_sid(pnntace, pownersid, deny_user_mode,
989 0700, ACCESS_DENIED, false);
990 num_aces++;
991 }
992
993 /* Group DENY ACE does not conflict with owner ALLOW ACE. Keep in preferred order*/
994 if (deny_group_mode && !(deny_group_mode & (user_mode >> 3))) {
995 pnntace = (struct cifs_ace *) (nacl_base + nsize);
996 nsize += fill_ace_for_sid(pnntace, pgrpsid, deny_group_mode,
997 0070, ACCESS_DENIED, false);
998 num_aces++;
999 }
1000
1001 pnntace = (struct cifs_ace *) (nacl_base + nsize);
1002 nsize += fill_ace_for_sid(pnntace, pownersid, user_mode,
1003 0700, ACCESS_ALLOWED, true);
1004 num_aces++;
1005
1006 /* Group DENY ACE conflicts with owner ALLOW ACE. So keep it after. */
1007 if (deny_group_mode && (deny_group_mode & (user_mode >> 3))) {
1008 pnntace = (struct cifs_ace *) (nacl_base + nsize);
1009 nsize += fill_ace_for_sid(pnntace, pgrpsid, deny_group_mode,
1010 0070, ACCESS_DENIED, false);
1011 num_aces++;
1012 }
1013
1014 pnntace = (struct cifs_ace *) (nacl_base + nsize);
1015 nsize += fill_ace_for_sid(pnntace, pgrpsid, group_mode,
1016 0070, ACCESS_ALLOWED, !sticky_set);
1017 num_aces++;
1018
1019 pnntace = (struct cifs_ace *) (nacl_base + nsize);
1020 nsize += fill_ace_for_sid(pnntace, &sid_everyone, other_mode,
1021 0007, ACCESS_ALLOWED, !sticky_set);
1022 num_aces++;
1023
1024 set_size:
1025 *pnum_aces = num_aces;
1026 *pnsize = nsize;
1027 }
1028
replace_sids_and_copy_aces(struct cifs_acl * pdacl,struct cifs_acl * pndacl,struct cifs_sid * pownersid,struct cifs_sid * pgrpsid,struct cifs_sid * pnownersid,struct cifs_sid * pngrpsid)1029 static __u16 replace_sids_and_copy_aces(struct cifs_acl *pdacl, struct cifs_acl *pndacl,
1030 struct cifs_sid *pownersid, struct cifs_sid *pgrpsid,
1031 struct cifs_sid *pnownersid, struct cifs_sid *pngrpsid)
1032 {
1033 int i;
1034 u16 size = 0;
1035 struct cifs_ace *pntace = NULL;
1036 char *acl_base = NULL;
1037 u32 src_num_aces = 0;
1038 u16 nsize = 0;
1039 struct cifs_ace *pnntace = NULL;
1040 char *nacl_base = NULL;
1041 u16 ace_size = 0;
1042
1043 acl_base = (char *)pdacl;
1044 size = sizeof(struct cifs_acl);
1045 src_num_aces = le32_to_cpu(pdacl->num_aces);
1046
1047 nacl_base = (char *)pndacl;
1048 nsize = sizeof(struct cifs_acl);
1049
1050 /* Go through all the ACEs */
1051 for (i = 0; i < src_num_aces; ++i) {
1052 pntace = (struct cifs_ace *) (acl_base + size);
1053 pnntace = (struct cifs_ace *) (nacl_base + nsize);
1054
1055 if (pnownersid && compare_sids(&pntace->sid, pownersid) == 0)
1056 ace_size = cifs_copy_ace(pnntace, pntace, pnownersid);
1057 else if (pngrpsid && compare_sids(&pntace->sid, pgrpsid) == 0)
1058 ace_size = cifs_copy_ace(pnntace, pntace, pngrpsid);
1059 else
1060 ace_size = cifs_copy_ace(pnntace, pntace, NULL);
1061
1062 size += le16_to_cpu(pntace->size);
1063 nsize += ace_size;
1064 }
1065
1066 return nsize;
1067 }
1068
set_chmod_dacl(struct cifs_acl * pdacl,struct cifs_acl * pndacl,struct cifs_sid * pownersid,struct cifs_sid * pgrpsid,__u64 * pnmode,bool mode_from_sid)1069 static int set_chmod_dacl(struct cifs_acl *pdacl, struct cifs_acl *pndacl,
1070 struct cifs_sid *pownersid, struct cifs_sid *pgrpsid,
1071 __u64 *pnmode, bool mode_from_sid)
1072 {
1073 int i;
1074 u16 size = 0;
1075 struct cifs_ace *pntace = NULL;
1076 char *acl_base = NULL;
1077 u32 src_num_aces = 0;
1078 u16 nsize = 0;
1079 struct cifs_ace *pnntace = NULL;
1080 char *nacl_base = NULL;
1081 u32 num_aces = 0;
1082 bool new_aces_set = false;
1083
1084 /* Assuming that pndacl and pnmode are never NULL */
1085 nacl_base = (char *)pndacl;
1086 nsize = sizeof(struct cifs_acl);
1087
1088 /* If pdacl is NULL, we don't have a src. Simply populate new ACL. */
1089 if (!pdacl) {
1090 populate_new_aces(nacl_base,
1091 pownersid, pgrpsid,
1092 pnmode, &num_aces, &nsize,
1093 mode_from_sid);
1094 goto finalize_dacl;
1095 }
1096
1097 acl_base = (char *)pdacl;
1098 size = sizeof(struct cifs_acl);
1099 src_num_aces = le32_to_cpu(pdacl->num_aces);
1100
1101 /* Retain old ACEs which we can retain */
1102 for (i = 0; i < src_num_aces; ++i) {
1103 pntace = (struct cifs_ace *) (acl_base + size);
1104
1105 if (!new_aces_set && (pntace->flags & INHERITED_ACE)) {
1106 /* Place the new ACEs in between existing explicit and inherited */
1107 populate_new_aces(nacl_base,
1108 pownersid, pgrpsid,
1109 pnmode, &num_aces, &nsize,
1110 mode_from_sid);
1111
1112 new_aces_set = true;
1113 }
1114
1115 /* If it's any one of the ACE we're replacing, skip! */
1116 if (((compare_sids(&pntace->sid, &sid_unix_NFS_mode) == 0) ||
1117 (compare_sids(&pntace->sid, pownersid) == 0) ||
1118 (compare_sids(&pntace->sid, pgrpsid) == 0) ||
1119 (compare_sids(&pntace->sid, &sid_everyone) == 0) ||
1120 (compare_sids(&pntace->sid, &sid_authusers) == 0))) {
1121 goto next_ace;
1122 }
1123
1124 /* update the pointer to the next ACE to populate*/
1125 pnntace = (struct cifs_ace *) (nacl_base + nsize);
1126
1127 nsize += cifs_copy_ace(pnntace, pntace, NULL);
1128 num_aces++;
1129
1130 next_ace:
1131 size += le16_to_cpu(pntace->size);
1132 }
1133
1134 /* If inherited ACEs are not present, place the new ones at the tail */
1135 if (!new_aces_set) {
1136 populate_new_aces(nacl_base,
1137 pownersid, pgrpsid,
1138 pnmode, &num_aces, &nsize,
1139 mode_from_sid);
1140
1141 new_aces_set = true;
1142 }
1143
1144 finalize_dacl:
1145 pndacl->num_aces = cpu_to_le32(num_aces);
1146 pndacl->size = cpu_to_le16(nsize);
1147
1148 return 0;
1149 }
1150
parse_sid(struct cifs_sid * psid,char * end_of_acl)1151 static int parse_sid(struct cifs_sid *psid, char *end_of_acl)
1152 {
1153 /* BB need to add parm so we can store the SID BB */
1154
1155 /* validate that we do not go past end of ACL - sid must be at least 8
1156 bytes long (assuming no sub-auths - e.g. the null SID */
1157 if (end_of_acl < (char *)psid + 8) {
1158 cifs_dbg(VFS, "ACL too small to parse SID %p\n", psid);
1159 return -EINVAL;
1160 }
1161
1162 #ifdef CONFIG_CIFS_DEBUG2
1163 if (psid->num_subauth) {
1164 int i;
1165 cifs_dbg(FYI, "SID revision %d num_auth %d\n",
1166 psid->revision, psid->num_subauth);
1167
1168 for (i = 0; i < psid->num_subauth; i++) {
1169 cifs_dbg(FYI, "SID sub_auth[%d]: 0x%x\n",
1170 i, le32_to_cpu(psid->sub_auth[i]));
1171 }
1172
1173 /* BB add length check to make sure that we do not have huge
1174 num auths and therefore go off the end */
1175 cifs_dbg(FYI, "RID 0x%x\n",
1176 le32_to_cpu(psid->sub_auth[psid->num_subauth-1]));
1177 }
1178 #endif
1179
1180 return 0;
1181 }
1182
1183
1184 /* Convert CIFS ACL to POSIX form */
parse_sec_desc(struct cifs_sb_info * cifs_sb,struct cifs_ntsd * pntsd,int acl_len,struct cifs_fattr * fattr,bool get_mode_from_special_sid)1185 static int parse_sec_desc(struct cifs_sb_info *cifs_sb,
1186 struct cifs_ntsd *pntsd, int acl_len, struct cifs_fattr *fattr,
1187 bool get_mode_from_special_sid)
1188 {
1189 int rc = 0;
1190 struct cifs_sid *owner_sid_ptr, *group_sid_ptr;
1191 struct cifs_acl *dacl_ptr; /* no need for SACL ptr */
1192 char *end_of_acl = ((char *)pntsd) + acl_len;
1193 __u32 dacloffset;
1194
1195 if (pntsd == NULL)
1196 return -EIO;
1197
1198 owner_sid_ptr = (struct cifs_sid *)((char *)pntsd +
1199 le32_to_cpu(pntsd->osidoffset));
1200 group_sid_ptr = (struct cifs_sid *)((char *)pntsd +
1201 le32_to_cpu(pntsd->gsidoffset));
1202 dacloffset = le32_to_cpu(pntsd->dacloffset);
1203 dacl_ptr = (struct cifs_acl *)((char *)pntsd + dacloffset);
1204 cifs_dbg(NOISY, "revision %d type 0x%x ooffset 0x%x goffset 0x%x sacloffset 0x%x dacloffset 0x%x\n",
1205 pntsd->revision, pntsd->type, le32_to_cpu(pntsd->osidoffset),
1206 le32_to_cpu(pntsd->gsidoffset),
1207 le32_to_cpu(pntsd->sacloffset), dacloffset);
1208 /* cifs_dump_mem("owner_sid: ", owner_sid_ptr, 64); */
1209 rc = parse_sid(owner_sid_ptr, end_of_acl);
1210 if (rc) {
1211 cifs_dbg(FYI, "%s: Error %d parsing Owner SID\n", __func__, rc);
1212 return rc;
1213 }
1214 rc = sid_to_id(cifs_sb, owner_sid_ptr, fattr, SIDOWNER);
1215 if (rc) {
1216 cifs_dbg(FYI, "%s: Error %d mapping Owner SID to uid\n",
1217 __func__, rc);
1218 return rc;
1219 }
1220
1221 rc = parse_sid(group_sid_ptr, end_of_acl);
1222 if (rc) {
1223 cifs_dbg(FYI, "%s: Error %d mapping Owner SID to gid\n",
1224 __func__, rc);
1225 return rc;
1226 }
1227 rc = sid_to_id(cifs_sb, group_sid_ptr, fattr, SIDGROUP);
1228 if (rc) {
1229 cifs_dbg(FYI, "%s: Error %d mapping Group SID to gid\n",
1230 __func__, rc);
1231 return rc;
1232 }
1233
1234 if (dacloffset)
1235 parse_dacl(dacl_ptr, end_of_acl, owner_sid_ptr,
1236 group_sid_ptr, fattr, get_mode_from_special_sid);
1237 else
1238 cifs_dbg(FYI, "no ACL\n"); /* BB grant all or default perms? */
1239
1240 return rc;
1241 }
1242
1243 /* Convert permission bits from mode to equivalent CIFS ACL */
build_sec_desc(struct cifs_ntsd * pntsd,struct cifs_ntsd * pnntsd,__u32 secdesclen,__u32 * pnsecdesclen,__u64 * pnmode,kuid_t uid,kgid_t gid,bool mode_from_sid,bool id_from_sid,int * aclflag)1244 static int build_sec_desc(struct cifs_ntsd *pntsd, struct cifs_ntsd *pnntsd,
1245 __u32 secdesclen, __u32 *pnsecdesclen, __u64 *pnmode, kuid_t uid, kgid_t gid,
1246 bool mode_from_sid, bool id_from_sid, int *aclflag)
1247 {
1248 int rc = 0;
1249 __u32 dacloffset;
1250 __u32 ndacloffset;
1251 __u32 sidsoffset;
1252 struct cifs_sid *owner_sid_ptr, *group_sid_ptr;
1253 struct cifs_sid *nowner_sid_ptr = NULL, *ngroup_sid_ptr = NULL;
1254 struct cifs_acl *dacl_ptr = NULL; /* no need for SACL ptr */
1255 struct cifs_acl *ndacl_ptr = NULL; /* no need for SACL ptr */
1256 char *end_of_acl = ((char *)pntsd) + secdesclen;
1257 u16 size = 0;
1258
1259 dacloffset = le32_to_cpu(pntsd->dacloffset);
1260 if (dacloffset) {
1261 dacl_ptr = (struct cifs_acl *)((char *)pntsd + dacloffset);
1262 if (end_of_acl < (char *)dacl_ptr + le16_to_cpu(dacl_ptr->size)) {
1263 cifs_dbg(VFS, "Server returned illegal ACL size\n");
1264 return -EINVAL;
1265 }
1266 }
1267
1268 owner_sid_ptr = (struct cifs_sid *)((char *)pntsd +
1269 le32_to_cpu(pntsd->osidoffset));
1270 group_sid_ptr = (struct cifs_sid *)((char *)pntsd +
1271 le32_to_cpu(pntsd->gsidoffset));
1272
1273 if (pnmode && *pnmode != NO_CHANGE_64) { /* chmod */
1274 ndacloffset = sizeof(struct cifs_ntsd);
1275 ndacl_ptr = (struct cifs_acl *)((char *)pnntsd + ndacloffset);
1276 ndacl_ptr->revision =
1277 dacloffset ? dacl_ptr->revision : cpu_to_le16(ACL_REVISION);
1278
1279 ndacl_ptr->size = cpu_to_le16(0);
1280 ndacl_ptr->num_aces = cpu_to_le32(0);
1281
1282 rc = set_chmod_dacl(dacl_ptr, ndacl_ptr, owner_sid_ptr, group_sid_ptr,
1283 pnmode, mode_from_sid);
1284
1285 sidsoffset = ndacloffset + le16_to_cpu(ndacl_ptr->size);
1286 /* copy the non-dacl portion of secdesc */
1287 *pnsecdesclen = copy_sec_desc(pntsd, pnntsd, sidsoffset,
1288 NULL, NULL);
1289
1290 *aclflag |= CIFS_ACL_DACL;
1291 } else {
1292 ndacloffset = sizeof(struct cifs_ntsd);
1293 ndacl_ptr = (struct cifs_acl *)((char *)pnntsd + ndacloffset);
1294 ndacl_ptr->revision =
1295 dacloffset ? dacl_ptr->revision : cpu_to_le16(ACL_REVISION);
1296 ndacl_ptr->num_aces = dacl_ptr ? dacl_ptr->num_aces : 0;
1297
1298 if (uid_valid(uid)) { /* chown */
1299 uid_t id;
1300 nowner_sid_ptr = kmalloc(sizeof(struct cifs_sid),
1301 GFP_KERNEL);
1302 if (!nowner_sid_ptr) {
1303 rc = -ENOMEM;
1304 goto chown_chgrp_exit;
1305 }
1306 id = from_kuid(&init_user_ns, uid);
1307 if (id_from_sid) {
1308 struct owner_sid *osid = (struct owner_sid *)nowner_sid_ptr;
1309 /* Populate the user ownership fields S-1-5-88-1 */
1310 osid->Revision = 1;
1311 osid->NumAuth = 3;
1312 osid->Authority[5] = 5;
1313 osid->SubAuthorities[0] = cpu_to_le32(88);
1314 osid->SubAuthorities[1] = cpu_to_le32(1);
1315 osid->SubAuthorities[2] = cpu_to_le32(id);
1316
1317 } else { /* lookup sid with upcall */
1318 rc = id_to_sid(id, SIDOWNER, nowner_sid_ptr);
1319 if (rc) {
1320 cifs_dbg(FYI, "%s: Mapping error %d for owner id %d\n",
1321 __func__, rc, id);
1322 goto chown_chgrp_exit;
1323 }
1324 }
1325 *aclflag |= CIFS_ACL_OWNER;
1326 }
1327 if (gid_valid(gid)) { /* chgrp */
1328 gid_t id;
1329 ngroup_sid_ptr = kmalloc(sizeof(struct cifs_sid),
1330 GFP_KERNEL);
1331 if (!ngroup_sid_ptr) {
1332 rc = -ENOMEM;
1333 goto chown_chgrp_exit;
1334 }
1335 id = from_kgid(&init_user_ns, gid);
1336 if (id_from_sid) {
1337 struct owner_sid *gsid = (struct owner_sid *)ngroup_sid_ptr;
1338 /* Populate the group ownership fields S-1-5-88-2 */
1339 gsid->Revision = 1;
1340 gsid->NumAuth = 3;
1341 gsid->Authority[5] = 5;
1342 gsid->SubAuthorities[0] = cpu_to_le32(88);
1343 gsid->SubAuthorities[1] = cpu_to_le32(2);
1344 gsid->SubAuthorities[2] = cpu_to_le32(id);
1345
1346 } else { /* lookup sid with upcall */
1347 rc = id_to_sid(id, SIDGROUP, ngroup_sid_ptr);
1348 if (rc) {
1349 cifs_dbg(FYI, "%s: Mapping error %d for group id %d\n",
1350 __func__, rc, id);
1351 goto chown_chgrp_exit;
1352 }
1353 }
1354 *aclflag |= CIFS_ACL_GROUP;
1355 }
1356
1357 if (dacloffset) {
1358 /* Replace ACEs for old owner with new one */
1359 size = replace_sids_and_copy_aces(dacl_ptr, ndacl_ptr,
1360 owner_sid_ptr, group_sid_ptr,
1361 nowner_sid_ptr, ngroup_sid_ptr);
1362 ndacl_ptr->size = cpu_to_le16(size);
1363 }
1364
1365 sidsoffset = ndacloffset + le16_to_cpu(ndacl_ptr->size);
1366 /* copy the non-dacl portion of secdesc */
1367 *pnsecdesclen = copy_sec_desc(pntsd, pnntsd, sidsoffset,
1368 nowner_sid_ptr, ngroup_sid_ptr);
1369
1370 chown_chgrp_exit:
1371 /* errors could jump here. So make sure we return soon after this */
1372 kfree(nowner_sid_ptr);
1373 kfree(ngroup_sid_ptr);
1374 }
1375
1376 return rc;
1377 }
1378
get_cifs_acl_by_fid(struct cifs_sb_info * cifs_sb,const struct cifs_fid * cifsfid,u32 * pacllen,u32 __maybe_unused unused)1379 struct cifs_ntsd *get_cifs_acl_by_fid(struct cifs_sb_info *cifs_sb,
1380 const struct cifs_fid *cifsfid, u32 *pacllen,
1381 u32 __maybe_unused unused)
1382 {
1383 struct cifs_ntsd *pntsd = NULL;
1384 unsigned int xid;
1385 int rc;
1386 struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1387
1388 if (IS_ERR(tlink))
1389 return ERR_CAST(tlink);
1390
1391 xid = get_xid();
1392 rc = CIFSSMBGetCIFSACL(xid, tlink_tcon(tlink), cifsfid->netfid, &pntsd,
1393 pacllen);
1394 free_xid(xid);
1395
1396 cifs_put_tlink(tlink);
1397
1398 cifs_dbg(FYI, "%s: rc = %d ACL len %d\n", __func__, rc, *pacllen);
1399 if (rc)
1400 return ERR_PTR(rc);
1401 return pntsd;
1402 }
1403
get_cifs_acl_by_path(struct cifs_sb_info * cifs_sb,const char * path,u32 * pacllen)1404 static struct cifs_ntsd *get_cifs_acl_by_path(struct cifs_sb_info *cifs_sb,
1405 const char *path, u32 *pacllen)
1406 {
1407 struct cifs_ntsd *pntsd = NULL;
1408 int oplock = 0;
1409 unsigned int xid;
1410 int rc;
1411 struct cifs_tcon *tcon;
1412 struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1413 struct cifs_fid fid;
1414 struct cifs_open_parms oparms;
1415
1416 if (IS_ERR(tlink))
1417 return ERR_CAST(tlink);
1418
1419 tcon = tlink_tcon(tlink);
1420 xid = get_xid();
1421
1422 oparms.tcon = tcon;
1423 oparms.cifs_sb = cifs_sb;
1424 oparms.desired_access = READ_CONTROL;
1425 oparms.create_options = cifs_create_options(cifs_sb, 0);
1426 oparms.disposition = FILE_OPEN;
1427 oparms.path = path;
1428 oparms.fid = &fid;
1429 oparms.reconnect = false;
1430
1431 rc = CIFS_open(xid, &oparms, &oplock, NULL);
1432 if (!rc) {
1433 rc = CIFSSMBGetCIFSACL(xid, tcon, fid.netfid, &pntsd, pacllen);
1434 CIFSSMBClose(xid, tcon, fid.netfid);
1435 }
1436
1437 cifs_put_tlink(tlink);
1438 free_xid(xid);
1439
1440 cifs_dbg(FYI, "%s: rc = %d ACL len %d\n", __func__, rc, *pacllen);
1441 if (rc)
1442 return ERR_PTR(rc);
1443 return pntsd;
1444 }
1445
1446 /* Retrieve an ACL from the server */
get_cifs_acl(struct cifs_sb_info * cifs_sb,struct inode * inode,const char * path,u32 * pacllen,u32 info)1447 struct cifs_ntsd *get_cifs_acl(struct cifs_sb_info *cifs_sb,
1448 struct inode *inode, const char *path,
1449 u32 *pacllen, u32 info)
1450 {
1451 struct cifs_ntsd *pntsd = NULL;
1452 struct cifsFileInfo *open_file = NULL;
1453
1454 if (inode)
1455 open_file = find_readable_file(CIFS_I(inode), true);
1456 if (!open_file)
1457 return get_cifs_acl_by_path(cifs_sb, path, pacllen);
1458
1459 pntsd = get_cifs_acl_by_fid(cifs_sb, &open_file->fid, pacllen, info);
1460 cifsFileInfo_put(open_file);
1461 return pntsd;
1462 }
1463
1464 /* Set an ACL on the server */
set_cifs_acl(struct cifs_ntsd * pnntsd,__u32 acllen,struct inode * inode,const char * path,int aclflag)1465 int set_cifs_acl(struct cifs_ntsd *pnntsd, __u32 acllen,
1466 struct inode *inode, const char *path, int aclflag)
1467 {
1468 int oplock = 0;
1469 unsigned int xid;
1470 int rc, access_flags;
1471 struct cifs_tcon *tcon;
1472 struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
1473 struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1474 struct cifs_fid fid;
1475 struct cifs_open_parms oparms;
1476
1477 if (IS_ERR(tlink))
1478 return PTR_ERR(tlink);
1479
1480 tcon = tlink_tcon(tlink);
1481 xid = get_xid();
1482
1483 if (aclflag == CIFS_ACL_OWNER || aclflag == CIFS_ACL_GROUP)
1484 access_flags = WRITE_OWNER;
1485 else
1486 access_flags = WRITE_DAC;
1487
1488 oparms.tcon = tcon;
1489 oparms.cifs_sb = cifs_sb;
1490 oparms.desired_access = access_flags;
1491 oparms.create_options = cifs_create_options(cifs_sb, 0);
1492 oparms.disposition = FILE_OPEN;
1493 oparms.path = path;
1494 oparms.fid = &fid;
1495 oparms.reconnect = false;
1496
1497 rc = CIFS_open(xid, &oparms, &oplock, NULL);
1498 if (rc) {
1499 cifs_dbg(VFS, "Unable to open file to set ACL\n");
1500 goto out;
1501 }
1502
1503 rc = CIFSSMBSetCIFSACL(xid, tcon, fid.netfid, pnntsd, acllen, aclflag);
1504 cifs_dbg(NOISY, "SetCIFSACL rc = %d\n", rc);
1505
1506 CIFSSMBClose(xid, tcon, fid.netfid);
1507 out:
1508 free_xid(xid);
1509 cifs_put_tlink(tlink);
1510 return rc;
1511 }
1512
1513 /* Translate the CIFS ACL (similar to NTFS ACL) for a file into mode bits */
1514 int
cifs_acl_to_fattr(struct cifs_sb_info * cifs_sb,struct cifs_fattr * fattr,struct inode * inode,bool mode_from_special_sid,const char * path,const struct cifs_fid * pfid)1515 cifs_acl_to_fattr(struct cifs_sb_info *cifs_sb, struct cifs_fattr *fattr,
1516 struct inode *inode, bool mode_from_special_sid,
1517 const char *path, const struct cifs_fid *pfid)
1518 {
1519 struct cifs_ntsd *pntsd = NULL;
1520 u32 acllen = 0;
1521 int rc = 0;
1522 struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1523 struct smb_version_operations *ops;
1524 const u32 info = 0;
1525
1526 cifs_dbg(NOISY, "converting ACL to mode for %s\n", path);
1527
1528 if (IS_ERR(tlink))
1529 return PTR_ERR(tlink);
1530
1531 ops = tlink_tcon(tlink)->ses->server->ops;
1532
1533 if (pfid && (ops->get_acl_by_fid))
1534 pntsd = ops->get_acl_by_fid(cifs_sb, pfid, &acllen, info);
1535 else if (ops->get_acl)
1536 pntsd = ops->get_acl(cifs_sb, inode, path, &acllen, info);
1537 else {
1538 cifs_put_tlink(tlink);
1539 return -EOPNOTSUPP;
1540 }
1541 /* if we can retrieve the ACL, now parse Access Control Entries, ACEs */
1542 if (IS_ERR(pntsd)) {
1543 rc = PTR_ERR(pntsd);
1544 cifs_dbg(VFS, "%s: error %d getting sec desc\n", __func__, rc);
1545 } else if (mode_from_special_sid) {
1546 rc = parse_sec_desc(cifs_sb, pntsd, acllen, fattr, true);
1547 kfree(pntsd);
1548 } else {
1549 /* get approximated mode from ACL */
1550 rc = parse_sec_desc(cifs_sb, pntsd, acllen, fattr, false);
1551 kfree(pntsd);
1552 if (rc)
1553 cifs_dbg(VFS, "parse sec desc failed rc = %d\n", rc);
1554 }
1555
1556 cifs_put_tlink(tlink);
1557
1558 return rc;
1559 }
1560
1561 /* Convert mode bits to an ACL so we can update the ACL on the server */
1562 int
id_mode_to_cifs_acl(struct inode * inode,const char * path,__u64 * pnmode,kuid_t uid,kgid_t gid)1563 id_mode_to_cifs_acl(struct inode *inode, const char *path, __u64 *pnmode,
1564 kuid_t uid, kgid_t gid)
1565 {
1566 int rc = 0;
1567 int aclflag = CIFS_ACL_DACL; /* default flag to set */
1568 __u32 secdesclen = 0;
1569 __u32 nsecdesclen = 0;
1570 __u32 dacloffset = 0;
1571 struct cifs_acl *dacl_ptr = NULL;
1572 struct cifs_ntsd *pntsd = NULL; /* acl obtained from server */
1573 struct cifs_ntsd *pnntsd = NULL; /* modified acl to be sent to server */
1574 struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
1575 struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1576 struct smb_version_operations *ops;
1577 bool mode_from_sid, id_from_sid;
1578 const u32 info = 0;
1579
1580 if (IS_ERR(tlink))
1581 return PTR_ERR(tlink);
1582
1583 ops = tlink_tcon(tlink)->ses->server->ops;
1584
1585 cifs_dbg(NOISY, "set ACL from mode for %s\n", path);
1586
1587 /* Get the security descriptor */
1588
1589 if (ops->get_acl == NULL) {
1590 cifs_put_tlink(tlink);
1591 return -EOPNOTSUPP;
1592 }
1593
1594 pntsd = ops->get_acl(cifs_sb, inode, path, &secdesclen, info);
1595 if (IS_ERR(pntsd)) {
1596 rc = PTR_ERR(pntsd);
1597 cifs_dbg(VFS, "%s: error %d getting sec desc\n", __func__, rc);
1598 cifs_put_tlink(tlink);
1599 return rc;
1600 }
1601
1602 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MODE_FROM_SID)
1603 mode_from_sid = true;
1604 else
1605 mode_from_sid = false;
1606
1607 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UID_FROM_ACL)
1608 id_from_sid = true;
1609 else
1610 id_from_sid = false;
1611
1612 /* Potentially, five new ACEs can be added to the ACL for U,G,O mapping */
1613 nsecdesclen = secdesclen;
1614 if (pnmode && *pnmode != NO_CHANGE_64) { /* chmod */
1615 if (mode_from_sid)
1616 nsecdesclen += sizeof(struct cifs_ace);
1617 else /* cifsacl */
1618 nsecdesclen += 5 * sizeof(struct cifs_ace);
1619 } else { /* chown */
1620 /* When ownership changes, changes new owner sid length could be different */
1621 nsecdesclen = sizeof(struct cifs_ntsd) + (sizeof(struct cifs_sid) * 2);
1622 dacloffset = le32_to_cpu(pntsd->dacloffset);
1623 if (dacloffset) {
1624 dacl_ptr = (struct cifs_acl *)((char *)pntsd + dacloffset);
1625 if (mode_from_sid)
1626 nsecdesclen +=
1627 le32_to_cpu(dacl_ptr->num_aces) * sizeof(struct cifs_ace);
1628 else /* cifsacl */
1629 nsecdesclen += le16_to_cpu(dacl_ptr->size);
1630 }
1631 }
1632
1633 /*
1634 * Add three ACEs for owner, group, everyone getting rid of other ACEs
1635 * as chmod disables ACEs and set the security descriptor. Allocate
1636 * memory for the smb header, set security descriptor request security
1637 * descriptor parameters, and security descriptor itself
1638 */
1639 nsecdesclen = max_t(u32, nsecdesclen, DEFAULT_SEC_DESC_LEN);
1640 pnntsd = kmalloc(nsecdesclen, GFP_KERNEL);
1641 if (!pnntsd) {
1642 kfree(pntsd);
1643 cifs_put_tlink(tlink);
1644 return -ENOMEM;
1645 }
1646
1647 rc = build_sec_desc(pntsd, pnntsd, secdesclen, &nsecdesclen, pnmode, uid, gid,
1648 mode_from_sid, id_from_sid, &aclflag);
1649
1650 cifs_dbg(NOISY, "build_sec_desc rc: %d\n", rc);
1651
1652 if (ops->set_acl == NULL)
1653 rc = -EOPNOTSUPP;
1654
1655 if (!rc) {
1656 /* Set the security descriptor */
1657 rc = ops->set_acl(pnntsd, nsecdesclen, inode, path, aclflag);
1658 cifs_dbg(NOISY, "set_cifs_acl rc: %d\n", rc);
1659 }
1660 cifs_put_tlink(tlink);
1661
1662 kfree(pnntsd);
1663 kfree(pntsd);
1664 return rc;
1665 }
1666