s4: popt: Global replace of cmdline_credentials -> popt_get_cmdline_credentials().
[gd/samba-autobuild/.git] / source4 / torture / smb2 / acls.c
1 /*
2    Unix SMB/CIFS implementation.
3
4    test security descriptor operations for SMB2
5
6    Copyright (C) Zack Kirsch 2009
7
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; either version 3 of the License, or
11    (at your option) any later version.
12
13    This program is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program.  If not, see <http://www.gnu.org/licenses/>.
20 */
21
22 #include "includes.h"
23 #include "lib/cmdline/popt_common.h"
24 #include "libcli/smb2/smb2.h"
25 #include "libcli/smb2/smb2_calls.h"
26 #include "libcli/smb/smbXcli_base.h"
27 #include "torture/torture.h"
28 #include "libcli/resolve/resolve.h"
29 #include "torture/util.h"
30 #include "torture/smb2/proto.h"
31 #include "libcli/security/security.h"
32 #include "librpc/gen_ndr/ndr_security.h"
33 #include "lib/param/param.h"
34
35 #define CHECK_STATUS(status, correct) do { \
36         if (!NT_STATUS_EQUAL(status, correct)) { \
37                 torture_result(tctx, TORTURE_FAIL, "(%s) Incorrect status %s - should be %s\n", \
38                        __location__, nt_errstr(status), nt_errstr(correct)); \
39                 ret = false; \
40                 goto done; \
41         }} while (0)
42
43 #define BASEDIR "smb2-testsd"
44
45 #define CHECK_ACCESS_IGNORE SEC_STD_SYNCHRONIZE
46
47 #define CHECK_ACCESS_FLAGS(_fh, flags) do { \
48         union smb_fileinfo _q; \
49         _q.access_information.level = RAW_FILEINFO_ACCESS_INFORMATION; \
50         _q.access_information.in.file.handle = (_fh); \
51         status = smb2_getinfo_file(tree, tctx, &_q); \
52         CHECK_STATUS(status, NT_STATUS_OK); \
53         /* Handle a Vista bug where SEC_STD_SYNCHRONIZE doesn't come back. */ \
54         if ((((flags) & CHECK_ACCESS_IGNORE) == CHECK_ACCESS_IGNORE) && \
55             ((_q.access_information.out.access_flags & CHECK_ACCESS_IGNORE) != CHECK_ACCESS_IGNORE)) { \
56                 torture_comment(tctx, "SKIPPING (Vista bug): (%s) Incorrect access_flags 0x%08x - should be 0x%08x\n", \
57                        __location__, _q.access_information.out.access_flags, (flags)); \
58         } \
59         if ((_q.access_information.out.access_flags & ~CHECK_ACCESS_IGNORE) != \
60             (((flags) & ~CHECK_ACCESS_IGNORE))) { \
61                 torture_result(tctx, TORTURE_FAIL, "(%s) Incorrect access_flags 0x%08x - should be 0x%08x\n", \
62                        __location__, _q.access_information.out.access_flags, (flags)); \
63                 ret = false; \
64                 goto done; \
65         } \
66 } while (0)
67
68 #define FAIL_UNLESS(__cond)                                     \
69         do {                                                    \
70                 if (__cond) {} else {                           \
71                         torture_result(tctx, TORTURE_FAIL, "%s) condition violated: %s\n",      \
72                                __location__, #__cond);          \
73                         ret = false; goto done;                 \
74                 }                                               \
75         } while(0)
76
77 #define CHECK_SECURITY_DESCRIPTOR(_sd1, _sd2) do { \
78         if (!security_descriptor_equal(_sd1, _sd2)) { \
79                 torture_warning(tctx, "security descriptors don't match!\n"); \
80                 torture_warning(tctx, "got:\n"); \
81                 NDR_PRINT_DEBUG(security_descriptor, _sd1); \
82                 torture_warning(tctx, "expected:\n"); \
83                 NDR_PRINT_DEBUG(security_descriptor, _sd2); \
84                 torture_result(tctx, TORTURE_FAIL, \
85                                "%s: security descriptors don't match!\n", \
86                                __location__); \
87                 ret = false; \
88         } \
89 } while (0)
90
91 /*
92   test the behaviour of the well known SID_CREATOR_OWNER sid, and some generic
93   mapping bits
94   Note: This test was copied from raw/acls.c.
95 */
96 static bool test_creator_sid(struct torture_context *tctx, struct smb2_tree *tree)
97 {
98         NTSTATUS status;
99         struct smb2_create io;
100         const char *fname = BASEDIR "\\creator.txt";
101         bool ret = true;
102         struct smb2_handle handle = {{0}};
103         union smb_fileinfo q;
104         union smb_setfileinfo set;
105         struct security_descriptor *sd, *sd_orig, *sd2;
106         const char *owner_sid;
107
108         if (!smb2_util_setup_dir(tctx, tree, BASEDIR))
109                 return false;
110
111         torture_comment(tctx, "TESTING SID_CREATOR_OWNER\n");
112
113         ZERO_STRUCT(io);
114         io.level = RAW_OPEN_SMB2;
115         io.in.create_flags = 0;
116         io.in.desired_access = SEC_STD_READ_CONTROL | SEC_STD_WRITE_DAC | SEC_STD_WRITE_OWNER;
117         io.in.create_options = 0;
118         io.in.file_attributes = FILE_ATTRIBUTE_NORMAL;
119         io.in.share_access = NTCREATEX_SHARE_ACCESS_DELETE |
120                 NTCREATEX_SHARE_ACCESS_READ |
121                 NTCREATEX_SHARE_ACCESS_WRITE;
122         io.in.alloc_size = 0;
123         io.in.create_disposition = NTCREATEX_DISP_OPEN_IF;
124         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
125         io.in.security_flags = 0;
126         io.in.fname = fname;
127
128         status = smb2_create(tree, tctx, &io);
129         CHECK_STATUS(status, NT_STATUS_OK);
130         handle = io.out.file.handle;
131
132         torture_comment(tctx, "get the original sd\n");
133         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
134         q.query_secdesc.in.file.handle = handle;
135         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
136         status = smb2_getinfo_file(tree, tctx, &q);
137         CHECK_STATUS(status, NT_STATUS_OK);
138         sd_orig = q.query_secdesc.out.sd;
139
140         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
141
142         torture_comment(tctx, "set a sec desc allowing no write by CREATOR_OWNER\n");
143         sd = security_descriptor_dacl_create(tctx,
144                                         0, NULL, NULL,
145                                         SID_CREATOR_OWNER,
146                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
147                                         SEC_RIGHTS_FILE_READ | SEC_STD_ALL,
148                                         0,
149                                         NULL);
150
151         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
152         set.set_secdesc.in.file.handle = handle;
153         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
154         set.set_secdesc.in.sd = sd;
155
156         status = smb2_setinfo_file(tree, &set);
157         CHECK_STATUS(status, NT_STATUS_OK);
158
159         torture_comment(tctx, "try open for write\n");
160         io.in.desired_access = SEC_FILE_WRITE_DATA;
161         status = smb2_create(tree, tctx, &io);
162         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
163
164         torture_comment(tctx, "try open for read\n");
165         io.in.desired_access = SEC_FILE_READ_DATA;
166         status = smb2_create(tree, tctx, &io);
167         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
168
169         torture_comment(tctx, "try open for generic write\n");
170         io.in.desired_access = SEC_GENERIC_WRITE;
171         status = smb2_create(tree, tctx, &io);
172         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
173
174         torture_comment(tctx, "try open for generic read\n");
175         io.in.desired_access = SEC_GENERIC_READ;
176         status = smb2_create(tree, tctx, &io);
177         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
178
179         torture_comment(tctx, "set a sec desc allowing no write by owner\n");
180         sd = security_descriptor_dacl_create(tctx,
181                                         0, owner_sid, NULL,
182                                         owner_sid,
183                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
184                                         SEC_RIGHTS_FILE_READ | SEC_STD_ALL,
185                                         0,
186                                         NULL);
187
188         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
189         set.set_secdesc.in.file.handle = handle;
190         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
191         set.set_secdesc.in.sd = sd;
192         status = smb2_setinfo_file(tree, &set);
193         CHECK_STATUS(status, NT_STATUS_OK);
194
195         torture_comment(tctx, "check that sd has been mapped correctly\n");
196         status = smb2_getinfo_file(tree, tctx, &q);
197         CHECK_STATUS(status, NT_STATUS_OK);
198         CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd);
199
200         torture_comment(tctx, "try open for write\n");
201         io.in.desired_access = SEC_FILE_WRITE_DATA;
202         status = smb2_create(tree, tctx, &io);
203         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
204
205         torture_comment(tctx, "try open for read\n");
206         io.in.desired_access = SEC_FILE_READ_DATA;
207         status = smb2_create(tree, tctx, &io);
208         CHECK_STATUS(status, NT_STATUS_OK);
209         CHECK_ACCESS_FLAGS(io.out.file.handle,
210                            SEC_FILE_READ_DATA);
211         smb2_util_close(tree, io.out.file.handle);
212
213         torture_comment(tctx, "try open for generic write\n");
214         io.in.desired_access = SEC_GENERIC_WRITE;
215         status = smb2_create(tree, tctx, &io);
216         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
217
218         torture_comment(tctx, "try open for generic read\n");
219         io.in.desired_access = SEC_GENERIC_READ;
220         status = smb2_create(tree, tctx, &io);
221         CHECK_STATUS(status, NT_STATUS_OK);
222         CHECK_ACCESS_FLAGS(io.out.file.handle,
223                            SEC_RIGHTS_FILE_READ);
224         smb2_util_close(tree, io.out.file.handle);
225
226         torture_comment(tctx, "set a sec desc allowing generic read by owner\n");
227         sd = security_descriptor_dacl_create(tctx,
228                                         0, NULL, NULL,
229                                         owner_sid,
230                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
231                                         SEC_GENERIC_READ | SEC_STD_ALL,
232                                         0,
233                                         NULL);
234
235         set.set_secdesc.in.sd = sd;
236         status = smb2_setinfo_file(tree, &set);
237         CHECK_STATUS(status, NT_STATUS_OK);
238
239         torture_comment(tctx, "check that generic read has been mapped correctly\n");
240         sd2 = security_descriptor_dacl_create(tctx,
241                                          0, owner_sid, NULL,
242                                          owner_sid,
243                                          SEC_ACE_TYPE_ACCESS_ALLOWED,
244                                          SEC_RIGHTS_FILE_READ | SEC_STD_ALL,
245                                          0,
246                                          NULL);
247
248         status = smb2_getinfo_file(tree, tctx, &q);
249         CHECK_STATUS(status, NT_STATUS_OK);
250         CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
251
252         torture_comment(tctx, "try open for write\n");
253         io.in.desired_access = SEC_FILE_WRITE_DATA;
254         status = smb2_create(tree, tctx, &io);
255         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
256
257         torture_comment(tctx, "try open for read\n");
258         io.in.desired_access = SEC_FILE_READ_DATA;
259         status = smb2_create(tree, tctx, &io);
260         CHECK_STATUS(status, NT_STATUS_OK);
261         CHECK_ACCESS_FLAGS(io.out.file.handle,
262                            SEC_FILE_READ_DATA);
263         smb2_util_close(tree, io.out.file.handle);
264
265         torture_comment(tctx, "try open for generic write\n");
266         io.in.desired_access = SEC_GENERIC_WRITE;
267         status = smb2_create(tree, tctx, &io);
268         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
269
270         torture_comment(tctx, "try open for generic read\n");
271         io.in.desired_access = SEC_GENERIC_READ;
272         status = smb2_create(tree, tctx, &io);
273         CHECK_STATUS(status, NT_STATUS_OK);
274         CHECK_ACCESS_FLAGS(io.out.file.handle, SEC_RIGHTS_FILE_READ);
275         smb2_util_close(tree, io.out.file.handle);
276
277
278         torture_comment(tctx, "put back original sd\n");
279         set.set_secdesc.in.sd = sd_orig;
280         status = smb2_setinfo_file(tree, &set);
281         CHECK_STATUS(status, NT_STATUS_OK);
282
283
284 done:
285         smb2_util_close(tree, handle);
286         smb2_deltree(tree, BASEDIR);
287         smb2_tdis(tree);
288         smb2_logoff(tree->session);
289         return ret;
290 }
291
292
293 /*
294   test the mapping of the SEC_GENERIC_xx bits to SEC_STD_xx and
295   SEC_FILE_xx bits
296   Note: This test was copied from raw/acls.c.
297 */
298 static bool test_generic_bits(struct torture_context *tctx, struct smb2_tree *tree)
299 {
300         NTSTATUS status;
301         struct smb2_create io;
302         const char *fname = BASEDIR "\\generic.txt";
303         bool ret = true;
304         struct smb2_handle handle = {{0}};
305         int i;
306         union smb_fileinfo q;
307         union smb_setfileinfo set;
308         struct security_descriptor *sd, *sd_orig, *sd2;
309         const char *owner_sid;
310         const struct {
311                 uint32_t gen_bits;
312                 uint32_t specific_bits;
313         } file_mappings[] = {
314                 { 0,                       0 },
315                 { SEC_GENERIC_READ,        SEC_RIGHTS_FILE_READ },
316                 { SEC_GENERIC_WRITE,       SEC_RIGHTS_FILE_WRITE },
317                 { SEC_GENERIC_EXECUTE,     SEC_RIGHTS_FILE_EXECUTE },
318                 { SEC_GENERIC_ALL,         SEC_RIGHTS_FILE_ALL },
319                 { SEC_FILE_READ_DATA,      SEC_FILE_READ_DATA },
320                 { SEC_FILE_READ_ATTRIBUTE, SEC_FILE_READ_ATTRIBUTE }
321         };
322         const struct {
323                 uint32_t gen_bits;
324                 uint32_t specific_bits;
325         } dir_mappings[] = {
326                 { 0,                   0 },
327                 { SEC_GENERIC_READ,    SEC_RIGHTS_DIR_READ },
328                 { SEC_GENERIC_WRITE,   SEC_RIGHTS_DIR_WRITE },
329                 { SEC_GENERIC_EXECUTE, SEC_RIGHTS_DIR_EXECUTE },
330                 { SEC_GENERIC_ALL,     SEC_RIGHTS_DIR_ALL }
331         };
332         bool has_restore_privilege = false;
333         bool has_take_ownership_privilege = false;
334
335         if (!smb2_util_setup_dir(tctx, tree, BASEDIR))
336                 return false;
337
338         torture_comment(tctx, "TESTING FILE GENERIC BITS\n");
339
340         ZERO_STRUCT(io);
341         io.level = RAW_OPEN_SMB2;
342         io.in.create_flags = 0;
343         io.in.desired_access =
344                 SEC_STD_READ_CONTROL |
345                 SEC_STD_WRITE_DAC |
346                 SEC_STD_WRITE_OWNER;
347         io.in.create_options = 0;
348         io.in.file_attributes = FILE_ATTRIBUTE_NORMAL;
349         io.in.share_access =
350                 NTCREATEX_SHARE_ACCESS_READ |
351                 NTCREATEX_SHARE_ACCESS_WRITE;
352         io.in.alloc_size = 0;
353         io.in.create_disposition = NTCREATEX_DISP_OPEN_IF;
354         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
355         io.in.security_flags = 0;
356         io.in.fname = fname;
357         status = smb2_create(tree, tctx, &io);
358         CHECK_STATUS(status, NT_STATUS_OK);
359         handle = io.out.file.handle;
360
361         torture_comment(tctx, "get the original sd\n");
362         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
363         q.query_secdesc.in.file.handle = handle;
364         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
365         status = smb2_getinfo_file(tree, tctx, &q);
366         CHECK_STATUS(status, NT_STATUS_OK);
367         sd_orig = q.query_secdesc.out.sd;
368
369         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
370
371 /*
372  * XXX: The smblsa calls use SMB as their transport - need to get rid of
373  * dependency.
374  */
375 /*
376         status = smblsa_sid_check_privilege(cli,
377                                             owner_sid,
378                                             sec_privilege_name(SEC_PRIV_RESTORE));
379         has_restore_privilege = NT_STATUS_IS_OK(status);
380         if (!NT_STATUS_IS_OK(status)) {
381                 torture_warning(tctx, "smblsa_sid_check_privilege - %s\n", nt_errstr(status));
382         }
383         torture_comment(tctx, "SEC_PRIV_RESTORE - %s\n", has_restore_privilege?"Yes":"No");
384
385         status = smblsa_sid_check_privilege(cli,
386                                             owner_sid,
387                                             sec_privilege_name(SEC_PRIV_TAKE_OWNERSHIP));
388         has_take_ownership_privilege = NT_STATUS_IS_OK(status);
389         if (!NT_STATUS_IS_OK(status)) {
390                 torture_warning(tctx, "smblsa_sid_check_privilege - %s\n", nt_errstr(status));
391         }
392         torture_comment(tctx, "SEC_PRIV_TAKE_OWNERSHIP - %s\n", has_take_ownership_privilege?"Yes":"No");
393 */
394
395         for (i=0;i<ARRAY_SIZE(file_mappings);i++) {
396                 uint32_t expected_mask =
397                         SEC_STD_WRITE_DAC |
398                         SEC_STD_READ_CONTROL |
399                         SEC_FILE_READ_ATTRIBUTE |
400                         SEC_STD_DELETE;
401                 uint32_t expected_mask_anon = SEC_FILE_READ_ATTRIBUTE;
402
403                 if (has_restore_privilege) {
404                         expected_mask_anon |= SEC_STD_DELETE;
405                 }
406
407                 torture_comment(tctx, "Testing generic bits 0x%08x\n",
408                        file_mappings[i].gen_bits);
409                 sd = security_descriptor_dacl_create(tctx,
410                                                 0, owner_sid, NULL,
411                                                 owner_sid,
412                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
413                                                 file_mappings[i].gen_bits,
414                                                 0,
415                                                 NULL);
416
417                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
418                 set.set_secdesc.in.file.handle = handle;
419                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
420                 set.set_secdesc.in.sd = sd;
421
422                 status = smb2_setinfo_file(tree, &set);
423                 CHECK_STATUS(status, NT_STATUS_OK);
424
425                 sd2 = security_descriptor_dacl_create(tctx,
426                                                  0, owner_sid, NULL,
427                                                  owner_sid,
428                                                  SEC_ACE_TYPE_ACCESS_ALLOWED,
429                                                  file_mappings[i].specific_bits,
430                                                  0,
431                                                  NULL);
432
433                 status = smb2_getinfo_file(tree, tctx, &q);
434                 CHECK_STATUS(status, NT_STATUS_OK);
435                 CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
436
437                 io.in.desired_access = SEC_FLAG_MAXIMUM_ALLOWED;
438                 status = smb2_create(tree, tctx, &io);
439                 CHECK_STATUS(status, NT_STATUS_OK);
440                 CHECK_ACCESS_FLAGS(io.out.file.handle,
441                                    expected_mask | file_mappings[i].specific_bits);
442                 smb2_util_close(tree, io.out.file.handle);
443
444                 if (!has_take_ownership_privilege) {
445                         continue;
446                 }
447
448                 torture_comment(tctx, "Testing generic bits 0x%08x (anonymous)\n",
449                        file_mappings[i].gen_bits);
450                 sd = security_descriptor_dacl_create(tctx,
451                                                 0, SID_NT_ANONYMOUS, NULL,
452                                                 owner_sid,
453                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
454                                                 file_mappings[i].gen_bits,
455                                                 0,
456                                                 NULL);
457
458                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
459                 set.set_secdesc.in.file.handle = handle;
460                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
461                 set.set_secdesc.in.sd = sd;
462
463                 status = smb2_setinfo_file(tree, &set);
464                 CHECK_STATUS(status, NT_STATUS_OK);
465
466                 sd2 = security_descriptor_dacl_create(tctx,
467                                                  0, SID_NT_ANONYMOUS, NULL,
468                                                  owner_sid,
469                                                  SEC_ACE_TYPE_ACCESS_ALLOWED,
470                                                  file_mappings[i].specific_bits,
471                                                  0,
472                                                  NULL);
473
474                 status = smb2_getinfo_file(tree, tctx, &q);
475                 CHECK_STATUS(status, NT_STATUS_OK);
476                 CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
477
478                 io.in.desired_access = SEC_FLAG_MAXIMUM_ALLOWED;
479                 status = smb2_create(tree, tctx, &io);
480                 CHECK_STATUS(status, NT_STATUS_OK);
481                 CHECK_ACCESS_FLAGS(io.out.file.handle,
482                                    expected_mask_anon | file_mappings[i].specific_bits);
483                 smb2_util_close(tree, io.out.file.handle);
484         }
485
486         torture_comment(tctx, "put back original sd\n");
487         set.set_secdesc.in.sd = sd_orig;
488         status = smb2_setinfo_file(tree, &set);
489         CHECK_STATUS(status, NT_STATUS_OK);
490
491         smb2_util_close(tree, handle);
492         smb2_util_unlink(tree, fname);
493
494
495         torture_comment(tctx, "TESTING DIR GENERIC BITS\n");
496
497         ZERO_STRUCT(io);
498         io.level = RAW_OPEN_SMB2;
499         io.in.create_flags = 0;
500         io.in.desired_access =
501                 SEC_STD_READ_CONTROL |
502                 SEC_STD_WRITE_DAC |
503                 SEC_STD_WRITE_OWNER;
504         io.in.create_options = NTCREATEX_OPTIONS_DIRECTORY;
505         io.in.file_attributes = FILE_ATTRIBUTE_DIRECTORY;
506         io.in.share_access =
507                 NTCREATEX_SHARE_ACCESS_READ |
508                 NTCREATEX_SHARE_ACCESS_WRITE;
509         io.in.alloc_size = 0;
510         io.in.create_disposition = NTCREATEX_DISP_OPEN_IF;
511         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
512         io.in.security_flags = 0;
513         io.in.fname = fname;
514         status = smb2_create(tree, tctx, &io);
515         CHECK_STATUS(status, NT_STATUS_OK);
516         handle = io.out.file.handle;
517
518         torture_comment(tctx, "get the original sd\n");
519         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
520         q.query_secdesc.in.file.handle = handle;
521         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
522         status = smb2_getinfo_file(tree, tctx, &q);
523         CHECK_STATUS(status, NT_STATUS_OK);
524         sd_orig = q.query_secdesc.out.sd;
525
526         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
527
528 /*
529  * XXX: The smblsa calls use SMB as their transport - need to get rid of
530  * dependency.
531  */
532 /*
533         status = smblsa_sid_check_privilege(cli,
534                                             owner_sid,
535                                             sec_privilege_name(SEC_PRIV_RESTORE));
536         has_restore_privilege = NT_STATUS_IS_OK(status);
537         if (!NT_STATUS_IS_OK(status)) {
538                 torture_warning(tctx, "smblsa_sid_check_privilege - %s\n", nt_errstr(status));
539         }
540         torture_comment(tctx, "SEC_PRIV_RESTORE - %s\n", has_restore_privilege?"Yes":"No");
541
542         status = smblsa_sid_check_privilege(cli,
543                                             owner_sid,
544                                             sec_privilege_name(SEC_PRIV_TAKE_OWNERSHIP));
545         has_take_ownership_privilege = NT_STATUS_IS_OK(status);
546         if (!NT_STATUS_IS_OK(status)) {
547                 torture_warning(tctx, "smblsa_sid_check_privilege - %s\n", nt_errstr(status));
548         }
549         torture_comment(tctx, "SEC_PRIV_TAKE_OWNERSHIP - %s\n", has_take_ownership_privilege?"Yes":"No");
550
551 */
552         for (i=0;i<ARRAY_SIZE(dir_mappings);i++) {
553                 uint32_t expected_mask =
554                         SEC_STD_WRITE_DAC |
555                         SEC_STD_READ_CONTROL |
556                         SEC_FILE_READ_ATTRIBUTE |
557                         SEC_STD_DELETE;
558                 uint32_t expected_mask_anon = SEC_FILE_READ_ATTRIBUTE;
559
560                 if (has_restore_privilege) {
561                         expected_mask_anon |= SEC_STD_DELETE;
562                 }
563
564                 torture_comment(tctx, "Testing generic bits 0x%08x\n",
565                        file_mappings[i].gen_bits);
566                 sd = security_descriptor_dacl_create(tctx,
567                                                 0, owner_sid, NULL,
568                                                 owner_sid,
569                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
570                                                 dir_mappings[i].gen_bits,
571                                                 0,
572                                                 NULL);
573
574                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
575                 set.set_secdesc.in.file.handle = handle;
576                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
577                 set.set_secdesc.in.sd = sd;
578
579                 status = smb2_setinfo_file(tree, &set);
580                 CHECK_STATUS(status, NT_STATUS_OK);
581
582                 sd2 = security_descriptor_dacl_create(tctx,
583                                                  0, owner_sid, NULL,
584                                                  owner_sid,
585                                                  SEC_ACE_TYPE_ACCESS_ALLOWED,
586                                                  dir_mappings[i].specific_bits,
587                                                  0,
588                                                  NULL);
589
590                 status = smb2_getinfo_file(tree, tctx, &q);
591                 CHECK_STATUS(status, NT_STATUS_OK);
592                 CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
593
594                 io.in.desired_access = SEC_FLAG_MAXIMUM_ALLOWED;
595                 status = smb2_create(tree, tctx, &io);
596                 CHECK_STATUS(status, NT_STATUS_OK);
597                 CHECK_ACCESS_FLAGS(io.out.file.handle,
598                                    expected_mask | dir_mappings[i].specific_bits);
599                 smb2_util_close(tree, io.out.file.handle);
600
601                 if (!has_take_ownership_privilege) {
602                         continue;
603                 }
604
605                 torture_comment(tctx, "Testing generic bits 0x%08x (anonymous)\n",
606                        file_mappings[i].gen_bits);
607                 sd = security_descriptor_dacl_create(tctx,
608                                                 0, SID_NT_ANONYMOUS, NULL,
609                                                 owner_sid,
610                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
611                                                 file_mappings[i].gen_bits,
612                                                 0,
613                                                 NULL);
614
615                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
616                 set.set_secdesc.in.file.handle = handle;
617                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
618                 set.set_secdesc.in.sd = sd;
619
620                 status = smb2_setinfo_file(tree, &set);
621                 CHECK_STATUS(status, NT_STATUS_OK);
622
623                 sd2 = security_descriptor_dacl_create(tctx,
624                                                  0, SID_NT_ANONYMOUS, NULL,
625                                                  owner_sid,
626                                                  SEC_ACE_TYPE_ACCESS_ALLOWED,
627                                                  file_mappings[i].specific_bits,
628                                                  0,
629                                                  NULL);
630
631                 status = smb2_getinfo_file(tree, tctx, &q);
632                 CHECK_STATUS(status, NT_STATUS_OK);
633                 CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
634
635                 io.in.desired_access = SEC_FLAG_MAXIMUM_ALLOWED;
636                 status = smb2_create(tree, tctx, &io);
637                 CHECK_STATUS(status, NT_STATUS_OK);
638                 CHECK_ACCESS_FLAGS(io.out.file.handle,
639                                    expected_mask_anon | dir_mappings[i].specific_bits);
640                 smb2_util_close(tree, io.out.file.handle);
641         }
642
643         torture_comment(tctx, "put back original sd\n");
644         set.set_secdesc.in.sd = sd_orig;
645         status = smb2_setinfo_file(tree, &set);
646         CHECK_STATUS(status, NT_STATUS_OK);
647
648         smb2_util_close(tree, handle);
649         smb2_util_unlink(tree, fname);
650
651 done:
652         smb2_util_close(tree, handle);
653         smb2_deltree(tree, BASEDIR);
654         smb2_tdis(tree);
655         smb2_logoff(tree->session);
656         return ret;
657 }
658
659
660 /*
661   see what access bits the owner of a file always gets
662   Note: This test was copied from raw/acls.c.
663 */
664 static bool test_owner_bits(struct torture_context *tctx, struct smb2_tree *tree)
665 {
666         NTSTATUS status;
667         struct smb2_create io;
668         const char *fname = BASEDIR "\\test_owner_bits.txt";
669         bool ret = true;
670         struct smb2_handle handle = {{0}};
671         int i;
672         union smb_fileinfo q;
673         union smb_setfileinfo set;
674         struct security_descriptor *sd, *sd_orig;
675         const char *owner_sid;
676         uint32_t expected_bits;
677
678         if (!smb2_util_setup_dir(tctx, tree, BASEDIR))
679                 return false;
680
681         torture_comment(tctx, "TESTING FILE OWNER BITS\n");
682
683         ZERO_STRUCT(io);
684         io.level = RAW_OPEN_SMB2;
685         io.in.create_flags = 0;
686         io.in.desired_access =
687                 SEC_STD_READ_CONTROL |
688                 SEC_STD_WRITE_DAC |
689                 SEC_STD_WRITE_OWNER;
690         io.in.create_options = 0;
691         io.in.file_attributes = FILE_ATTRIBUTE_NORMAL;
692         io.in.share_access =
693                 NTCREATEX_SHARE_ACCESS_READ |
694                 NTCREATEX_SHARE_ACCESS_WRITE;
695         io.in.alloc_size = 0;
696         io.in.create_disposition = NTCREATEX_DISP_OPEN_IF;
697         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
698         io.in.security_flags = 0;
699         io.in.fname = fname;
700         status = smb2_create(tree, tctx, &io);
701         CHECK_STATUS(status, NT_STATUS_OK);
702         handle = io.out.file.handle;
703
704         torture_comment(tctx, "get the original sd\n");
705         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
706         q.query_secdesc.in.file.handle = handle;
707         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
708         status = smb2_getinfo_file(tree, tctx, &q);
709         CHECK_STATUS(status, NT_STATUS_OK);
710         sd_orig = q.query_secdesc.out.sd;
711
712         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
713
714 /*
715  * XXX: The smblsa calls use SMB as their transport - need to get rid of
716  * dependency.
717  */
718 /*
719         status = smblsa_sid_check_privilege(cli,
720                                             owner_sid,
721                                             sec_privilege_name(SEC_PRIV_RESTORE));
722         has_restore_privilege = NT_STATUS_IS_OK(status);
723         if (!NT_STATUS_IS_OK(status)) {
724                 torture_warning(tctx, "smblsa_sid_check_privilege - %s\n", nt_errstr(status));
725         }
726         torture_comment(tctx, "SEC_PRIV_RESTORE - %s\n", has_restore_privilege?"Yes":"No");
727
728         status = smblsa_sid_check_privilege(cli,
729                                             owner_sid,
730                                             sec_privilege_name(SEC_PRIV_TAKE_OWNERSHIP));
731         has_take_ownership_privilege = NT_STATUS_IS_OK(status);
732         if (!NT_STATUS_IS_OK(status)) {
733                 torture_warning(tctx, "smblsa_sid_check_privilege - %s\n", nt_errstr(status));
734         }
735         torture_comment(tctx, "SEC_PRIV_TAKE_OWNERSHIP - %s\n", has_take_ownership_privilege?"Yes":"No");
736 */
737
738         sd = security_descriptor_dacl_create(tctx,
739                                         0, NULL, NULL,
740                                         owner_sid,
741                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
742                                         SEC_FILE_WRITE_DATA,
743                                         0,
744                                         NULL);
745
746         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
747         set.set_secdesc.in.file.handle = handle;
748         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
749         set.set_secdesc.in.sd = sd;
750
751         status = smb2_setinfo_file(tree, &set);
752         CHECK_STATUS(status, NT_STATUS_OK);
753
754         expected_bits = SEC_FILE_WRITE_DATA | SEC_FILE_READ_ATTRIBUTE;
755
756         for (i=0;i<16;i++) {
757                 uint32_t bit = (1<<i);
758                 io.in.desired_access = bit;
759                 status = smb2_create(tree, tctx, &io);
760                 if (expected_bits & bit) {
761                         if (!NT_STATUS_IS_OK(status)) {
762                                 torture_warning(tctx, "failed with access mask 0x%08x of expected 0x%08x\n",
763                                        bit, expected_bits);
764                         }
765                         CHECK_STATUS(status, NT_STATUS_OK);
766                         CHECK_ACCESS_FLAGS(io.out.file.handle, bit);
767                         smb2_util_close(tree, io.out.file.handle);
768                 } else {
769                         if (NT_STATUS_IS_OK(status)) {
770                                 torture_warning(tctx, "open succeeded with access mask 0x%08x of "
771                                         "expected 0x%08x - should fail\n",
772                                        bit, expected_bits);
773                         }
774                         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
775                 }
776         }
777
778         torture_comment(tctx, "put back original sd\n");
779         set.set_secdesc.in.sd = sd_orig;
780         status = smb2_setinfo_file(tree, &set);
781         CHECK_STATUS(status, NT_STATUS_OK);
782
783 done:
784         smb2_util_close(tree, handle);
785         smb2_util_unlink(tree, fname);
786         smb2_deltree(tree, BASEDIR);
787         smb2_tdis(tree);
788         smb2_logoff(tree->session);
789         return ret;
790 }
791
792
793
794 /*
795   test the inheritance of ACL flags onto new files and directories
796   Note: This test was copied from raw/acls.c.
797 */
798 static bool test_inheritance(struct torture_context *tctx, struct smb2_tree *tree)
799 {
800         NTSTATUS status;
801         struct smb2_create io;
802         const char *dname = BASEDIR "\\inheritance";
803         const char *fname1 = BASEDIR "\\inheritance\\testfile";
804         const char *fname2 = BASEDIR "\\inheritance\\testdir";
805         bool ret = true;
806         struct smb2_handle handle = {{0}};
807         struct smb2_handle handle2 = {{0}};
808         int i;
809         union smb_fileinfo q;
810         union smb_setfileinfo set;
811         struct security_descriptor *sd, *sd2, *sd_orig=NULL, *sd_def1, *sd_def2;
812         const char *owner_sid;
813         const struct dom_sid *creator_owner;
814         const struct {
815                 uint32_t parent_flags;
816                 uint32_t file_flags;
817                 uint32_t dir_flags;
818         } test_flags[] = {
819                 {
820                         0,
821                         0,
822                         0
823                 },
824                 {
825                         SEC_ACE_FLAG_OBJECT_INHERIT,
826                         0,
827                         SEC_ACE_FLAG_OBJECT_INHERIT |
828                         SEC_ACE_FLAG_INHERIT_ONLY,
829                 },
830                 {
831                         SEC_ACE_FLAG_CONTAINER_INHERIT,
832                         0,
833                         SEC_ACE_FLAG_CONTAINER_INHERIT,
834                 },
835                 {
836                         SEC_ACE_FLAG_OBJECT_INHERIT |
837                         SEC_ACE_FLAG_CONTAINER_INHERIT,
838                         0,
839                         SEC_ACE_FLAG_OBJECT_INHERIT |
840                         SEC_ACE_FLAG_CONTAINER_INHERIT,
841                 },
842                 {
843                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT,
844                         0,
845                         0,
846                 },
847                 {
848                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT |
849                         SEC_ACE_FLAG_OBJECT_INHERIT,
850                         0,
851                         0,
852                 },
853                 {
854                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT |
855                         SEC_ACE_FLAG_CONTAINER_INHERIT,
856                         0,
857                         0,
858                 },
859                 {
860                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT |
861                         SEC_ACE_FLAG_CONTAINER_INHERIT |
862                         SEC_ACE_FLAG_OBJECT_INHERIT,
863                         0,
864                         0,
865                 },
866                 {
867                         SEC_ACE_FLAG_INHERIT_ONLY,
868                         0,
869                         0,
870                 },
871                 {
872                         SEC_ACE_FLAG_INHERIT_ONLY |
873                         SEC_ACE_FLAG_OBJECT_INHERIT,
874                         0,
875                         SEC_ACE_FLAG_OBJECT_INHERIT |
876                         SEC_ACE_FLAG_INHERIT_ONLY,
877                 },
878                 {
879                         SEC_ACE_FLAG_INHERIT_ONLY |
880                         SEC_ACE_FLAG_CONTAINER_INHERIT,
881                         0,
882                         SEC_ACE_FLAG_CONTAINER_INHERIT,
883                 },
884                 {
885                         SEC_ACE_FLAG_INHERIT_ONLY |
886                         SEC_ACE_FLAG_CONTAINER_INHERIT |
887                         SEC_ACE_FLAG_OBJECT_INHERIT,
888                         0,
889                         SEC_ACE_FLAG_CONTAINER_INHERIT |
890                         SEC_ACE_FLAG_OBJECT_INHERIT,
891                 },
892                 {
893                         SEC_ACE_FLAG_INHERIT_ONLY |
894                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT,
895                         0,
896                         0,
897                 },
898                 {
899                         SEC_ACE_FLAG_INHERIT_ONLY |
900                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT |
901                         SEC_ACE_FLAG_OBJECT_INHERIT,
902                         0,
903                         0,
904                 },
905                 {
906                         SEC_ACE_FLAG_INHERIT_ONLY |
907                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT |
908                         SEC_ACE_FLAG_CONTAINER_INHERIT,
909                         0,
910                         0,
911                 },
912                 {
913                         SEC_ACE_FLAG_INHERIT_ONLY |
914                         SEC_ACE_FLAG_NO_PROPAGATE_INHERIT |
915                         SEC_ACE_FLAG_CONTAINER_INHERIT |
916                         SEC_ACE_FLAG_OBJECT_INHERIT,
917                         0,
918                         0,
919                 }
920         };
921
922         if (!smb2_util_setup_dir(tctx, tree, BASEDIR))
923                 return false;
924
925         torture_comment(tctx, "TESTING ACL INHERITANCE\n");
926
927         ZERO_STRUCT(io);
928         io.level = RAW_OPEN_SMB2;
929         io.in.create_flags = 0;
930         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
931         io.in.create_options = NTCREATEX_OPTIONS_DIRECTORY;
932         io.in.file_attributes = FILE_ATTRIBUTE_DIRECTORY;
933         io.in.share_access = 0;
934         io.in.alloc_size = 0;
935         io.in.create_disposition = NTCREATEX_DISP_CREATE;
936         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
937         io.in.security_flags = 0;
938         io.in.fname = dname;
939
940         status = smb2_create(tree, tctx, &io);
941         CHECK_STATUS(status, NT_STATUS_OK);
942         handle = io.out.file.handle;
943
944         torture_comment(tctx, "get the original sd\n");
945         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
946         q.query_secdesc.in.file.handle = handle;
947         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
948         status = smb2_getinfo_file(tree, tctx, &q);
949         CHECK_STATUS(status, NT_STATUS_OK);
950         sd_orig = q.query_secdesc.out.sd;
951
952         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
953
954         torture_comment(tctx, "owner_sid is %s\n", owner_sid);
955
956         /*
957          * The Windows Default ACL for a new file, when there is no ACL to be
958          * inherited: FullControl for the owner and SYSTEM.
959          */
960         sd_def1 = security_descriptor_dacl_create(tctx,
961                                             0, owner_sid, NULL,
962                                             owner_sid,
963                                             SEC_ACE_TYPE_ACCESS_ALLOWED,
964                                             SEC_RIGHTS_FILE_ALL,
965                                             0,
966                                             SID_NT_SYSTEM,
967                                             SEC_ACE_TYPE_ACCESS_ALLOWED,
968                                             SEC_RIGHTS_FILE_ALL,
969                                             0,
970                                             NULL);
971
972         /*
973          * Use this in the case the system being tested does not add an ACE for
974          * the SYSTEM SID.
975          */
976         sd_def2 = security_descriptor_dacl_create(tctx,
977                                             0, owner_sid, NULL,
978                                             owner_sid,
979                                             SEC_ACE_TYPE_ACCESS_ALLOWED,
980                                             SEC_RIGHTS_FILE_ALL,
981                                             0,
982                                             NULL);
983
984         creator_owner = dom_sid_parse_talloc(tctx, SID_CREATOR_OWNER);
985
986         for (i=0;i<ARRAY_SIZE(test_flags);i++) {
987                 sd = security_descriptor_dacl_create(tctx,
988                                                 0, NULL, NULL,
989                                                 SID_CREATOR_OWNER,
990                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
991                                                 SEC_FILE_WRITE_DATA,
992                                                 test_flags[i].parent_flags,
993                                                 SID_WORLD,
994                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
995                                                 SEC_FILE_ALL | SEC_STD_ALL,
996                                                 0,
997                                                 NULL);
998                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
999                 set.set_secdesc.in.file.handle = handle;
1000                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1001                 set.set_secdesc.in.sd = sd;
1002                 status = smb2_setinfo_file(tree, &set);
1003                 CHECK_STATUS(status, NT_STATUS_OK);
1004
1005                 io.in.fname = fname1;
1006                 io.in.create_options = 0;
1007                 status = smb2_create(tree, tctx, &io);
1008                 CHECK_STATUS(status, NT_STATUS_OK);
1009                 handle2 = io.out.file.handle;
1010
1011                 q.query_secdesc.in.file.handle = handle2;
1012                 status = smb2_getinfo_file(tree, tctx, &q);
1013                 CHECK_STATUS(status, NT_STATUS_OK);
1014
1015                 smb2_util_close(tree, handle2);
1016                 smb2_util_unlink(tree, fname1);
1017
1018                 if (!(test_flags[i].parent_flags & SEC_ACE_FLAG_OBJECT_INHERIT)) {
1019                         if (!security_descriptor_equal(q.query_secdesc.out.sd, sd_def1) &&
1020                             !security_descriptor_equal(q.query_secdesc.out.sd, sd_def2)) {
1021                                 torture_warning(tctx, "Expected default sd:\n");
1022                                 NDR_PRINT_DEBUG(security_descriptor, sd_def1);
1023                                 torture_warning(tctx, "at %d - got:\n", i);
1024                                 NDR_PRINT_DEBUG(security_descriptor, q.query_secdesc.out.sd);
1025                         }
1026                         goto check_dir;
1027                 }
1028
1029                 if (q.query_secdesc.out.sd->dacl == NULL ||
1030                     q.query_secdesc.out.sd->dacl->num_aces != 1 ||
1031                     q.query_secdesc.out.sd->dacl->aces[0].access_mask != SEC_FILE_WRITE_DATA ||
1032                     !dom_sid_equal(&q.query_secdesc.out.sd->dacl->aces[0].trustee,
1033                                    sd_orig->owner_sid)) {
1034                         torture_warning(tctx, "Bad sd in child file at %d\n", i);
1035                         NDR_PRINT_DEBUG(security_descriptor, q.query_secdesc.out.sd);
1036                         ret = false;
1037                         goto check_dir;
1038                 }
1039
1040                 if (q.query_secdesc.out.sd->dacl->aces[0].flags !=
1041                     test_flags[i].file_flags) {
1042                         torture_warning(tctx, "incorrect file_flags 0x%x - expected 0x%x for parent 0x%x with (i=%d)\n",
1043                                q.query_secdesc.out.sd->dacl->aces[0].flags,
1044                                test_flags[i].file_flags,
1045                                test_flags[i].parent_flags,
1046                                i);
1047                         ret = false;
1048                 }
1049
1050         check_dir:
1051                 io.in.fname = fname2;
1052                 io.in.create_options = NTCREATEX_OPTIONS_DIRECTORY;
1053                 status = smb2_create(tree, tctx, &io);
1054                 CHECK_STATUS(status, NT_STATUS_OK);
1055                 handle2 = io.out.file.handle;
1056
1057                 q.query_secdesc.in.file.handle = handle2;
1058                 status = smb2_getinfo_file(tree, tctx, &q);
1059                 CHECK_STATUS(status, NT_STATUS_OK);
1060
1061                 smb2_util_close(tree, handle2);
1062                 smb2_util_rmdir(tree, fname2);
1063
1064                 if (!(test_flags[i].parent_flags & SEC_ACE_FLAG_CONTAINER_INHERIT) &&
1065                     (!(test_flags[i].parent_flags & SEC_ACE_FLAG_OBJECT_INHERIT) ||
1066                      (test_flags[i].parent_flags & SEC_ACE_FLAG_NO_PROPAGATE_INHERIT))) {
1067                         if (!security_descriptor_equal(q.query_secdesc.out.sd, sd_def1) &&
1068                             !security_descriptor_equal(q.query_secdesc.out.sd, sd_def2)) {
1069                                 torture_warning(tctx, "Expected default sd for dir at %d:\n", i);
1070                                 NDR_PRINT_DEBUG(security_descriptor, sd_def1);
1071                                 torture_warning(tctx, "got:\n");
1072                                 NDR_PRINT_DEBUG(security_descriptor, q.query_secdesc.out.sd);
1073                         }
1074                         continue;
1075                 }
1076
1077                 if ((test_flags[i].parent_flags & SEC_ACE_FLAG_CONTAINER_INHERIT) &&
1078                     (test_flags[i].parent_flags & SEC_ACE_FLAG_NO_PROPAGATE_INHERIT)) {
1079                         if (q.query_secdesc.out.sd->dacl == NULL ||
1080                             q.query_secdesc.out.sd->dacl->num_aces != 1 ||
1081                             q.query_secdesc.out.sd->dacl->aces[0].access_mask != SEC_FILE_WRITE_DATA ||
1082                             !dom_sid_equal(&q.query_secdesc.out.sd->dacl->aces[0].trustee,
1083                                            sd_orig->owner_sid) ||
1084                             q.query_secdesc.out.sd->dacl->aces[0].flags != test_flags[i].dir_flags) {
1085                                 torture_warning(tctx, "(CI & NP) Bad sd in child dir - expected 0x%x for parent 0x%x (i=%d)\n",
1086                                        test_flags[i].dir_flags,
1087                                        test_flags[i].parent_flags, i);
1088                                 NDR_PRINT_DEBUG(security_descriptor, q.query_secdesc.out.sd);
1089                                 torture_warning(tctx, "FYI, here is the parent sd:\n");
1090                                 NDR_PRINT_DEBUG(security_descriptor, sd);
1091                                 ret = false;
1092                                 continue;
1093                         }
1094                 } else if (test_flags[i].parent_flags & SEC_ACE_FLAG_CONTAINER_INHERIT) {
1095                         if (q.query_secdesc.out.sd->dacl == NULL ||
1096                             q.query_secdesc.out.sd->dacl->num_aces != 2 ||
1097                             q.query_secdesc.out.sd->dacl->aces[0].access_mask != SEC_FILE_WRITE_DATA ||
1098                             !dom_sid_equal(&q.query_secdesc.out.sd->dacl->aces[0].trustee,
1099                                            sd_orig->owner_sid) ||
1100                             q.query_secdesc.out.sd->dacl->aces[1].access_mask != SEC_FILE_WRITE_DATA ||
1101                             !dom_sid_equal(&q.query_secdesc.out.sd->dacl->aces[1].trustee,
1102                                            creator_owner) ||
1103                             q.query_secdesc.out.sd->dacl->aces[0].flags != 0 ||
1104                             q.query_secdesc.out.sd->dacl->aces[1].flags !=
1105                             (test_flags[i].dir_flags | SEC_ACE_FLAG_INHERIT_ONLY)) {
1106                                 torture_warning(tctx, "(CI) Bad sd in child dir - expected 0x%x for parent 0x%x (i=%d)\n",
1107                                        test_flags[i].dir_flags,
1108                                        test_flags[i].parent_flags, i);
1109                                 NDR_PRINT_DEBUG(security_descriptor, q.query_secdesc.out.sd);
1110                                 torture_warning(tctx, "FYI, here is the parent sd:\n");
1111                                 NDR_PRINT_DEBUG(security_descriptor, sd);
1112                                 ret = false;
1113                                 continue;
1114                         }
1115                 } else {
1116                         if (q.query_secdesc.out.sd->dacl == NULL ||
1117                             q.query_secdesc.out.sd->dacl->num_aces != 1 ||
1118                             q.query_secdesc.out.sd->dacl->aces[0].access_mask != SEC_FILE_WRITE_DATA ||
1119                             !dom_sid_equal(&q.query_secdesc.out.sd->dacl->aces[0].trustee,
1120                                            creator_owner) ||
1121                             q.query_secdesc.out.sd->dacl->aces[0].flags != test_flags[i].dir_flags) {
1122                                 torture_warning(tctx, "(0) Bad sd in child dir - expected 0x%x for parent 0x%x (i=%d)\n",
1123                                        test_flags[i].dir_flags,
1124                                        test_flags[i].parent_flags, i);
1125                                 NDR_PRINT_DEBUG(security_descriptor, q.query_secdesc.out.sd);
1126                                 torture_warning(tctx, "FYI, here is the parent sd:\n");
1127                                 NDR_PRINT_DEBUG(security_descriptor, sd);
1128                                 ret = false;
1129                                 continue;
1130                         }
1131                 }
1132         }
1133
1134         torture_comment(tctx, "Testing access checks on inherited create with %s\n", fname1);
1135         sd = security_descriptor_dacl_create(tctx,
1136                                         0, NULL, NULL,
1137                                         owner_sid,
1138                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
1139                                         SEC_FILE_WRITE_DATA | SEC_STD_WRITE_DAC,
1140                                         SEC_ACE_FLAG_OBJECT_INHERIT,
1141                                         SID_WORLD,
1142                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
1143                                         SEC_FILE_ALL | SEC_STD_ALL,
1144                                         0,
1145                                         NULL);
1146         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
1147         set.set_secdesc.in.file.handle = handle;
1148         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1149         set.set_secdesc.in.sd = sd;
1150         status = smb2_setinfo_file(tree, &set);
1151         CHECK_STATUS(status, NT_STATUS_OK);
1152
1153         /* Check DACL we just set. */
1154         torture_comment(tctx, "checking new sd\n");
1155         q.query_secdesc.in.file.handle = handle;
1156         q.query_secdesc.in.secinfo_flags = SECINFO_DACL;
1157         status = smb2_getinfo_file(tree, tctx, &q);
1158         CHECK_STATUS(status, NT_STATUS_OK);
1159         CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd);
1160
1161         io.in.fname = fname1;
1162         io.in.create_options = 0;
1163         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1164         io.in.create_disposition = NTCREATEX_DISP_CREATE;
1165         status = smb2_create(tree, tctx, &io);
1166         CHECK_STATUS(status, NT_STATUS_OK);
1167         handle2 = io.out.file.handle;
1168         CHECK_ACCESS_FLAGS(handle2, SEC_RIGHTS_FILE_ALL);
1169
1170         q.query_secdesc.in.file.handle = handle2;
1171         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
1172         status = smb2_getinfo_file(tree, tctx, &q);
1173         CHECK_STATUS(status, NT_STATUS_OK);
1174         smb2_util_close(tree, handle2);
1175
1176         sd2 = security_descriptor_dacl_create(tctx,
1177                                          0, owner_sid, NULL,
1178                                          owner_sid,
1179                                          SEC_ACE_TYPE_ACCESS_ALLOWED,
1180                                          SEC_FILE_WRITE_DATA | SEC_STD_WRITE_DAC,
1181                                          0,
1182                                          NULL);
1183         CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
1184
1185         io.in.create_disposition = NTCREATEX_DISP_OPEN;
1186         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1187         status = smb2_create(tree, tctx, &io);
1188         if (NT_STATUS_IS_OK(status)) {
1189                 torture_warning(tctx, "failed: w2k3 ACL bug (allowed open when ACL should deny)\n");
1190                 ret = false;
1191                 handle2 = io.out.file.handle;
1192                 CHECK_ACCESS_FLAGS(handle2, SEC_RIGHTS_FILE_ALL);
1193                 smb2_util_close(tree, handle2);
1194         } else {
1195                 if (torture_setting_bool(tctx, "hide_on_access_denied",
1196                                          false)) {
1197                         CHECK_STATUS(status, NT_STATUS_OBJECT_NAME_NOT_FOUND);
1198                 } else {
1199                         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
1200                 }
1201         }
1202
1203         torture_comment(tctx, "trying without execute\n");
1204         io.in.create_disposition = NTCREATEX_DISP_OPEN;
1205         io.in.desired_access = SEC_RIGHTS_FILE_ALL & ~SEC_FILE_EXECUTE;
1206         status = smb2_create(tree, tctx, &io);
1207         if (torture_setting_bool(tctx, "hide_on_access_denied", false)) {
1208                 CHECK_STATUS(status, NT_STATUS_OBJECT_NAME_NOT_FOUND);
1209         } else {
1210                 CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
1211         }
1212
1213         torture_comment(tctx, "and with full permissions again\n");
1214         io.in.create_disposition = NTCREATEX_DISP_OPEN;
1215         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1216         status = smb2_create(tree, tctx, &io);
1217         if (torture_setting_bool(tctx, "hide_on_access_denied", false)) {
1218                 CHECK_STATUS(status, NT_STATUS_OBJECT_NAME_NOT_FOUND);
1219         } else {
1220                 CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
1221         }
1222
1223         io.in.desired_access = SEC_FILE_WRITE_DATA;
1224         status = smb2_create(tree, tctx, &io);
1225         CHECK_STATUS(status, NT_STATUS_OK);
1226         handle2 = io.out.file.handle;
1227         CHECK_ACCESS_FLAGS(handle2, SEC_FILE_WRITE_DATA);
1228         smb2_util_close(tree, handle2);
1229
1230         torture_comment(tctx, "put back original sd\n");
1231         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
1232         set.set_secdesc.in.file.handle = handle;
1233         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1234         set.set_secdesc.in.sd = sd_orig;
1235         status = smb2_setinfo_file(tree, &set);
1236         CHECK_STATUS(status, NT_STATUS_OK);
1237
1238         smb2_util_close(tree, handle);
1239
1240         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1241         status = smb2_create(tree, tctx, &io);
1242         if (torture_setting_bool(tctx, "hide_on_access_denied", false)) {
1243                 CHECK_STATUS(status, NT_STATUS_OBJECT_NAME_NOT_FOUND);
1244         } else {
1245                 CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
1246         }
1247
1248         io.in.desired_access = SEC_FILE_WRITE_DATA;
1249         status = smb2_create(tree, tctx, &io);
1250         CHECK_STATUS(status, NT_STATUS_OK);
1251         handle2 = io.out.file.handle;
1252         CHECK_ACCESS_FLAGS(handle2, SEC_FILE_WRITE_DATA);
1253         smb2_util_close(tree, handle2);
1254
1255         smb2_util_unlink(tree, fname1);
1256         smb2_util_rmdir(tree, dname);
1257
1258 done:
1259         if (sd_orig != NULL) {
1260                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
1261                 set.set_secdesc.in.file.handle = handle;
1262                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1263                 set.set_secdesc.in.sd = sd_orig;
1264                 status = smb2_setinfo_file(tree, &set);
1265         }
1266
1267         smb2_util_close(tree, handle);
1268         smb2_deltree(tree, BASEDIR);
1269         smb2_tdis(tree);
1270         smb2_logoff(tree->session);
1271         return ret;
1272 }
1273
1274 static bool test_inheritance_flags(struct torture_context *tctx,
1275     struct smb2_tree *tree)
1276 {
1277         NTSTATUS status;
1278         struct smb2_create io;
1279         const char *dname = BASEDIR "\\inheritance";
1280         const char *fname1 = BASEDIR "\\inheritance\\testfile";
1281         bool ret = true;
1282         struct smb2_handle handle = {{0}};
1283         struct smb2_handle handle2 = {{0}};
1284         int i, j;
1285         union smb_fileinfo q;
1286         union smb_setfileinfo set;
1287         struct security_descriptor *sd, *sd2, *sd_orig=NULL;
1288         const char *owner_sid;
1289         struct {
1290                 uint32_t parent_set_sd_type; /* 3 options */
1291                 uint32_t parent_set_ace_inherit; /* 1 option */
1292                 uint32_t parent_get_sd_type;
1293                 uint32_t parent_get_ace_inherit;
1294                 uint32_t child_get_sd_type;
1295                 uint32_t child_get_ace_inherit;
1296         } tflags[16] = {{0}}; /* 2^4 */
1297
1298         for (i = 0; i < 15; i++) {
1299                 torture_comment(tctx, "i=%d:", i);
1300
1301                 if (i & 1) {
1302                         tflags[i].parent_set_sd_type |=
1303                             SEC_DESC_DACL_AUTO_INHERITED;
1304                         torture_comment(tctx, "AUTO_INHERITED, ");
1305                 }
1306                 if (i & 2) {
1307                         tflags[i].parent_set_sd_type |=
1308                             SEC_DESC_DACL_AUTO_INHERIT_REQ;
1309                         torture_comment(tctx, "AUTO_INHERIT_REQ, ");
1310                 }
1311                 if (i & 4) {
1312                         tflags[i].parent_set_sd_type |=
1313                             SEC_DESC_DACL_PROTECTED;
1314                         torture_comment(tctx, "PROTECTED, ");
1315                         tflags[i].parent_get_sd_type |=
1316                             SEC_DESC_DACL_PROTECTED;
1317                 }
1318                 if (i & 8) {
1319                         tflags[i].parent_set_ace_inherit |=
1320                             SEC_ACE_FLAG_INHERITED_ACE;
1321                         torture_comment(tctx, "INHERITED, ");
1322                         tflags[i].parent_get_ace_inherit |=
1323                             SEC_ACE_FLAG_INHERITED_ACE;
1324                 }
1325
1326                 if ((tflags[i].parent_set_sd_type &
1327                     (SEC_DESC_DACL_AUTO_INHERITED | SEC_DESC_DACL_AUTO_INHERIT_REQ)) ==
1328                     (SEC_DESC_DACL_AUTO_INHERITED | SEC_DESC_DACL_AUTO_INHERIT_REQ)) {
1329                         tflags[i].parent_get_sd_type |=
1330                             SEC_DESC_DACL_AUTO_INHERITED;
1331                         tflags[i].child_get_sd_type |=
1332                             SEC_DESC_DACL_AUTO_INHERITED;
1333                         tflags[i].child_get_ace_inherit |=
1334                             SEC_ACE_FLAG_INHERITED_ACE;
1335                         torture_comment(tctx, "  ... parent is AUTO INHERITED");
1336                 }
1337
1338                 if (tflags[i].parent_set_ace_inherit &
1339                     SEC_ACE_FLAG_INHERITED_ACE) {
1340                         tflags[i].parent_get_ace_inherit =
1341                             SEC_ACE_FLAG_INHERITED_ACE;
1342                         torture_comment(tctx, "  ... parent ACE is INHERITED");
1343                 }
1344
1345                 torture_comment(tctx, "\n");
1346         }
1347
1348         if (!smb2_util_setup_dir(tctx, tree, BASEDIR))
1349                 return false;
1350
1351         torture_comment(tctx, "TESTING ACL INHERITANCE FLAGS\n");
1352
1353         ZERO_STRUCT(io);
1354         io.level = RAW_OPEN_SMB2;
1355         io.in.create_flags = 0;
1356         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1357         io.in.create_options = NTCREATEX_OPTIONS_DIRECTORY;
1358         io.in.file_attributes = FILE_ATTRIBUTE_DIRECTORY;
1359         io.in.share_access = NTCREATEX_SHARE_ACCESS_MASK;
1360         io.in.alloc_size = 0;
1361         io.in.create_disposition = NTCREATEX_DISP_CREATE;
1362         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
1363         io.in.security_flags = 0;
1364         io.in.fname = dname;
1365
1366         torture_comment(tctx, "creating initial directory %s\n", dname);
1367         status = smb2_create(tree, tctx, &io);
1368         CHECK_STATUS(status, NT_STATUS_OK);
1369         handle = io.out.file.handle;
1370
1371         torture_comment(tctx, "getting original sd\n");
1372         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
1373         q.query_secdesc.in.file.handle = handle;
1374         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
1375         status = smb2_getinfo_file(tree, tctx, &q);
1376         CHECK_STATUS(status, NT_STATUS_OK);
1377         sd_orig = q.query_secdesc.out.sd;
1378
1379         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
1380         torture_comment(tctx, "owner_sid is %s\n", owner_sid);
1381
1382         for (i=0; i < ARRAY_SIZE(tflags); i++) {
1383                 torture_comment(tctx, "setting a new sd on directory, pass #%d\n", i);
1384
1385                 sd = security_descriptor_dacl_create(tctx,
1386                                                 tflags[i].parent_set_sd_type,
1387                                                 NULL, NULL,
1388                                                 owner_sid,
1389                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
1390                                                 SEC_FILE_WRITE_DATA | SEC_STD_WRITE_DAC,
1391                                                 SEC_ACE_FLAG_OBJECT_INHERIT |
1392                                                 SEC_ACE_FLAG_CONTAINER_INHERIT |
1393                                                 tflags[i].parent_set_ace_inherit,
1394                                                 SID_WORLD,
1395                                                 SEC_ACE_TYPE_ACCESS_ALLOWED,
1396                                                 SEC_FILE_ALL | SEC_STD_ALL,
1397                                                 0,
1398                                                 NULL);
1399                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
1400                 set.set_secdesc.in.file.handle = handle;
1401                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1402                 set.set_secdesc.in.sd = sd;
1403                 status = smb2_setinfo_file(tree, &set);
1404                 CHECK_STATUS(status, NT_STATUS_OK);
1405
1406                 /*
1407                  * Check DACL we just set, except change the bits to what they
1408                  * should be.
1409                  */
1410                 torture_comment(tctx, "  checking new sd\n");
1411
1412                 /* REQ bit should always be false. */
1413                 sd->type &= ~SEC_DESC_DACL_AUTO_INHERIT_REQ;
1414
1415                 if ((tflags[i].parent_get_sd_type & SEC_DESC_DACL_AUTO_INHERITED) == 0)
1416                         sd->type &= ~SEC_DESC_DACL_AUTO_INHERITED;
1417
1418                 q.query_secdesc.in.file.handle = handle;
1419                 q.query_secdesc.in.secinfo_flags = SECINFO_DACL;
1420                 status = smb2_getinfo_file(tree, tctx, &q);
1421                 CHECK_STATUS(status, NT_STATUS_OK);
1422                 CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd);
1423
1424                 /* Create file. */
1425                 torture_comment(tctx, "  creating file %s\n", fname1);
1426                 io.in.fname = fname1;
1427                 io.in.create_options = 0;
1428                 io.in.file_attributes = FILE_ATTRIBUTE_NORMAL;
1429                 io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1430                 io.in.create_disposition = NTCREATEX_DISP_CREATE;
1431                 status = smb2_create(tree, tctx, &io);
1432                 CHECK_STATUS(status, NT_STATUS_OK);
1433                 handle2 = io.out.file.handle;
1434                 CHECK_ACCESS_FLAGS(handle2, SEC_RIGHTS_FILE_ALL);
1435
1436                 q.query_secdesc.in.file.handle = handle2;
1437                 q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
1438                 status = smb2_getinfo_file(tree, tctx, &q);
1439                 CHECK_STATUS(status, NT_STATUS_OK);
1440
1441                 torture_comment(tctx, "  checking sd on file %s\n", fname1);
1442                 sd2 = security_descriptor_dacl_create(tctx,
1443                                                  tflags[i].child_get_sd_type,
1444                                                  owner_sid, NULL,
1445                                                  owner_sid,
1446                                                  SEC_ACE_TYPE_ACCESS_ALLOWED,
1447                                                  SEC_FILE_WRITE_DATA | SEC_STD_WRITE_DAC,
1448                                                  tflags[i].child_get_ace_inherit,
1449                                                  NULL);
1450                 CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
1451
1452                 /*
1453                  * Set new sd on file ... prove that the bits have nothing to
1454                  * do with the parents bits when manually setting an ACL. The
1455                  * _AUTO_INHERITED bit comes directly from the ACL set.
1456                  */
1457                 for (j = 0; j < ARRAY_SIZE(tflags); j++) {
1458                         torture_comment(tctx, "  setting new file sd, pass #%d\n", j);
1459
1460                         /* Change sd type. */
1461                         sd2->type &= ~(SEC_DESC_DACL_AUTO_INHERITED |
1462                             SEC_DESC_DACL_AUTO_INHERIT_REQ |
1463                             SEC_DESC_DACL_PROTECTED);
1464                         sd2->type |= tflags[j].parent_set_sd_type;
1465
1466                         sd2->dacl->aces[0].flags &=
1467                             ~SEC_ACE_FLAG_INHERITED_ACE;
1468                         sd2->dacl->aces[0].flags |=
1469                             tflags[j].parent_set_ace_inherit;
1470
1471                         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
1472                         set.set_secdesc.in.file.handle = handle2;
1473                         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1474                         set.set_secdesc.in.sd = sd2;
1475                         status = smb2_setinfo_file(tree, &set);
1476                         CHECK_STATUS(status, NT_STATUS_OK);
1477
1478                         /* Check DACL we just set. */
1479                         sd2->type &= ~SEC_DESC_DACL_AUTO_INHERIT_REQ;
1480                         if ((tflags[j].parent_get_sd_type & SEC_DESC_DACL_AUTO_INHERITED) == 0)
1481                                 sd2->type &= ~SEC_DESC_DACL_AUTO_INHERITED;
1482
1483                         q.query_secdesc.in.file.handle = handle2;
1484                         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
1485                         status = smb2_getinfo_file(tree, tctx, &q);
1486                         CHECK_STATUS(status, NT_STATUS_OK);
1487
1488                         CHECK_SECURITY_DESCRIPTOR(q.query_secdesc.out.sd, sd2);
1489                 }
1490
1491                 smb2_util_close(tree, handle2);
1492                 smb2_util_unlink(tree, fname1);
1493         }
1494
1495 done:
1496         smb2_util_close(tree, handle);
1497         smb2_deltree(tree, BASEDIR);
1498         smb2_tdis(tree);
1499         smb2_logoff(tree->session);
1500         return ret;
1501 }
1502
1503 /*
1504   test dynamic acl inheritance
1505   Note: This test was copied from raw/acls.c.
1506 */
1507 static bool test_inheritance_dynamic(struct torture_context *tctx,
1508     struct smb2_tree *tree)
1509 {
1510         NTSTATUS status;
1511         struct smb2_create io;
1512         const char *dname = BASEDIR "\\inheritance";
1513         const char *fname1 = BASEDIR "\\inheritance\\testfile";
1514         bool ret = true;
1515         struct smb2_handle handle = {{0}};
1516         struct smb2_handle handle2 = {{0}};
1517         union smb_fileinfo q;
1518         union smb_setfileinfo set;
1519         struct security_descriptor *sd, *sd_orig=NULL;
1520         const char *owner_sid;
1521
1522         torture_comment(tctx, "TESTING DYNAMIC ACL INHERITANCE\n");
1523
1524         if (!smb2_util_setup_dir(tctx, tree, BASEDIR))
1525                 return false;
1526
1527         ZERO_STRUCT(io);
1528         io.level = RAW_OPEN_SMB2;
1529         io.in.create_flags = 0;
1530         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1531         io.in.create_options = NTCREATEX_OPTIONS_DIRECTORY;
1532         io.in.file_attributes = FILE_ATTRIBUTE_DIRECTORY;
1533         io.in.share_access = 0;
1534         io.in.alloc_size = 0;
1535         io.in.create_disposition = NTCREATEX_DISP_CREATE;
1536         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
1537         io.in.security_flags = 0;
1538         io.in.fname = dname;
1539
1540         status = smb2_create(tree, tctx, &io);
1541         CHECK_STATUS(status, NT_STATUS_OK);
1542         handle = io.out.file.handle;
1543
1544         torture_comment(tctx, "get the original sd\n");
1545         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
1546         q.query_secdesc.in.file.handle = handle;
1547         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
1548         status = smb2_getinfo_file(tree, tctx, &q);
1549         CHECK_STATUS(status, NT_STATUS_OK);
1550         sd_orig = q.query_secdesc.out.sd;
1551
1552         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
1553
1554         torture_comment(tctx, "owner_sid is %s\n", owner_sid);
1555
1556         sd = security_descriptor_dacl_create(tctx,
1557                                         0, NULL, NULL,
1558                                         owner_sid,
1559                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
1560                                         SEC_FILE_WRITE_DATA | SEC_STD_DELETE | SEC_FILE_READ_ATTRIBUTE,
1561                                         SEC_ACE_FLAG_OBJECT_INHERIT,
1562                                         NULL);
1563         sd->type |= SEC_DESC_DACL_AUTO_INHERITED | SEC_DESC_DACL_AUTO_INHERIT_REQ;
1564
1565         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
1566         set.set_secdesc.in.file.handle = handle;
1567         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1568         set.set_secdesc.in.sd = sd;
1569         status = smb2_setinfo_file(tree, &set);
1570         CHECK_STATUS(status, NT_STATUS_OK);
1571
1572         torture_comment(tctx, "create a file with an inherited acl\n");
1573         io.in.fname = fname1;
1574         io.in.create_options = 0;
1575         io.in.desired_access = SEC_FILE_READ_ATTRIBUTE;
1576         io.in.create_disposition = NTCREATEX_DISP_CREATE;
1577         status = smb2_create(tree, tctx, &io);
1578         CHECK_STATUS(status, NT_STATUS_OK);
1579         handle2 = io.out.file.handle;
1580         smb2_util_close(tree, handle2);
1581
1582         torture_comment(tctx, "try and access file with base rights - should be OK\n");
1583         io.in.desired_access = SEC_FILE_WRITE_DATA;
1584         io.in.create_disposition = NTCREATEX_DISP_OPEN;
1585         status = smb2_create(tree, tctx, &io);
1586         CHECK_STATUS(status, NT_STATUS_OK);
1587         handle2 = io.out.file.handle;
1588         smb2_util_close(tree, handle2);
1589
1590         torture_comment(tctx, "try and access file with extra rights - should be denied\n");
1591         io.in.desired_access = SEC_FILE_WRITE_DATA | SEC_FILE_EXECUTE;
1592         status = smb2_create(tree, tctx, &io);
1593         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
1594
1595         torture_comment(tctx, "update parent sd\n");
1596         sd = security_descriptor_dacl_create(tctx,
1597                                         0, NULL, NULL,
1598                                         owner_sid,
1599                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
1600                                         SEC_FILE_WRITE_DATA | SEC_STD_DELETE | SEC_FILE_READ_ATTRIBUTE | SEC_FILE_EXECUTE,
1601                                         SEC_ACE_FLAG_OBJECT_INHERIT,
1602                                         NULL);
1603         sd->type |= SEC_DESC_DACL_AUTO_INHERITED | SEC_DESC_DACL_AUTO_INHERIT_REQ;
1604
1605         set.set_secdesc.in.sd = sd;
1606         status = smb2_setinfo_file(tree, &set);
1607         CHECK_STATUS(status, NT_STATUS_OK);
1608
1609         torture_comment(tctx, "try and access file with base rights - should be OK\n");
1610         io.in.desired_access = SEC_FILE_WRITE_DATA;
1611         status = smb2_create(tree, tctx, &io);
1612         CHECK_STATUS(status, NT_STATUS_OK);
1613         handle2 = io.out.file.handle;
1614         smb2_util_close(tree, handle2);
1615
1616
1617         torture_comment(tctx, "try and access now - should be OK if dynamic inheritance works\n");
1618         io.in.desired_access = SEC_FILE_WRITE_DATA | SEC_FILE_EXECUTE;
1619         status = smb2_create(tree, tctx, &io);
1620         if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
1621                 torture_comment(tctx, "Server does not have dynamic inheritance\n");
1622         }
1623         if (NT_STATUS_EQUAL(status, NT_STATUS_OK)) {
1624                 torture_comment(tctx, "Server does have dynamic inheritance\n");
1625         }
1626         CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED);
1627
1628         smb2_util_unlink(tree, fname1);
1629
1630 done:
1631         torture_comment(tctx, "put back original sd\n");
1632         set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
1633         set.set_secdesc.in.file.handle = handle;
1634         set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
1635         set.set_secdesc.in.sd = sd_orig;
1636         status = smb2_setinfo_file(tree, &set);
1637
1638         smb2_util_close(tree, handle);
1639         smb2_util_rmdir(tree, dname);
1640         smb2_deltree(tree, BASEDIR);
1641         smb2_tdis(tree);
1642         smb2_logoff(tree->session);
1643
1644         return ret;
1645 }
1646
1647 #define CHECK_STATUS_FOR_BIT_ACTION(status, bits, action) do { \
1648         if (!(bits & desired_64)) {\
1649                 CHECK_STATUS(status, NT_STATUS_ACCESS_DENIED); \
1650                 action; \
1651         } else { \
1652                 CHECK_STATUS(status, NT_STATUS_OK); \
1653         } \
1654 } while (0)
1655
1656 #define CHECK_STATUS_FOR_BIT(status, bits, access) do { \
1657         if (NT_STATUS_IS_OK(status)) { \
1658                 if (!(granted & access)) {\
1659                         ret = false; \
1660                         torture_result(tctx, TORTURE_FAIL, "(%s) %s but flags 0x%08X are not granted! granted[0x%08X] desired[0x%08X]\n", \
1661                                __location__, nt_errstr(status), access, granted, desired); \
1662                         goto done; \
1663                 } \
1664         } else { \
1665                 if (granted & access) {\
1666                         ret = false; \
1667                         torture_result(tctx, TORTURE_FAIL, "(%s) %s but flags 0x%08X are granted! granted[0x%08X] desired[0x%08X]\n", \
1668                                __location__, nt_errstr(status), access, granted, desired); \
1669                         goto done; \
1670                 } \
1671         } \
1672         CHECK_STATUS_FOR_BIT_ACTION(status, bits, do {} while (0)); \
1673 } while (0)
1674
1675 #if 0
1676 /* test what access mask is needed for getting and setting security_descriptors */
1677 /* Note: This test was copied from raw/acls.c. */
1678 static bool test_sd_get_set(struct torture_context *tctx, struct smb2_tree *tree)
1679 {
1680         NTSTATUS status;
1681         bool ret = true;
1682         struct smb2_create io;
1683         union smb_fileinfo fi;
1684         union smb_setfileinfo si;
1685         struct security_descriptor *sd;
1686         struct security_descriptor *sd_owner = NULL;
1687         struct security_descriptor *sd_group = NULL;
1688         struct security_descriptor *sd_dacl = NULL;
1689         struct security_descriptor *sd_sacl = NULL;
1690         struct smb2_handle handle;
1691         const char *fname = BASEDIR "\\sd_get_set.txt";
1692         uint64_t desired_64;
1693         uint32_t desired = 0, granted;
1694         int i = 0;
1695 #define NO_BITS_HACK (((uint64_t)1)<<32)
1696         uint64_t open_bits =
1697                 SEC_MASK_GENERIC |
1698                 SEC_FLAG_SYSTEM_SECURITY |
1699                 SEC_FLAG_MAXIMUM_ALLOWED |
1700                 SEC_STD_ALL |
1701                 SEC_FILE_ALL |
1702                 NO_BITS_HACK;
1703         uint64_t get_owner_bits = SEC_MASK_GENERIC | SEC_FLAG_MAXIMUM_ALLOWED | SEC_STD_READ_CONTROL;
1704         uint64_t set_owner_bits = SEC_GENERIC_ALL  | SEC_FLAG_MAXIMUM_ALLOWED | SEC_STD_WRITE_OWNER;
1705         uint64_t get_group_bits = SEC_MASK_GENERIC | SEC_FLAG_MAXIMUM_ALLOWED | SEC_STD_READ_CONTROL;
1706         uint64_t set_group_bits = SEC_GENERIC_ALL  | SEC_FLAG_MAXIMUM_ALLOWED | SEC_STD_WRITE_OWNER;
1707         uint64_t get_dacl_bits  = SEC_MASK_GENERIC | SEC_FLAG_MAXIMUM_ALLOWED | SEC_STD_READ_CONTROL;
1708         uint64_t set_dacl_bits  = SEC_GENERIC_ALL  | SEC_FLAG_MAXIMUM_ALLOWED | SEC_STD_WRITE_DAC;
1709         uint64_t get_sacl_bits  = SEC_FLAG_SYSTEM_SECURITY;
1710         uint64_t set_sacl_bits  = SEC_FLAG_SYSTEM_SECURITY;
1711
1712         if (!smb2_util_setup_dir(tctx, tree, BASEDIR))
1713                 return false;
1714
1715         torture_comment(tctx, "TESTING ACCESS MASKS FOR SD GET/SET\n");
1716
1717         /* first create a file with full access for everyone */
1718         sd = security_descriptor_dacl_create(tctx,
1719                                         0, SID_NT_ANONYMOUS, SID_BUILTIN_USERS,
1720                                         SID_WORLD,
1721                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
1722                                         SEC_GENERIC_ALL,
1723                                         0,
1724                                         NULL);
1725         sd->type |= SEC_DESC_SACL_PRESENT;
1726         sd->sacl = NULL;
1727         ZERO_STRUCT(io);
1728         io.level = RAW_OPEN_SMB2;
1729         io.in.create_flags = 0;
1730         io.in.desired_access = SEC_GENERIC_ALL;
1731         io.in.create_options = 0;
1732         io.in.file_attributes = FILE_ATTRIBUTE_NORMAL;
1733         io.in.share_access = NTCREATEX_SHARE_ACCESS_READ | NTCREATEX_SHARE_ACCESS_WRITE;
1734         io.in.alloc_size = 0;
1735         io.in.create_disposition = NTCREATEX_DISP_OVERWRITE_IF;
1736         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
1737         io.in.security_flags = 0;
1738         io.in.fname = fname;
1739         io.in.sec_desc = sd;
1740         status = smb2_create(tree, tctx, &io);
1741         CHECK_STATUS(status, NT_STATUS_OK);
1742         handle = io.out.file.handle;
1743
1744         status = smb2_util_close(tree, handle);
1745         CHECK_STATUS(status, NT_STATUS_OK);
1746
1747         /*
1748          * now try each access_mask bit and no bit at all in a loop
1749          * and see what's allowed
1750          * NOTE: if i == 32 it means access_mask = 0 (see NO_BITS_HACK above)
1751          */
1752         for (i=0; i <= 32; i++) {
1753                 desired_64 = ((uint64_t)1) << i;
1754                 desired = (uint32_t)desired_64;
1755
1756                 /* first open the file with the desired access */
1757                 io.level = RAW_OPEN_SMB2;
1758                 io.in.desired_access = desired;
1759                 io.in.create_disposition = NTCREATEX_DISP_OPEN;
1760                 status = smb2_create(tree, tctx, &io);
1761                 CHECK_STATUS_FOR_BIT_ACTION(status, open_bits, goto next);
1762                 handle = io.out.file.handle;
1763
1764                 /* then check what access was granted */
1765                 fi.access_information.level             = RAW_FILEINFO_ACCESS_INFORMATION;
1766                 fi.access_information.in.file.handle    = handle;
1767                 status = smb2_getinfo_file(tree, tctx, &fi);
1768                 CHECK_STATUS(status, NT_STATUS_OK);
1769                 granted = fi.access_information.out.access_flags;
1770
1771                 /* test the owner */
1772                 ZERO_STRUCT(fi);
1773                 fi.query_secdesc.level                  = RAW_FILEINFO_SEC_DESC;
1774                 fi.query_secdesc.in.file.handle         = handle;
1775                 fi.query_secdesc.in.secinfo_flags       = SECINFO_OWNER;
1776                 status = smb2_getinfo_file(tree, tctx, &fi);
1777                 CHECK_STATUS_FOR_BIT(status, get_owner_bits, SEC_STD_READ_CONTROL);
1778                 if (fi.query_secdesc.out.sd) {
1779                         sd_owner = fi.query_secdesc.out.sd;
1780                 } else if (!sd_owner) {
1781                         sd_owner = sd;
1782                 }
1783                 si.set_secdesc.level                    = RAW_SFILEINFO_SEC_DESC;
1784                 si.set_secdesc.in.file.handle           = handle;
1785                 si.set_secdesc.in.secinfo_flags         = SECINFO_OWNER;
1786                 si.set_secdesc.in.sd                    = sd_owner;
1787                 status = smb2_setinfo_file(tree, &si);
1788                 CHECK_STATUS_FOR_BIT(status, set_owner_bits, SEC_STD_WRITE_OWNER);
1789
1790                 /* test the group */
1791                 ZERO_STRUCT(fi);
1792                 fi.query_secdesc.level                  = RAW_FILEINFO_SEC_DESC;
1793                 fi.query_secdesc.in.file.handle         = handle;
1794                 fi.query_secdesc.in.secinfo_flags       = SECINFO_GROUP;
1795                 status = smb2_getinfo_file(tree, tctx, &fi);
1796                 CHECK_STATUS_FOR_BIT(status, get_group_bits, SEC_STD_READ_CONTROL);
1797                 if (fi.query_secdesc.out.sd) {
1798                         sd_group = fi.query_secdesc.out.sd;
1799                 } else if (!sd_group) {
1800                         sd_group = sd;
1801                 }
1802                 si.set_secdesc.level                    = RAW_SFILEINFO_SEC_DESC;
1803                 si.set_secdesc.in.file.handle           = handle;
1804                 si.set_secdesc.in.secinfo_flags         = SECINFO_GROUP;
1805                 si.set_secdesc.in.sd                    = sd_group;
1806                 status = smb2_setinfo_file(tree, &si);
1807                 CHECK_STATUS_FOR_BIT(status, set_group_bits, SEC_STD_WRITE_OWNER);
1808
1809                 /* test the DACL */
1810                 ZERO_STRUCT(fi);
1811                 fi.query_secdesc.level                  = RAW_FILEINFO_SEC_DESC;
1812                 fi.query_secdesc.in.file.handle         = handle;
1813                 fi.query_secdesc.in.secinfo_flags       = SECINFO_DACL;
1814                 status = smb2_getinfo_file(tree, tctx, &fi);
1815                 CHECK_STATUS_FOR_BIT(status, get_dacl_bits, SEC_STD_READ_CONTROL);
1816                 if (fi.query_secdesc.out.sd) {
1817                         sd_dacl = fi.query_secdesc.out.sd;
1818                 } else if (!sd_dacl) {
1819                         sd_dacl = sd;
1820                 }
1821                 si.set_secdesc.level                    = RAW_SFILEINFO_SEC_DESC;
1822                 si.set_secdesc.in.file.handle           = handle;
1823                 si.set_secdesc.in.secinfo_flags         = SECINFO_DACL;
1824                 si.set_secdesc.in.sd                    = sd_dacl;
1825                 status = smb2_setinfo_file(tree, &si);
1826                 CHECK_STATUS_FOR_BIT(status, set_dacl_bits, SEC_STD_WRITE_DAC);
1827
1828                 /* test the SACL */
1829                 ZERO_STRUCT(fi);
1830                 fi.query_secdesc.level                  = RAW_FILEINFO_SEC_DESC;
1831                 fi.query_secdesc.in.file.handle         = handle;
1832                 fi.query_secdesc.in.secinfo_flags       = SECINFO_SACL;
1833                 status = smb2_getinfo_file(tree, tctx, &fi);
1834                 CHECK_STATUS_FOR_BIT(status, get_sacl_bits, SEC_FLAG_SYSTEM_SECURITY);
1835                 if (fi.query_secdesc.out.sd) {
1836                         sd_sacl = fi.query_secdesc.out.sd;
1837                 } else if (!sd_sacl) {
1838                         sd_sacl = sd;
1839                 }
1840                 si.set_secdesc.level                    = RAW_SFILEINFO_SEC_DESC;
1841                 si.set_secdesc.in.file.handle           = handle;
1842                 si.set_secdesc.in.secinfo_flags         = SECINFO_SACL;
1843                 si.set_secdesc.in.sd                    = sd_sacl;
1844                 status = smb2_setinfo_file(tree, &si);
1845                 CHECK_STATUS_FOR_BIT(status, set_sacl_bits, SEC_FLAG_SYSTEM_SECURITY);
1846
1847                 /* close the handle */
1848                 status = smb2_util_close(tree, handle);
1849                 CHECK_STATUS(status, NT_STATUS_OK);
1850 next:
1851                 continue;
1852         }
1853
1854 done:
1855         smb2_util_close(tree, handle);
1856         smb2_util_unlink(tree, fname);
1857         smb2_deltree(tree, BASEDIR);
1858         smb2_tdis(tree);
1859         smb2_logoff(tree->session);
1860
1861         return ret;
1862 }
1863 #endif
1864
1865 /**
1866  * SMB2 connect with explicit share
1867  **/
1868 static bool torture_smb2_con_share(struct torture_context *tctx,
1869                            const char *share,
1870                            struct smb2_tree **tree)
1871 {
1872         struct smbcli_options options;
1873         NTSTATUS status;
1874         const char *host = torture_setting_string(tctx, "host", NULL);
1875         struct cli_credentials *credentials = popt_get_cmdline_credentials();
1876
1877         lpcfg_smbcli_options(tctx->lp_ctx, &options);
1878
1879         status = smb2_connect_ext(tctx,
1880                                   host,
1881                                   lpcfg_smb_ports(tctx->lp_ctx),
1882                                   share,
1883                                   lpcfg_resolve_context(tctx->lp_ctx),
1884                                   credentials,
1885                                   0,
1886                                   tree,
1887                                   tctx->ev,
1888                                   &options,
1889                                   lpcfg_socket_options(tctx->lp_ctx),
1890                                   lpcfg_gensec_settings(tctx, tctx->lp_ctx)
1891                                   );
1892         if (!NT_STATUS_IS_OK(status)) {
1893                 torture_comment(tctx, "Failed to connect to SMB2 share \\\\%s\\%s - %s\n",
1894                         host, share, nt_errstr(status));
1895                 return false;
1896         }
1897         return true;
1898 }
1899
1900 static bool test_access_based(struct torture_context *tctx,
1901                                 struct smb2_tree *tree)
1902 {
1903         struct smb2_tree *tree1 = NULL;
1904         NTSTATUS status;
1905         struct smb2_create io;
1906         const char *fname = BASEDIR "\\testfile";
1907         bool ret = true;
1908         struct smb2_handle fhandle, dhandle;
1909         union smb_fileinfo q;
1910         union smb_setfileinfo set;
1911         struct security_descriptor *sd, *sd_orig=NULL;
1912         const char *owner_sid;
1913         uint32_t flags = 0;
1914         /*
1915          * Can't test without SEC_STD_READ_CONTROL as we
1916          * own the file and implicitly have SEC_STD_READ_CONTROL.
1917         */
1918         uint32_t access_masks[] = {
1919                 /* Full READ access. */
1920                 SEC_STD_READ_CONTROL|FILE_READ_DATA|
1921                 FILE_READ_ATTRIBUTES|FILE_READ_EA,
1922
1923                 /* Missing FILE_READ_EA. */
1924                 SEC_STD_READ_CONTROL|FILE_READ_DATA|
1925                 FILE_READ_ATTRIBUTES,
1926
1927                 /* Missing FILE_READ_ATTRIBUTES. */
1928                 SEC_STD_READ_CONTROL|FILE_READ_DATA|
1929                 FILE_READ_EA,
1930
1931                 /* Missing FILE_READ_DATA. */
1932                 SEC_STD_READ_CONTROL|
1933                 FILE_READ_ATTRIBUTES|FILE_READ_EA,
1934         };
1935         unsigned int i;
1936         unsigned int count;
1937         struct smb2_find f;
1938         union smb_search_data *d;
1939
1940         ZERO_STRUCT(fhandle);
1941         ZERO_STRUCT(dhandle);
1942
1943         if (!torture_smb2_con_share(tctx, "hideunread", &tree1)) {
1944                 torture_result(tctx, TORTURE_FAIL, "(%s) Unable to connect "
1945                         "to share 'hideunread'\n",
1946                        __location__);
1947                 ret = false;
1948                 goto done;
1949         }
1950
1951         flags = smb2cli_tcon_flags(tree1->smbXcli);
1952
1953         smb2_util_unlink(tree1, fname);
1954         smb2_deltree(tree1, BASEDIR);
1955
1956         torture_comment(tctx, "TESTING ACCESS BASED ENUMERATION\n");
1957
1958         if ((flags & SMB2_SHAREFLAG_ACCESS_BASED_DIRECTORY_ENUM)==0) {
1959                 torture_result(tctx, TORTURE_FAIL, "(%s) No access enumeration "
1960                         "on share 'hideunread'\n",
1961                        __location__);
1962                 ret = false;
1963                 goto done;
1964         }
1965
1966         if (!smb2_util_setup_dir(tctx, tree1, BASEDIR)) {
1967                 torture_result(tctx, TORTURE_FAIL, "(%s) Unable to setup %s\n",
1968                        __location__, BASEDIR);
1969                 ret = false;
1970                 goto done;
1971         }
1972
1973         /* Get a handle to the BASEDIR directory. */
1974         status = torture_smb2_testdir(tree1, BASEDIR, &dhandle);
1975         CHECK_STATUS(status, NT_STATUS_OK);
1976         smb2_util_close(tree1, dhandle);
1977         ZERO_STRUCT(dhandle);
1978
1979         ZERO_STRUCT(io);
1980         io.level = RAW_OPEN_SMB2;
1981         io.in.create_flags = 0;
1982         io.in.desired_access = SEC_RIGHTS_FILE_ALL;
1983         io.in.create_options = 0;
1984         io.in.file_attributes = FILE_ATTRIBUTE_NORMAL;
1985         io.in.share_access = 0;
1986         io.in.alloc_size = 0;
1987         io.in.create_disposition = NTCREATEX_DISP_CREATE;
1988         io.in.impersonation_level = NTCREATEX_IMPERSONATION_ANONYMOUS;
1989         io.in.security_flags = 0;
1990         io.in.fname = fname;
1991
1992         status = smb2_create(tree1, tctx, &io);
1993         CHECK_STATUS(status, NT_STATUS_OK);
1994         fhandle = io.out.file.handle;
1995
1996         torture_comment(tctx, "get the original sd\n");
1997         q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
1998         q.query_secdesc.in.file.handle = fhandle;
1999         q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER;
2000         status = smb2_getinfo_file(tree1, tctx, &q);
2001         CHECK_STATUS(status, NT_STATUS_OK);
2002         sd_orig = q.query_secdesc.out.sd;
2003
2004         owner_sid = dom_sid_string(tctx, sd_orig->owner_sid);
2005
2006         torture_comment(tctx, "owner_sid is %s\n", owner_sid);
2007
2008         /* Setup for the search. */
2009         ZERO_STRUCT(f);
2010         f.in.pattern            = "*";
2011         f.in.continue_flags     = SMB2_CONTINUE_FLAG_REOPEN;
2012         f.in.max_response_size  = 0x1000;
2013         f.in.level              = SMB2_FIND_DIRECTORY_INFO;
2014
2015         for (i = 0; i < ARRAY_SIZE(access_masks); i++) {
2016
2017                 sd = security_descriptor_dacl_create(tctx,
2018                                         0, NULL, NULL,
2019                                         owner_sid,
2020                                         SEC_ACE_TYPE_ACCESS_ALLOWED,
2021                                         access_masks[i]|SEC_STD_SYNCHRONIZE,
2022                                         0,
2023                                         NULL);
2024
2025                 set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
2026                 set.set_secdesc.in.file.handle = fhandle;
2027                 set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
2028                 set.set_secdesc.in.sd = sd;
2029                 status = smb2_setinfo_file(tree1, &set);
2030                 CHECK_STATUS(status, NT_STATUS_OK);
2031
2032                 /* Now see if we can see the file in a directory listing. */
2033
2034                 /* Re-open dhandle. */
2035                 status = torture_smb2_testdir(tree1, BASEDIR, &dhandle);
2036                 CHECK_STATUS(status, NT_STATUS_OK);
2037                 f.in.file.handle = dhandle;
2038
2039                 count = 0;
2040                 d = NULL;
2041                 status = smb2_find_level(tree1, tree1, &f, &count, &d);
2042                 TALLOC_FREE(d);
2043
2044                 CHECK_STATUS(status, NT_STATUS_OK);
2045
2046                 smb2_util_close(tree1, dhandle);
2047                 ZERO_STRUCT(dhandle);
2048
2049                 if (i == 0) {
2050                         /* We should see the first sd. */
2051                         if (count != 3) {
2052                                 torture_result(tctx, TORTURE_FAIL,
2053                                         "(%s) Normal SD - Unable "
2054                                         "to see file %s\n",
2055                                         __location__,
2056                                         BASEDIR);
2057                                 ret = false;
2058                                 goto done;
2059                         }
2060                 } else {
2061                         /* But no others. */
2062                         if (count != 2) {
2063                                 torture_result(tctx, TORTURE_FAIL,
2064                                         "(%s) SD 0x%x - can "
2065                                         "see file %s\n",
2066                                         __location__,
2067                                         access_masks[i],
2068                                         BASEDIR);
2069                                 ret = false;
2070                                 goto done;
2071                         }
2072                 }
2073         }
2074
2075 done:
2076
2077         if (tree1) {
2078                 smb2_util_close(tree1, fhandle);
2079                 smb2_util_close(tree1, dhandle);
2080                 smb2_util_unlink(tree1, fname);
2081                 smb2_deltree(tree1, BASEDIR);
2082                 smb2_tdis(tree1);
2083                 smb2_logoff(tree1->session);
2084         }
2085         smb2_tdis(tree);
2086         smb2_logoff(tree->session);
2087         return ret;
2088 }
2089
2090 /*
2091    basic testing of SMB2 ACLs
2092 */
2093 struct torture_suite *torture_smb2_acls_init(TALLOC_CTX *ctx)
2094 {
2095         struct torture_suite *suite = torture_suite_create(ctx, "acls");
2096
2097         torture_suite_add_1smb2_test(suite, "CREATOR", test_creator_sid);
2098         torture_suite_add_1smb2_test(suite, "GENERIC", test_generic_bits);
2099         torture_suite_add_1smb2_test(suite, "OWNER", test_owner_bits);
2100         torture_suite_add_1smb2_test(suite, "INHERITANCE", test_inheritance);
2101         torture_suite_add_1smb2_test(suite, "INHERITFLAGS", test_inheritance_flags);
2102         torture_suite_add_1smb2_test(suite, "DYNAMIC", test_inheritance_dynamic);
2103 #if 0
2104         /* XXX This test does not work against XP or Vista. */
2105         torture_suite_add_1smb2_test(suite, "GETSET", test_sd_get_set);
2106 #endif
2107         torture_suite_add_1smb2_test(suite, "ACCESSBASED", test_access_based);
2108
2109         suite->description = talloc_strdup(suite, "SMB2-ACLS tests");
2110
2111         return suite;
2112 }