Coverage Report

Created: 2025-12-31 06:20

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/samba/source3/groupdb/mapping.c
Line
Count
Source
1
/* 
2
 *  Unix SMB/CIFS implementation.
3
 *  RPC Pipe client / server routines
4
 *  Copyright (C) Andrew Tridgell              1992-2000,
5
 *  Copyright (C) Jean François Micouleau      1998-2001.
6
 *  Copyright (C) Volker Lendecke              2006.
7
 *  Copyright (C) Gerald Carter                2006.
8
 *  
9
 *  This program is free software; you can redistribute it and/or modify
10
 *  it under the terms of the GNU General Public License as published by
11
 *  the Free Software Foundation; either version 3 of the License, or
12
 *  (at your option) any later version.
13
 *  
14
 *  This program is distributed in the hope that it will be useful,
15
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
 *  GNU General Public License for more details.
18
 *  
19
 *  You should have received a copy of the GNU General Public License
20
 *  along with this program; if not, see <http://www.gnu.org/licenses/>.
21
 */
22
23
#include "includes.h"
24
#include "system/passwd.h"
25
#include "passdb.h"
26
#include "groupdb/mapping.h"
27
#include "../libcli/security/security.h"
28
#include "lib/winbind_util.h"
29
#include <tdb.h>
30
#include "groupdb/mapping_tdb.h"
31
#include "lib/util/smb_strtox.h"
32
33
static const struct mapping_backend *backend;
34
35
/*
36
  initialise a group mapping backend
37
 */
38
static bool init_group_mapping(void)
39
0
{
40
0
  if (backend != NULL) {
41
    /* already initialised */
42
0
    return True;
43
0
  }
44
45
0
        backend = groupdb_tdb_init();
46
47
0
  return backend != NULL;
48
0
}
49
50
/****************************************************************************
51
initialise first time the mapping list
52
****************************************************************************/
53
NTSTATUS add_initial_entry(gid_t gid, const char *sid, enum lsa_SidType sid_name_use, const char *nt_name, const char *comment)
54
0
{
55
0
  NTSTATUS status;
56
0
  GROUP_MAP *map;
57
58
0
  if(!init_group_mapping()) {
59
0
    DEBUG(0,("failed to initialize group mapping\n"));
60
0
    return NT_STATUS_UNSUCCESSFUL;
61
0
  }
62
63
0
  map = talloc_zero(NULL, GROUP_MAP);
64
0
  if (!map) {
65
0
    return NT_STATUS_NO_MEMORY;
66
0
  }
67
68
0
  map->gid=gid;
69
0
  if (!string_to_sid(&map->sid, sid)) {
70
0
    DEBUG(0, ("string_to_sid failed: %s\n", sid));
71
0
    status = NT_STATUS_UNSUCCESSFUL;
72
0
    goto done;
73
0
  }
74
75
0
  map->sid_name_use=sid_name_use;
76
0
  map->nt_name = talloc_strdup(map, nt_name);
77
0
  if (!map->nt_name) {
78
0
    status = NT_STATUS_NO_MEMORY;
79
0
    goto done;
80
0
  }
81
82
0
  if (comment) {
83
0
    map->comment = talloc_strdup(map, comment);
84
0
  } else {
85
0
    map->comment = talloc_strdup(map, "");
86
0
  }
87
0
  if (!map->comment) {
88
0
    status = NT_STATUS_NO_MEMORY;
89
0
    goto done;
90
0
  }
91
92
0
  status = pdb_add_group_mapping_entry(map);
93
94
0
done:
95
0
  TALLOC_FREE(map);
96
0
  return status;
97
0
}
98
99
static NTSTATUS alias_memberships(const struct dom_sid *members, size_t num_members,
100
          struct dom_sid **sids, size_t *num)
101
0
{
102
0
  size_t i;
103
104
0
  *num = 0;
105
0
  *sids = NULL;
106
107
0
  for (i=0; i<num_members; i++) {
108
0
    NTSTATUS status = backend->one_alias_membership(&members[i], sids, num);
109
0
    if (!NT_STATUS_IS_OK(status))
110
0
      return status;
111
0
  }
112
0
  return NT_STATUS_OK;
113
0
}
114
115
struct aliasmem_closure {
116
  const struct dom_sid *alias;
117
  struct dom_sid **sids;
118
  size_t *num;
119
};
120
121
122
123
/*
124
 *
125
 * High level functions
126
 * better to use them than the lower ones.
127
 *
128
 * we are checking if the group is in the mapping file
129
 * and if the group is an existing unix group
130
 *
131
 */
