2 * Unix SMB/CIFS implementation.
4 * Unit test for NFS4 ACL handling
6 * Copyright (C) Christof Schmitt 2019
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.
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.
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/>.
22 #include "nfs4_acls.c"
23 #include "librpc/gen_ndr/idmap.h"
24 #include "idmap_cache.h"
29 struct unixid unix_id;
31 { "S-1-5-2-123-456-789-100", { 1000, ID_TYPE_UID }},
32 { "S-1-5-2-123-456-789-101", { 1001, ID_TYPE_GID }},
33 { "S-1-5-2-123-456-789-102", { 1002, ID_TYPE_BOTH }},
34 { SID_CREATOR_OWNER, { 1003, ID_TYPE_UID }},
35 { SID_CREATOR_GROUP, { 1004, ID_TYPE_GID }},
36 { "S-1-5-2-123-456-789-103", { 1000, ID_TYPE_GID }},
37 { "S-1-5-2-123-456-789-104", { 1005, ID_TYPE_BOTH }},
38 { "S-1-5-2-123-456-789-105", { 1006, ID_TYPE_BOTH }},
39 { "S-1-5-2-123-456-789-106", { 1007, ID_TYPE_BOTH }},
42 static int group_setup(void **state)
44 struct dom_sid *sids = NULL;
47 sids = talloc_array(NULL, struct dom_sid, ARRAY_SIZE(test_sids));
48 assert_non_null(sids);
50 for (i = 0; i < ARRAY_SIZE(test_sids); i++) {
51 assert_true(dom_sid_parse(test_sids[i].sid_str, &sids[i]));
52 idmap_cache_set_sid2unixid(&sids[i], &test_sids[i].unix_id);
61 static int group_teardown(void **state)
63 struct dom_sid *sids = *state;
66 for (i = 0; i < ARRAY_SIZE(test_sids); i++) {
67 assert_true(idmap_cache_del_sid(&sids[i]));
77 * Run this as first test to verify that the id mappings used by other
78 * tests are available in the cache.
80 static void test_cached_id_mappings(void **state)
82 struct dom_sid *sids = *state;
85 for (i = 0; i < ARRAY_SIZE(test_sids); i++) {
86 struct dom_sid *sid = &sids[i];
87 struct unixid *unix_id = &test_sids[i].unix_id;
91 switch(unix_id->type) {
93 assert_true(sid_to_uid(sid, &uid));
94 assert_int_equal(uid, unix_id->id);
95 assert_false(sid_to_gid(sid, &gid));
98 assert_false(sid_to_uid(sid, &uid));
99 assert_true(sid_to_gid(sid, &gid));
100 assert_int_equal(gid, unix_id->id);
103 assert_true(sid_to_uid(sid, &uid));
104 assert_int_equal(uid, unix_id->id);
105 assert_true(sid_to_gid(sid, &gid));
106 assert_int_equal(gid, unix_id->id);
109 fail_msg("Unknown id type %d\n", unix_id->type);
115 static void test_empty_nfs4_to_dacl(void **state)
117 struct dom_sid *sids = *state;
118 TALLOC_CTX *frame = talloc_stackframe();
119 struct SMB4ACL_T *nfs4_acl;
120 struct security_ace *dacl_aces;
122 struct smbacl4_vfs_params params = {
126 .map_full_control = true,
129 nfs4_acl = smb_create_smb4acl(frame);
130 assert_non_null(nfs4_acl);
132 assert_true(smbacl4_nfs42win(frame, ¶ms, nfs4_acl,
133 &sids[0], &sids[1], false,
134 &dacl_aces, &good_aces));
136 assert_int_equal(good_aces, 0);
137 assert_null(dacl_aces);
142 static void test_empty_dacl_to_nfs4(void **state)
144 TALLOC_CTX *frame = talloc_stackframe();
145 struct SMB4ACL_T *nfs4_acl;
146 struct security_acl *dacl;
147 struct smbacl4_vfs_params params = {
151 .map_full_control = true,
154 dacl = make_sec_acl(frame, SECURITY_ACL_REVISION_ADS, 0, NULL);
155 assert_non_null(dacl);
157 nfs4_acl = smbacl4_win2nfs4(frame, false, dacl, ¶ms, 1001, 1002);
159 assert_non_null(nfs4_acl);
160 assert_int_equal(smbacl4_get_controlflags(nfs4_acl),
161 SEC_DESC_SELF_RELATIVE);
162 assert_int_equal(smb_get_naces(nfs4_acl), 0);
163 assert_null(smb_first_ace4(nfs4_acl));
166 struct ace_dacl_type_mapping {
168 enum security_ace_type dacl_type;
169 } ace_dacl_type_mapping[] = {
170 { SMB_ACE4_ACCESS_ALLOWED_ACE_TYPE, SEC_ACE_TYPE_ACCESS_ALLOWED },
171 { SMB_ACE4_ACCESS_DENIED_ACE_TYPE, SEC_ACE_TYPE_ACCESS_DENIED },
174 static void test_acl_type_nfs4_to_dacl(void **state)
176 struct dom_sid *sids = *state;
177 TALLOC_CTX *frame = talloc_stackframe();
180 for (i = 0; i < ARRAY_SIZE(ace_dacl_type_mapping); i++) {
181 struct SMB4ACL_T *nfs4_acl;
182 SMB_ACE4PROP_T nfs4_ace;
183 struct security_ace *dacl_aces;
185 struct smbacl4_vfs_params params = {
189 .map_full_control = true,
192 nfs4_acl = smb_create_smb4acl(frame);
193 assert_non_null(nfs4_acl);
195 nfs4_ace = (SMB_ACE4PROP_T) {
198 .aceType = ace_dacl_type_mapping[i].nfs4_type,
200 .aceMask = SMB_ACE4_READ_DATA,
202 assert_non_null(smb_add_ace4(nfs4_acl, &nfs4_ace));
204 assert_true(smbacl4_nfs42win(frame, ¶ms, nfs4_acl,
205 &sids[2], &sids[3], false,
206 &dacl_aces, &good_aces));
208 assert_int_equal(good_aces, 1);
209 assert_non_null(dacl_aces);
211 assert_int_equal(dacl_aces[0].type,
212 ace_dacl_type_mapping[i].dacl_type);
213 assert_int_equal(dacl_aces[0].flags, 0);
214 assert_int_equal(dacl_aces[0].access_mask, SEC_FILE_READ_DATA);
215 assert_true(dom_sid_equal(&dacl_aces[0].trustee, &sids[0]));
221 static void test_acl_type_dacl_to_nfs4(void **state)
223 struct dom_sid *sids = *state;
224 TALLOC_CTX *frame = talloc_stackframe();
227 for (i = 0; i < ARRAY_SIZE(ace_dacl_type_mapping); i++) {
228 struct SMB4ACL_T *nfs4_acl;
229 struct SMB4ACE_T *nfs4_ace_container;
230 SMB_ACE4PROP_T *nfs4_ace;
231 struct security_ace dacl_aces[1];
232 struct security_acl *dacl;
233 struct smbacl4_vfs_params params = {
237 .map_full_control = true,
240 init_sec_ace(&dacl_aces[0], &sids[0],
241 ace_dacl_type_mapping[i].dacl_type,
242 SEC_FILE_READ_DATA, 0);
243 dacl = make_sec_acl(frame, SECURITY_ACL_REVISION_ADS,
244 ARRAY_SIZE(dacl_aces), dacl_aces);
245 assert_non_null(dacl);
247 nfs4_acl = smbacl4_win2nfs4(frame, false, dacl, ¶ms,
250 assert_non_null(nfs4_acl);
251 assert_int_equal(smbacl4_get_controlflags(nfs4_acl),
252 SEC_DESC_SELF_RELATIVE);
253 assert_int_equal(smb_get_naces(nfs4_acl), 1);
255 nfs4_ace_container = smb_first_ace4(nfs4_acl);
256 assert_non_null(nfs4_ace_container);
257 assert_null(smb_next_ace4(nfs4_ace_container));
259 nfs4_ace = smb_get_ace4(nfs4_ace_container);
260 assert_int_equal(nfs4_ace->flags, 0);
261 assert_int_equal(nfs4_ace->who.uid, 1000);
262 assert_int_equal(nfs4_ace->aceFlags, 0);
263 assert_int_equal(nfs4_ace->aceType,
264 ace_dacl_type_mapping[i].nfs4_type);
265 assert_int_equal(nfs4_ace->aceMask, SMB_ACE4_READ_DATA);
271 int main(int argc, char **argv)
273 const struct CMUnitTest tests[] = {
274 cmocka_unit_test(test_cached_id_mappings),
275 cmocka_unit_test(test_empty_nfs4_to_dacl),
276 cmocka_unit_test(test_empty_dacl_to_nfs4),
277 cmocka_unit_test(test_acl_type_nfs4_to_dacl),
278 cmocka_unit_test(test_acl_type_dacl_to_nfs4),
281 cmocka_set_message_output(CM_OUTPUT_SUBUNIT);
284 print_error("Usage: %s smb.conf\n", argv[0]);
289 * Initialize enough of the Samba internals to have the
290 * mappings tests work.
293 lp_load_global(argv[1]);
295 return cmocka_run_group_tests(tests, group_setup, group_teardown);