Merge branch 'pm-cpufreq'
[linux-2.6-microblaze.git] / fs / cifs / cifsacl.c
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
36 /* security id for everyone/world system group */
37 static const struct cifs_sid sid_everyone = {
38         1, 1, {0, 0, 0, 0, 0, 1}, {0} };
39 /* security id for Authenticated Users system group */
40 static const struct cifs_sid sid_authusers = {
41         1, 1, {0, 0, 0, 0, 0, 5}, {cpu_to_le32(11)} };
42
43 /* S-1-22-1 Unmapped Unix users */
44 static const struct cifs_sid sid_unix_users = {1, 1, {0, 0, 0, 0, 0, 22},
45                 {cpu_to_le32(1), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
46
47 /* S-1-22-2 Unmapped Unix groups */
48 static const struct cifs_sid sid_unix_groups = { 1, 1, {0, 0, 0, 0, 0, 22},
49                 {cpu_to_le32(2), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
50
51 /*
52  * See https://technet.microsoft.com/en-us/library/hh509017(v=ws.10).aspx
53  */
54
55 /* S-1-5-88 MS NFS and Apple style UID/GID/mode */
56
57 /* S-1-5-88-1 Unix uid */
58 static const struct cifs_sid sid_unix_NFS_users = { 1, 2, {0, 0, 0, 0, 0, 5},
59         {cpu_to_le32(88),
60          cpu_to_le32(1), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
61
62 /* S-1-5-88-2 Unix gid */
63 static const struct cifs_sid sid_unix_NFS_groups = { 1, 2, {0, 0, 0, 0, 0, 5},
64         {cpu_to_le32(88),
65          cpu_to_le32(2), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
66
67 /* S-1-5-88-3 Unix mode */
68 static const struct cifs_sid sid_unix_NFS_mode = { 1, 2, {0, 0, 0, 0, 0, 5},
69         {cpu_to_le32(88),
70          cpu_to_le32(3), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} };
71
72 static const struct cred *root_cred;
73
74 static int
75 cifs_idmap_key_instantiate(struct key *key, struct key_preparsed_payload *prep)
76 {
77         char *payload;
78
79         /*
80          * If the payload is less than or equal to the size of a pointer, then
81          * an allocation here is wasteful. Just copy the data directly to the
82          * payload.value union member instead.
83          *
84          * With this however, you must check the datalen before trying to
85          * dereference payload.data!
86          */
87         if (prep->datalen <= sizeof(key->payload)) {
88                 key->payload.data[0] = NULL;
89                 memcpy(&key->payload, prep->data, prep->datalen);
90         } else {
91                 payload = kmemdup(prep->data, prep->datalen, GFP_KERNEL);
92                 if (!payload)
93                         return -ENOMEM;
94                 key->payload.data[0] = payload;
95         }
96
97         key->datalen = prep->datalen;
98         return 0;
99 }
100
101 static inline void
102 cifs_idmap_key_destroy(struct key *key)
103 {
104         if (key->datalen > sizeof(key->payload))
105                 kfree(key->payload.data[0]);
106 }
107
108 static struct key_type cifs_idmap_key_type = {
109         .name        = "cifs.idmap",
110         .instantiate = cifs_idmap_key_instantiate,
111         .destroy     = cifs_idmap_key_destroy,
112         .describe    = user_describe,
113 };
114
115 static char *
116 sid_to_key_str(struct cifs_sid *sidptr, unsigned int type)
117 {
118         int i, len;
119         unsigned int saval;
120         char *sidstr, *strptr;
121         unsigned long long id_auth_val;
122
123         /* 3 bytes for prefix */
124         sidstr = kmalloc(3 + SID_STRING_BASE_SIZE +
125                          (SID_STRING_SUBAUTH_SIZE * sidptr->num_subauth),
126                          GFP_KERNEL);
127         if (!sidstr)
128                 return sidstr;
129
130         strptr = sidstr;
131         len = sprintf(strptr, "%cs:S-%hhu", type == SIDOWNER ? 'o' : 'g',
132                         sidptr->revision);
133         strptr += len;
134
135         /* The authority field is a single 48-bit number */
136         id_auth_val = (unsigned long long)sidptr->authority[5];
137         id_auth_val |= (unsigned long long)sidptr->authority[4] << 8;
138         id_auth_val |= (unsigned long long)sidptr->authority[3] << 16;
139         id_auth_val |= (unsigned long long)sidptr->authority[2] << 24;
140         id_auth_val |= (unsigned long long)sidptr->authority[1] << 32;
141         id_auth_val |= (unsigned long long)sidptr->authority[0] << 48;
142
143         /*
144          * MS-DTYP states that if the authority is >= 2^32, then it should be
145          * expressed as a hex value.
146          */
147         if (id_auth_val <= UINT_MAX)
148                 len = sprintf(strptr, "-%llu", id_auth_val);
149         else
150                 len = sprintf(strptr, "-0x%llx", id_auth_val);
151
152         strptr += len;
153
154         for (i = 0; i < sidptr->num_subauth; ++i) {
155                 saval = le32_to_cpu(sidptr->sub_auth[i]);
156                 len = sprintf(strptr, "-%u", saval);
157                 strptr += len;
158         }
159
160         return sidstr;
161 }
162
163 /*
164  * if the two SIDs (roughly equivalent to a UUID for a user or group) are
165  * the same returns zero, if they do not match returns non-zero.
166  */
167 static int
168 compare_sids(const struct cifs_sid *ctsid, const struct cifs_sid *cwsid)
169 {
170         int i;
171         int num_subauth, num_sat, num_saw;
172
173         if ((!ctsid) || (!cwsid))
174                 return 1;
175
176         /* compare the revision */
177         if (ctsid->revision != cwsid->revision) {
178                 if (ctsid->revision > cwsid->revision)
179                         return 1;
180                 else
181                         return -1;
182         }
183
184         /* compare all of the six auth values */
185         for (i = 0; i < NUM_AUTHS; ++i) {
186                 if (ctsid->authority[i] != cwsid->authority[i]) {
187                         if (ctsid->authority[i] > cwsid->authority[i])
188                                 return 1;
189                         else
190                                 return -1;
191                 }
192         }
193
194         /* compare all of the subauth values if any */
195         num_sat = ctsid->num_subauth;
196         num_saw = cwsid->num_subauth;
197         num_subauth = num_sat < num_saw ? num_sat : num_saw;
198         if (num_subauth) {
199                 for (i = 0; i < num_subauth; ++i) {
200                         if (ctsid->sub_auth[i] != cwsid->sub_auth[i]) {
201                                 if (le32_to_cpu(ctsid->sub_auth[i]) >
202                                         le32_to_cpu(cwsid->sub_auth[i]))
203                                         return 1;
204                                 else
205                                         return -1;
206                         }
207                 }
208         }
209
210         return 0; /* sids compare/match */
211 }
212
213 static bool
214 is_well_known_sid(const struct cifs_sid *psid, uint32_t *puid, bool is_group)
215 {
216         int i;
217         int num_subauth;
218         const struct cifs_sid *pwell_known_sid;
219
220         if (!psid || (puid == NULL))
221                 return false;
222
223         num_subauth = psid->num_subauth;
224
225         /* check if Mac (or Windows NFS) vs. Samba format for Unix owner SID */
226         if (num_subauth == 2) {
227                 if (is_group)
228                         pwell_known_sid = &sid_unix_groups;
229                 else
230                         pwell_known_sid = &sid_unix_users;
231         } else if (num_subauth == 3) {
232                 if (is_group)
233                         pwell_known_sid = &sid_unix_NFS_groups;
234                 else
235                         pwell_known_sid = &sid_unix_NFS_users;
236         } else
237                 return false;
238
239         /* compare the revision */
240         if (psid->revision != pwell_known_sid->revision)
241                 return false;
242
243         /* compare all of the six auth values */
244         for (i = 0; i < NUM_AUTHS; ++i) {
245                 if (psid->authority[i] != pwell_known_sid->authority[i]) {
246                         cifs_dbg(FYI, "auth %d did not match\n", i);
247                         return false;
248                 }
249         }
250
251         if (num_subauth == 2) {
252                 if (psid->sub_auth[0] != pwell_known_sid->sub_auth[0])
253                         return false;
254
255                 *puid = le32_to_cpu(psid->sub_auth[1]);
256         } else /* 3 subauths, ie Windows/Mac style */ {
257                 *puid = le32_to_cpu(psid->sub_auth[0]);
258                 if ((psid->sub_auth[0] != pwell_known_sid->sub_auth[0]) ||
259                     (psid->sub_auth[1] != pwell_known_sid->sub_auth[1]))
260                         return false;
261
262                 *puid = le32_to_cpu(psid->sub_auth[2]);
263         }
264
265         cifs_dbg(FYI, "Unix UID %d returned from SID\n", *puid);
266         return true; /* well known sid found, uid returned */
267 }
268
269 static void
270 cifs_copy_sid(struct cifs_sid *dst, const struct cifs_sid *src)
271 {
272         int i;
273
274         dst->revision = src->revision;
275         dst->num_subauth = min_t(u8, src->num_subauth, SID_MAX_SUB_AUTHORITIES);
276         for (i = 0; i < NUM_AUTHS; ++i)
277                 dst->authority[i] = src->authority[i];
278         for (i = 0; i < dst->num_subauth; ++i)
279                 dst->sub_auth[i] = src->sub_auth[i];
280 }
281
282 static int
283 id_to_sid(unsigned int cid, uint sidtype, struct cifs_sid *ssid)
284 {
285         int rc;
286         struct key *sidkey;
287         struct cifs_sid *ksid;
288         unsigned int ksid_size;
289         char desc[3 + 10 + 1]; /* 3 byte prefix + 10 bytes for value + NULL */
290         const struct cred *saved_cred;
291
292         rc = snprintf(desc, sizeof(desc), "%ci:%u",
293                         sidtype == SIDOWNER ? 'o' : 'g', cid);
294         if (rc >= sizeof(desc))
295                 return -EINVAL;
296
297         rc = 0;
298         saved_cred = override_creds(root_cred);
299         sidkey = request_key(&cifs_idmap_key_type, desc, "");
300         if (IS_ERR(sidkey)) {
301                 rc = -EINVAL;
302                 cifs_dbg(FYI, "%s: Can't map %cid %u to a SID\n",
303                          __func__, sidtype == SIDOWNER ? 'u' : 'g', cid);
304                 goto out_revert_creds;
305         } else if (sidkey->datalen < CIFS_SID_BASE_SIZE) {
306                 rc = -EIO;
307                 cifs_dbg(FYI, "%s: Downcall contained malformed key (datalen=%hu)\n",
308                          __func__, sidkey->datalen);
309                 goto invalidate_key;
310         }
311
312         /*
313          * A sid is usually too large to be embedded in payload.value, but if
314          * there are no subauthorities and the host has 8-byte pointers, then
315          * it could be.
316          */
317         ksid = sidkey->datalen <= sizeof(sidkey->payload) ?
318                 (struct cifs_sid *)&sidkey->payload :
319                 (struct cifs_sid *)sidkey->payload.data[0];
320
321         ksid_size = CIFS_SID_BASE_SIZE + (ksid->num_subauth * sizeof(__le32));
322         if (ksid_size > sidkey->datalen) {
323                 rc = -EIO;
324                 cifs_dbg(FYI, "%s: Downcall contained malformed key (datalen=%hu, ksid_size=%u)\n",
325                          __func__, sidkey->datalen, ksid_size);
326                 goto invalidate_key;
327         }
328
329         cifs_copy_sid(ssid, ksid);
330 out_key_put:
331         key_put(sidkey);
332 out_revert_creds:
333         revert_creds(saved_cred);
334         return rc;
335
336 invalidate_key:
337         key_invalidate(sidkey);
338         goto out_key_put;
339 }
340
341 int
342 sid_to_id(struct cifs_sb_info *cifs_sb, struct cifs_sid *psid,
343                 struct cifs_fattr *fattr, uint sidtype)
344 {
345         int rc = 0;
346         struct key *sidkey;
347         char *sidstr;
348         const struct cred *saved_cred;
349         kuid_t fuid = cifs_sb->mnt_uid;
350         kgid_t fgid = cifs_sb->mnt_gid;
351
352         /*
353          * If we have too many subauthorities, then something is really wrong.
354          * Just return an error.
355          */
356         if (unlikely(psid->num_subauth > SID_MAX_SUB_AUTHORITIES)) {
357                 cifs_dbg(FYI, "%s: %u subauthorities is too many!\n",
358                          __func__, psid->num_subauth);
359                 return -EIO;
360         }
361
362         if ((cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UID_FROM_ACL) ||
363             (cifs_sb_master_tcon(cifs_sb)->posix_extensions)) {
364                 uint32_t unix_id;
365                 bool is_group;
366
367                 if (sidtype != SIDOWNER)
368                         is_group = true;
369                 else
370                         is_group = false;
371
372                 if (is_well_known_sid(psid, &unix_id, is_group) == false)
373                         goto try_upcall_to_get_id;
374
375                 if (is_group) {
376                         kgid_t gid;
377                         gid_t id;
378
379                         id = (gid_t)unix_id;
380                         gid = make_kgid(&init_user_ns, id);
381                         if (gid_valid(gid)) {
382                                 fgid = gid;
383                                 goto got_valid_id;
384                         }
385                 } else {
386                         kuid_t uid;
387                         uid_t id;
388
389                         id = (uid_t)unix_id;
390                         uid = make_kuid(&init_user_ns, id);
391                         if (uid_valid(uid)) {
392                                 fuid = uid;
393                                 goto got_valid_id;
394                         }
395                 }
396                 /* If unable to find uid/gid easily from SID try via upcall */
397         }
398
399 try_upcall_to_get_id:
400         sidstr = sid_to_key_str(psid, sidtype);
401         if (!sidstr)
402                 return -ENOMEM;
403
404         saved_cred = override_creds(root_cred);
405         sidkey = request_key(&cifs_idmap_key_type, sidstr, "");
406         if (IS_ERR(sidkey)) {
407                 rc = -EINVAL;
408                 cifs_dbg(FYI, "%s: Can't map SID %s to a %cid\n",
409                          __func__, sidstr, sidtype == SIDOWNER ? 'u' : 'g');
410                 goto out_revert_creds;
411         }
412
413         /*
414          * FIXME: Here we assume that uid_t and gid_t are same size. It's
415          * probably a safe assumption but might be better to check based on
416          * sidtype.
417          */
418         BUILD_BUG_ON(sizeof(uid_t) != sizeof(gid_t));
419         if (sidkey->datalen != sizeof(uid_t)) {
420                 rc = -EIO;
421                 cifs_dbg(FYI, "%s: Downcall contained malformed key (datalen=%hu)\n",
422                          __func__, sidkey->datalen);
423                 key_invalidate(sidkey);
424                 goto out_key_put;
425         }
426
427         if (sidtype == SIDOWNER) {
428                 kuid_t uid;
429                 uid_t id;
430                 memcpy(&id, &sidkey->payload.data[0], sizeof(uid_t));
431                 uid = make_kuid(&init_user_ns, id);
432                 if (uid_valid(uid))
433                         fuid = uid;
434         } else {
435                 kgid_t gid;
436                 gid_t id;
437                 memcpy(&id, &sidkey->payload.data[0], sizeof(gid_t));
438                 gid = make_kgid(&init_user_ns, id);
439                 if (gid_valid(gid))
440                         fgid = gid;
441         }
442
443 out_key_put:
444         key_put(sidkey);
445 out_revert_creds:
446         revert_creds(saved_cred);
447         kfree(sidstr);
448
449         /*
450          * Note that we return 0 here unconditionally. If the mapping
451          * fails then we just fall back to using the mnt_uid/mnt_gid.
452          */
453 got_valid_id:
454         rc = 0;
455         if (sidtype == SIDOWNER)
456                 fattr->cf_uid = fuid;
457         else
458                 fattr->cf_gid = fgid;
459         return rc;
460 }
461
462 int
463 init_cifs_idmap(void)
464 {
465         struct cred *cred;
466         struct key *keyring;
467         int ret;
468
469         cifs_dbg(FYI, "Registering the %s key type\n",
470                  cifs_idmap_key_type.name);
471
472         /* create an override credential set with a special thread keyring in
473          * which requests are cached
474          *
475          * this is used to prevent malicious redirections from being installed
476          * with add_key().
477          */
478         cred = prepare_kernel_cred(NULL);
479         if (!cred)
480                 return -ENOMEM;
481
482         keyring = keyring_alloc(".cifs_idmap",
483                                 GLOBAL_ROOT_UID, GLOBAL_ROOT_GID, cred,
484                                 (KEY_POS_ALL & ~KEY_POS_SETATTR) |
485                                 KEY_USR_VIEW | KEY_USR_READ,
486                                 KEY_ALLOC_NOT_IN_QUOTA, NULL, NULL);
487         if (IS_ERR(keyring)) {
488                 ret = PTR_ERR(keyring);
489                 goto failed_put_cred;
490         }
491
492         ret = register_key_type(&cifs_idmap_key_type);
493         if (ret < 0)
494                 goto failed_put_key;
495
496         /* instruct request_key() to use this special keyring as a cache for
497          * the results it looks up */
498         set_bit(KEY_FLAG_ROOT_CAN_CLEAR, &keyring->flags);
499         cred->thread_keyring = keyring;
500         cred->jit_keyring = KEY_REQKEY_DEFL_THREAD_KEYRING;
501         root_cred = cred;
502
503         cifs_dbg(FYI, "cifs idmap keyring: %d\n", key_serial(keyring));
504         return 0;
505
506 failed_put_key:
507         key_put(keyring);
508 failed_put_cred:
509         put_cred(cred);
510         return ret;
511 }
512
513 void
514 exit_cifs_idmap(void)
515 {
516         key_revoke(root_cred->thread_keyring);
517         unregister_key_type(&cifs_idmap_key_type);
518         put_cred(root_cred);
519         cifs_dbg(FYI, "Unregistered %s key type\n", cifs_idmap_key_type.name);
520 }
521
522 /* copy ntsd, owner sid, and group sid from a security descriptor to another */
523 static void copy_sec_desc(const struct cifs_ntsd *pntsd,
524                                 struct cifs_ntsd *pnntsd, __u32 sidsoffset)
525 {
526         struct cifs_sid *owner_sid_ptr, *group_sid_ptr;
527         struct cifs_sid *nowner_sid_ptr, *ngroup_sid_ptr;
528
529         /* copy security descriptor control portion */
530         pnntsd->revision = pntsd->revision;
531         pnntsd->type = pntsd->type;
532         pnntsd->dacloffset = cpu_to_le32(sizeof(struct cifs_ntsd));
533         pnntsd->sacloffset = 0;
534         pnntsd->osidoffset = cpu_to_le32(sidsoffset);
535         pnntsd->gsidoffset = cpu_to_le32(sidsoffset + sizeof(struct cifs_sid));
536
537         /* copy owner sid */
538         owner_sid_ptr = (struct cifs_sid *)((char *)pntsd +
539                                 le32_to_cpu(pntsd->osidoffset));
540         nowner_sid_ptr = (struct cifs_sid *)((char *)pnntsd + sidsoffset);
541         cifs_copy_sid(nowner_sid_ptr, owner_sid_ptr);
542
543         /* copy group sid */
544         group_sid_ptr = (struct cifs_sid *)((char *)pntsd +
545                                 le32_to_cpu(pntsd->gsidoffset));
546         ngroup_sid_ptr = (struct cifs_sid *)((char *)pnntsd + sidsoffset +
547                                         sizeof(struct cifs_sid));
548         cifs_copy_sid(ngroup_sid_ptr, group_sid_ptr);
549
550         return;
551 }
552
553
554 /*
555    change posix mode to reflect permissions
556    pmode is the existing mode (we only want to overwrite part of this
557    bits to set can be: S_IRWXU, S_IRWXG or S_IRWXO ie 00700 or 00070 or 00007
558 */
559 static void access_flags_to_mode(__le32 ace_flags, int type, umode_t *pmode,
560                                  umode_t *pbits_to_set)
561 {
562         __u32 flags = le32_to_cpu(ace_flags);
563         /* the order of ACEs is important.  The canonical order is to begin with
564            DENY entries followed by ALLOW, otherwise an allow entry could be
565            encountered first, making the subsequent deny entry like "dead code"
566            which would be superflous since Windows stops when a match is made
567            for the operation you are trying to perform for your user */
568
569         /* For deny ACEs we change the mask so that subsequent allow access
570            control entries do not turn on the bits we are denying */
571         if (type == ACCESS_DENIED) {
572                 if (flags & GENERIC_ALL)
573                         *pbits_to_set &= ~S_IRWXUGO;
574
575                 if ((flags & GENERIC_WRITE) ||
576                         ((flags & FILE_WRITE_RIGHTS) == FILE_WRITE_RIGHTS))
577                         *pbits_to_set &= ~S_IWUGO;
578                 if ((flags & GENERIC_READ) ||
579                         ((flags & FILE_READ_RIGHTS) == FILE_READ_RIGHTS))
580                         *pbits_to_set &= ~S_IRUGO;
581                 if ((flags & GENERIC_EXECUTE) ||
582                         ((flags & FILE_EXEC_RIGHTS) == FILE_EXEC_RIGHTS))
583                         *pbits_to_set &= ~S_IXUGO;
584                 return;
585         } else if (type != ACCESS_ALLOWED) {
586                 cifs_dbg(VFS, "unknown access control type %d\n", type);
587                 return;
588         }
589         /* else ACCESS_ALLOWED type */
590
591         if (flags & GENERIC_ALL) {
592                 *pmode |= (S_IRWXUGO & (*pbits_to_set));
593                 cifs_dbg(NOISY, "all perms\n");
594                 return;
595         }
596         if ((flags & GENERIC_WRITE) ||
597                         ((flags & FILE_WRITE_RIGHTS) == FILE_WRITE_RIGHTS))
598                 *pmode |= (S_IWUGO & (*pbits_to_set));
599         if ((flags & GENERIC_READ) ||
600                         ((flags & FILE_READ_RIGHTS) == FILE_READ_RIGHTS))
601                 *pmode |= (S_IRUGO & (*pbits_to_set));
602         if ((flags & GENERIC_EXECUTE) ||
603                         ((flags & FILE_EXEC_RIGHTS) == FILE_EXEC_RIGHTS))
604                 *pmode |= (S_IXUGO & (*pbits_to_set));
605
606         cifs_dbg(NOISY, "access flags 0x%x mode now %04o\n", flags, *pmode);
607         return;
608 }
609
610 /*
611    Generate access flags to reflect permissions mode is the existing mode.
612    This function is called for every ACE in the DACL whose SID matches
613    with either owner or group or everyone.
614 */
615
616 static void mode_to_access_flags(umode_t mode, umode_t bits_to_use,
617                                 __u32 *pace_flags)
618 {
619         /* reset access mask */
620         *pace_flags = 0x0;
621
622         /* bits to use are either S_IRWXU or S_IRWXG or S_IRWXO */
623         mode &= bits_to_use;
624
625         /* check for R/W/X UGO since we do not know whose flags
626            is this but we have cleared all the bits sans RWX for
627            either user or group or other as per bits_to_use */
628         if (mode & S_IRUGO)
629                 *pace_flags |= SET_FILE_READ_RIGHTS;
630         if (mode & S_IWUGO)
631                 *pace_flags |= SET_FILE_WRITE_RIGHTS;
632         if (mode & S_IXUGO)
633                 *pace_flags |= SET_FILE_EXEC_RIGHTS;
634
635         cifs_dbg(NOISY, "mode: %04o, access flags now 0x%x\n",
636                  mode, *pace_flags);
637         return;
638 }
639
640 static __u16 fill_ace_for_sid(struct cifs_ace *pntace,
641                         const struct cifs_sid *psid, __u64 nmode, umode_t bits)
642 {
643         int i;
644         __u16 size = 0;
645         __u32 access_req = 0;
646
647         pntace->type = ACCESS_ALLOWED;
648         pntace->flags = 0x0;
649         mode_to_access_flags(nmode, bits, &access_req);
650         if (!access_req)
651                 access_req = SET_MINIMUM_RIGHTS;
652         pntace->access_req = cpu_to_le32(access_req);
653
654         pntace->sid.revision = psid->revision;
655         pntace->sid.num_subauth = psid->num_subauth;
656         for (i = 0; i < NUM_AUTHS; i++)
657                 pntace->sid.authority[i] = psid->authority[i];
658         for (i = 0; i < psid->num_subauth; i++)
659                 pntace->sid.sub_auth[i] = psid->sub_auth[i];
660
661         size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth * 4);
662         pntace->size = cpu_to_le16(size);
663
664         return size;
665 }
666
667
668 #ifdef CONFIG_CIFS_DEBUG2
669 static void dump_ace(struct cifs_ace *pace, char *end_of_acl)
670 {
671         int num_subauth;
672
673         /* validate that we do not go past end of acl */
674
675         if (le16_to_cpu(pace->size) < 16) {
676                 cifs_dbg(VFS, "ACE too small %d\n", le16_to_cpu(pace->size));
677                 return;
678         }
679
680         if (end_of_acl < (char *)pace + le16_to_cpu(pace->size)) {
681                 cifs_dbg(VFS, "ACL too small to parse ACE\n");
682                 return;
683         }
684
685         num_subauth = pace->sid.num_subauth;
686         if (num_subauth) {
687                 int i;
688                 cifs_dbg(FYI, "ACE revision %d num_auth %d type %d flags %d size %d\n",
689                          pace->sid.revision, pace->sid.num_subauth, pace->type,
690                          pace->flags, le16_to_cpu(pace->size));
691                 for (i = 0; i < num_subauth; ++i) {
692                         cifs_dbg(FYI, "ACE sub_auth[%d]: 0x%x\n",
693                                  i, le32_to_cpu(pace->sid.sub_auth[i]));
694                 }
695
696                 /* BB add length check to make sure that we do not have huge
697                         num auths and therefore go off the end */
698         }
699
700         return;
701 }
702 #endif
703
704 static void parse_dacl(struct cifs_acl *pdacl, char *end_of_acl,
705                        struct cifs_sid *pownersid, struct cifs_sid *pgrpsid,
706                        struct cifs_fattr *fattr, bool mode_from_special_sid)
707 {
708         int i;
709         int num_aces = 0;
710         int acl_size;
711         char *acl_base;
712         struct cifs_ace **ppace;
713
714         /* BB need to add parm so we can store the SID BB */
715
716         if (!pdacl) {
717                 /* no DACL in the security descriptor, set
718                    all the permissions for user/group/other */
719                 fattr->cf_mode |= S_IRWXUGO;
720                 return;
721         }
722
723         /* validate that we do not go past end of acl */
724         if (end_of_acl < (char *)pdacl + le16_to_cpu(pdacl->size)) {
725                 cifs_dbg(VFS, "ACL too small to parse DACL\n");
726                 return;
727         }
728
729         cifs_dbg(NOISY, "DACL revision %d size %d num aces %d\n",
730                  le16_to_cpu(pdacl->revision), le16_to_cpu(pdacl->size),
731                  le32_to_cpu(pdacl->num_aces));
732
733         /* reset rwx permissions for user/group/other.
734            Also, if num_aces is 0 i.e. DACL has no ACEs,
735            user/group/other have no permissions */
736         fattr->cf_mode &= ~(S_IRWXUGO);
737
738         acl_base = (char *)pdacl;
739         acl_size = sizeof(struct cifs_acl);
740
741         num_aces = le32_to_cpu(pdacl->num_aces);
742         if (num_aces > 0) {
743                 umode_t user_mask = S_IRWXU;
744                 umode_t group_mask = S_IRWXG;
745                 umode_t other_mask = S_IRWXU | S_IRWXG | S_IRWXO;
746
747                 if (num_aces > ULONG_MAX / sizeof(struct cifs_ace *))
748                         return;
749                 ppace = kmalloc_array(num_aces, sizeof(struct cifs_ace *),
750                                       GFP_KERNEL);
751                 if (!ppace)
752                         return;
753
754                 for (i = 0; i < num_aces; ++i) {
755                         ppace[i] = (struct cifs_ace *) (acl_base + acl_size);
756 #ifdef CONFIG_CIFS_DEBUG2
757                         dump_ace(ppace[i], end_of_acl);
758 #endif
759                         if (mode_from_special_sid &&
760                             (compare_sids(&(ppace[i]->sid),
761                                           &sid_unix_NFS_mode) == 0)) {
762                                 /*
763                                  * Full permissions are:
764                                  * 07777 = S_ISUID | S_ISGID | S_ISVTX |
765                                  *         S_IRWXU | S_IRWXG | S_IRWXO
766                                  */
767                                 fattr->cf_mode &= ~07777;
768                                 fattr->cf_mode |=
769                                         le32_to_cpu(ppace[i]->sid.sub_auth[2]);
770                                 break;
771                         } else if (compare_sids(&(ppace[i]->sid), pownersid) == 0)
772                                 access_flags_to_mode(ppace[i]->access_req,
773                                                      ppace[i]->type,
774                                                      &fattr->cf_mode,
775                                                      &user_mask);
776                         else if (compare_sids(&(ppace[i]->sid), pgrpsid) == 0)
777                                 access_flags_to_mode(ppace[i]->access_req,
778                                                      ppace[i]->type,
779                                                      &fattr->cf_mode,
780                                                      &group_mask);
781                         else if (compare_sids(&(ppace[i]->sid), &sid_everyone) == 0)
782                                 access_flags_to_mode(ppace[i]->access_req,
783                                                      ppace[i]->type,
784                                                      &fattr->cf_mode,
785                                                      &other_mask);
786                         else if (compare_sids(&(ppace[i]->sid), &sid_authusers) == 0)
787                                 access_flags_to_mode(ppace[i]->access_req,
788                                                      ppace[i]->type,
789                                                      &fattr->cf_mode,
790                                                      &other_mask);
791
792
793 /*                      memcpy((void *)(&(cifscred->aces[i])),
794                                 (void *)ppace[i],
795                                 sizeof(struct cifs_ace)); */
796
797                         acl_base = (char *)ppace[i];
798                         acl_size = le16_to_cpu(ppace[i]->size);
799                 }
800
801                 kfree(ppace);
802         }
803
804         return;
805 }
806
807 unsigned int setup_authusers_ACE(struct cifs_ace *pntace)
808 {
809         int i;
810         unsigned int ace_size = 20;
811
812         pntace->type = ACCESS_ALLOWED_ACE_TYPE;
813         pntace->flags = 0x0;
814         pntace->access_req = cpu_to_le32(GENERIC_ALL);
815         pntace->sid.num_subauth = 1;
816         pntace->sid.revision = 1;
817         for (i = 0; i < NUM_AUTHS; i++)
818                 pntace->sid.authority[i] =  sid_authusers.authority[i];
819
820         pntace->sid.sub_auth[0] =  sid_authusers.sub_auth[0];
821
822         /* size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth*4) */
823         pntace->size = cpu_to_le16(ace_size);
824         return ace_size;
825 }
826
827 /*
828  * Fill in the special SID based on the mode. See
829  * https://technet.microsoft.com/en-us/library/hh509017(v=ws.10).aspx
830  */
831 unsigned int setup_special_mode_ACE(struct cifs_ace *pntace, __u64 nmode)
832 {
833         int i;
834         unsigned int ace_size = 28;
835
836         pntace->type = ACCESS_DENIED_ACE_TYPE;
837         pntace->flags = 0x0;
838         pntace->access_req = 0;
839         pntace->sid.num_subauth = 3;
840         pntace->sid.revision = 1;
841         for (i = 0; i < NUM_AUTHS; i++)
842                 pntace->sid.authority[i] = sid_unix_NFS_mode.authority[i];
843
844         pntace->sid.sub_auth[0] = sid_unix_NFS_mode.sub_auth[0];
845         pntace->sid.sub_auth[1] = sid_unix_NFS_mode.sub_auth[1];
846         pntace->sid.sub_auth[2] = cpu_to_le32(nmode & 07777);
847
848         /* size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth*4) */
849         pntace->size = cpu_to_le16(ace_size);
850         return ace_size;
851 }
852
853 unsigned int setup_special_user_owner_ACE(struct cifs_ace *pntace)
854 {
855         int i;
856         unsigned int ace_size = 28;
857
858         pntace->type = ACCESS_ALLOWED_ACE_TYPE;
859         pntace->flags = 0x0;
860         pntace->access_req = cpu_to_le32(GENERIC_ALL);
861         pntace->sid.num_subauth = 3;
862         pntace->sid.revision = 1;
863         for (i = 0; i < NUM_AUTHS; i++)
864                 pntace->sid.authority[i] = sid_unix_NFS_users.authority[i];
865
866         pntace->sid.sub_auth[0] = sid_unix_NFS_users.sub_auth[0];
867         pntace->sid.sub_auth[1] = sid_unix_NFS_users.sub_auth[1];
868         pntace->sid.sub_auth[2] = cpu_to_le32(current_fsgid().val);
869
870         /* size = 1 + 1 + 2 + 4 + 1 + 1 + 6 + (psid->num_subauth*4) */
871         pntace->size = cpu_to_le16(ace_size);
872         return ace_size;
873 }
874
875 static int set_chmod_dacl(struct cifs_acl *pndacl, struct cifs_sid *pownersid,
876                         struct cifs_sid *pgrpsid, __u64 nmode, bool modefromsid)
877 {
878         u16 size = 0;
879         u32 num_aces = 0;
880         struct cifs_acl *pnndacl;
881
882         pnndacl = (struct cifs_acl *)((char *)pndacl + sizeof(struct cifs_acl));
883
884         if (modefromsid) {
885                 struct cifs_ace *pntace =
886                         (struct cifs_ace *)((char *)pnndacl + size);
887
888                 size += setup_special_mode_ACE(pntace, nmode);
889                 num_aces++;
890         }
891
892         size += fill_ace_for_sid((struct cifs_ace *) ((char *)pnndacl + size),
893                                         pownersid, nmode, S_IRWXU);
894         num_aces++;
895         size += fill_ace_for_sid((struct cifs_ace *)((char *)pnndacl + size),
896                                         pgrpsid, nmode, S_IRWXG);
897         num_aces++;
898         size += fill_ace_for_sid((struct cifs_ace *)((char *)pnndacl + size),
899                                          &sid_everyone, nmode, S_IRWXO);
900         num_aces++;
901
902         pndacl->num_aces = cpu_to_le32(num_aces);
903         pndacl->size = cpu_to_le16(size + sizeof(struct cifs_acl));
904
905         return 0;
906 }
907
908
909 static int parse_sid(struct cifs_sid *psid, char *end_of_acl)
910 {
911         /* BB need to add parm so we can store the SID BB */
912
913         /* validate that we do not go past end of ACL - sid must be at least 8
914            bytes long (assuming no sub-auths - e.g. the null SID */
915         if (end_of_acl < (char *)psid + 8) {
916                 cifs_dbg(VFS, "ACL too small to parse SID %p\n", psid);
917                 return -EINVAL;
918         }
919
920 #ifdef CONFIG_CIFS_DEBUG2
921         if (psid->num_subauth) {
922                 int i;
923                 cifs_dbg(FYI, "SID revision %d num_auth %d\n",
924                          psid->revision, psid->num_subauth);
925
926                 for (i = 0; i < psid->num_subauth; i++) {
927                         cifs_dbg(FYI, "SID sub_auth[%d]: 0x%x\n",
928                                  i, le32_to_cpu(psid->sub_auth[i]));
929                 }
930
931                 /* BB add length check to make sure that we do not have huge
932                         num auths and therefore go off the end */
933                 cifs_dbg(FYI, "RID 0x%x\n",
934                          le32_to_cpu(psid->sub_auth[psid->num_subauth-1]));
935         }
936 #endif
937
938         return 0;
939 }
940
941
942 /* Convert CIFS ACL to POSIX form */
943 static int parse_sec_desc(struct cifs_sb_info *cifs_sb,
944                 struct cifs_ntsd *pntsd, int acl_len, struct cifs_fattr *fattr,
945                 bool get_mode_from_special_sid)
946 {
947         int rc = 0;
948         struct cifs_sid *owner_sid_ptr, *group_sid_ptr;
949         struct cifs_acl *dacl_ptr; /* no need for SACL ptr */
950         char *end_of_acl = ((char *)pntsd) + acl_len;
951         __u32 dacloffset;
952
953         if (pntsd == NULL)
954                 return -EIO;
955
956         owner_sid_ptr = (struct cifs_sid *)((char *)pntsd +
957                                 le32_to_cpu(pntsd->osidoffset));
958         group_sid_ptr = (struct cifs_sid *)((char *)pntsd +
959                                 le32_to_cpu(pntsd->gsidoffset));
960         dacloffset = le32_to_cpu(pntsd->dacloffset);
961         dacl_ptr = (struct cifs_acl *)((char *)pntsd + dacloffset);
962         cifs_dbg(NOISY, "revision %d type 0x%x ooffset 0x%x goffset 0x%x sacloffset 0x%x dacloffset 0x%x\n",
963                  pntsd->revision, pntsd->type, le32_to_cpu(pntsd->osidoffset),
964                  le32_to_cpu(pntsd->gsidoffset),
965                  le32_to_cpu(pntsd->sacloffset), dacloffset);
966 /*      cifs_dump_mem("owner_sid: ", owner_sid_ptr, 64); */
967         rc = parse_sid(owner_sid_ptr, end_of_acl);
968         if (rc) {
969                 cifs_dbg(FYI, "%s: Error %d parsing Owner SID\n", __func__, rc);
970                 return rc;
971         }
972         rc = sid_to_id(cifs_sb, owner_sid_ptr, fattr, SIDOWNER);
973         if (rc) {
974                 cifs_dbg(FYI, "%s: Error %d mapping Owner SID to uid\n",
975                          __func__, rc);
976                 return rc;
977         }
978
979         rc = parse_sid(group_sid_ptr, end_of_acl);
980         if (rc) {
981                 cifs_dbg(FYI, "%s: Error %d mapping Owner SID to gid\n",
982                          __func__, rc);
983                 return rc;
984         }
985         rc = sid_to_id(cifs_sb, group_sid_ptr, fattr, SIDGROUP);
986         if (rc) {
987                 cifs_dbg(FYI, "%s: Error %d mapping Group SID to gid\n",
988                          __func__, rc);
989                 return rc;
990         }
991
992         if (dacloffset)
993                 parse_dacl(dacl_ptr, end_of_acl, owner_sid_ptr,
994                            group_sid_ptr, fattr, get_mode_from_special_sid);
995         else
996                 cifs_dbg(FYI, "no ACL\n"); /* BB grant all or default perms? */
997
998         return rc;
999 }
1000
1001 /* Convert permission bits from mode to equivalent CIFS ACL */
1002 static int build_sec_desc(struct cifs_ntsd *pntsd, struct cifs_ntsd *pnntsd,
1003         __u32 secdesclen, __u64 nmode, kuid_t uid, kgid_t gid,
1004         bool mode_from_sid, bool id_from_sid, int *aclflag)
1005 {
1006         int rc = 0;
1007         __u32 dacloffset;
1008         __u32 ndacloffset;
1009         __u32 sidsoffset;
1010         struct cifs_sid *owner_sid_ptr, *group_sid_ptr;
1011         struct cifs_sid *nowner_sid_ptr, *ngroup_sid_ptr;
1012         struct cifs_acl *dacl_ptr = NULL;  /* no need for SACL ptr */
1013         struct cifs_acl *ndacl_ptr = NULL; /* no need for SACL ptr */
1014
1015         if (nmode != NO_CHANGE_64) { /* chmod */
1016                 owner_sid_ptr = (struct cifs_sid *)((char *)pntsd +
1017                                 le32_to_cpu(pntsd->osidoffset));
1018                 group_sid_ptr = (struct cifs_sid *)((char *)pntsd +
1019                                 le32_to_cpu(pntsd->gsidoffset));
1020                 dacloffset = le32_to_cpu(pntsd->dacloffset);
1021                 dacl_ptr = (struct cifs_acl *)((char *)pntsd + dacloffset);
1022                 ndacloffset = sizeof(struct cifs_ntsd);
1023                 ndacl_ptr = (struct cifs_acl *)((char *)pnntsd + ndacloffset);
1024                 ndacl_ptr->revision = dacl_ptr->revision;
1025                 ndacl_ptr->size = 0;
1026                 ndacl_ptr->num_aces = 0;
1027
1028                 rc = set_chmod_dacl(ndacl_ptr, owner_sid_ptr, group_sid_ptr,
1029                                     nmode, mode_from_sid);
1030                 sidsoffset = ndacloffset + le16_to_cpu(ndacl_ptr->size);
1031                 /* copy sec desc control portion & owner and group sids */
1032                 copy_sec_desc(pntsd, pnntsd, sidsoffset);
1033                 *aclflag = CIFS_ACL_DACL;
1034         } else {
1035                 memcpy(pnntsd, pntsd, secdesclen);
1036                 if (uid_valid(uid)) { /* chown */
1037                         uid_t id;
1038                         owner_sid_ptr = (struct cifs_sid *)((char *)pnntsd +
1039                                         le32_to_cpu(pnntsd->osidoffset));
1040                         nowner_sid_ptr = kmalloc(sizeof(struct cifs_sid),
1041                                                                 GFP_KERNEL);
1042                         if (!nowner_sid_ptr)
1043                                 return -ENOMEM;
1044                         id = from_kuid(&init_user_ns, uid);
1045                         if (id_from_sid) {
1046                                 struct owner_sid *osid = (struct owner_sid *)nowner_sid_ptr;
1047                                 /* Populate the user ownership fields S-1-5-88-1 */
1048                                 osid->Revision = 1;
1049                                 osid->NumAuth = 3;
1050                                 osid->Authority[5] = 5;
1051                                 osid->SubAuthorities[0] = cpu_to_le32(88);
1052                                 osid->SubAuthorities[1] = cpu_to_le32(1);
1053                                 osid->SubAuthorities[2] = cpu_to_le32(id);
1054                         } else { /* lookup sid with upcall */
1055                                 rc = id_to_sid(id, SIDOWNER, nowner_sid_ptr);
1056                                 if (rc) {
1057                                         cifs_dbg(FYI, "%s: Mapping error %d for owner id %d\n",
1058                                                  __func__, rc, id);
1059                                         kfree(nowner_sid_ptr);
1060                                         return rc;
1061                                 }
1062                         }
1063                         cifs_copy_sid(owner_sid_ptr, nowner_sid_ptr);
1064                         kfree(nowner_sid_ptr);
1065                         *aclflag = CIFS_ACL_OWNER;
1066                 }
1067                 if (gid_valid(gid)) { /* chgrp */
1068                         gid_t id;
1069                         group_sid_ptr = (struct cifs_sid *)((char *)pnntsd +
1070                                         le32_to_cpu(pnntsd->gsidoffset));
1071                         ngroup_sid_ptr = kmalloc(sizeof(struct cifs_sid),
1072                                                                 GFP_KERNEL);
1073                         if (!ngroup_sid_ptr)
1074                                 return -ENOMEM;
1075                         id = from_kgid(&init_user_ns, gid);
1076                         if (id_from_sid) {
1077                                 struct owner_sid *gsid = (struct owner_sid *)ngroup_sid_ptr;
1078                                 /* Populate the group ownership fields S-1-5-88-2 */
1079                                 gsid->Revision = 1;
1080                                 gsid->NumAuth = 3;
1081                                 gsid->Authority[5] = 5;
1082                                 gsid->SubAuthorities[0] = cpu_to_le32(88);
1083                                 gsid->SubAuthorities[1] = cpu_to_le32(2);
1084                                 gsid->SubAuthorities[2] = cpu_to_le32(id);
1085                         } else { /* lookup sid with upcall */
1086                                 rc = id_to_sid(id, SIDGROUP, ngroup_sid_ptr);
1087                                 if (rc) {
1088                                         cifs_dbg(FYI, "%s: Mapping error %d for group id %d\n",
1089                                                  __func__, rc, id);
1090                                         kfree(ngroup_sid_ptr);
1091                                         return rc;
1092                                 }
1093                         }
1094                         cifs_copy_sid(group_sid_ptr, ngroup_sid_ptr);
1095                         kfree(ngroup_sid_ptr);
1096                         *aclflag = CIFS_ACL_GROUP;
1097                 }
1098         }
1099
1100         return rc;
1101 }
1102
1103 struct cifs_ntsd *get_cifs_acl_by_fid(struct cifs_sb_info *cifs_sb,
1104                 const struct cifs_fid *cifsfid, u32 *pacllen)
1105 {
1106         struct cifs_ntsd *pntsd = NULL;
1107         unsigned int xid;
1108         int rc;
1109         struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1110
1111         if (IS_ERR(tlink))
1112                 return ERR_CAST(tlink);
1113
1114         xid = get_xid();
1115         rc = CIFSSMBGetCIFSACL(xid, tlink_tcon(tlink), cifsfid->netfid, &pntsd,
1116                                 pacllen);
1117         free_xid(xid);
1118
1119         cifs_put_tlink(tlink);
1120
1121         cifs_dbg(FYI, "%s: rc = %d ACL len %d\n", __func__, rc, *pacllen);
1122         if (rc)
1123                 return ERR_PTR(rc);
1124         return pntsd;
1125 }
1126
1127 static struct cifs_ntsd *get_cifs_acl_by_path(struct cifs_sb_info *cifs_sb,
1128                 const char *path, u32 *pacllen)
1129 {
1130         struct cifs_ntsd *pntsd = NULL;
1131         int oplock = 0;
1132         unsigned int xid;
1133         int rc;
1134         struct cifs_tcon *tcon;
1135         struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1136         struct cifs_fid fid;
1137         struct cifs_open_parms oparms;
1138
1139         if (IS_ERR(tlink))
1140                 return ERR_CAST(tlink);
1141
1142         tcon = tlink_tcon(tlink);
1143         xid = get_xid();
1144
1145         oparms.tcon = tcon;
1146         oparms.cifs_sb = cifs_sb;
1147         oparms.desired_access = READ_CONTROL;
1148         oparms.create_options = cifs_create_options(cifs_sb, 0);
1149         oparms.disposition = FILE_OPEN;
1150         oparms.path = path;
1151         oparms.fid = &fid;
1152         oparms.reconnect = false;
1153
1154         rc = CIFS_open(xid, &oparms, &oplock, NULL);
1155         if (!rc) {
1156                 rc = CIFSSMBGetCIFSACL(xid, tcon, fid.netfid, &pntsd, pacllen);
1157                 CIFSSMBClose(xid, tcon, fid.netfid);
1158         }
1159
1160         cifs_put_tlink(tlink);
1161         free_xid(xid);
1162
1163         cifs_dbg(FYI, "%s: rc = %d ACL len %d\n", __func__, rc, *pacllen);
1164         if (rc)
1165                 return ERR_PTR(rc);
1166         return pntsd;
1167 }
1168
1169 /* Retrieve an ACL from the server */
1170 struct cifs_ntsd *get_cifs_acl(struct cifs_sb_info *cifs_sb,
1171                                       struct inode *inode, const char *path,
1172                                       u32 *pacllen)
1173 {
1174         struct cifs_ntsd *pntsd = NULL;
1175         struct cifsFileInfo *open_file = NULL;
1176
1177         if (inode)
1178                 open_file = find_readable_file(CIFS_I(inode), true);
1179         if (!open_file)
1180                 return get_cifs_acl_by_path(cifs_sb, path, pacllen);
1181
1182         pntsd = get_cifs_acl_by_fid(cifs_sb, &open_file->fid, pacllen);
1183         cifsFileInfo_put(open_file);
1184         return pntsd;
1185 }
1186
1187  /* Set an ACL on the server */
1188 int set_cifs_acl(struct cifs_ntsd *pnntsd, __u32 acllen,
1189                         struct inode *inode, const char *path, int aclflag)
1190 {
1191         int oplock = 0;
1192         unsigned int xid;
1193         int rc, access_flags;
1194         struct cifs_tcon *tcon;
1195         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
1196         struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1197         struct cifs_fid fid;
1198         struct cifs_open_parms oparms;
1199
1200         if (IS_ERR(tlink))
1201                 return PTR_ERR(tlink);
1202
1203         tcon = tlink_tcon(tlink);
1204         xid = get_xid();
1205
1206         if (aclflag == CIFS_ACL_OWNER || aclflag == CIFS_ACL_GROUP)
1207                 access_flags = WRITE_OWNER;
1208         else
1209                 access_flags = WRITE_DAC;
1210
1211         oparms.tcon = tcon;
1212         oparms.cifs_sb = cifs_sb;
1213         oparms.desired_access = access_flags;
1214         oparms.create_options = cifs_create_options(cifs_sb, 0);
1215         oparms.disposition = FILE_OPEN;
1216         oparms.path = path;
1217         oparms.fid = &fid;
1218         oparms.reconnect = false;
1219
1220         rc = CIFS_open(xid, &oparms, &oplock, NULL);
1221         if (rc) {
1222                 cifs_dbg(VFS, "Unable to open file to set ACL\n");
1223                 goto out;
1224         }
1225
1226         rc = CIFSSMBSetCIFSACL(xid, tcon, fid.netfid, pnntsd, acllen, aclflag);
1227         cifs_dbg(NOISY, "SetCIFSACL rc = %d\n", rc);
1228
1229         CIFSSMBClose(xid, tcon, fid.netfid);
1230 out:
1231         free_xid(xid);
1232         cifs_put_tlink(tlink);
1233         return rc;
1234 }
1235
1236 /* Translate the CIFS ACL (similar to NTFS ACL) for a file into mode bits */
1237 int
1238 cifs_acl_to_fattr(struct cifs_sb_info *cifs_sb, struct cifs_fattr *fattr,
1239                   struct inode *inode, bool mode_from_special_sid,
1240                   const char *path, const struct cifs_fid *pfid)
1241 {
1242         struct cifs_ntsd *pntsd = NULL;
1243         u32 acllen = 0;
1244         int rc = 0;
1245         struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1246         struct smb_version_operations *ops;
1247
1248         cifs_dbg(NOISY, "converting ACL to mode for %s\n", path);
1249
1250         if (IS_ERR(tlink))
1251                 return PTR_ERR(tlink);
1252
1253         ops = tlink_tcon(tlink)->ses->server->ops;
1254
1255         if (pfid && (ops->get_acl_by_fid))
1256                 pntsd = ops->get_acl_by_fid(cifs_sb, pfid, &acllen);
1257         else if (ops->get_acl)
1258                 pntsd = ops->get_acl(cifs_sb, inode, path, &acllen);
1259         else {
1260                 cifs_put_tlink(tlink);
1261                 return -EOPNOTSUPP;
1262         }
1263         /* if we can retrieve the ACL, now parse Access Control Entries, ACEs */
1264         if (IS_ERR(pntsd)) {
1265                 rc = PTR_ERR(pntsd);
1266                 cifs_dbg(VFS, "%s: error %d getting sec desc\n", __func__, rc);
1267         } else if (mode_from_special_sid) {
1268                 rc = parse_sec_desc(cifs_sb, pntsd, acllen, fattr, true);
1269                 kfree(pntsd);
1270         } else {
1271                 /* get approximated mode from ACL */
1272                 rc = parse_sec_desc(cifs_sb, pntsd, acllen, fattr, false);
1273                 kfree(pntsd);
1274                 if (rc)
1275                         cifs_dbg(VFS, "parse sec desc failed rc = %d\n", rc);
1276         }
1277
1278         cifs_put_tlink(tlink);
1279
1280         return rc;
1281 }
1282
1283 /* Convert mode bits to an ACL so we can update the ACL on the server */
1284 int
1285 id_mode_to_cifs_acl(struct inode *inode, const char *path, __u64 nmode,
1286                         kuid_t uid, kgid_t gid)
1287 {
1288         int rc = 0;
1289         int aclflag = CIFS_ACL_DACL; /* default flag to set */
1290         __u32 secdesclen = 0;
1291         struct cifs_ntsd *pntsd = NULL; /* acl obtained from server */
1292         struct cifs_ntsd *pnntsd = NULL; /* modified acl to be sent to server */
1293         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
1294         struct tcon_link *tlink = cifs_sb_tlink(cifs_sb);
1295         struct smb_version_operations *ops;
1296         bool mode_from_sid, id_from_sid;
1297
1298         if (IS_ERR(tlink))
1299                 return PTR_ERR(tlink);
1300
1301         ops = tlink_tcon(tlink)->ses->server->ops;
1302
1303         cifs_dbg(NOISY, "set ACL from mode for %s\n", path);
1304
1305         /* Get the security descriptor */
1306
1307         if (ops->get_acl == NULL) {
1308                 cifs_put_tlink(tlink);
1309                 return -EOPNOTSUPP;
1310         }
1311
1312         pntsd = ops->get_acl(cifs_sb, inode, path, &secdesclen);
1313         if (IS_ERR(pntsd)) {
1314                 rc = PTR_ERR(pntsd);
1315                 cifs_dbg(VFS, "%s: error %d getting sec desc\n", __func__, rc);
1316                 cifs_put_tlink(tlink);
1317                 return rc;
1318         }
1319
1320         /*
1321          * Add three ACEs for owner, group, everyone getting rid of other ACEs
1322          * as chmod disables ACEs and set the security descriptor. Allocate
1323          * memory for the smb header, set security descriptor request security
1324          * descriptor parameters, and secuirty descriptor itself
1325          */
1326         secdesclen = max_t(u32, secdesclen, DEFAULT_SEC_DESC_LEN);
1327         pnntsd = kmalloc(secdesclen, GFP_KERNEL);
1328         if (!pnntsd) {
1329                 kfree(pntsd);
1330                 cifs_put_tlink(tlink);
1331                 return -ENOMEM;
1332         }
1333
1334         if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MODE_FROM_SID)
1335                 mode_from_sid = true;
1336         else
1337                 mode_from_sid = false;
1338
1339         if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UID_FROM_ACL)
1340                 id_from_sid = true;
1341         else
1342                 id_from_sid = false;
1343
1344         rc = build_sec_desc(pntsd, pnntsd, secdesclen, nmode, uid, gid,
1345                             mode_from_sid, id_from_sid, &aclflag);
1346
1347         cifs_dbg(NOISY, "build_sec_desc rc: %d\n", rc);
1348
1349         if (ops->set_acl == NULL)
1350                 rc = -EOPNOTSUPP;
1351
1352         if (!rc) {
1353                 /* Set the security descriptor */
1354                 rc = ops->set_acl(pnntsd, secdesclen, inode, path, aclflag);
1355                 cifs_dbg(NOISY, "set_cifs_acl rc: %d\n", rc);
1356         }
1357         cifs_put_tlink(tlink);
1358
1359         kfree(pnntsd);
1360         kfree(pntsd);
1361         return rc;
1362 }