132
133
/* get a domain group from it's SID */
134
135
bool get_domain_group_from_sid(struct dom_sid sid, GROUP_MAP *map)
136
0
{
137
0
  struct group *grp;
138
0
  bool ret;
139
140
0
  if(!init_group_mapping()) {
141
0
    DEBUG(0,("failed to initialize group mapping\n"));
142
0
    return(False);
143
0
  }
144
145
0
  DEBUG(10, ("get_domain_group_from_sid\n"));
146
147
  /* if the group is NOT in the database, it CAN NOT be a domain group */
148
149
0
  become_root();
150
0
  ret = pdb_getgrsid(map, sid);
151
0
  unbecome_root();
152
153
  /* special case check for rid 513 */
154
155
0
  if ( !ret ) {
156
0
    uint32_t rid;
157
158
0
    sid_peek_rid( &sid, &rid );
159
160
0
    if ( rid == DOMAIN_RID_USERS ) {
161
0
      map->nt_name = talloc_strdup(map, "None");
162
0
      if (!map->nt_name) {
163
0
        return false;
164
0
      }
165
0
      map->comment = talloc_strdup(map, "Ordinary Users");
166
0
      if (!map->comment) {
167
0
        return false;
168
0
      }
169
0
      sid_copy( &map->sid, &sid );
170
0
      map->sid_name_use = SID_NAME_DOM_GRP;
171
0
      map->gid = (gid_t)-1;
172
0
      return True;
173
0
    }
174
0
    return False;
175
0
  }
176
177
0
  DEBUG(10, ("get_domain_group_from_sid: SID found in passdb\n"));
178
179
  /* if it's not a domain group, continue */
180
0
  if (map->sid_name_use!=SID_NAME_DOM_GRP) {
181
0
    return False;
182
0
  }
183
184
0
  DEBUG(10, ("get_domain_group_from_sid: SID is a domain group\n"));
185
186
0
  if (map->gid==-1) {
187
0
    return False;
188
0
  }
189
190
0
  DEBUG(10, ("get_domain_group_from_sid: SID is mapped to gid:%lu\n",(unsigned long)map->gid));
191
192
0
  grp = getgrgid(map->gid);
193
0
  if ( !grp ) {
194
0
    DEBUG(10, ("get_domain_group_from_sid: gid DOESN'T exist in UNIX security\n"));
195
0
    return False;
196
0
  }
197
198
0
  DEBUG(10, ("get_domain_group_from_sid: gid exists in UNIX security\n"));
199
200
0
  return True;
201
0
}
202
203
/****************************************************************************
204
 Create a UNIX group on demand.
205
****************************************************************************/
206
207
int smb_create_group(const char *unix_group, gid_t *new_gid)
208
0
{
209
0
  const struct loadparm_substitution *lp_sub =
210
0
    loadparm_s3_global_substitution();
211
0
  char *add_script = NULL;
212
0
  int   ret = -1;
213
0
  int   fd = 0;
214
0
  int error = 0;
215
216
0
  *new_gid = 0;
217
218
  /* defer to scripts */
219
220
0
  if ( *lp_add_group_script(talloc_tos(), lp_sub) ) {
221
0
    TALLOC_CTX *ctx = talloc_tos();
222
223
0
    add_script = talloc_strdup(ctx,
224
0
          lp_add_group_script(ctx, lp_sub));
225
0
    if (!add_script) {
226
0
      return -1;
227
0
    }
228
0
    add_script = talloc_string_sub(ctx,
229
0
        add_script, "%g", unix_group);
230
0
    if (!add_script) {
231
0
      return -1;
232
0
    }
233
234
0
    ret = smbrun(add_script, &fd, NULL);
235
0
    DEBUG(ret ? 0 : 3,("smb_create_group: Running the command `%s' gave %d\n",add_script,ret));
236
0
    if (ret == 0) {
237
0
      smb_nscd_flush_group_cache();
238
0
    }
239
0
    if (ret != 0)
240
0
      return ret;
241
242
0
    if (fd != 0) {
243
0
      fstring output;
244
0
      ssize_t nread;
245
246
0
      *new_gid = 0;
247
248
0
      nread = read(fd, output, sizeof(output)-1);
249
0
      if (nread > 0) {
250
0
        output[nread] = '\0';
251
0
        *new_gid = (gid_t)smb_strtoul(output,
252
0
                    NULL,
253
0
                    10,
254
0
                    &error,
255
0
                    SMB_STR_STANDARD);
256
0
        if (error != 0) {
257
0
          *new_gid = 0;
258
0
          close(fd);
259
0
          return -1;
260
0
        }
261
0
      }
262
263
0
      close(fd);
264
0
    }
265
266
0
  }
267
268
0
  if (*new_gid == 0) {
269
0
    struct group *grp = getgrnam(unix_group);
270
271
0
    if (grp != NULL)
272
0
      *new_gid = grp->gr_gid;
273
0
  }
274
275
0
  return ret;
276
0
}
277
278
/****************************************************************************
279
 Delete a UNIX group on demand.
280
****************************************************************************/
281
282
int smb_delete_group(const char *unix_group)
283
0
{
284
0
  const struct loadparm_substitution *lp_sub =
285
0
    loadparm_s3_global_substitution();
286
0
  char *del_script = NULL;
287
0
  int ret = -1;
288
289
  /* defer to scripts */
290
291
0
  if ( *lp_delete_group_script(talloc_tos(), lp_sub) ) {
292
0
    TALLOC_CTX *ctx = talloc_tos();
293
294
0
    del_script = talloc_strdup(ctx,
295
0
        lp_delete_group_script(ctx, lp_sub));
296
0
    if (!del_script) {
297
0
      return -1;
298
0
    }
299
0
    del_script = talloc_string_sub(ctx,
300
0
        del_script, "%g", unix_group);
301
0
    if (!del_script) {
302
0
      return -1;
303
0
    }
304
0
    ret = smbrun(del_script, NULL, NULL);
305
0
    DEBUG(ret ? 0 : 3,("smb_delete_group: Running the command `%s' gave %d\n",del_script,ret));
306
0
    if (ret == 0) {
307
0
      smb_nscd_flush_group_cache();
308
0
    }
309
0
    return ret;
310
0
  }
311
312
0
  return -1;
313
0
}
314
315
/****************************************************************************
316
 Set a user's primary UNIX group.
317
****************************************************************************/
318
319
int smb_set_primary_group(const char *unix_group, const char* unix_user)
320
0
{
321
0
  const struct loadparm_substitution *lp_sub =
322
0
    loadparm_s3_global_substitution();
323
0
  char *add_script = NULL;
324
0
  int ret = -1;
325
326
  /* defer to scripts */
327
328
0
  if ( *lp_set_primary_group_script(talloc_tos(), lp_sub) ) {
329
0
    TALLOC_CTX *ctx = talloc_tos();
330
331
0
    add_script = talloc_strdup(ctx,
332
0
        lp_set_primary_group_script(ctx, lp_sub));
333
0
    if (!add_script) {
334
0
      return -1;
335
0
    }
336
0
    add_script = talloc_all_string_sub(ctx,
337
0
        add_script, "%g", unix_group);
338
0
    if (!add_script) {
339
0
      return -1;
340
0
    }
341
0
    add_script = talloc_string_sub(ctx,
342
0
        add_script, "%u", unix_user);
343
0
    if (!add_script) {
344
0
      return -1;
345
0
    }
346
0
    ret = smbrun(add_script, NULL, NULL);
347
0
    flush_pwnam_cache();
348
0
    DEBUG(ret ? 0 : 3,("smb_set_primary_group: "
349
0
       "Running the command `%s' gave %d\n",add_script,ret));
350
0
    if (ret == 0) {
351
0
      smb_nscd_flush_group_cache();
352
0
    }
353
0
    return ret;
354
0
  }
355
356
0
  return -1;
357
0
}
358
359
/****************************************************************************
360
 Add a user to a UNIX group.
361
****************************************************************************/
362
363
int smb_add_user_group(const char *unix_group, const char *unix_user)
364
0
{
365
0
  const struct loadparm_substitution *lp_sub =
366
0
    loadparm_s3_global_substitution();
367
0
  char *add_script = NULL;
368
0
  int ret = -1;
369
370
  /* defer to scripts */
371
372
0
  if ( *lp_add_user_to_group_script(talloc_tos(), lp_sub) ) {
373
0
    TALLOC_CTX *ctx = talloc_tos();
374
375
0
    add_script = talloc_strdup(ctx,
376
0
        lp_add_user_to_group_script(ctx, lp_sub));
377
0
    if (!add_script) {
378
0
      return -1;
379
0
    }
380
0
    add_script = talloc_string_sub(ctx,
381
0
        add_script, "%g", unix_group);
382
0
    if (!add_script) {
383
0
      return -1;
384
0
    }
385
0
    add_script = talloc_string_sub2(ctx,
386
0
        add_script, "%u", unix_user, true, false, true);
387
0
    if (!add_script) {
388
0
      return -1;
389
0
    }
390
0
    ret = smbrun(add_script, NULL, NULL);
391
0
    DEBUG(ret ? 0 : 3,("smb_add_user_group: Running the command `%s' gave %d\n",add_script,ret));
392
0
    if (ret == 0) {
393
0
      smb_nscd_flush_group_cache();
394
0
    }
395
0
    return ret;
396
0
  }
397
398
0
  return -1;
399
0
}
400
401
/****************************************************************************
402
 Delete a user from a UNIX group
403
****************************************************************************/
404
405
int smb_delete_user_group(const char *unix_group, const char *unix_user)
406
0
{
407
0
  const struct loadparm_substitution *lp_sub =
408
0
    loadparm_s3_global_substitution();
409
0
  char *del_script = NULL;
410
0
  int ret = -1;
411
412
  /* defer to scripts */
413
414
0
  if ( *lp_delete_user_from_group_script(talloc_tos(), lp_sub) ) {
415
0
    TALLOC_CTX *ctx = talloc_tos();
416
417
0
    del_script = talloc_strdup(ctx,
418
0
        lp_delete_user_from_group_script(ctx, lp_sub));
419
0
    if (!del_script) {
420
0
      return -1;
421
0
    }
422
0
    del_script = talloc_string_sub(ctx,
423
0
        del_script, "%g", unix_group);
424
0
    if (!del_script) {
425
0
      return -1;
426
0
    }
427
0
    del_script = talloc_string_sub2(ctx,
428
0
        del_script, "%u", unix_user, true, false, true);
429
0
    if (!del_script) {
430
0
      return -1;
431
0
    }
432
0
    ret = smbrun(del_script, NULL, NULL);
433
0
    DEBUG(ret ? 0 : 3,("smb_delete_user_group: Running the command `%s' gave %d\n",del_script,ret));
434
0
    if (ret == 0) {
435
0
      smb_nscd_flush_group_cache();
436
0
    }
437
0
    return ret;
438
0
  }
439
440
0
  return -1;
441
0
}
442
443
444
NTSTATUS pdb_default_getgrsid(struct pdb_methods *methods, GROUP_MAP *map,
445
         struct dom_sid sid)
