Line data Source code
1 : /*
2 : Unix SMB/CIFS implementation.
3 :
4 : Copyright (C) Ralph Boehme 2016
5 :
6 : This program is free software; you can redistribute it and/or modify
7 : it under the terms of the GNU General Public License as published by
8 : the Free Software Foundation; either version 3 of the License, or
9 : (at your option) any later version.
10 :
11 : This program is distributed in the hope that it will be useful,
12 : but WITHOUT ANY WARRANTY; without even the implied warranty of
13 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 : GNU General Public License for more details.
15 :
16 : You should have received a copy of the GNU General Public License
17 : along with this program. If not, see <http://www.gnu.org/licenses/>.
18 : */
19 :
20 : #include "includes.h"
21 : #include "lib/cmdline/cmdline.h"
22 : #include "libcli/smb2/smb2.h"
23 : #include "libcli/smb2/smb2_calls.h"
24 : #include "libcli/smb/smbXcli_base.h"
25 : #include "torture/torture.h"
26 : #include "torture/vfs/proto.h"
27 : #include "libcli/resolve/resolve.h"
28 : #include "torture/util.h"
29 : #include "torture/smb2/proto.h"
30 : #include "libcli/security/security.h"
31 : #include "librpc/gen_ndr/ndr_security.h"
32 : #include "lib/param/param.h"
33 :
34 : #define BASEDIR "smb2-testsd"
35 :
36 : #define CHECK_SECURITY_DESCRIPTOR(_sd1, _sd2) do { \
37 : if (!security_descriptor_equal(_sd1, _sd2)) { \
38 : torture_warning(tctx, "security descriptors don't match!\n"); \
39 : torture_warning(tctx, "got:\n"); \
40 : NDR_PRINT_DEBUG(security_descriptor, _sd1); \
41 : torture_warning(tctx, "expected:\n"); \
42 : NDR_PRINT_DEBUG(security_descriptor, _sd2); \
43 : torture_result(tctx, TORTURE_FAIL, \
44 : "%s: security descriptors don't match!\n", \
45 : __location__); \
46 : ret = false; \
47 : } \
48 : } while (0)
49 :
50 0 : static bool test_default_acl_posix(struct torture_context *tctx,
51 : struct smb2_tree *tree_unused)
52 : {
53 0 : struct smb2_tree *tree = NULL;
54 : NTSTATUS status;
55 : bool ok;
56 0 : bool ret = true;
57 0 : const char *dname = BASEDIR "\\testdir";
58 0 : const char *fname = BASEDIR "\\testdir\\testfile";
59 0 : struct smb2_handle fhandle = {{0}};
60 0 : struct smb2_handle dhandle = {{0}};
61 : union smb_fileinfo q;
62 : union smb_setfileinfo set;
63 0 : struct security_descriptor *sd = NULL;
64 0 : struct security_descriptor *exp_sd = NULL;
65 0 : char *owner_sid = NULL;
66 0 : char *group_sid = NULL;
67 :
68 0 : ok = torture_smb2_con_share(tctx, "acl_xattr_ign_sysacl_posix", &tree);
69 0 : torture_assert_goto(tctx, ok == true, ret, done,
70 : "Unable to connect to 'acl_xattr_ign_sysacl_posix'\n");
71 :
72 0 : ok = smb2_util_setup_dir(tctx, tree, BASEDIR);
73 0 : torture_assert_goto(tctx, ok == true, ret, done, "Unable to setup testdir\n");
74 :
75 0 : ZERO_STRUCT(dhandle);
76 0 : status = torture_smb2_testdir(tree, dname, &dhandle);
77 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "torture_smb2_testdir\n");
78 :
79 0 : torture_comment(tctx, "Get the original sd\n");
80 :
81 0 : ZERO_STRUCT(q);
82 0 : q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
83 0 : q.query_secdesc.in.file.handle = dhandle;
84 0 : q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER | SECINFO_GROUP;
85 0 : status = smb2_getinfo_file(tree, tctx, &q);
86 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_getinfo_file\n");
87 :
88 0 : sd = q.query_secdesc.out.sd;
89 0 : owner_sid = dom_sid_string(tctx, sd->owner_sid);
90 0 : group_sid = dom_sid_string(tctx, sd->group_sid);
91 0 : torture_comment(tctx, "owner [%s] group [%s]\n", owner_sid, group_sid);
92 :
93 0 : torture_comment(tctx, "Set ACL with no inheritable ACE\n");
94 :
95 0 : sd = security_descriptor_dacl_create(tctx,
96 : 0, NULL, NULL,
97 : owner_sid,
98 : SEC_ACE_TYPE_ACCESS_ALLOWED,
99 : SEC_RIGHTS_DIR_ALL,
100 : 0,
101 : NULL);
102 :
103 0 : ZERO_STRUCT(set);
104 0 : set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
105 0 : set.set_secdesc.in.file.handle = dhandle;
106 0 : set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
107 0 : set.set_secdesc.in.sd = sd;
108 0 : status = smb2_setinfo_file(tree, &set);
109 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_setinfo_file\n");
110 :
111 0 : TALLOC_FREE(sd);
112 0 : smb2_util_close(tree, dhandle);
113 :
114 0 : torture_comment(tctx, "Create file\n");
115 :
116 0 : ZERO_STRUCT(fhandle);
117 0 : status = torture_smb2_testfile(tree, fname, &fhandle);
118 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_create_complex_file\n");
119 :
120 0 : torture_comment(tctx, "Query file SD\n");
121 :
122 0 : ZERO_STRUCT(q);
123 0 : q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
124 0 : q.query_secdesc.in.file.handle = fhandle;
125 0 : q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER | SECINFO_GROUP;
126 0 : status = smb2_getinfo_file(tree, tctx, &q);
127 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_getinfo_file\n");
128 0 : sd = q.query_secdesc.out.sd;
129 :
130 0 : smb2_util_close(tree, fhandle);
131 0 : ZERO_STRUCT(fhandle);
132 :
133 0 : torture_comment(tctx, "Checking actual file SD against expected SD\n");
134 :
135 0 : exp_sd = security_descriptor_dacl_create(
136 : tctx, 0, owner_sid, group_sid,
137 : owner_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, SEC_RIGHTS_FILE_ALL, 0,
138 : group_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, FILE_GENERIC_READ|FILE_GENERIC_WRITE|FILE_GENERIC_EXECUTE, 0,
139 : SID_WORLD, SEC_ACE_TYPE_ACCESS_ALLOWED, FILE_GENERIC_READ|FILE_GENERIC_WRITE|FILE_GENERIC_EXECUTE, 0,
140 : SID_NT_SYSTEM, SEC_ACE_TYPE_ACCESS_ALLOWED, SEC_RIGHTS_FILE_ALL, 0,
141 : NULL);
142 :
143 0 : CHECK_SECURITY_DESCRIPTOR(sd, exp_sd);
144 :
145 0 : done:
146 0 : if (!smb2_util_handle_empty(fhandle)) {
147 0 : smb2_util_close(tree, fhandle);
148 : }
149 0 : if (!smb2_util_handle_empty(dhandle)) {
150 0 : smb2_util_close(tree, dhandle);
151 : }
152 0 : if (tree != NULL) {
153 0 : smb2_deltree(tree, BASEDIR);
154 0 : smb2_tdis(tree);
155 : }
156 :
157 0 : return ret;
158 : }
159 :
160 0 : static bool test_default_acl_win(struct torture_context *tctx,
161 : struct smb2_tree *tree_unused)
162 : {
163 0 : struct smb2_tree *tree = NULL;
164 : NTSTATUS status;
165 : bool ok;
166 0 : bool ret = true;
167 0 : const char *dname = BASEDIR "\\testdir";
168 0 : const char *fname = BASEDIR "\\testdir\\testfile";
169 0 : struct smb2_handle fhandle = {{0}};
170 0 : struct smb2_handle dhandle = {{0}};
171 : union smb_fileinfo q;
172 : union smb_setfileinfo set;
173 0 : struct security_descriptor *sd = NULL;
174 0 : struct security_descriptor *exp_sd = NULL;
175 0 : char *owner_sid = NULL;
176 0 : char *group_sid = NULL;
177 :
178 0 : ok = torture_smb2_con_share(tctx, "acl_xattr_ign_sysacl_windows", &tree);
179 0 : torture_assert_goto(tctx, ok == true, ret, done,
180 : "Unable to connect to 'acl_xattr_ign_sysacl_windows'\n");
181 :
182 0 : ok = smb2_util_setup_dir(tctx, tree, BASEDIR);
183 0 : torture_assert_goto(tctx, ok == true, ret, done, "Unable to setup testdir\n");
184 :
185 0 : ZERO_STRUCT(dhandle);
186 0 : status = torture_smb2_testdir(tree, dname, &dhandle);
187 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "torture_smb2_testdir\n");
188 :
189 0 : torture_comment(tctx, "Get the original sd\n");
190 :
191 0 : ZERO_STRUCT(q);
192 0 : q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
193 0 : q.query_secdesc.in.file.handle = dhandle;
194 0 : q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER | SECINFO_GROUP;
195 0 : status = smb2_getinfo_file(tree, tctx, &q);
196 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_getinfo_file\n");
197 :
198 0 : sd = q.query_secdesc.out.sd;
199 0 : owner_sid = dom_sid_string(tctx, sd->owner_sid);
200 0 : group_sid = dom_sid_string(tctx, sd->group_sid);
201 0 : torture_comment(tctx, "owner [%s] group [%s]\n", owner_sid, group_sid);
202 :
203 0 : torture_comment(tctx, "Set ACL with no inheritable ACE\n");
204 :
205 0 : sd = security_descriptor_dacl_create(tctx,
206 : 0, NULL, NULL,
207 : owner_sid,
208 : SEC_ACE_TYPE_ACCESS_ALLOWED,
209 : SEC_RIGHTS_DIR_ALL,
210 : 0,
211 : NULL);
212 :
213 0 : ZERO_STRUCT(set);
214 0 : set.set_secdesc.level = RAW_SFILEINFO_SEC_DESC;
215 0 : set.set_secdesc.in.file.handle = dhandle;
216 0 : set.set_secdesc.in.secinfo_flags = SECINFO_DACL;
217 0 : set.set_secdesc.in.sd = sd;
218 0 : status = smb2_setinfo_file(tree, &set);
219 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_setinfo_file\n");
220 :
221 0 : TALLOC_FREE(sd);
222 0 : smb2_util_close(tree, dhandle);
223 :
224 0 : torture_comment(tctx, "Create file\n");
225 :
226 0 : ZERO_STRUCT(fhandle);
227 0 : status = torture_smb2_testfile(tree, fname, &fhandle);
228 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_create_complex_file\n");
229 :
230 0 : torture_comment(tctx, "Query file SD\n");
231 :
232 0 : ZERO_STRUCT(q);
233 0 : q.query_secdesc.level = RAW_FILEINFO_SEC_DESC;
234 0 : q.query_secdesc.in.file.handle = fhandle;
235 0 : q.query_secdesc.in.secinfo_flags = SECINFO_DACL | SECINFO_OWNER | SECINFO_GROUP;
236 0 : status = smb2_getinfo_file(tree, tctx, &q);
237 0 : torture_assert_ntstatus_ok_goto(tctx, status, ret, done, "smb2_getinfo_file\n");
238 0 : sd = q.query_secdesc.out.sd;
239 :
240 0 : smb2_util_close(tree, fhandle);
241 0 : ZERO_STRUCT(fhandle);
242 :
243 0 : torture_comment(tctx, "Checking actual file SD against expected SD\n");
244 :
245 0 : exp_sd = security_descriptor_dacl_create(
246 : tctx, 0, owner_sid, group_sid,
247 : owner_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, SEC_RIGHTS_FILE_ALL, 0,
248 : SID_NT_SYSTEM, SEC_ACE_TYPE_ACCESS_ALLOWED, SEC_RIGHTS_FILE_ALL, 0,
249 : NULL);
250 :
251 0 : CHECK_SECURITY_DESCRIPTOR(sd, exp_sd);
252 :
253 0 : done:
254 0 : if (!smb2_util_handle_empty(fhandle)) {
255 0 : smb2_util_close(tree, fhandle);
256 : }
257 0 : if (!smb2_util_handle_empty(dhandle)) {
258 0 : smb2_util_close(tree, dhandle);
259 : }
260 0 : if (tree != NULL) {
261 0 : smb2_deltree(tree, BASEDIR);
262 0 : smb2_tdis(tree);
263 : }
264 :
265 0 : return ret;
266 : }
267 :
268 : /*
269 : basic testing of vfs_acl_xattr
270 : */
271 964 : struct torture_suite *torture_acl_xattr(TALLOC_CTX *ctx)
272 : {
273 964 : struct torture_suite *suite = torture_suite_create(ctx, "acl_xattr");
274 :
275 964 : torture_suite_add_1smb2_test(suite, "default-acl-style-posix", test_default_acl_posix);
276 964 : torture_suite_add_1smb2_test(suite, "default-acl-style-windows", test_default_acl_win);
277 :
278 964 : suite->description = talloc_strdup(suite, "vfs_acl_xattr tests");
279 :
280 964 : return suite;
281 : }
|