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