446
0
{
447
0
  if (!init_group_mapping()) {
448
0
    DEBUG(0,("failed to initialize group mapping\n"));
449
0
    return NT_STATUS_UNSUCCESSFUL;
450
0
  }
451
0
  return backend->get_group_map_from_sid(sid, map) ?
452
0
    NT_STATUS_OK : NT_STATUS_UNSUCCESSFUL;
453
0
}
454
455
NTSTATUS pdb_default_getgrgid(struct pdb_methods *methods, GROUP_MAP *map,
456
         gid_t gid)
457
0
{
458
0
  if (!init_group_mapping()) {
459
0
    DEBUG(0,("failed to initialize group mapping\n"));
460
0
    return NT_STATUS_UNSUCCESSFUL;
461
0
  }
462
0
  return backend->get_group_map_from_gid(gid, map) ?
463
0
    NT_STATUS_OK : NT_STATUS_UNSUCCESSFUL;
464
0
}
465
466
NTSTATUS pdb_default_getgrnam(struct pdb_methods *methods, GROUP_MAP *map,
467
         const char *name)
468
0
{
469
0
  if (!init_group_mapping()) {
470
0
    DEBUG(0,("failed to initialize group mapping\n"));
471
0
    return NT_STATUS_UNSUCCESSFUL;
472
0
  }
473
0
  return backend->get_group_map_from_ntname(name, map) ?
474
0
    NT_STATUS_OK : NT_STATUS_UNSUCCESSFUL;
475
0
}
476
477
NTSTATUS pdb_default_add_group_mapping_entry(struct pdb_methods *methods,
478
            GROUP_MAP *map)
479
0
{
480
0
  if (!init_group_mapping()) {
481
0
    DEBUG(0,("failed to initialize group mapping\n"));
482
0
    return NT_STATUS_UNSUCCESSFUL;
483
0
  }
484
0
  return backend->add_mapping_entry(map, TDB_INSERT) ?
485
0
    NT_STATUS_OK : NT_STATUS_UNSUCCESSFUL;
486
0
}
487
488
NTSTATUS pdb_default_update_group_mapping_entry(struct pdb_methods *methods,
489
               GROUP_MAP *map)
490
0
{
491
0
  if (!init_group_mapping()) {
492
0
    DEBUG(0,("failed to initialize group mapping\n"));
493
0
    return NT_STATUS_UNSUCCESSFUL;
494
0
  }
495
0
  return backend->add_mapping_entry(map, TDB_REPLACE) ?
496
0
    NT_STATUS_OK : NT_STATUS_UNSUCCESSFUL;
497
0
}
498
499
NTSTATUS pdb_default_delete_group_mapping_entry(struct pdb_methods *methods,
500
               struct dom_sid sid)
501
0
{
502
0
  if (!init_group_mapping()) {
503
0
    DEBUG(0,("failed to initialize group mapping\n"));
504
0
    return NT_STATUS_UNSUCCESSFUL;
505
0
  }
506
0
  return backend->group_map_remove(&sid) ?
507
0
    NT_STATUS_OK : NT_STATUS_UNSUCCESSFUL;
508
0
}
509
510
NTSTATUS pdb_default_enum_group_mapping(struct pdb_methods *methods,
511
          const struct dom_sid *sid,
512
          enum lsa_SidType sid_name_use,
513
          GROUP_MAP ***pp_rmap,
514
          size_t *p_num_entries,
515
          bool unix_only)
516
0
{
517
0
  if (!init_group_mapping()) {
518
0
    DEBUG(0,("failed to initialize group mapping\n"));
519
0
    return NT_STATUS_UNSUCCESSFUL;
520
0
  }
521
0
  return backend->enum_group_mapping(sid, sid_name_use, pp_rmap, p_num_entries, unix_only) ?
522
0
    NT_STATUS_OK : NT_STATUS_UNSUCCESSFUL;
523
0
}
524
525
NTSTATUS pdb_default_create_alias(struct pdb_methods *methods,
526
          const char *name, uint32_t *rid)
527
0
{
528
0
  struct dom_sid sid;
529
0
  enum lsa_SidType type;
530
0
  uint32_t new_rid;
531
0
  gid_t gid;
532
0
  bool exists;
533
0
  GROUP_MAP *map;
534
0
  TALLOC_CTX *mem_ctx;
535
0
  NTSTATUS status;
536
537
0
  DEBUG(10, ("Trying to create alias %s\n", name));
538
539
0
  mem_ctx = talloc_new(NULL);
540
0
  if (mem_ctx == NULL) {
541
0
    return NT_STATUS_NO_MEMORY;
542
0
  }
543
544
0
  exists = lookup_name(mem_ctx, name, LOOKUP_NAME_LOCAL,
545
0
           NULL, NULL, &sid, &type);
546
547
0
  if (exists) {
548
0
    status = NT_STATUS_ALIAS_EXISTS;
549
0
    goto done;
550
0
  }
551
552
0
  if (!pdb_new_rid(&new_rid)) {
553
0
    DEBUG(0, ("Could not allocate a RID.\n"));
554
0
    status = NT_STATUS_ACCESS_DENIED;
555
0
    goto done;
556
0
  }
557
558
0
  sid_compose(&sid, get_global_sam_sid(), new_rid);
559
560
0
  if (!winbind_allocate_gid(&gid)) {
561
0
    DEBUG(3, ("Could not get a gid out of winbind - "
562
0
        "wasted a rid :-(\n"));
563
0
    status = NT_STATUS_ACCESS_DENIED;
564
0
    goto done;
565
0
  }
566
567
0
  DEBUG(10, ("Creating alias %s with gid %u and rid %u\n",
568
0
       name, (unsigned int)gid, (unsigned int)new_rid));
569
570
0
  map = talloc_zero(mem_ctx, GROUP_MAP);
571
0
  if (!map) {
572
0
    status = NT_STATUS_NO_MEMORY;
573
0
    goto done;
574
0
  }
575
576
0
  map->gid = gid;
577
0
  sid_copy(&map->sid, &sid);
578
0
  map->sid_name_use = SID_NAME_ALIAS;
579
0
  map->nt_name = talloc_strdup(map, name);
580
0
  if (!map->nt_name) {
581
0
    status = NT_STATUS_NO_MEMORY;
582
0
    goto done;
583
0
  }
584
0
  map->comment = talloc_strdup(map, "");
585
0
  if (!map->comment) {
586
0
    status = NT_STATUS_NO_MEMORY;
587
0
    goto done;
588
0
  }
589
590
0
  status = pdb_add_group_mapping_entry(map);
591
592
0
  if (!NT_STATUS_IS_OK(status)) {
593
0
    DEBUG(0, ("Could not add group mapping entry for alias %s "
594
0
        "(%s)\n", name, nt_errstr(status)));
595
0
    goto done;
596
0
  }
597
598
0
  *rid = new_rid;
599
600
0
done:
601
0
  TALLOC_FREE(mem_ctx);
602
0
  return status;
603
0
}
604
605
NTSTATUS pdb_default_delete_alias(struct pdb_methods *methods,
606
          const struct dom_sid *sid)
607
0
{
608
0
  return pdb_delete_group_mapping_entry(*sid);
609
0
}
610
611
NTSTATUS pdb_default_get_aliasinfo(struct pdb_methods *methods,
612
           const struct dom_sid *sid,
613
           struct acct_info *info)
614
0
{
615
0
  NTSTATUS status = NT_STATUS_OK;
616
0
  GROUP_MAP *map;
617
618
0
  map = talloc_zero(NULL, GROUP_MAP);
619
0
  if (!map) {
620
0
    return NT_STATUS_NO_MEMORY;
621
0
  }
622
623
0
  if (!pdb_getgrsid(map, *sid)) {
624
0
    status = NT_STATUS_NO_SUCH_ALIAS;
625
0
    goto done;
626
0
  }
627
628
0
  if ((map->sid_name_use != SID_NAME_ALIAS) &&
629
0
      (map->sid_name_use != SID_NAME_WKN_GRP)) {
630
0
    struct dom_sid_buf buf;
631
0
    DEBUG(2, ("%s is a %s, expected an alias\n",
632
0
        dom_sid_str_buf(sid, &buf),
633
0
        sid_type_lookup(map->sid_name_use)));
634
0
    status = NT_STATUS_NO_SUCH_ALIAS;
635
0
    goto done;
636
0
  }
637
638
0
  info->acct_name = talloc_move(info, &map->nt_name);
639
0
  if (!info->acct_name) {
640
0
    status = NT_STATUS_NO_MEMORY;
641
0
    goto done;
642
0
  }
643
0
  info->acct_desc = talloc_move(info, &map->comment);
644
0
  if (!info->acct_desc) {
645
0
    status = NT_STATUS_NO_MEMORY;
646
0
    goto done;
647
0
  }
648
0
  sid_peek_rid(&map->sid, &info->rid);
649
650
0
done:
651
0
  TALLOC_FREE(map);
652
0
  return status;
653
0
}
654
655
NTSTATUS pdb_default_set_aliasinfo(struct pdb_methods *methods,
656
           const struct dom_sid *sid,
657
           struct acct_info *info)
658
0
{
659
0
  NTSTATUS status;
660
0
  GROUP_MAP *map;
661
662
0
  map = talloc_zero(NULL, GROUP_MAP);
663
0
  if (!map) {
664
0
    return NT_STATUS_NO_MEMORY;
665
0
  }
666
667
0
  if (!pdb_getgrsid(map, *sid)) {
668
0
    status = NT_STATUS_NO_SUCH_ALIAS;
669
0
    goto done;
670
0
  }
671
672
0
  map->nt_name = talloc_strdup(map, info->acct_name);
673
0
  if (!map->nt_name) {
674
0
    status = NT_STATUS_NO_MEMORY;
675
0
    goto done;
676
0
  }
677
0
  map->comment = talloc_strdup(map, info->acct_desc);
678
0
  if (!map->comment) {
679
0
    status = NT_STATUS_NO_MEMORY;
680
0
    goto done;
681
0
  }
682
683
0
  status = pdb_update_group_mapping_entry(map);
684
685
0
done:
686
0
  TALLOC_FREE(map);
687
0
  return status;
688
0
}
689
690
NTSTATUS pdb_default_add_aliasmem(struct pdb_methods *methods,
691
          const struct dom_sid *alias, const struct dom_sid *member)
692
0
{
693
0
  if (!init_group_mapping()) {
694
0
    DEBUG(0,("failed to initialize group mapping\n"));
695
0
    return NT_STATUS_UNSUCCESSFUL;
696
0
  }
697
0
  return backend->add_aliasmem(alias, member);
698
0
}
699
700
NTSTATUS pdb_default_del_aliasmem(struct pdb_methods *methods,
701
          const struct dom_sid *alias, const struct dom_sid *member)
702
0
{
703
0
  if (!init_group_mapping()) {
704
0
    DEBUG(0,("failed to initialize group mapping\n"));
705
0
    return NT_STATUS_UNSUCCESSFUL;
706
0
  }
707
0
  return backend->del_aliasmem(alias, member);
708
0
}
709
710
NTSTATUS pdb_default_enum_aliasmem(struct pdb_methods *methods,
711
           const struct dom_sid *alias, TALLOC_CTX *mem_ctx,
712
           struct dom_sid **pp_members, size_t *p_num_members)
713
0
{
714
0
  if (!init_group_mapping()) {
715
0
    DEBUG(0,("failed to initialize group mapping\n"));
716
0
    return NT_STATUS_UNSUCCESSFUL;
717
0
  }
718
0
  return backend->enum_aliasmem(alias, mem_ctx, pp_members,
719
0
              p_num_members);
720
0
}
721
722
NTSTATUS pdb_default_alias_memberships(struct pdb_methods *methods,
723
               TALLOC_CTX *mem_ctx,
724
               const struct dom_sid *domain_sid,
725
               const struct dom_sid *members,
726
               size_t num_members,
727
               uint32_t **pp_alias_rids,
728
               size_t *p_num_alias_rids)
729
0
{
730
0
  struct dom_sid *alias_sids;
731
0
  size_t i, num_alias_sids;
732
0
  NTSTATUS result;
733
734
0
  if (!init_group_mapping()) {
735
0
    DEBUG(0,("failed to initialize group mapping\n"));
736
0
    return NT_STATUS_UNSUCCESSFUL;
737
0
  }
738
739
0
  alias_sids = NULL;
740
0
  num_alias_sids = 0;
741
742
0
  result = alias_memberships(members, num_members,
743
0
           &alias_sids, &num_alias_sids);
744
745
0
  if (!NT_STATUS_IS_OK(result))
746
0
    return result;
747
748
0
  *p_num_alias_rids = 0;
749
750
0
  if (num_alias_sids == 0) {
751
0
    TALLOC_FREE(alias_sids);
752
0
    return NT_STATUS_OK;
753
0
  }
754
755
0
  *pp_alias_rids = talloc_array(mem_ctx, uint32_t, num_alias_sids);
756
0
  if (*pp_alias_rids == NULL)
757
0
    return NT_STATUS_NO_MEMORY;
758
759
0
  for (i=0; i<num_alias_sids; i++) {
760
0
    if (!sid_peek_check_rid(domain_sid, &alias_sids[i],
761
0
          &(*pp_alias_rids)[*p_num_alias_rids]))
762
0
      continue;
763
0
    *p_num_alias_rids += 1;
764
0
  }
765
766
0
  TALLOC_FREE(alias_sids);
767
768
0
  return NT_STATUS_OK;
769
0
}
770
771
/**********************************************************************
772
 no ops for passdb backends that don't implement group mapping
773
 *********************************************************************/
774
775
NTSTATUS pdb_nop_getgrsid(struct pdb_methods *methods, GROUP_MAP *map,
776
         struct dom_sid sid)
777
0
{
778
0
  return NT_STATUS_UNSUCCESSFUL;
779
0
}
780
781
NTSTATUS pdb_nop_getgrgid(struct pdb_methods *methods, GROUP_MAP *map,
782
         gid_t gid)
783
0
{
784
0
  return NT_STATUS_UNSUCCESSFUL;
785
0
}
786
787
NTSTATUS pdb_nop_getgrnam(struct pdb_methods *methods, GROUP_MAP *map,
788
         const char *name)
789
0
{
790
0
  return NT_STATUS_UNSUCCESSFUL;
791
0
}
792
793
NTSTATUS pdb_nop_add_group_mapping_entry(struct pdb_methods *methods,
794
            GROUP_MAP *map)
795
0
{
796
0
  return NT_STATUS_UNSUCCESSFUL;
797
0
}
798
799
NTSTATUS pdb_nop_update_group_mapping_entry(struct pdb_methods *methods,
800
               GROUP_MAP *map)
801
0
{
802
0
  return NT_STATUS_UNSUCCESSFUL;
803
0
}
804
805
NTSTATUS pdb_nop_delete_group_mapping_entry(struct pdb_methods *methods,
806
               struct dom_sid sid)
807
0
{
808
0
  return NT_STATUS_UNSUCCESSFUL;
809
0
}
810
811
NTSTATUS pdb_nop_enum_group_mapping(struct pdb_methods *methods,
812
             enum lsa_SidType sid_name_use,
813
             GROUP_MAP **rmap, size_t *num_entries,
814
             bool unix_only)
815
0
{
816
0
  return NT_STATUS_UNSUCCESSFUL;
817
0
}
818
819
/**
820
* @brief Add a new group mapping
821
*
822
* @param[in] gid gid to use to store the mapping. If gid is 0,
823
*                new gid will be allocated from winbind
824
*
825
* @return Normal NTSTATUS return
826
*/
827
NTSTATUS pdb_create_builtin_alias(uint32_t rid, gid_t gid)
828
0
{
829
0
  struct dom_sid sid;
830
0
  enum lsa_SidType type;
831
0
  gid_t gidformap;
832
0
  GROUP_MAP *map;
833
0
  NTSTATUS status;
834
0
  const char *name = NULL;
835
836
0
  DEBUG(10, ("Trying to create builtin alias %d\n", rid));
837
838
0
  if ( !sid_compose( &sid, &global_sid_Builtin, rid ) ) {
839
0
    return NT_STATUS_NO_SUCH_ALIAS;
840
0
  }
841
842
  /* use map as overall temp mem context */
843
0
  map = talloc_zero(NULL, GROUP_MAP);
844
0
  if (!map) {
845
0
    return NT_STATUS_NO_MEMORY;
846
0
  }
847
848
0
  if (!lookup_sid(map, &sid, NULL, &name, &type)) {
849
0
    status = NT_STATUS_NO_SUCH_ALIAS;
850
0
    goto done;
851
0
  }
852
853
0
  if (gid == 0) {
854
0
    if (!winbind_allocate_gid(&gidformap)) {
855
0
      DEBUG(3, ("pdb_create_builtin_alias: Could not get a "
856
0
          "gid out of winbind\n"));
857
0
      status = NT_STATUS_ACCESS_DENIED;
858
0
      goto done;
859
0
    }
860
0
  } else {
861
0
    gidformap = gid;
862
0
  }
863
864
0
  DEBUG(10, ("Creating alias %s with gid %u\n", name,
865
0
       (unsigned) gidformap));
866
867
0
  map->gid = gidformap;
868
0
  sid_copy(&map->sid, &sid);
869
0
  map->sid_name_use = SID_NAME_ALIAS;
870
0
  map->nt_name = talloc_strdup(map, name);
871
0
  if (!map->nt_name) {
872
0
    status = NT_STATUS_NO_MEMORY;
873
0
    goto done;
874
0
  }
875
0
  map->comment = talloc_strdup(map, "");
876
0
  if (!map->comment) {
877
0
    status = NT_STATUS_NO_MEMORY;
878
0
    goto done;
879
0
  }
880
881
0
  status = pdb_add_group_mapping_entry(map);
882
883
0
  if (!NT_STATUS_IS_OK(status)) {
884
0
    DEBUG(0, ("pdb_create_builtin_alias: Could not add group mapping entry for alias %d "
885
0
        "(%s)\n", rid, nt_errstr(status)));
886
0
  }
887
888
0
done:
889
  TALLOC_FREE(map);
890
0
  return status;
891
0
}
892
893