1dc20a302Sas200622 /* 2dc20a302Sas200622 * CDDL HEADER START 3dc20a302Sas200622 * 4dc20a302Sas200622 * The contents of this file are subject to the terms of the 5dc20a302Sas200622 * Common Development and Distribution License (the "License"). 6dc20a302Sas200622 * You may not use this file except in compliance with the License. 7dc20a302Sas200622 * 8dc20a302Sas200622 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9dc20a302Sas200622 * or http://www.opensolaris.org/os/licensing. 10dc20a302Sas200622 * See the License for the specific language governing permissions 11dc20a302Sas200622 * and limitations under the License. 12dc20a302Sas200622 * 13dc20a302Sas200622 * When distributing Covered Code, include this CDDL HEADER in each 14dc20a302Sas200622 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15dc20a302Sas200622 * If applicable, add the following below this CDDL HEADER, with the 16dc20a302Sas200622 * fields enclosed by brackets "[]" replaced with your own identifying 17dc20a302Sas200622 * information: Portions Copyright [yyyy] [name of copyright owner] 18dc20a302Sas200622 * 19dc20a302Sas200622 * CDDL HEADER END 20dc20a302Sas200622 */ 21148c5f43SAlan Wright 22dc20a302Sas200622 /* 2336a00406SGordon Ross * Copyright 2011 Nexenta Systems, Inc. All rights reserved. 24c5866007SKeyur Desai * Copyright (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved. 25*a7fe1d5bSAndy Stormont * Copyright (c) 2013 RackTop Systems. 26dc20a302Sas200622 */ 27dc20a302Sas200622 28dc20a302Sas200622 #include <stdlib.h> 29dc20a302Sas200622 #include <strings.h> 30dc20a302Sas200622 #include <unistd.h> 31dc20a302Sas200622 #include <syslog.h> 32dc20a302Sas200622 #include <thread.h> 33dc20a302Sas200622 #include <synch.h> 34dc20a302Sas200622 #include <grp.h> 35dc20a302Sas200622 #include <assert.h> 36dc20a302Sas200622 #include <libintl.h> 37dc20a302Sas200622 #include <smbsrv/libsmb.h> 387b59d02dSjb150015 #include <smb_sqlite.h> 39148c5f43SAlan Wright #include <sys/types.h> 40148c5f43SAlan Wright #include <sys/stat.h> 41148c5f43SAlan Wright #include <sys/param.h> 42*a7fe1d5bSAndy Stormont #include <libcmdutils.h> 43dc20a302Sas200622 44faa1795aSjb150015 /* 45faa1795aSjb150015 * Local domain SID (aka machine SID) is not stored in the domain table 46faa1795aSjb150015 * therefore the index is 0 47faa1795aSjb150015 */ 48dc20a302Sas200622 #define SMB_LGRP_LOCAL_IDX 0 49dc20a302Sas200622 #define SMB_LGRP_BUILTIN_IDX 1 50dc20a302Sas200622 51dc20a302Sas200622 #define SMB_LGRP_DB_NAME "/var/smb/smbgroup.db" 52dc20a302Sas200622 #define SMB_LGRP_DB_TIMEOUT 3000 /* in millisecond */ 53dc20a302Sas200622 #define SMB_LGRP_DB_VERMAJOR 1 54dc20a302Sas200622 #define SMB_LGRP_DB_VERMINOR 0 55dc20a302Sas200622 #define SMB_LGRP_DB_MAGIC 0x4C475250 /* LGRP */ 56dc20a302Sas200622 57dc20a302Sas200622 #define SMB_LGRP_DB_ORD 1 /* open read-only */ 58dc20a302Sas200622 #define SMB_LGRP_DB_ORW 2 /* open read/write */ 59dc20a302Sas200622 60dc20a302Sas200622 #define SMB_LGRP_DB_ADDMEMBER 1 61dc20a302Sas200622 #define SMB_LGRP_DB_DELMEMBER 2 62dc20a302Sas200622 63dc20a302Sas200622 /* 64dc20a302Sas200622 * members column of the groups table is an array of 65dc20a302Sas200622 * member structure smb_lgmid_t defined below. 66dc20a302Sas200622 * 67dc20a302Sas200622 * privs column of the groups table is an array of bytes 68dc20a302Sas200622 * where each byte is the id of an enable privilege 69dc20a302Sas200622 */ 70dc20a302Sas200622 #define SMB_LGRP_DB_SQL \ 71dc20a302Sas200622 "CREATE TABLE db_info (" \ 72dc20a302Sas200622 " ver_major INTEGER," \ 73dc20a302Sas200622 " ver_minor INTEGER," \ 74dc20a302Sas200622 " magic INTEGER" \ 75dc20a302Sas200622 ");" \ 76dc20a302Sas200622 "" \ 77dc20a302Sas200622 "CREATE TABLE domains (" \ 78dc20a302Sas200622 " dom_idx INTEGER PRIMARY KEY," \ 79dc20a302Sas200622 " dom_sid TEXT UNIQUE," \ 80dc20a302Sas200622 " dom_cnt INTEGER" \ 81dc20a302Sas200622 ");" \ 82dc20a302Sas200622 "" \ 83dc20a302Sas200622 "CREATE UNIQUE INDEX domsid_idx ON domains (dom_sid);" \ 84dc20a302Sas200622 "" \ 85dc20a302Sas200622 "CREATE TABLE groups (" \ 86dc20a302Sas200622 " name TEXT PRIMARY KEY," \ 87dc20a302Sas200622 " sid_idx INTEGER," \ 88dc20a302Sas200622 " sid_rid INTEGER," \ 89dc20a302Sas200622 " sid_type INTEGER," \ 90dc20a302Sas200622 " sid_attrs INTEGER," \ 91dc20a302Sas200622 " comment TEXT," \ 92dc20a302Sas200622 " n_privs INTEGER," \ 93dc20a302Sas200622 " privs BLOB," \ 94dc20a302Sas200622 " n_members INTEGER," \ 95dc20a302Sas200622 " members BLOB" \ 96dc20a302Sas200622 ");" \ 97dc20a302Sas200622 "" \ 98dc20a302Sas200622 "CREATE INDEX grprid_idx ON groups (sid_rid);" 99dc20a302Sas200622 100dc20a302Sas200622 /* 101dc20a302Sas200622 * Number of groups table columns 102dc20a302Sas200622 */ 103dc20a302Sas200622 #define SMB_LGRP_GTBL_NCOL 10 104dc20a302Sas200622 105dc20a302Sas200622 #define SMB_LGRP_GTBL_NAME 0 106dc20a302Sas200622 #define SMB_LGRP_GTBL_SIDIDX 1 107dc20a302Sas200622 #define SMB_LGRP_GTBL_SIDRID 2 108dc20a302Sas200622 #define SMB_LGRP_GTBL_SIDTYP 3 109dc20a302Sas200622 #define SMB_LGRP_GTBL_SIDATR 4 110dc20a302Sas200622 #define SMB_LGRP_GTBL_CMNT 5 111dc20a302Sas200622 #define SMB_LGRP_GTBL_NPRIVS 6 112dc20a302Sas200622 #define SMB_LGRP_GTBL_PRIVS 7 113dc20a302Sas200622 #define SMB_LGRP_GTBL_NMEMBS 8 114dc20a302Sas200622 #define SMB_LGRP_GTBL_MEMBS 9 115dc20a302Sas200622 116dc20a302Sas200622 #define SMB_LGRP_INFO_NONE 0x00 117dc20a302Sas200622 #define SMB_LGRP_INFO_NAME 0x01 118dc20a302Sas200622 #define SMB_LGRP_INFO_CMNT 0x02 119dc20a302Sas200622 #define SMB_LGRP_INFO_SID 0x04 120dc20a302Sas200622 #define SMB_LGRP_INFO_PRIV 0x08 121dc20a302Sas200622 #define SMB_LGRP_INFO_MEMB 0x10 122dc20a302Sas200622 #define SMB_LGRP_INFO_ALL 0x1F 123dc20a302Sas200622 124148c5f43SAlan Wright #define SMB_LGRP_PGRP_GRPTMP "/etc/gtmp" 125148c5f43SAlan Wright #define SMB_LGRP_PGRP_GRPBUFSIZ 5120 126148c5f43SAlan Wright #define SMB_LGRP_PGRP_GROUP "/etc/group" 127148c5f43SAlan Wright #define SMB_LGRP_PGRP_MAXGLEN 9 /* max length of group name */ 128*a7fe1d5bSAndy Stormont #define SMB_LGRP_PGRP_DEFRID 1000 /* lowest cifs created gid */ 129148c5f43SAlan Wright 130148c5f43SAlan Wright #define SMB_LGRP_PGRP_NOTUNIQUE 0 131148c5f43SAlan Wright #define SMB_LGRP_PGRP_RESERVED 1 132148c5f43SAlan Wright #define SMB_LGRP_PGRP_UNIQUE 2 133148c5f43SAlan Wright #define SMB_LGRP_PGRP_TOOBIG 3 134148c5f43SAlan Wright #define SMB_LGRP_PGRP_INVALID 4 135148c5f43SAlan Wright 136dc20a302Sas200622 #define NULL_MSGCHK(msg) ((msg) ? (msg) : "NULL") 137dc20a302Sas200622 138dc20a302Sas200622 /* Member ID */ 139dc20a302Sas200622 typedef struct smb_lgmid { 140dc20a302Sas200622 uint32_t m_idx; 141dc20a302Sas200622 uint32_t m_rid; 142dc20a302Sas200622 uint16_t m_type; 143dc20a302Sas200622 } smb_lgmid_t; 144dc20a302Sas200622 145dc20a302Sas200622 #define SMB_LGRP_MID_HEXSZ 32 146dc20a302Sas200622 147dc20a302Sas200622 /* Member list */ 148dc20a302Sas200622 typedef struct smb_lgmlist { 149dc20a302Sas200622 uint32_t m_cnt; 150dc20a302Sas200622 char *m_ids; 151dc20a302Sas200622 } smb_lgmlist_t; 152dc20a302Sas200622 153dc20a302Sas200622 /* Privilege ID */ 154dc20a302Sas200622 typedef uint8_t smb_lgpid_t; 155dc20a302Sas200622 156dc20a302Sas200622 /* Privilege list */ 157dc20a302Sas200622 typedef struct smb_lgplist { 158dc20a302Sas200622 uint32_t p_cnt; 159dc20a302Sas200622 smb_lgpid_t *p_ids; 160dc20a302Sas200622 } smb_lgplist_t; 161dc20a302Sas200622 1629fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States static struct { 1639fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States int errnum; 1649fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States char *errmsg; 1659fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } errtab[] = { 1669fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_SUCCESS, "success" }, 1679fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_INVALID_ARG, "invalid argument" }, 1689fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_INVALID_MEMBER, "invalid member type" }, 1699fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_INVALID_NAME, "invalid name" }, 1709fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_NOT_FOUND, "group not found" }, 1719fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_EXISTS, "group exists" }, 1729fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_NO_SID, "cannot obtain a SID" }, 1739fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_NO_LOCAL_SID, "cannot get the machine SID" }, 1749fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_SID_NOTLOCAL, "local account has non-local SID" }, 1759fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_WKSID, 1769fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States "operation not permitted on well-known account" }, 1779fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_NO_MEMORY, "not enough memory" }, 1789fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DB_ERROR, "database operation error" }, 1799fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DBINIT_ERROR, "database initialization error" }, 1809fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_INTERNAL_ERROR, "internal error" }, 1819fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_MEMBER_IN_GROUP, "member already in group" }, 1829fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_MEMBER_NOT_IN_GROUP, "not a member" }, 1839fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_NO_SUCH_PRIV, "no such privilege" }, 1849fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_NO_SUCH_DOMAIN, "no such domain SID" }, 1859fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_PRIV_HELD, "privilege already held" }, 1869fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_PRIV_NOT_HELD, "privilege not held" }, 1879fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_BAD_DATA, "bad data" }, 1889fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_NO_MORE, "no more groups" }, 1899fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DBOPEN_FAILED, "database open failed" }, 1909fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DBEXEC_FAILED, "database operation failed" }, 1919fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DBINIT_FAILED, "database initialization failed" }, 1929fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DOMLKP_FAILED, "domain SID lookup failed" }, 1939fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DOMINS_FAILED, "domain SID insert failed" }, 1949fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_INSERT_FAILED, "group insert failed" }, 1959fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_DELETE_FAILED, "group delete failed" }, 1969fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_UPDATE_FAILED, "group update failed" }, 1979fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { SMB_LGRP_LOOKUP_FAILED, "group lookup failed" }, 198148c5f43SAlan Wright { SMB_LGRP_OFFLINE, "local group service is offline" }, 199148c5f43SAlan Wright { SMB_LGRP_POSIXCREATE_FAILED, "posix group create failed" } 2009fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States }; 201dc20a302Sas200622 2029fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States /* 2039fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States * Serialization for the local group API. 2049fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States */ 2059fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States typedef struct { 2069fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States mutex_t lg_mutex; 2079fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States cond_t lg_cv; 2089fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States boolean_t lg_online; 2099fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States uint32_t lg_refcnt; 2109fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_sid_t *lg_machine_sid; 2119fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } smb_localgrp_t; 2129fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 2139fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States static smb_localgrp_t smb_localgrp; 2149fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 2159fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States static boolean_t smb_lgrp_enter(void); 2169fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States static void smb_lgrp_exit(void); 217dc20a302Sas200622 static int smb_lgrp_db_init(void); 218dc20a302Sas200622 static sqlite *smb_lgrp_db_open(int); 219dc20a302Sas200622 static void smb_lgrp_db_close(sqlite *); 220dc20a302Sas200622 static int smb_lgrp_db_setinfo(sqlite *); 221dc20a302Sas200622 222dc20a302Sas200622 static boolean_t smb_lgrp_gtbl_exists(sqlite *, char *); 223dc20a302Sas200622 static int smb_lgrp_gtbl_lookup(sqlite *, int, smb_group_t *, int, ...); 224dc20a302Sas200622 static int smb_lgrp_gtbl_insert(sqlite *, smb_group_t *); 225dc20a302Sas200622 static int smb_lgrp_gtbl_update(sqlite *, char *, smb_group_t *, int); 226dc20a302Sas200622 static int smb_lgrp_gtbl_delete(sqlite *, char *); 227dc20a302Sas200622 static int smb_lgrp_gtbl_update_mlist(sqlite *, char *, smb_gsid_t *, int); 228dc20a302Sas200622 static int smb_lgrp_gtbl_update_plist(sqlite *, char *, uint8_t, boolean_t); 229dc20a302Sas200622 static int smb_lgrp_gtbl_count(sqlite *, int, int *); 230dc20a302Sas200622 231dc20a302Sas200622 static int smb_lgrp_dtbl_insert(sqlite *, char *, uint32_t *); 2326537f381Sas200622 static int smb_lgrp_dtbl_getidx(sqlite *, smb_sid_t *, uint16_t, 233dc20a302Sas200622 uint32_t *, uint32_t *); 2346537f381Sas200622 static int smb_lgrp_dtbl_getsid(sqlite *, uint32_t, smb_sid_t **); 235dc20a302Sas200622 236dc20a302Sas200622 static int smb_lgrp_mlist_add(smb_lgmlist_t *, smb_lgmid_t *, smb_lgmlist_t *); 237dc20a302Sas200622 static int smb_lgrp_mlist_del(smb_lgmlist_t *, smb_lgmid_t *, smb_lgmlist_t *); 238dc20a302Sas200622 239dc20a302Sas200622 static int smb_lgrp_plist_add(smb_lgplist_t *, smb_lgpid_t, smb_lgplist_t *); 240dc20a302Sas200622 static int smb_lgrp_plist_del(smb_lgplist_t *, smb_lgpid_t, smb_lgplist_t *); 241dc20a302Sas200622 242dc20a302Sas200622 static void smb_lgrp_encode_privset(smb_group_t *, smb_lgplist_t *); 243dc20a302Sas200622 244dc20a302Sas200622 static int smb_lgrp_decode(smb_group_t *, char **, int, sqlite *); 245dc20a302Sas200622 static int smb_lgrp_decode_privset(smb_group_t *, char *, char *); 246dc20a302Sas200622 static int smb_lgrp_decode_members(smb_group_t *, char *, char *, sqlite *); 247dc20a302Sas200622 248dc20a302Sas200622 static void smb_lgrp_set_default_privs(smb_group_t *); 249fe1c642dSBill Krier static boolean_t smb_lgrp_normalize_name(char *); 250dc20a302Sas200622 static boolean_t smb_lgrp_chkmember(uint16_t); 2516537f381Sas200622 static int smb_lgrp_getsid(int, uint32_t *, uint16_t, sqlite *, smb_sid_t **); 252c8ec8eeaSjose borrego static int smb_lgrp_getgid(uint32_t rid, gid_t *gid); 25329bd2886SAlan Wright static boolean_t smb_lgrp_exists(char *); 254148c5f43SAlan Wright static int smb_lgrp_pgrp_add(char *); 255dc20a302Sas200622 256dc20a302Sas200622 /* 257dc20a302Sas200622 * smb_lgrp_add 258dc20a302Sas200622 * 259dc20a302Sas200622 * Create a local group with the given name and comment. 260dc20a302Sas200622 * This new group doesn't have any members and no enabled 261dc20a302Sas200622 * privileges. 262dc20a302Sas200622 * 263dc20a302Sas200622 * No well-known accounts can be added other than Administators, 264dc20a302Sas200622 * Backup Operators and Power Users. These built-in groups 265dc20a302Sas200622 * won't have any members when created but a set of default 266dc20a302Sas200622 * privileges will be enabled for them. 267dc20a302Sas200622 */ 268dc20a302Sas200622 int 269dc20a302Sas200622 smb_lgrp_add(char *gname, char *cmnt) 270dc20a302Sas200622 { 2716537f381Sas200622 smb_wka_t *wka; 272dc20a302Sas200622 struct group *pxgrp; 273dc20a302Sas200622 smb_group_t grp; 2746537f381Sas200622 smb_sid_t *sid = NULL; 275dc20a302Sas200622 sqlite *db; 276dc20a302Sas200622 int rc; 277dc20a302Sas200622 278fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 279dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 280dc20a302Sas200622 281dc20a302Sas200622 if (cmnt && (strlen(cmnt) > SMB_LGRP_COMMENT_MAX)) 282dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 283dc20a302Sas200622 284dc20a302Sas200622 bzero(&grp, sizeof (grp)); 285bbf6f00cSJordan Brown grp.sg_name = smb_strlwr(gname); 286dc20a302Sas200622 grp.sg_cmnt = cmnt; 287dc20a302Sas200622 2889fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 2899fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 2909fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 2917f667e74Sjose borrego wka = smb_wka_lookup_name(gname); 2926537f381Sas200622 if (wka == NULL) { 2939fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if ((pxgrp = getgrnam(gname)) == NULL) { 294148c5f43SAlan Wright if (smb_lgrp_pgrp_add(gname) != 0) { 295148c5f43SAlan Wright smb_lgrp_exit(); 296148c5f43SAlan Wright return (SMB_LGRP_POSIXCREATE_FAILED); 297148c5f43SAlan Wright } 298148c5f43SAlan Wright 299148c5f43SAlan Wright if ((pxgrp = getgrnam(gname)) == NULL) { 3009fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 301dc20a302Sas200622 return (SMB_LGRP_NOT_FOUND); 3029fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 303148c5f43SAlan Wright } 304dc20a302Sas200622 305dc20a302Sas200622 /* 306dc20a302Sas200622 * Make sure a local SID can be obtained 307dc20a302Sas200622 */ 308dc20a302Sas200622 if (smb_idmap_getsid(pxgrp->gr_gid, SMB_IDMAP_GROUP, &sid) 3099fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States != IDMAP_SUCCESS) { 3109fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 311dc20a302Sas200622 return (SMB_LGRP_NO_SID); 3129fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 313dc20a302Sas200622 3149fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_sid_indomain(smb_localgrp.lg_machine_sid, sid)) { 315dc20a302Sas200622 free(sid); 3169fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 317dc20a302Sas200622 return (SMB_LGRP_SID_NOTLOCAL); 318dc20a302Sas200622 } 319dc20a302Sas200622 3209fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States free(sid); 321dc20a302Sas200622 grp.sg_id.gs_type = SidTypeAlias; 3229fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States grp.sg_domain = SMB_DOMAIN_LOCAL; 323dc20a302Sas200622 grp.sg_rid = pxgrp->gr_gid; 324dc20a302Sas200622 } else { 3256537f381Sas200622 if ((wka->wka_flags & SMB_WKAFLG_LGRP_ENABLE) == 0) { 326dc20a302Sas200622 /* cannot add well-known accounts */ 3279fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 328dc20a302Sas200622 return (SMB_LGRP_WKSID); 329dc20a302Sas200622 } 330dc20a302Sas200622 3316537f381Sas200622 grp.sg_id.gs_type = wka->wka_type; 3329fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if ((sid = smb_sid_fromstr(wka->wka_sid)) == NULL) { 3339fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 334dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 3359fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 3369fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 3376537f381Sas200622 (void) smb_sid_getrid(sid, &grp.sg_rid); 338dc20a302Sas200622 free(sid); 3399fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States grp.sg_domain = SMB_DOMAIN_BUILTIN; 340dc20a302Sas200622 grp.sg_privs = smb_privset_new(); 341dc20a302Sas200622 smb_lgrp_set_default_privs(&grp); 342dc20a302Sas200622 } 343dc20a302Sas200622 3449fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (smb_lgrp_exists(grp.sg_name)) { 3459fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 34696a62adaSjoyce mcintosh return (SMB_LGRP_EXISTS); 3479fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 348dc20a302Sas200622 349dc20a302Sas200622 grp.sg_attr = SE_GROUP_MANDATORY | SE_GROUP_ENABLED_BY_DEFAULT | 350dc20a302Sas200622 SE_GROUP_ENABLED; 351dc20a302Sas200622 352dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORW); 353dc20a302Sas200622 rc = smb_lgrp_gtbl_insert(db, &grp); 354dc20a302Sas200622 smb_lgrp_db_close(db); 355dc20a302Sas200622 356dc20a302Sas200622 smb_privset_free(grp.sg_privs); 3579fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 358dc20a302Sas200622 return (rc); 359dc20a302Sas200622 } 360dc20a302Sas200622 361dc20a302Sas200622 /* 362dc20a302Sas200622 * smb_lgrp_rename 363dc20a302Sas200622 * 364dc20a302Sas200622 * Renames the given group 365dc20a302Sas200622 */ 366dc20a302Sas200622 int 367dc20a302Sas200622 smb_lgrp_rename(char *gname, char *new_gname) 368dc20a302Sas200622 { 369dc20a302Sas200622 smb_group_t grp; 370dc20a302Sas200622 sqlite *db; 371dc20a302Sas200622 int rc; 372dc20a302Sas200622 373fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 374dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 375dc20a302Sas200622 376fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 377dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 378dc20a302Sas200622 379bbf6f00cSJordan Brown if (smb_strcasecmp(gname, new_gname, 0) == 0) 380dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 381dc20a302Sas200622 382dc20a302Sas200622 /* Cannot rename well-known groups */ 3837f667e74Sjose borrego if (smb_wka_lookup_name(gname) != NULL) 384dc20a302Sas200622 return (SMB_LGRP_WKSID); 385dc20a302Sas200622 386dc20a302Sas200622 /* Cannot rename to a well-known groups */ 3877f667e74Sjose borrego if (smb_wka_lookup_name(new_gname) != NULL) 388dc20a302Sas200622 return (SMB_LGRP_WKSID); 389dc20a302Sas200622 390dc20a302Sas200622 grp.sg_name = new_gname; 391dc20a302Sas200622 3929fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 3939fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 3949fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 395148c5f43SAlan Wright if (getgrnam(new_gname) == NULL) { 396148c5f43SAlan Wright if (smb_lgrp_pgrp_add(new_gname) != 0) { 397148c5f43SAlan Wright smb_lgrp_exit(); 398148c5f43SAlan Wright return (SMB_LGRP_POSIXCREATE_FAILED); 399148c5f43SAlan Wright } 400148c5f43SAlan Wright 401148c5f43SAlan Wright if (getgrnam(new_gname) == NULL) { 402148c5f43SAlan Wright smb_lgrp_exit(); 403148c5f43SAlan Wright return (SMB_LGRP_NOT_FOUND); 404148c5f43SAlan Wright } 405148c5f43SAlan Wright } 406148c5f43SAlan Wright 407dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORW); 408dc20a302Sas200622 rc = smb_lgrp_gtbl_update(db, gname, &grp, SMB_LGRP_GTBL_NAME); 409dc20a302Sas200622 smb_lgrp_db_close(db); 410dc20a302Sas200622 4119fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 412dc20a302Sas200622 return (rc); 413dc20a302Sas200622 } 414dc20a302Sas200622 415dc20a302Sas200622 /* 416dc20a302Sas200622 * smb_lgrp_delete 417dc20a302Sas200622 * 418dc20a302Sas200622 * Deletes the specified local group. 419dc20a302Sas200622 */ 420dc20a302Sas200622 int 421dc20a302Sas200622 smb_lgrp_delete(char *gname) 422dc20a302Sas200622 { 423dc20a302Sas200622 sqlite *db; 424dc20a302Sas200622 int rc; 425dc20a302Sas200622 426fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 427dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 428dc20a302Sas200622 429dc20a302Sas200622 /* Cannot remove a built-in group */ 4307f667e74Sjose borrego if (smb_wka_lookup_name(gname) != NULL) 431dc20a302Sas200622 return (SMB_LGRP_WKSID); 432dc20a302Sas200622 43396a62adaSjoyce mcintosh 43496a62adaSjoyce mcintosh if (!smb_lgrp_exists(gname)) 43596a62adaSjoyce mcintosh return (SMB_LGRP_NOT_FOUND); 43696a62adaSjoyce mcintosh 4379fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 4389fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 4399fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 440dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORW); 441dc20a302Sas200622 rc = smb_lgrp_gtbl_delete(db, gname); 442dc20a302Sas200622 smb_lgrp_db_close(db); 443dc20a302Sas200622 4449fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 445dc20a302Sas200622 return (rc); 446dc20a302Sas200622 } 447dc20a302Sas200622 448dc20a302Sas200622 /* 449dc20a302Sas200622 * smb_lgrp_setcmnt 450dc20a302Sas200622 * 451dc20a302Sas200622 * Sets the description for the given group 452dc20a302Sas200622 */ 453dc20a302Sas200622 int 454dc20a302Sas200622 smb_lgrp_setcmnt(char *gname, char *cmnt) 455dc20a302Sas200622 { 456dc20a302Sas200622 smb_group_t grp; 457dc20a302Sas200622 sqlite *db; 458dc20a302Sas200622 int rc; 459dc20a302Sas200622 460fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 461dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 462dc20a302Sas200622 463dc20a302Sas200622 if (cmnt && (strlen(cmnt) > SMB_LGRP_COMMENT_MAX)) 464dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 465dc20a302Sas200622 466dc20a302Sas200622 grp.sg_cmnt = cmnt; 467dc20a302Sas200622 4689fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 4699fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 4709fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 471dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORW); 472dc20a302Sas200622 rc = smb_lgrp_gtbl_update(db, gname, &grp, SMB_LGRP_GTBL_CMNT); 473dc20a302Sas200622 smb_lgrp_db_close(db); 474dc20a302Sas200622 4759fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 476dc20a302Sas200622 return (rc); 477dc20a302Sas200622 } 478dc20a302Sas200622 479dc20a302Sas200622 /* 480dc20a302Sas200622 * smb_lgrp_getcmnt 481dc20a302Sas200622 * 482dc20a302Sas200622 * Obtain the description of the specified group 483dc20a302Sas200622 */ 484dc20a302Sas200622 int 485dc20a302Sas200622 smb_lgrp_getcmnt(char *gname, char **cmnt) 486dc20a302Sas200622 { 487dc20a302Sas200622 smb_group_t grp; 488dc20a302Sas200622 sqlite *db; 489dc20a302Sas200622 int rc; 490dc20a302Sas200622 491fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 492dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 493dc20a302Sas200622 494dc20a302Sas200622 if (cmnt == NULL) 495dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 496dc20a302Sas200622 4979fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 4989fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 4999fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 500dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORD); 501dc20a302Sas200622 rc = smb_lgrp_gtbl_lookup(db, SMB_LGRP_GTBL_NAME, &grp, 502dc20a302Sas200622 SMB_LGRP_INFO_CMNT, gname); 503dc20a302Sas200622 smb_lgrp_db_close(db); 5049fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 505dc20a302Sas200622 506dc20a302Sas200622 if (rc == SMB_LGRP_SUCCESS) { 507dc20a302Sas200622 *cmnt = grp.sg_cmnt; 508dc20a302Sas200622 grp.sg_cmnt = NULL; 509dc20a302Sas200622 smb_lgrp_free(&grp); 510dc20a302Sas200622 } 511dc20a302Sas200622 512dc20a302Sas200622 return (rc); 513dc20a302Sas200622 } 514dc20a302Sas200622 515dc20a302Sas200622 516dc20a302Sas200622 /* 517dc20a302Sas200622 * smb_lgrp_setpriv 518dc20a302Sas200622 * 519dc20a302Sas200622 * Enable/disable the specified privilge for the group 520dc20a302Sas200622 */ 521dc20a302Sas200622 int 522dc20a302Sas200622 smb_lgrp_setpriv(char *gname, uint8_t priv_lid, boolean_t enable) 523dc20a302Sas200622 { 524dc20a302Sas200622 sqlite *db; 525dc20a302Sas200622 int rc; 526dc20a302Sas200622 527fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 528dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 529dc20a302Sas200622 530dc20a302Sas200622 if ((priv_lid < SE_MIN_LUID) || (priv_lid > SE_MAX_LUID)) 531dc20a302Sas200622 return (SMB_LGRP_NO_SUCH_PRIV); 532dc20a302Sas200622 5339fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 5349fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 5359fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 536dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORW); 537dc20a302Sas200622 rc = smb_lgrp_gtbl_update_plist(db, gname, priv_lid, enable); 538dc20a302Sas200622 smb_lgrp_db_close(db); 5399fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 540dc20a302Sas200622 541dc20a302Sas200622 if (enable) { 542dc20a302Sas200622 if (rc == SMB_LGRP_PRIV_HELD) 543dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 544dc20a302Sas200622 } else { 545dc20a302Sas200622 if (rc == SMB_LGRP_PRIV_NOT_HELD) 546dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 547dc20a302Sas200622 } 548dc20a302Sas200622 549dc20a302Sas200622 return (rc); 550dc20a302Sas200622 } 551dc20a302Sas200622 552dc20a302Sas200622 /* 553dc20a302Sas200622 * smb_lgrp_getpriv 554dc20a302Sas200622 * 555dc20a302Sas200622 * Obtain the status of the specified privilge for the group 556dc20a302Sas200622 */ 557dc20a302Sas200622 int 558dc20a302Sas200622 smb_lgrp_getpriv(char *gname, uint8_t priv_lid, boolean_t *enable) 559dc20a302Sas200622 { 560dc20a302Sas200622 sqlite *db; 561dc20a302Sas200622 smb_group_t grp; 562dc20a302Sas200622 int rc; 563dc20a302Sas200622 564fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 565dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 566dc20a302Sas200622 567dc20a302Sas200622 if ((priv_lid < SE_MIN_LUID) || (priv_lid > SE_MAX_LUID)) 568dc20a302Sas200622 return (SMB_LGRP_NO_SUCH_PRIV); 569dc20a302Sas200622 5709fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 5719fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 5729fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 573dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORD); 574dc20a302Sas200622 rc = smb_lgrp_gtbl_lookup(db, SMB_LGRP_GTBL_NAME, &grp, 575dc20a302Sas200622 SMB_LGRP_INFO_PRIV, gname); 576dc20a302Sas200622 smb_lgrp_db_close(db); 5779fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 578dc20a302Sas200622 579dc20a302Sas200622 if (rc == SMB_LGRP_SUCCESS) { 580dc20a302Sas200622 *enable = (smb_privset_query(grp.sg_privs, priv_lid) == 1); 581dc20a302Sas200622 smb_lgrp_free(&grp); 582dc20a302Sas200622 } 583dc20a302Sas200622 584dc20a302Sas200622 return (rc); 585dc20a302Sas200622 } 586dc20a302Sas200622 587dc20a302Sas200622 /* 588dc20a302Sas200622 * smb_lgrp_add_member 589dc20a302Sas200622 * 590dc20a302Sas200622 * Add the given account to the specified group as its member. 591dc20a302Sas200622 */ 592dc20a302Sas200622 int 5936537f381Sas200622 smb_lgrp_add_member(char *gname, smb_sid_t *msid, uint16_t sid_type) 594dc20a302Sas200622 { 595dc20a302Sas200622 sqlite *db; 596dc20a302Sas200622 smb_gsid_t mid; 597dc20a302Sas200622 int rc; 598dc20a302Sas200622 599fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 600dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 601dc20a302Sas200622 6026537f381Sas200622 if (!smb_sid_isvalid(msid)) 603dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 604dc20a302Sas200622 605dc20a302Sas200622 if (!smb_lgrp_chkmember(sid_type)) 606dc20a302Sas200622 return (SMB_LGRP_INVALID_MEMBER); 607dc20a302Sas200622 608dc20a302Sas200622 mid.gs_sid = msid; 609dc20a302Sas200622 mid.gs_type = sid_type; 610dc20a302Sas200622 6119fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 6129fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 6139fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 614dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORW); 615dc20a302Sas200622 rc = smb_lgrp_gtbl_update_mlist(db, gname, &mid, SMB_LGRP_DB_ADDMEMBER); 616dc20a302Sas200622 smb_lgrp_db_close(db); 617dc20a302Sas200622 6189fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 619dc20a302Sas200622 return (rc); 620dc20a302Sas200622 } 621dc20a302Sas200622 622dc20a302Sas200622 /* 623dc20a302Sas200622 * smb_lgrp_del_member 624dc20a302Sas200622 * 625dc20a302Sas200622 * Delete the specified member from the given group. 626dc20a302Sas200622 */ 627dc20a302Sas200622 int 6286537f381Sas200622 smb_lgrp_del_member(char *gname, smb_sid_t *msid, uint16_t sid_type) 629dc20a302Sas200622 { 630dc20a302Sas200622 sqlite *db; 631dc20a302Sas200622 smb_gsid_t mid; 632dc20a302Sas200622 int rc; 633dc20a302Sas200622 634fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 635dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 636dc20a302Sas200622 6376537f381Sas200622 if (!smb_sid_isvalid(msid)) 638dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 639dc20a302Sas200622 640dc20a302Sas200622 mid.gs_sid = msid; 641dc20a302Sas200622 mid.gs_type = sid_type; 642dc20a302Sas200622 6439fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 6449fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 6459fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 646dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORW); 647dc20a302Sas200622 rc = smb_lgrp_gtbl_update_mlist(db, gname, &mid, SMB_LGRP_DB_DELMEMBER); 648dc20a302Sas200622 smb_lgrp_db_close(db); 649dc20a302Sas200622 6509fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 651dc20a302Sas200622 return (rc); 652dc20a302Sas200622 } 653dc20a302Sas200622 654dc20a302Sas200622 /* 655dc20a302Sas200622 * smb_lgrp_getbyname 656dc20a302Sas200622 * 657dc20a302Sas200622 * Retrieves the information of the group specified by 658dc20a302Sas200622 * the given name. 659dc20a302Sas200622 * 660dc20a302Sas200622 * Note that this function doesn't allocate the group 661dc20a302Sas200622 * structure itself only the fields, so the given grp 662dc20a302Sas200622 * pointer has to point to a group structure. 663dc20a302Sas200622 * Caller must free the allocated memories for the fields 664dc20a302Sas200622 * by calling smb_lgrp_free(). 665dc20a302Sas200622 */ 666dc20a302Sas200622 int 667dc20a302Sas200622 smb_lgrp_getbyname(char *gname, smb_group_t *grp) 668dc20a302Sas200622 { 669dc20a302Sas200622 sqlite *db; 670dc20a302Sas200622 int rc; 671dc20a302Sas200622 672fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 673dc20a302Sas200622 return (SMB_LGRP_INVALID_NAME); 674dc20a302Sas200622 6759fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 6769fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 6779fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 678dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORD); 679dc20a302Sas200622 rc = smb_lgrp_gtbl_lookup(db, SMB_LGRP_GTBL_NAME, grp, 680dc20a302Sas200622 SMB_LGRP_INFO_ALL, gname); 681dc20a302Sas200622 smb_lgrp_db_close(db); 682dc20a302Sas200622 6839fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 684dc20a302Sas200622 return (rc); 685dc20a302Sas200622 } 686dc20a302Sas200622 687dc20a302Sas200622 /* 688dc20a302Sas200622 * smb_lgrp_getbyrid 689dc20a302Sas200622 * 690dc20a302Sas200622 * Retrieves the information of the group specified by 691dc20a302Sas200622 * the given RID and domain type. 692dc20a302Sas200622 * 693dc20a302Sas200622 * Note that this function doesn't allocate the group 694dc20a302Sas200622 * structure itself only the fields, so the given grp 695dc20a302Sas200622 * pointer has to point to a group structure. 696dc20a302Sas200622 * Caller must free the allocated memories for the fields 697dc20a302Sas200622 * by calling smb_lgrp_free(). 698dc20a302Sas200622 * 699dc20a302Sas200622 * If grp is NULL no information would be returned. The 700dc20a302Sas200622 * return value of SMB_LGRP_SUCCESS will indicate that a 701dc20a302Sas200622 * group with the given information exists. 702dc20a302Sas200622 */ 703dc20a302Sas200622 int 7049fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_getbyrid(uint32_t rid, smb_domain_type_t domtype, smb_group_t *grp) 705dc20a302Sas200622 { 706dc20a302Sas200622 smb_group_t tmpgrp; 707dc20a302Sas200622 sqlite *db; 708dc20a302Sas200622 int infolvl = SMB_LGRP_INFO_ALL; 709dc20a302Sas200622 int rc; 710dc20a302Sas200622 7119fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 7129fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 7139fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 714dc20a302Sas200622 if (grp == NULL) { 715dc20a302Sas200622 grp = &tmpgrp; 716dc20a302Sas200622 infolvl = SMB_LGRP_INFO_NONE; 717dc20a302Sas200622 } 718dc20a302Sas200622 719dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORD); 720dc20a302Sas200622 rc = smb_lgrp_gtbl_lookup(db, SMB_LGRP_GTBL_SIDRID, grp, infolvl, 721dc20a302Sas200622 rid, domtype); 722dc20a302Sas200622 smb_lgrp_db_close(db); 723dc20a302Sas200622 7249fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 725dc20a302Sas200622 return (rc); 726dc20a302Sas200622 } 727dc20a302Sas200622 728dc20a302Sas200622 /* 729dc20a302Sas200622 * smb_lgrp_numbydomain 730dc20a302Sas200622 * 731dc20a302Sas200622 * Returns the number of groups in the given domain in the 732dc20a302Sas200622 * arg 'count' 733dc20a302Sas200622 */ 734dc20a302Sas200622 int 7359fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_numbydomain(smb_domain_type_t dom_type, int *count) 736dc20a302Sas200622 { 737dc20a302Sas200622 sqlite *db; 738dc20a302Sas200622 int dom_idx; 739dc20a302Sas200622 int rc; 740dc20a302Sas200622 741dc20a302Sas200622 switch (dom_type) { 7429fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States case SMB_DOMAIN_LOCAL: 743dc20a302Sas200622 dom_idx = SMB_LGRP_LOCAL_IDX; 744dc20a302Sas200622 break; 7459fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States case SMB_DOMAIN_BUILTIN: 746dc20a302Sas200622 dom_idx = SMB_LGRP_BUILTIN_IDX; 747dc20a302Sas200622 break; 748dc20a302Sas200622 default: 749dc20a302Sas200622 *count = 0; 750dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 751dc20a302Sas200622 } 752dc20a302Sas200622 7539fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 7549fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 7559fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 756dc20a302Sas200622 db = smb_lgrp_db_open(SMB_LGRP_DB_ORD); 757dc20a302Sas200622 rc = smb_lgrp_gtbl_count(db, dom_idx, count); 758dc20a302Sas200622 smb_lgrp_db_close(db); 759dc20a302Sas200622 7609fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 761dc20a302Sas200622 return (rc); 762dc20a302Sas200622 } 763dc20a302Sas200622 764dc20a302Sas200622 /* 765dc20a302Sas200622 * smb_lgrp_free 766dc20a302Sas200622 * 767dc20a302Sas200622 * Frees the allocated memory for the fields of the given 768dc20a302Sas200622 * group structure. Note that this function doesn't free 769dc20a302Sas200622 * the group itself. 770dc20a302Sas200622 */ 771dc20a302Sas200622 void 772dc20a302Sas200622 smb_lgrp_free(smb_group_t *grp) 773dc20a302Sas200622 { 774dc20a302Sas200622 int i; 775dc20a302Sas200622 776dc20a302Sas200622 if (grp == NULL) 777dc20a302Sas200622 return; 778dc20a302Sas200622 779dc20a302Sas200622 free(grp->sg_name); 780dc20a302Sas200622 free(grp->sg_cmnt); 7816537f381Sas200622 smb_sid_free(grp->sg_id.gs_sid); 782dc20a302Sas200622 smb_privset_free(grp->sg_privs); 783dc20a302Sas200622 784dc20a302Sas200622 for (i = 0; i < grp->sg_nmembers; i++) 7856537f381Sas200622 smb_sid_free(grp->sg_members[i].gs_sid); 786dc20a302Sas200622 free(grp->sg_members); 787dc20a302Sas200622 } 788dc20a302Sas200622 789dc20a302Sas200622 /* 790dc20a302Sas200622 * smb_lgrp_iteropen 791dc20a302Sas200622 * 792dc20a302Sas200622 * Initializes the given group iterator by opening 793dc20a302Sas200622 * the group database and creating a virtual machine 794dc20a302Sas200622 * for iteration. 795dc20a302Sas200622 */ 796dc20a302Sas200622 int 797dc20a302Sas200622 smb_lgrp_iteropen(smb_giter_t *iter) 798dc20a302Sas200622 { 799dc20a302Sas200622 char *sql; 800dc20a302Sas200622 char *errmsg = NULL; 801dc20a302Sas200622 int rc = SMB_LGRP_SUCCESS; 802dc20a302Sas200622 803dc20a302Sas200622 assert(iter); 804dc20a302Sas200622 8059fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 8069fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 8079fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 808dc20a302Sas200622 bzero(iter, sizeof (smb_giter_t)); 809dc20a302Sas200622 810dc20a302Sas200622 sql = sqlite_mprintf("SELECT * FROM groups"); 8119fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (sql == NULL) { 8129fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 813dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 8149fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 815dc20a302Sas200622 816dc20a302Sas200622 iter->sgi_db = smb_lgrp_db_open(SMB_LGRP_DB_ORD); 817dc20a302Sas200622 if (iter->sgi_db == NULL) { 818dc20a302Sas200622 sqlite_freemem(sql); 8199fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 820dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 821dc20a302Sas200622 } 822dc20a302Sas200622 823dc20a302Sas200622 rc = sqlite_compile(iter->sgi_db, sql, NULL, &iter->sgi_vm, &errmsg); 824dc20a302Sas200622 sqlite_freemem(sql); 825dc20a302Sas200622 826dc20a302Sas200622 if (rc != SQLITE_OK) { 827dc20a302Sas200622 syslog(LOG_DEBUG, "failed to create a VM (%s)", 828dc20a302Sas200622 NULL_MSGCHK(errmsg)); 829dc20a302Sas200622 rc = SMB_LGRP_DB_ERROR; 830dc20a302Sas200622 } 831dc20a302Sas200622 8329fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 833dc20a302Sas200622 return (rc); 834dc20a302Sas200622 } 835dc20a302Sas200622 836dc20a302Sas200622 /* 837dc20a302Sas200622 * smb_lgrp_iterclose 838dc20a302Sas200622 * 839dc20a302Sas200622 * Closes the given group iterator. 840dc20a302Sas200622 */ 841dc20a302Sas200622 void 842dc20a302Sas200622 smb_lgrp_iterclose(smb_giter_t *iter) 843dc20a302Sas200622 { 844dc20a302Sas200622 char *errmsg = NULL; 845dc20a302Sas200622 int rc; 846dc20a302Sas200622 847dc20a302Sas200622 assert(iter); 848dc20a302Sas200622 8499fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 8509fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return; 8519fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 852dc20a302Sas200622 rc = sqlite_finalize(iter->sgi_vm, &errmsg); 853dc20a302Sas200622 if (rc != SQLITE_OK) { 854dc20a302Sas200622 syslog(LOG_DEBUG, "failed to destroy a VM (%s)", 855dc20a302Sas200622 NULL_MSGCHK(errmsg)); 856dc20a302Sas200622 } 857dc20a302Sas200622 858dc20a302Sas200622 smb_lgrp_db_close(iter->sgi_db); 8599fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 8609fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 8619fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 8629fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States /* 8639fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States * Returns B_TRUE if there has been an error during 8649fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States * iteration. 8659fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States */ 8669fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States boolean_t 8679fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_itererror(smb_giter_t *iter) 8689fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { 8699fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (iter->sgi_nerr != 0); 870dc20a302Sas200622 } 871dc20a302Sas200622 872dc20a302Sas200622 /* 873dc20a302Sas200622 * smb_lgrp_iterate 874dc20a302Sas200622 * 875dc20a302Sas200622 * Iterate through group database 876dc20a302Sas200622 * Group information is returned in provided group structure. 877dc20a302Sas200622 * 878dc20a302Sas200622 * Note that this function doesn't allocate the group 879dc20a302Sas200622 * structure itself only the fields, so the given grp 880dc20a302Sas200622 * pointer has to point to a group structure. 881dc20a302Sas200622 * Caller must free the allocated memories for the fields 882dc20a302Sas200622 * by calling smb_lgrp_free(). 883dc20a302Sas200622 */ 884dc20a302Sas200622 int 885dc20a302Sas200622 smb_lgrp_iterate(smb_giter_t *iter, smb_group_t *grp) 886dc20a302Sas200622 { 887dc20a302Sas200622 const char **values; 888dc20a302Sas200622 int ncol; 889dc20a302Sas200622 int rc; 890dc20a302Sas200622 int i; 891dc20a302Sas200622 892dc20a302Sas200622 if (iter->sgi_vm == NULL || iter->sgi_db == NULL) 893dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 894dc20a302Sas200622 8959fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_lgrp_enter()) 8969fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_OFFLINE); 8979fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 8989fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States for (;;) { 899dc20a302Sas200622 bzero(grp, sizeof (smb_group_t)); 900dc20a302Sas200622 rc = sqlite_step(iter->sgi_vm, &ncol, &values, NULL); 9019fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (rc == SQLITE_DONE) { 9029fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 903dc20a302Sas200622 return (SMB_LGRP_NO_MORE); 9049fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 905dc20a302Sas200622 9069fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (rc != SQLITE_ROW) { 9079fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 908dc20a302Sas200622 return (SMB_LGRP_DBEXEC_FAILED); 9099fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 910dc20a302Sas200622 9119fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (ncol != SMB_LGRP_GTBL_NCOL) { 9129fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 913dc20a302Sas200622 return (SMB_LGRP_DB_ERROR); 914dc20a302Sas200622 } 915dc20a302Sas200622 9169fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States for (i = 0; i < ncol; i++) { 9179fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (values[i] == NULL) { 9189fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 9199fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (SMB_LGRP_DB_ERROR); 9209fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 9219fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 9229fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 9239fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States rc = smb_lgrp_decode(grp, (char **)values, SMB_LGRP_INFO_ALL, 9249fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States iter->sgi_db); 9259fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (rc == SMB_LGRP_SUCCESS) 9269fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States break; 9279fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 9289fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States iter->sgi_nerr++; 9299fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States syslog(LOG_ERR, "smb_lgrp_iterate: %s", smb_lgrp_strerror(rc)); 9309fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 9319fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 9329fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(); 9339fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (rc); 9349fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 935dc20a302Sas200622 } 936dc20a302Sas200622 937dc20a302Sas200622 /* 938dc20a302Sas200622 * smb_lgrp_is_member 939dc20a302Sas200622 * 940dc20a302Sas200622 * Check to see if the specified account is a member of 941dc20a302Sas200622 * the given group. 942dc20a302Sas200622 */ 943dc20a302Sas200622 boolean_t 9446537f381Sas200622 smb_lgrp_is_member(smb_group_t *grp, smb_sid_t *sid) 945dc20a302Sas200622 { 946dc20a302Sas200622 int i; 947dc20a302Sas200622 948dc20a302Sas200622 if (grp == NULL || grp->sg_members == NULL || sid == NULL) 949dc20a302Sas200622 return (B_FALSE); 950dc20a302Sas200622 951dc20a302Sas200622 for (i = 0; i < grp->sg_nmembers; i++) { 9526537f381Sas200622 if (smb_sid_cmp(grp->sg_members[i].gs_sid, sid)) 953dc20a302Sas200622 return (B_TRUE); 954dc20a302Sas200622 } 955dc20a302Sas200622 956dc20a302Sas200622 return (B_FALSE); 957dc20a302Sas200622 } 958dc20a302Sas200622 959dc20a302Sas200622 /* 960dc20a302Sas200622 * smb_lgrp_strerror 961dc20a302Sas200622 * 962dc20a302Sas200622 * Returns a text for the given group error code. 963dc20a302Sas200622 */ 964dc20a302Sas200622 char * 9659fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_strerror(int errnum) 966dc20a302Sas200622 { 9679fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States int i; 9689fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States int nerr = (sizeof (errtab) / sizeof (errtab[0])); 9699fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 9709fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States for (i = 0; i < nerr; ++i) { 9719fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (errnum == errtab[i].errnum) 9729fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (errtab[i].errmsg); 973dc20a302Sas200622 } 974dc20a302Sas200622 9759fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return ("unknown local group error"); 976dc20a302Sas200622 } 977dc20a302Sas200622 978dc20a302Sas200622 /* 979c5866007SKeyur Desai * smb_lgrp_err_to_ntstatus 980c5866007SKeyur Desai * 981c5866007SKeyur Desai * This routine maps Local group operation errors to NT Status error codes. 982c5866007SKeyur Desai */ 983c5866007SKeyur Desai uint32_t 984c5866007SKeyur Desai smb_lgrp_err_to_ntstatus(uint32_t lgrp_err) 985c5866007SKeyur Desai { 986c5866007SKeyur Desai int i; 987c5866007SKeyur Desai static struct err_map { 988c5866007SKeyur Desai uint32_t lgrp_err; 989c5866007SKeyur Desai uint32_t nt_status; 990c5866007SKeyur Desai } err_map[] = { 991c5866007SKeyur Desai { SMB_LGRP_SUCCESS, NT_STATUS_SUCCESS }, 992c5866007SKeyur Desai { SMB_LGRP_INVALID_ARG, NT_STATUS_INVALID_PARAMETER }, 993c5866007SKeyur Desai { SMB_LGRP_INVALID_MEMBER, NT_STATUS_INVALID_MEMBER }, 994c5866007SKeyur Desai { SMB_LGRP_INVALID_NAME, NT_STATUS_INVALID_PARAMETER }, 995c5866007SKeyur Desai { SMB_LGRP_NOT_FOUND, NT_STATUS_NO_SUCH_ALIAS }, 996c5866007SKeyur Desai { SMB_LGRP_EXISTS, NT_STATUS_ALIAS_EXISTS }, 997c5866007SKeyur Desai { SMB_LGRP_NO_SID, NT_STATUS_INVALID_SID }, 998c5866007SKeyur Desai { SMB_LGRP_NO_LOCAL_SID, NT_STATUS_INVALID_SID }, 999c5866007SKeyur Desai { SMB_LGRP_SID_NOTLOCAL, NT_STATUS_INVALID_SID }, 1000c5866007SKeyur Desai { SMB_LGRP_WKSID, NT_STATUS_INVALID_SID }, 1001c5866007SKeyur Desai { SMB_LGRP_NO_MEMORY, NT_STATUS_NO_MEMORY }, 1002c5866007SKeyur Desai { SMB_LGRP_DB_ERROR, NT_STATUS_INTERNAL_DB_ERROR }, 1003c5866007SKeyur Desai { SMB_LGRP_DBINIT_ERROR, NT_STATUS_INTERNAL_DB_ERROR }, 1004c5866007SKeyur Desai { SMB_LGRP_INTERNAL_ERROR, NT_STATUS_INTERNAL_ERROR }, 1005c5866007SKeyur Desai { SMB_LGRP_MEMBER_IN_GROUP, NT_STATUS_MEMBER_IN_ALIAS }, 1006c5866007SKeyur Desai { SMB_LGRP_MEMBER_NOT_IN_GROUP, NT_STATUS_MEMBER_NOT_IN_ALIAS }, 1007c5866007SKeyur Desai { SMB_LGRP_NO_SUCH_PRIV, NT_STATUS_NO_SUCH_PRIVILEGE }, 1008c5866007SKeyur Desai { SMB_LGRP_NO_SUCH_DOMAIN, NT_STATUS_NO_SUCH_DOMAIN }, 1009c5866007SKeyur Desai { SMB_LGRP_PRIV_HELD, NT_STATUS_SUCCESS }, 1010c5866007SKeyur Desai { SMB_LGRP_PRIV_NOT_HELD, NT_STATUS_PRIVILEGE_NOT_HELD }, 1011c5866007SKeyur Desai { SMB_LGRP_BAD_DATA, NT_STATUS_DATA_ERROR }, 1012148c5f43SAlan Wright { SMB_LGRP_NO_MORE, NT_STATUS_NO_MORE_ENTRIES }, 1013c5866007SKeyur Desai { SMB_LGRP_DBOPEN_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1014c5866007SKeyur Desai { SMB_LGRP_DBEXEC_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1015c5866007SKeyur Desai { SMB_LGRP_DBINIT_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1016c5866007SKeyur Desai { SMB_LGRP_DOMLKP_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1017c5866007SKeyur Desai { SMB_LGRP_DOMINS_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1018c5866007SKeyur Desai { SMB_LGRP_INSERT_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1019c5866007SKeyur Desai { SMB_LGRP_DELETE_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1020c5866007SKeyur Desai { SMB_LGRP_UPDATE_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1021c5866007SKeyur Desai { SMB_LGRP_LOOKUP_FAILED, NT_STATUS_INTERNAL_DB_ERROR }, 1022c5866007SKeyur Desai { SMB_LGRP_NOT_SUPPORTED, NT_STATUS_NOT_SUPPORTED }, 1023148c5f43SAlan Wright { SMB_LGRP_OFFLINE, NT_STATUS_INTERNAL_ERROR }, 1024148c5f43SAlan Wright { SMB_LGRP_POSIXCREATE_FAILED, NT_STATUS_UNSUCCESSFUL } 1025c5866007SKeyur Desai }; 1026c5866007SKeyur Desai 1027c5866007SKeyur Desai for (i = 0; i < sizeof (err_map)/sizeof (err_map[0]); ++i) { 1028c5866007SKeyur Desai if (err_map[i].lgrp_err == lgrp_err) 1029c5866007SKeyur Desai return (err_map[i].nt_status); 1030c5866007SKeyur Desai } 1031c5866007SKeyur Desai 1032c5866007SKeyur Desai return (NT_STATUS_INTERNAL_ERROR); 1033c5866007SKeyur Desai } 1034c5866007SKeyur Desai 1035c5866007SKeyur Desai /* 1036dc20a302Sas200622 * smb_lgrp_chkmember 1037dc20a302Sas200622 * 1038dc20a302Sas200622 * Determines valid account types for being member of 103936a00406SGordon Ross * a local group. We really have no business trying to 104036a00406SGordon Ross * keep track of the "type" of SIDs in a group, so just 104136a00406SGordon Ross * validate that the SID type is a known enum value. 1042dc20a302Sas200622 */ 1043dc20a302Sas200622 static boolean_t 1044dc20a302Sas200622 smb_lgrp_chkmember(uint16_t sid_type) 1045dc20a302Sas200622 { 104636a00406SGordon Ross switch (sid_type) { 104736a00406SGordon Ross case SidTypeNull: 104836a00406SGordon Ross case SidTypeUser: 104936a00406SGordon Ross case SidTypeGroup: 105036a00406SGordon Ross case SidTypeAlias: 105136a00406SGordon Ross case SidTypeWellKnownGroup: 105236a00406SGordon Ross case SidTypeDeletedAccount: 105336a00406SGordon Ross case SidTypeInvalid: 105436a00406SGordon Ross case SidTypeUnknown: 105536a00406SGordon Ross return (B_TRUE); 105636a00406SGordon Ross } 105736a00406SGordon Ross return (B_FALSE); 1058dc20a302Sas200622 } 1059dc20a302Sas200622 1060dc20a302Sas200622 /* 1061dc20a302Sas200622 * smb_lgrp_start 1062dc20a302Sas200622 * 1063dc20a302Sas200622 * Initializes the library private global variables. 10649fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States * Create the database, if it doesn't exist, and add 10659fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States * the predefined builtin groups. 1066dc20a302Sas200622 */ 1067dc20a302Sas200622 int 1068dc20a302Sas200622 smb_lgrp_start(void) 1069dc20a302Sas200622 { 10709fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States static char *builtin[] = { 10719fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States "Administrators", 10729fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States "Backup Operators", 10739fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States "Power Users" 10749fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States }; 10756537f381Sas200622 smb_wka_t *wka; 10769fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States char *localsid; 10779fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States int i, rc; 10789fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States int ngrp = sizeof (builtin) / sizeof (builtin[0]); 1079dc20a302Sas200622 10809fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_lock(&smb_localgrp.lg_mutex); 10819fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 10829fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if ((localsid = smb_config_get_localsid()) == NULL) { 10839fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_unlock(&smb_localgrp.lg_mutex); 1084dc20a302Sas200622 return (SMB_LGRP_NO_LOCAL_SID); 1085dc20a302Sas200622 } 1086dc20a302Sas200622 10879fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_localgrp.lg_machine_sid = smb_sid_fromstr(localsid); 10889fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States free(localsid); 10899fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 10909fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_sid_isvalid(smb_localgrp.lg_machine_sid)) { 10919fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States free(smb_localgrp.lg_machine_sid); 10929fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_localgrp.lg_machine_sid = NULL; 10939fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_unlock(&smb_localgrp.lg_mutex); 1094dc20a302Sas200622 return (SMB_LGRP_NO_LOCAL_SID); 1095dc20a302Sas200622 } 1096dc20a302Sas200622 1097dc20a302Sas200622 rc = smb_lgrp_db_init(); 1098dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) { 10999fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States free(smb_localgrp.lg_machine_sid); 11009fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_localgrp.lg_machine_sid = NULL; 11019fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_unlock(&smb_localgrp.lg_mutex); 1102dc20a302Sas200622 return (rc); 1103dc20a302Sas200622 } 1104dc20a302Sas200622 11059fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_localgrp.lg_online = B_TRUE; 11069fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_unlock(&smb_localgrp.lg_mutex); 11079fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 1108dc20a302Sas200622 for (i = 0; i < ngrp; i++) { 1109c28afb19SYuri Pankov char *tname; 1110c28afb19SYuri Pankov 11119fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if ((wka = smb_wka_lookup_name(builtin[i])) == NULL) 1112dc20a302Sas200622 continue; 11139fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 1114c28afb19SYuri Pankov if ((tname = strdup(wka->wka_name)) == NULL) 1115c28afb19SYuri Pankov return (SMB_LGRP_NO_MEMORY); 1116c28afb19SYuri Pankov if (!smb_lgrp_exists(tname)) { 1117c28afb19SYuri Pankov rc = smb_lgrp_add(tname, wka->wka_desc); 111829bd2886SAlan Wright if (rc != SMB_LGRP_SUCCESS) { 111929bd2886SAlan Wright syslog(LOG_DEBUG, "failed to add %s", 1120c28afb19SYuri Pankov tname); 112129bd2886SAlan Wright } 112229bd2886SAlan Wright } 1123c28afb19SYuri Pankov free(tname); 1124dc20a302Sas200622 } 1125dc20a302Sas200622 1126dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 1127dc20a302Sas200622 } 1128dc20a302Sas200622 1129dc20a302Sas200622 /* 1130dc20a302Sas200622 * smb_lgrp_stop 1131dc20a302Sas200622 * 1132dc20a302Sas200622 * Unintialize the library global private variables. 1133dc20a302Sas200622 */ 1134dc20a302Sas200622 void 1135dc20a302Sas200622 smb_lgrp_stop(void) 1136dc20a302Sas200622 { 11379fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_lock(&smb_localgrp.lg_mutex); 11389fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_localgrp.lg_online) 11399fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return; 11409fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11419fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_localgrp.lg_online = B_FALSE; 11429fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11439fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States while (smb_localgrp.lg_refcnt > 0) 11449fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) cond_wait(&smb_localgrp.lg_cv, &smb_localgrp.lg_mutex); 11459fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11469fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States free(smb_localgrp.lg_machine_sid); 11479fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_localgrp.lg_machine_sid = NULL; 11489fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_unlock(&smb_localgrp.lg_mutex); 11499fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 11509fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11519fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States static boolean_t 11529fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_enter(void) 11539fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { 11549fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States boolean_t status; 11559fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11569fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_lock(&smb_localgrp.lg_mutex); 11579fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11589fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States status = smb_localgrp.lg_online; 11599fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11609fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (smb_localgrp.lg_online) 11619fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States ++smb_localgrp.lg_refcnt; 11629fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11639fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_unlock(&smb_localgrp.lg_mutex); 11649fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (status); 11659fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 11669fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11679fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States static void 11689fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States smb_lgrp_exit(void) 11699fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States { 11709fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_lock(&smb_localgrp.lg_mutex); 11719fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States assert(smb_localgrp.lg_refcnt > 0); 11729fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11739fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if ((--smb_localgrp.lg_refcnt) == 0) 11749fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) cond_signal(&smb_localgrp.lg_cv); 11759fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States 11769fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (void) mutex_unlock(&smb_localgrp.lg_mutex); 1177dc20a302Sas200622 } 1178dc20a302Sas200622 1179dc20a302Sas200622 /* 1180dc20a302Sas200622 * smb_lgrp_db_open 1181dc20a302Sas200622 * 1182dc20a302Sas200622 * Opens group database with the given mode. 1183dc20a302Sas200622 */ 1184dc20a302Sas200622 static sqlite * 1185dc20a302Sas200622 smb_lgrp_db_open(int mode) 1186dc20a302Sas200622 { 1187dc20a302Sas200622 sqlite *db; 1188dc20a302Sas200622 char *errmsg = NULL; 1189dc20a302Sas200622 1190dc20a302Sas200622 db = sqlite_open(SMB_LGRP_DB_NAME, mode, &errmsg); 1191dc20a302Sas200622 if (db == NULL) { 1192dc20a302Sas200622 syslog(LOG_ERR, "failed to open group database (%s)", 1193dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1194dc20a302Sas200622 sqlite_freemem(errmsg); 1195dc20a302Sas200622 } 1196dc20a302Sas200622 1197dc20a302Sas200622 return (db); 1198dc20a302Sas200622 } 1199dc20a302Sas200622 1200dc20a302Sas200622 /* 1201dc20a302Sas200622 * smb_lgrp_db_close 1202dc20a302Sas200622 * 1203dc20a302Sas200622 * Closes the given database handle 1204dc20a302Sas200622 */ 1205dc20a302Sas200622 static void 1206dc20a302Sas200622 smb_lgrp_db_close(sqlite *db) 1207dc20a302Sas200622 { 1208dc20a302Sas200622 if (db) { 1209dc20a302Sas200622 sqlite_close(db); 1210dc20a302Sas200622 } 1211dc20a302Sas200622 } 1212dc20a302Sas200622 1213dc20a302Sas200622 /* 1214dc20a302Sas200622 * smb_lgrp_db_init 1215dc20a302Sas200622 * 1216dc20a302Sas200622 * Creates the group database based on the defined SQL statement. 1217dc20a302Sas200622 * It also initializes db_info and domain tables. 1218dc20a302Sas200622 */ 1219dc20a302Sas200622 static int 1220dc20a302Sas200622 smb_lgrp_db_init(void) 1221dc20a302Sas200622 { 1222dc20a302Sas200622 int dbrc = SQLITE_OK; 1223dc20a302Sas200622 int rc = SMB_LGRP_SUCCESS; 1224dc20a302Sas200622 sqlite *db = NULL; 1225dc20a302Sas200622 char *errmsg = NULL; 1226dc20a302Sas200622 1227dc20a302Sas200622 db = sqlite_open(SMB_LGRP_DB_NAME, 0600, &errmsg); 1228dc20a302Sas200622 if (db == NULL) { 1229dc20a302Sas200622 syslog(LOG_ERR, "failed to create group database (%s)", 1230dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1231dc20a302Sas200622 sqlite_freemem(errmsg); 1232dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1233dc20a302Sas200622 } 1234dc20a302Sas200622 1235dc20a302Sas200622 sqlite_busy_timeout(db, SMB_LGRP_DB_TIMEOUT); 1236dc20a302Sas200622 dbrc = sqlite_exec(db, "BEGIN TRANSACTION;", NULL, NULL, &errmsg); 1237dc20a302Sas200622 if (dbrc != SQLITE_OK) { 1238dc20a302Sas200622 syslog(LOG_DEBUG, "failed to begin database transaction (%s)", 1239dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1240dc20a302Sas200622 sqlite_freemem(errmsg); 1241dc20a302Sas200622 sqlite_close(db); 1242dc20a302Sas200622 return (SMB_LGRP_DBEXEC_FAILED); 1243dc20a302Sas200622 } 1244dc20a302Sas200622 1245dc20a302Sas200622 switch (sqlite_exec(db, SMB_LGRP_DB_SQL, NULL, NULL, &errmsg)) { 1246dc20a302Sas200622 case SQLITE_ERROR: 1247dc20a302Sas200622 /* 1248dc20a302Sas200622 * This is the normal situation: CREATE probably failed because 1249dc20a302Sas200622 * tables already exist. It may indicate an error in SQL as well 1250dc20a302Sas200622 * but we cannot tell. 1251dc20a302Sas200622 */ 1252dc20a302Sas200622 sqlite_freemem(errmsg); 1253dc20a302Sas200622 dbrc = sqlite_exec(db, "ROLLBACK TRANSACTION", NULL, NULL, 1254dc20a302Sas200622 &errmsg); 1255dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 1256dc20a302Sas200622 break; 1257dc20a302Sas200622 1258dc20a302Sas200622 case SQLITE_OK: 1259dc20a302Sas200622 dbrc = sqlite_exec(db, "COMMIT TRANSACTION", NULL, NULL, 1260dc20a302Sas200622 &errmsg); 1261dc20a302Sas200622 if (dbrc != SQLITE_OK) 1262dc20a302Sas200622 break; 1263dc20a302Sas200622 rc = smb_lgrp_dtbl_insert(db, NT_BUILTIN_DOMAIN_SIDSTR, 1264dc20a302Sas200622 NULL); 1265dc20a302Sas200622 if (rc == SMB_LGRP_SUCCESS) 1266dc20a302Sas200622 rc = smb_lgrp_db_setinfo(db); 1267dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) { 1268dc20a302Sas200622 (void) sqlite_close(db); 1269dc20a302Sas200622 (void) unlink(SMB_LGRP_DB_NAME); 1270dc20a302Sas200622 return (rc); 1271dc20a302Sas200622 } 1272dc20a302Sas200622 break; 1273dc20a302Sas200622 1274dc20a302Sas200622 default: 1275dc20a302Sas200622 syslog(LOG_ERR, 1276dc20a302Sas200622 "failed to initialize group database (%s)", errmsg); 1277dc20a302Sas200622 sqlite_freemem(errmsg); 1278dc20a302Sas200622 dbrc = sqlite_exec(db, "ROLLBACK TRANSACTION", NULL, NULL, 1279dc20a302Sas200622 &errmsg); 1280dc20a302Sas200622 rc = SMB_LGRP_DBINIT_FAILED; 1281dc20a302Sas200622 break; 1282dc20a302Sas200622 } 1283dc20a302Sas200622 1284dc20a302Sas200622 if (dbrc != SQLITE_OK) { 1285dc20a302Sas200622 /* this is bad - database may be left in a locked state */ 1286dc20a302Sas200622 syslog(LOG_DEBUG, "failed to close a transaction (%s)", 1287dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1288dc20a302Sas200622 sqlite_freemem(errmsg); 1289dc20a302Sas200622 } 1290dc20a302Sas200622 1291dc20a302Sas200622 (void) sqlite_close(db); 1292dc20a302Sas200622 return (rc); 1293dc20a302Sas200622 } 1294dc20a302Sas200622 1295dc20a302Sas200622 /* 1296dc20a302Sas200622 * smb_lgrp_gtbl_lookup 1297dc20a302Sas200622 * 1298dc20a302Sas200622 * This is a flexible lookup function for the group database. 1299dc20a302Sas200622 * The key type can be specified by the 'key' arg and the actual key 1300dc20a302Sas200622 * values can be passed after the 'infolvl' arg. 'infolvl' arg specifies 1301dc20a302Sas200622 * what information items for the specified group is needed. 1302dc20a302Sas200622 * 1303dc20a302Sas200622 * Note that the function assumes the given key is unique and only 1304dc20a302Sas200622 * specifies one or 0 group. The keys that are supported now are 1305dc20a302Sas200622 * the group name and the group SID 1306dc20a302Sas200622 * 1307dc20a302Sas200622 * Note that this function doesn't allocate the group 1308dc20a302Sas200622 * structure itself only the fields, so the given grp 1309dc20a302Sas200622 * pointer has to point to a group structure. 1310dc20a302Sas200622 * Caller must free the allocated memories for the fields 1311dc20a302Sas200622 * by calling smb_lgrp_free(). 1312dc20a302Sas200622 */ 1313dc20a302Sas200622 static int 1314dc20a302Sas200622 smb_lgrp_gtbl_lookup(sqlite *db, int key, smb_group_t *grp, int infolvl, ...) 1315dc20a302Sas200622 { 1316dc20a302Sas200622 char *errmsg = NULL; 1317dc20a302Sas200622 char *sql; 1318dc20a302Sas200622 char **result; 1319dc20a302Sas200622 int nrow, ncol; 1320dc20a302Sas200622 int rc, dom_idx; 1321c8ec8eeaSjose borrego smb_group_t grpkey; 1322dc20a302Sas200622 va_list ap; 1323dc20a302Sas200622 1324dc20a302Sas200622 if (db == NULL) 1325dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1326dc20a302Sas200622 1327dc20a302Sas200622 bzero(grp, sizeof (smb_group_t)); 1328dc20a302Sas200622 va_start(ap, infolvl); 1329dc20a302Sas200622 1330dc20a302Sas200622 switch (key) { 1331dc20a302Sas200622 case SMB_LGRP_GTBL_NAME: 1332c8ec8eeaSjose borrego grpkey.sg_name = va_arg(ap, char *); 1333dc20a302Sas200622 sql = sqlite_mprintf("SELECT * FROM groups WHERE name = '%s'", 1334c8ec8eeaSjose borrego grpkey.sg_name); 1335dc20a302Sas200622 break; 1336dc20a302Sas200622 1337dc20a302Sas200622 case SMB_LGRP_GTBL_SIDRID: 1338c8ec8eeaSjose borrego grpkey.sg_rid = va_arg(ap, uint32_t); 13399fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States grpkey.sg_domain = va_arg(ap, smb_domain_type_t); 13409fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (grpkey.sg_domain == SMB_DOMAIN_LOCAL) { 1341c8ec8eeaSjose borrego dom_idx = SMB_LGRP_LOCAL_IDX; 1342c8ec8eeaSjose borrego /* need to map the given rid to a gid */ 1343c8ec8eeaSjose borrego rc = smb_lgrp_getgid(grpkey.sg_rid, 1344c8ec8eeaSjose borrego (gid_t *)&grpkey.sg_rid); 1345c8ec8eeaSjose borrego if (rc != SMB_LGRP_SUCCESS) { 1346c8ec8eeaSjose borrego va_end(ap); 1347c8ec8eeaSjose borrego return (rc); 1348c8ec8eeaSjose borrego } 1349c8ec8eeaSjose borrego } else { 1350c8ec8eeaSjose borrego dom_idx = SMB_LGRP_BUILTIN_IDX; 1351c8ec8eeaSjose borrego } 1352c8ec8eeaSjose borrego 1353dc20a302Sas200622 sql = sqlite_mprintf("SELECT * FROM groups " 1354dc20a302Sas200622 "WHERE (sid_idx = %d) AND (sid_rid = %u)", 1355c8ec8eeaSjose borrego dom_idx, grpkey.sg_rid); 1356dc20a302Sas200622 break; 1357dc20a302Sas200622 1358dc20a302Sas200622 default: 1359dc20a302Sas200622 va_end(ap); 1360dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 1361dc20a302Sas200622 } 1362dc20a302Sas200622 1363dc20a302Sas200622 va_end(ap); 1364dc20a302Sas200622 if (sql == NULL) 1365dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1366dc20a302Sas200622 1367dc20a302Sas200622 rc = sqlite_get_table(db, sql, &result, &nrow, &ncol, &errmsg); 1368dc20a302Sas200622 sqlite_freemem(sql); 1369dc20a302Sas200622 1370dc20a302Sas200622 if (rc != SQLITE_OK) { 1371dc20a302Sas200622 syslog(LOG_DEBUG, "failed to lookup (%s)", NULL_MSGCHK(errmsg)); 1372dc20a302Sas200622 sqlite_freemem(errmsg); 1373dc20a302Sas200622 return (SMB_LGRP_LOOKUP_FAILED); 1374dc20a302Sas200622 } 1375dc20a302Sas200622 1376dc20a302Sas200622 if (nrow == 0) { 1377dc20a302Sas200622 /* group not found */ 1378dc20a302Sas200622 sqlite_free_table(result); 1379dc20a302Sas200622 return (SMB_LGRP_NOT_FOUND); 1380dc20a302Sas200622 } 1381dc20a302Sas200622 1382dc20a302Sas200622 if (nrow != 1 || ncol != SMB_LGRP_GTBL_NCOL) { 1383dc20a302Sas200622 sqlite_free_table(result); 1384dc20a302Sas200622 return (SMB_LGRP_DB_ERROR); 1385dc20a302Sas200622 } 1386dc20a302Sas200622 1387dc20a302Sas200622 rc = smb_lgrp_decode(grp, &result[SMB_LGRP_GTBL_NCOL], infolvl, db); 1388dc20a302Sas200622 sqlite_free_table(result); 1389dc20a302Sas200622 return (rc); 1390dc20a302Sas200622 } 1391dc20a302Sas200622 1392dc20a302Sas200622 /* 1393dc20a302Sas200622 * smb_lgrp_gtbl_exists 1394dc20a302Sas200622 * 1395dc20a302Sas200622 * Checks to see if the given group exists or not. 1396dc20a302Sas200622 */ 1397dc20a302Sas200622 static boolean_t 1398dc20a302Sas200622 smb_lgrp_gtbl_exists(sqlite *db, char *gname) 1399dc20a302Sas200622 { 1400dc20a302Sas200622 char *errmsg = NULL; 1401dc20a302Sas200622 char *sql; 1402dc20a302Sas200622 char **result; 1403dc20a302Sas200622 int nrow, ncol; 1404dc20a302Sas200622 int rc; 1405dc20a302Sas200622 1406dc20a302Sas200622 if (db == NULL) 1407dc20a302Sas200622 return (NULL); 1408dc20a302Sas200622 1409dc20a302Sas200622 sql = sqlite_mprintf("SELECT name FROM groups WHERE name = '%s'", 1410dc20a302Sas200622 gname); 1411dc20a302Sas200622 rc = sqlite_get_table(db, sql, &result, &nrow, &ncol, &errmsg); 1412dc20a302Sas200622 sqlite_freemem(sql); 1413dc20a302Sas200622 1414dc20a302Sas200622 if (rc != SQLITE_OK) { 1415dc20a302Sas200622 syslog(LOG_DEBUG, "failed to lookup %s (%s)", 1416dc20a302Sas200622 gname, NULL_MSGCHK(errmsg)); 1417dc20a302Sas200622 sqlite_freemem(errmsg); 1418dc20a302Sas200622 return (B_FALSE); 1419dc20a302Sas200622 } 1420dc20a302Sas200622 1421dc20a302Sas200622 sqlite_free_table(result); 1422dc20a302Sas200622 return (nrow != 0); 1423dc20a302Sas200622 } 1424dc20a302Sas200622 1425dc20a302Sas200622 /* 1426dc20a302Sas200622 * smb_lgrp_gtbl_count 1427dc20a302Sas200622 * 1428dc20a302Sas200622 * Counts the number of groups in the domain specified by 1429dc20a302Sas200622 * 'dom_idx' 1430dc20a302Sas200622 */ 1431dc20a302Sas200622 static int 1432dc20a302Sas200622 smb_lgrp_gtbl_count(sqlite *db, int dom_idx, int *count) 1433dc20a302Sas200622 { 1434dc20a302Sas200622 char *errmsg = NULL; 1435dc20a302Sas200622 char *sql; 1436dc20a302Sas200622 char **result; 1437dc20a302Sas200622 int nrow, ncol; 1438dc20a302Sas200622 int rc; 1439dc20a302Sas200622 1440dc20a302Sas200622 *count = 0; 1441dc20a302Sas200622 if (db == NULL) 1442dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1443dc20a302Sas200622 1444dc20a302Sas200622 sql = sqlite_mprintf("SELECT sid_idx FROM groups WHERE sid_idx = %d", 1445dc20a302Sas200622 dom_idx); 1446dc20a302Sas200622 rc = sqlite_get_table(db, sql, &result, &nrow, &ncol, &errmsg); 1447dc20a302Sas200622 sqlite_freemem(sql); 1448dc20a302Sas200622 1449dc20a302Sas200622 if (rc != SQLITE_OK) { 1450dc20a302Sas200622 syslog(LOG_DEBUG, "failed to count (%s)", NULL_MSGCHK(errmsg)); 1451dc20a302Sas200622 sqlite_freemem(errmsg); 1452dc20a302Sas200622 return (SMB_LGRP_LOOKUP_FAILED); 1453dc20a302Sas200622 } 1454dc20a302Sas200622 1455dc20a302Sas200622 sqlite_free_table(result); 1456faa1795aSjb150015 if (ncol > 1) 1457dc20a302Sas200622 return (SMB_LGRP_DB_ERROR); 1458dc20a302Sas200622 1459dc20a302Sas200622 *count = nrow; 1460dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 1461dc20a302Sas200622 } 1462dc20a302Sas200622 1463dc20a302Sas200622 /* 1464dc20a302Sas200622 * smb_lgrp_gtbl_insert 1465dc20a302Sas200622 * 1466dc20a302Sas200622 * Insert a record for the given group in the group database. 1467dc20a302Sas200622 * 1468dc20a302Sas200622 * NOTE: this function assumes that this group has no members 1469dc20a302Sas200622 * at this time. 1470dc20a302Sas200622 */ 1471dc20a302Sas200622 static int 1472dc20a302Sas200622 smb_lgrp_gtbl_insert(sqlite *db, smb_group_t *grp) 1473dc20a302Sas200622 { 1474dc20a302Sas200622 smb_lgpid_t privs[SE_MAX_LUID + 1]; 1475dc20a302Sas200622 smb_lgplist_t plist; 1476dc20a302Sas200622 char *errmsg = NULL; 1477dc20a302Sas200622 char *sql; 1478dc20a302Sas200622 int dom_idx; 1479dc20a302Sas200622 int rc; 1480dc20a302Sas200622 1481dc20a302Sas200622 if (db == NULL) 1482dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1483dc20a302Sas200622 14849fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States dom_idx = (grp->sg_domain == SMB_DOMAIN_LOCAL) 1485dc20a302Sas200622 ? SMB_LGRP_LOCAL_IDX : SMB_LGRP_BUILTIN_IDX; 1486dc20a302Sas200622 1487dc20a302Sas200622 plist.p_cnt = SE_MAX_LUID; 1488dc20a302Sas200622 plist.p_ids = privs; 1489dc20a302Sas200622 smb_lgrp_encode_privset(grp, &plist); 1490dc20a302Sas200622 1491dc20a302Sas200622 sql = sqlite_mprintf("INSERT INTO groups " 1492dc20a302Sas200622 "(name, sid_idx, sid_rid, sid_type, sid_attrs, comment, " 1493dc20a302Sas200622 "n_privs, privs, n_members, members) " 1494dc20a302Sas200622 "VALUES('%s', %u, %u, %u, %u, '%q', %u, '%q', %u, '%q')", 1495dc20a302Sas200622 grp->sg_name, dom_idx, grp->sg_rid, grp->sg_id.gs_type, 1496dc20a302Sas200622 grp->sg_attr, (grp->sg_cmnt) ? grp->sg_cmnt : "", 1497dc20a302Sas200622 plist.p_cnt, (char *)plist.p_ids, 0, ""); 1498dc20a302Sas200622 1499dc20a302Sas200622 if (sql == NULL) 1500dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1501dc20a302Sas200622 1502dc20a302Sas200622 rc = sqlite_exec(db, sql, NULL, NULL, &errmsg); 1503dc20a302Sas200622 sqlite_freemem(sql); 1504dc20a302Sas200622 1505dc20a302Sas200622 if (rc != SQLITE_OK) { 1506dc20a302Sas200622 syslog(LOG_DEBUG, "failed to insert %s (%s)", 1507dc20a302Sas200622 grp->sg_name, NULL_MSGCHK(errmsg)); 1508dc20a302Sas200622 sqlite_freemem(errmsg); 1509dc20a302Sas200622 rc = SMB_LGRP_INSERT_FAILED; 1510dc20a302Sas200622 } else { 1511dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 1512dc20a302Sas200622 } 1513dc20a302Sas200622 1514dc20a302Sas200622 return (rc); 1515dc20a302Sas200622 } 1516dc20a302Sas200622 1517dc20a302Sas200622 /* 1518dc20a302Sas200622 * smb_lgrp_gtbl_delete 1519dc20a302Sas200622 * 1520dc20a302Sas200622 * Removes the specified group from the database 1521dc20a302Sas200622 */ 1522dc20a302Sas200622 static int 1523dc20a302Sas200622 smb_lgrp_gtbl_delete(sqlite *db, char *gname) 1524dc20a302Sas200622 { 1525dc20a302Sas200622 char *errmsg = NULL; 1526dc20a302Sas200622 char *sql; 1527dc20a302Sas200622 int rc; 1528dc20a302Sas200622 1529dc20a302Sas200622 if (db == NULL) 1530dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1531dc20a302Sas200622 1532dc20a302Sas200622 sql = sqlite_mprintf("DELETE FROM groups WHERE name = '%s'", gname); 1533dc20a302Sas200622 if (sql == NULL) 1534dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1535dc20a302Sas200622 1536dc20a302Sas200622 rc = sqlite_exec(db, sql, NULL, NULL, &errmsg); 1537dc20a302Sas200622 sqlite_freemem(sql); 1538dc20a302Sas200622 1539dc20a302Sas200622 if (rc != SQLITE_OK) { 1540dc20a302Sas200622 syslog(LOG_DEBUG, "failed to delete %s (%s)", 1541dc20a302Sas200622 gname, NULL_MSGCHK(errmsg)); 1542dc20a302Sas200622 sqlite_freemem(errmsg); 1543dc20a302Sas200622 rc = SMB_LGRP_DELETE_FAILED; 1544dc20a302Sas200622 } else { 1545dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 1546dc20a302Sas200622 } 1547dc20a302Sas200622 1548dc20a302Sas200622 return (rc); 1549dc20a302Sas200622 } 1550dc20a302Sas200622 1551dc20a302Sas200622 /* 1552dc20a302Sas200622 * smb_lgrp_gtbl_update 1553dc20a302Sas200622 * 1554dc20a302Sas200622 * Updates the specified group information, the supported items 1555dc20a302Sas200622 * are group name and comment 1556dc20a302Sas200622 */ 1557dc20a302Sas200622 static int 1558dc20a302Sas200622 smb_lgrp_gtbl_update(sqlite *db, char *gname, smb_group_t *grp, int col_id) 1559dc20a302Sas200622 { 1560dc20a302Sas200622 char *errmsg = NULL; 1561dc20a302Sas200622 char *sql; 1562dc20a302Sas200622 int rc; 1563dc20a302Sas200622 1564dc20a302Sas200622 if (db == NULL) 1565dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1566dc20a302Sas200622 1567dc20a302Sas200622 /* UPDATE doesn't fail if gname doesn't exist */ 1568dc20a302Sas200622 if (!smb_lgrp_gtbl_exists(db, gname)) 1569dc20a302Sas200622 return (SMB_LGRP_NOT_FOUND); 1570dc20a302Sas200622 1571dc20a302Sas200622 switch (col_id) { 1572dc20a302Sas200622 case SMB_LGRP_GTBL_NAME: 1573dc20a302Sas200622 if (smb_lgrp_gtbl_exists(db, grp->sg_name)) 1574dc20a302Sas200622 return (SMB_LGRP_EXISTS); 1575dc20a302Sas200622 sql = sqlite_mprintf("UPDATE groups SET name = '%s' " 1576dc20a302Sas200622 "WHERE name = '%s'", grp->sg_name, gname); 1577dc20a302Sas200622 break; 1578dc20a302Sas200622 1579dc20a302Sas200622 case SMB_LGRP_GTBL_CMNT: 1580dc20a302Sas200622 sql = sqlite_mprintf("UPDATE groups SET comment = '%q' " 1581dc20a302Sas200622 "WHERE name = '%s'", grp->sg_cmnt, gname); 1582dc20a302Sas200622 break; 1583dc20a302Sas200622 1584dc20a302Sas200622 default: 1585dc20a302Sas200622 return (SMB_LGRP_INVALID_ARG); 1586dc20a302Sas200622 } 1587dc20a302Sas200622 1588dc20a302Sas200622 if (sql == NULL) 1589dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1590dc20a302Sas200622 1591dc20a302Sas200622 rc = sqlite_exec(db, sql, NULL, NULL, &errmsg); 1592dc20a302Sas200622 sqlite_freemem(sql); 1593dc20a302Sas200622 1594dc20a302Sas200622 if (rc != SQLITE_OK) { 1595dc20a302Sas200622 syslog(LOG_DEBUG, "failed to update %s (%s)", 1596dc20a302Sas200622 gname, NULL_MSGCHK(errmsg)); 1597dc20a302Sas200622 sqlite_freemem(errmsg); 1598dc20a302Sas200622 rc = SMB_LGRP_UPDATE_FAILED; 1599dc20a302Sas200622 } else { 1600dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 1601dc20a302Sas200622 } 1602dc20a302Sas200622 1603dc20a302Sas200622 return (rc); 1604dc20a302Sas200622 } 1605dc20a302Sas200622 1606dc20a302Sas200622 /* 1607dc20a302Sas200622 * smb_lgrp_gtbl_update_mlist 1608dc20a302Sas200622 * 1609dc20a302Sas200622 * Adds/removes the specified member from the member list of the 1610dc20a302Sas200622 * given group 1611dc20a302Sas200622 */ 1612dc20a302Sas200622 static int 1613dc20a302Sas200622 smb_lgrp_gtbl_update_mlist(sqlite *db, char *gname, smb_gsid_t *member, 1614dc20a302Sas200622 int flags) 1615dc20a302Sas200622 { 1616dc20a302Sas200622 smb_lgmlist_t new_members; 1617dc20a302Sas200622 smb_lgmlist_t members; 1618dc20a302Sas200622 smb_lgmid_t mid; 1619dc20a302Sas200622 char *errmsg = NULL; 1620dc20a302Sas200622 char *sql; 1621dc20a302Sas200622 char **result; 1622dc20a302Sas200622 int nrow, ncol; 1623dc20a302Sas200622 int rc; 1624dc20a302Sas200622 1625dc20a302Sas200622 if (db == NULL) 1626dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1627dc20a302Sas200622 1628dc20a302Sas200622 sql = sqlite_mprintf("SELECT n_members, members FROM groups " 1629dc20a302Sas200622 "WHERE name = '%s'", gname); 1630dc20a302Sas200622 1631dc20a302Sas200622 if (sql == NULL) 1632dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1633dc20a302Sas200622 1634dc20a302Sas200622 rc = sqlite_get_table(db, sql, &result, &nrow, &ncol, &errmsg); 1635dc20a302Sas200622 sqlite_freemem(sql); 1636dc20a302Sas200622 1637dc20a302Sas200622 if (rc != SQLITE_OK) { 1638dc20a302Sas200622 syslog(LOG_DEBUG, "failed to lookup %s (%s)", 1639dc20a302Sas200622 gname, NULL_MSGCHK(errmsg)); 1640dc20a302Sas200622 sqlite_freemem(errmsg); 1641dc20a302Sas200622 return (SMB_LGRP_LOOKUP_FAILED); 1642dc20a302Sas200622 } 1643dc20a302Sas200622 1644dc20a302Sas200622 if (nrow == 0) { 1645dc20a302Sas200622 /* group not found */ 1646dc20a302Sas200622 sqlite_free_table(result); 1647dc20a302Sas200622 return (SMB_LGRP_NOT_FOUND); 1648dc20a302Sas200622 } 1649dc20a302Sas200622 1650dc20a302Sas200622 if (nrow != 1 || ncol != 2) { 1651dc20a302Sas200622 sqlite_free_table(result); 1652dc20a302Sas200622 return (SMB_LGRP_DB_ERROR); 1653dc20a302Sas200622 } 1654dc20a302Sas200622 1655dc20a302Sas200622 bzero(&mid, sizeof (mid)); 1656dc20a302Sas200622 mid.m_type = member->gs_type; 1657dc20a302Sas200622 rc = smb_lgrp_dtbl_getidx(db, member->gs_sid, mid.m_type, 1658dc20a302Sas200622 &mid.m_idx, &mid.m_rid); 1659dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) { 1660dc20a302Sas200622 sqlite_free_table(result); 1661dc20a302Sas200622 return (rc); 1662dc20a302Sas200622 } 1663dc20a302Sas200622 1664dc20a302Sas200622 members.m_cnt = atoi(result[2]); 1665dc20a302Sas200622 members.m_ids = result[3]; 1666dc20a302Sas200622 1667dc20a302Sas200622 switch (flags) { 1668dc20a302Sas200622 case SMB_LGRP_DB_ADDMEMBER: 1669dc20a302Sas200622 rc = smb_lgrp_mlist_add(&members, &mid, &new_members); 1670dc20a302Sas200622 break; 1671dc20a302Sas200622 case SMB_LGRP_DB_DELMEMBER: 1672dc20a302Sas200622 rc = smb_lgrp_mlist_del(&members, &mid, &new_members); 1673dc20a302Sas200622 break; 1674dc20a302Sas200622 default: 1675dc20a302Sas200622 rc = SMB_LGRP_INVALID_ARG; 1676dc20a302Sas200622 } 1677dc20a302Sas200622 1678dc20a302Sas200622 sqlite_free_table(result); 1679dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) 1680dc20a302Sas200622 return (rc); 1681dc20a302Sas200622 1682dc20a302Sas200622 sql = sqlite_mprintf("UPDATE groups SET n_members = %u, members = '%s'" 1683dc20a302Sas200622 " WHERE name = '%s'", new_members.m_cnt, new_members.m_ids, gname); 1684dc20a302Sas200622 1685dc20a302Sas200622 free(new_members.m_ids); 1686dc20a302Sas200622 1687dc20a302Sas200622 if (sql == NULL) 1688dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1689dc20a302Sas200622 1690dc20a302Sas200622 rc = sqlite_exec(db, sql, NULL, NULL, &errmsg); 1691dc20a302Sas200622 sqlite_freemem(sql); 1692dc20a302Sas200622 1693dc20a302Sas200622 if (rc != SQLITE_OK) { 1694dc20a302Sas200622 syslog(LOG_DEBUG, "failed to update %s (%s)", gname, 1695dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1696dc20a302Sas200622 sqlite_freemem(errmsg); 1697dc20a302Sas200622 rc = SMB_LGRP_UPDATE_FAILED; 1698dc20a302Sas200622 } else { 1699dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 1700dc20a302Sas200622 } 1701dc20a302Sas200622 1702dc20a302Sas200622 return (rc); 1703dc20a302Sas200622 } 1704dc20a302Sas200622 1705dc20a302Sas200622 /* 1706dc20a302Sas200622 * smb_lgrp_gtbl_update_plist 1707dc20a302Sas200622 * 1708dc20a302Sas200622 * Adds/removes the specified privilege from the privilege list of the 1709dc20a302Sas200622 * given group 1710dc20a302Sas200622 */ 1711dc20a302Sas200622 static int 1712dc20a302Sas200622 smb_lgrp_gtbl_update_plist(sqlite *db, char *gname, uint8_t priv_id, 1713dc20a302Sas200622 boolean_t enable) 1714dc20a302Sas200622 { 1715dc20a302Sas200622 char *sql; 1716dc20a302Sas200622 char *errmsg = NULL; 1717dc20a302Sas200622 char **result; 1718dc20a302Sas200622 int nrow, ncol; 1719dc20a302Sas200622 int rc; 1720dc20a302Sas200622 smb_lgplist_t privs; 1721dc20a302Sas200622 smb_lgplist_t new_privs; 1722dc20a302Sas200622 1723dc20a302Sas200622 if (db == NULL) 1724dc20a302Sas200622 return (SMB_LGRP_DBOPEN_FAILED); 1725dc20a302Sas200622 1726dc20a302Sas200622 sql = sqlite_mprintf("SELECT n_privs, privs FROM groups " 1727dc20a302Sas200622 "WHERE name = '%s'", gname); 1728dc20a302Sas200622 1729dc20a302Sas200622 if (sql == NULL) 1730dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1731dc20a302Sas200622 1732dc20a302Sas200622 rc = sqlite_get_table(db, sql, &result, &nrow, &ncol, &errmsg); 1733dc20a302Sas200622 sqlite_freemem(sql); 1734dc20a302Sas200622 1735dc20a302Sas200622 if (rc != SQLITE_OK) { 1736dc20a302Sas200622 syslog(LOG_DEBUG, "failed to lookup %s (%s)", 1737dc20a302Sas200622 gname, NULL_MSGCHK(errmsg)); 1738dc20a302Sas200622 sqlite_freemem(errmsg); 1739dc20a302Sas200622 return (SMB_LGRP_LOOKUP_FAILED); 1740dc20a302Sas200622 } 1741dc20a302Sas200622 1742dc20a302Sas200622 if (nrow == 0) { 1743dc20a302Sas200622 /* group not found */ 1744dc20a302Sas200622 sqlite_free_table(result); 1745dc20a302Sas200622 return (SMB_LGRP_NOT_FOUND); 1746dc20a302Sas200622 } 1747dc20a302Sas200622 1748dc20a302Sas200622 if (nrow != 1 || ncol != 2) { 1749dc20a302Sas200622 sqlite_free_table(result); 1750dc20a302Sas200622 return (SMB_LGRP_DB_ERROR); 1751dc20a302Sas200622 } 1752dc20a302Sas200622 1753dc20a302Sas200622 privs.p_cnt = atoi(result[2]); 1754dc20a302Sas200622 privs.p_ids = (smb_lgpid_t *)result[3]; 1755dc20a302Sas200622 1756dc20a302Sas200622 if (enable) 1757dc20a302Sas200622 rc = smb_lgrp_plist_add(&privs, priv_id, &new_privs); 1758dc20a302Sas200622 else 1759dc20a302Sas200622 rc = smb_lgrp_plist_del(&privs, priv_id, &new_privs); 1760dc20a302Sas200622 1761dc20a302Sas200622 sqlite_free_table(result); 1762dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) 1763dc20a302Sas200622 return (rc); 1764dc20a302Sas200622 1765dc20a302Sas200622 sql = sqlite_mprintf("UPDATE groups SET n_privs = %u, privs = '%q'" 1766dc20a302Sas200622 " WHERE name = '%s'", new_privs.p_cnt, (char *)new_privs.p_ids, 1767dc20a302Sas200622 gname); 1768dc20a302Sas200622 1769dc20a302Sas200622 free(new_privs.p_ids); 1770dc20a302Sas200622 1771dc20a302Sas200622 if (sql == NULL) 1772dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1773dc20a302Sas200622 1774dc20a302Sas200622 rc = sqlite_exec(db, sql, NULL, NULL, &errmsg); 1775dc20a302Sas200622 sqlite_freemem(sql); 1776dc20a302Sas200622 1777dc20a302Sas200622 if (rc != SQLITE_OK) { 1778dc20a302Sas200622 syslog(LOG_DEBUG, "failed to update %s (%s)", 1779dc20a302Sas200622 gname, NULL_MSGCHK(errmsg)); 1780dc20a302Sas200622 sqlite_freemem(errmsg); 1781dc20a302Sas200622 rc = SMB_LGRP_UPDATE_FAILED; 1782dc20a302Sas200622 } else { 1783dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 1784dc20a302Sas200622 } 1785dc20a302Sas200622 1786dc20a302Sas200622 return (rc); 1787dc20a302Sas200622 } 1788dc20a302Sas200622 1789dc20a302Sas200622 /* 1790dc20a302Sas200622 * smb_lgrp_dtbl_insert 1791dc20a302Sas200622 * 1792dc20a302Sas200622 * Inserts the specified domain SID in the dmain table. 1793dc20a302Sas200622 * Upon successful insert the index will be returned in 1794dc20a302Sas200622 * 'dom_idx' arg. 1795dc20a302Sas200622 */ 1796dc20a302Sas200622 static int 1797dc20a302Sas200622 smb_lgrp_dtbl_insert(sqlite *db, char *dom_sid, uint32_t *dom_idx) 1798dc20a302Sas200622 { 1799dc20a302Sas200622 char *errmsg = NULL; 1800dc20a302Sas200622 char *sql; 1801dc20a302Sas200622 int rc; 1802dc20a302Sas200622 1803dc20a302Sas200622 sql = sqlite_mprintf("INSERT INTO domains (dom_sid, dom_cnt)" 1804dc20a302Sas200622 " VALUES('%s', 1);", dom_sid); 1805dc20a302Sas200622 if (sql == NULL) 1806dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1807dc20a302Sas200622 1808dc20a302Sas200622 rc = sqlite_exec(db, sql, NULL, NULL, &errmsg); 1809dc20a302Sas200622 sqlite_freemem(sql); 1810dc20a302Sas200622 1811dc20a302Sas200622 if (rc != SQLITE_OK) { 1812dc20a302Sas200622 syslog(LOG_DEBUG, "failed to insert domain SID (%s)", 1813dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1814dc20a302Sas200622 sqlite_freemem(errmsg); 1815dc20a302Sas200622 return (SMB_LGRP_DOMINS_FAILED); 1816dc20a302Sas200622 } 1817dc20a302Sas200622 1818dc20a302Sas200622 if (dom_idx) 1819dc20a302Sas200622 *dom_idx = sqlite_last_insert_rowid(db); 1820dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 1821dc20a302Sas200622 } 1822dc20a302Sas200622 1823dc20a302Sas200622 /* 1824dc20a302Sas200622 * smb_lgrp_dtbl_getidx 1825dc20a302Sas200622 * 1826dc20a302Sas200622 * Searches the domain table for the domain SID of the 1827dc20a302Sas200622 * given member SID. If it finds the domain SID it'll 1828dc20a302Sas200622 * return the index and the RID, otherwise it'll insert 1829dc20a302Sas200622 * it in the domain table as a new SID. 1830dc20a302Sas200622 */ 1831dc20a302Sas200622 static int 18326537f381Sas200622 smb_lgrp_dtbl_getidx(sqlite *db, smb_sid_t *sid, uint16_t sid_type, 1833dc20a302Sas200622 uint32_t *dom_idx, uint32_t *rid) 1834dc20a302Sas200622 { 18356537f381Sas200622 char sidstr[SMB_SID_STRSZ]; 18366537f381Sas200622 smb_sid_t *dom_sid; 1837dc20a302Sas200622 char **result; 1838dc20a302Sas200622 int nrow, ncol; 1839dc20a302Sas200622 char *errmsg = NULL; 1840dc20a302Sas200622 char *sql; 1841dc20a302Sas200622 int rc; 1842dc20a302Sas200622 18439fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (smb_sid_indomain(smb_localgrp.lg_machine_sid, sid)) { 1844dc20a302Sas200622 /* This is a local SID */ 1845dc20a302Sas200622 int id_type = (sid_type == SidTypeUser) 1846dc20a302Sas200622 ? SMB_IDMAP_USER : SMB_IDMAP_GROUP; 1847dc20a302Sas200622 *dom_idx = SMB_LGRP_LOCAL_IDX; 1848dc20a302Sas200622 if (smb_idmap_getid(sid, rid, &id_type) != IDMAP_SUCCESS) 1849dc20a302Sas200622 return (SMB_LGRP_INTERNAL_ERROR); 1850faa1795aSjb150015 1851faa1795aSjb150015 return (SMB_LGRP_SUCCESS); 1852dc20a302Sas200622 } 1853dc20a302Sas200622 18547f667e74Sjose borrego if ((dom_sid = smb_sid_split(sid, rid)) == NULL) 1855dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1856dc20a302Sas200622 18576537f381Sas200622 smb_sid_tostr(dom_sid, sidstr); 1858dc20a302Sas200622 free(dom_sid); 1859dc20a302Sas200622 1860dc20a302Sas200622 sql = sqlite_mprintf("SELECT dom_idx FROM domains WHERE dom_sid = '%s'", 1861dc20a302Sas200622 sidstr); 1862dc20a302Sas200622 if (sql == NULL) 1863dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1864dc20a302Sas200622 1865dc20a302Sas200622 rc = sqlite_get_table(db, sql, &result, &nrow, &ncol, &errmsg); 1866dc20a302Sas200622 sqlite_freemem(sql); 1867dc20a302Sas200622 1868dc20a302Sas200622 if (rc != SQLITE_OK) { 1869dc20a302Sas200622 syslog(LOG_DEBUG, "failed to lookup domain SID (%s)", 1870dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1871dc20a302Sas200622 sqlite_freemem(errmsg); 1872dc20a302Sas200622 return (SMB_LGRP_DOMLKP_FAILED); 1873dc20a302Sas200622 } 1874dc20a302Sas200622 1875dc20a302Sas200622 switch (nrow) { 1876dc20a302Sas200622 case 0: 1877dc20a302Sas200622 /* new domain SID; insert it into the domains table */ 1878dc20a302Sas200622 sqlite_free_table(result); 1879dc20a302Sas200622 return (smb_lgrp_dtbl_insert(db, sidstr, dom_idx)); 1880dc20a302Sas200622 1881dc20a302Sas200622 case 1: 1882dc20a302Sas200622 *dom_idx = atoi(result[1]); 1883dc20a302Sas200622 sqlite_free_table(result); 1884dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 1885dc20a302Sas200622 } 1886dc20a302Sas200622 1887dc20a302Sas200622 sqlite_free_table(result); 1888dc20a302Sas200622 return (SMB_LGRP_DB_ERROR); 1889dc20a302Sas200622 } 1890dc20a302Sas200622 1891dc20a302Sas200622 /* 1892dc20a302Sas200622 * smb_lgrp_dtbl_getsid 1893dc20a302Sas200622 * 1894dc20a302Sas200622 * Searchs the domain table for the given domain index. 1895dc20a302Sas200622 * Converts the found domain SID to binary format and 1896dc20a302Sas200622 * returns it in the 'sid' arg. 1897dc20a302Sas200622 * 1898dc20a302Sas200622 * Caller must free the returned SID by calling free(). 1899dc20a302Sas200622 */ 1900dc20a302Sas200622 static int 19016537f381Sas200622 smb_lgrp_dtbl_getsid(sqlite *db, uint32_t dom_idx, smb_sid_t **sid) 1902dc20a302Sas200622 { 1903dc20a302Sas200622 char **result; 1904dc20a302Sas200622 int nrow, ncol; 1905dc20a302Sas200622 char *errmsg = NULL; 1906dc20a302Sas200622 char *sql; 1907dc20a302Sas200622 int rc; 1908dc20a302Sas200622 1909dc20a302Sas200622 sql = sqlite_mprintf("SELECT dom_sid FROM domains WHERE dom_idx = %u", 1910dc20a302Sas200622 dom_idx); 1911dc20a302Sas200622 if (sql == NULL) 1912dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1913dc20a302Sas200622 1914dc20a302Sas200622 rc = sqlite_get_table(db, sql, &result, &nrow, &ncol, &errmsg); 1915dc20a302Sas200622 sqlite_freemem(sql); 1916dc20a302Sas200622 1917dc20a302Sas200622 if (rc != SQLITE_OK) { 1918dc20a302Sas200622 syslog(LOG_DEBUG, "failed to lookup domain index (%s)", 1919dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1920dc20a302Sas200622 sqlite_freemem(errmsg); 1921dc20a302Sas200622 return (SMB_LGRP_DOMLKP_FAILED); 1922dc20a302Sas200622 } 1923dc20a302Sas200622 1924dc20a302Sas200622 switch (nrow) { 1925dc20a302Sas200622 case 0: 1926dc20a302Sas200622 rc = SMB_LGRP_NO_SUCH_DOMAIN; 1927dc20a302Sas200622 break; 1928dc20a302Sas200622 1929dc20a302Sas200622 case 1: 19306537f381Sas200622 *sid = smb_sid_fromstr(result[1]); 1931dc20a302Sas200622 rc = (*sid == NULL) 1932dc20a302Sas200622 ? SMB_LGRP_INTERNAL_ERROR : SMB_LGRP_SUCCESS; 1933dc20a302Sas200622 break; 1934dc20a302Sas200622 1935dc20a302Sas200622 default: 1936dc20a302Sas200622 rc = SMB_LGRP_DB_ERROR; 1937dc20a302Sas200622 break; 1938dc20a302Sas200622 } 1939dc20a302Sas200622 1940dc20a302Sas200622 sqlite_free_table(result); 1941dc20a302Sas200622 return (rc); 1942dc20a302Sas200622 } 1943dc20a302Sas200622 1944dc20a302Sas200622 /* 1945dc20a302Sas200622 * smb_lgrp_db_setinfo 1946dc20a302Sas200622 * 1947dc20a302Sas200622 * Initializes the db_info table upon database creation. 1948dc20a302Sas200622 */ 1949dc20a302Sas200622 static int 1950dc20a302Sas200622 smb_lgrp_db_setinfo(sqlite *db) 1951dc20a302Sas200622 { 1952dc20a302Sas200622 char *errmsg = NULL; 1953dc20a302Sas200622 char *sql; 1954dc20a302Sas200622 int rc; 1955dc20a302Sas200622 1956dc20a302Sas200622 sql = sqlite_mprintf("INSERT INTO db_info (ver_major, ver_minor," 1957dc20a302Sas200622 " magic) VALUES (%d, %d, %u)", SMB_LGRP_DB_VERMAJOR, 1958dc20a302Sas200622 SMB_LGRP_DB_VERMINOR, SMB_LGRP_DB_MAGIC); 1959dc20a302Sas200622 1960dc20a302Sas200622 if (sql == NULL) 1961dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 1962dc20a302Sas200622 1963dc20a302Sas200622 rc = sqlite_exec(db, sql, NULL, NULL, &errmsg); 1964dc20a302Sas200622 sqlite_freemem(sql); 1965dc20a302Sas200622 if (rc != SQLITE_OK) { 1966dc20a302Sas200622 syslog(LOG_DEBUG, "failed to insert database information (%s)", 1967dc20a302Sas200622 NULL_MSGCHK(errmsg)); 1968dc20a302Sas200622 sqlite_freemem(errmsg); 1969dc20a302Sas200622 rc = SMB_LGRP_DBINIT_ERROR; 1970dc20a302Sas200622 } else { 1971dc20a302Sas200622 rc = SMB_LGRP_SUCCESS; 1972dc20a302Sas200622 } 1973dc20a302Sas200622 1974dc20a302Sas200622 return (rc); 1975dc20a302Sas200622 } 1976dc20a302Sas200622 1977dc20a302Sas200622 /* 1978dc20a302Sas200622 * smb_lgrp_mlist_add 1979dc20a302Sas200622 * 1980dc20a302Sas200622 * Adds the given member (newm) to the input member list (in_members) 1981dc20a302Sas200622 * if it's not already there. The result list will be returned in 1982dc20a302Sas200622 * out_members. The caller must free the allocated memory for 1983dc20a302Sas200622 * out_members by calling free(). 1984dc20a302Sas200622 * 1985dc20a302Sas200622 * in_members and out_members are hex strings. 1986dc20a302Sas200622 */ 1987dc20a302Sas200622 static int 1988dc20a302Sas200622 smb_lgrp_mlist_add(smb_lgmlist_t *in_members, smb_lgmid_t *newm, 1989dc20a302Sas200622 smb_lgmlist_t *out_members) 1990dc20a302Sas200622 { 1991dc20a302Sas200622 char mid_hex[SMB_LGRP_MID_HEXSZ]; 1992dc20a302Sas200622 char *in_list; 1993dc20a302Sas200622 char *out_list; 1994dc20a302Sas200622 int in_size; 1995dc20a302Sas200622 int out_size; 1996dc20a302Sas200622 int mid_hexsz; 1997dc20a302Sas200622 int i; 1998dc20a302Sas200622 1999dc20a302Sas200622 out_members->m_cnt = 0; 2000dc20a302Sas200622 out_members->m_ids = NULL; 2001dc20a302Sas200622 2002dc20a302Sas200622 bzero(mid_hex, sizeof (mid_hex)); 2003dc20a302Sas200622 mid_hexsz = bintohex((const char *)newm, sizeof (smb_lgmid_t), 2004dc20a302Sas200622 mid_hex, sizeof (mid_hex)); 2005dc20a302Sas200622 2006dc20a302Sas200622 /* 2007dc20a302Sas200622 * Check to see if this is already a group member 2008dc20a302Sas200622 */ 2009dc20a302Sas200622 in_list = in_members->m_ids; 2010dc20a302Sas200622 for (i = 0; i < in_members->m_cnt; i++) { 2011dc20a302Sas200622 if (strncmp(in_list, mid_hex, mid_hexsz) == 0) 2012dc20a302Sas200622 return (SMB_LGRP_MEMBER_IN_GROUP); 2013dc20a302Sas200622 in_list += mid_hexsz; 2014dc20a302Sas200622 } 2015dc20a302Sas200622 2016dc20a302Sas200622 in_size = (in_members->m_ids) ? strlen(in_members->m_ids) : 0; 2017dc20a302Sas200622 out_size = in_size + sizeof (mid_hex) + 1; 2018dc20a302Sas200622 out_list = malloc(out_size); 2019dc20a302Sas200622 if (out_list == NULL) 2020dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2021dc20a302Sas200622 2022dc20a302Sas200622 bzero(out_list, out_size); 2023dc20a302Sas200622 if (in_members->m_ids) 2024dc20a302Sas200622 (void) strlcpy(out_list, in_members->m_ids, out_size); 2025dc20a302Sas200622 (void) strcat(out_list, mid_hex); 2026dc20a302Sas200622 2027dc20a302Sas200622 out_members->m_cnt = in_members->m_cnt + 1; 2028dc20a302Sas200622 out_members->m_ids = out_list; 2029dc20a302Sas200622 2030dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2031dc20a302Sas200622 } 2032dc20a302Sas200622 2033dc20a302Sas200622 /* 2034dc20a302Sas200622 * smb_lgrp_mlist_del 2035dc20a302Sas200622 * 2036dc20a302Sas200622 * Removes the given member (msid) from the input member list 2037dc20a302Sas200622 * (in_members) if it's already there. The result list will b 2038dc20a302Sas200622 * returned in out_members. The caller must free the allocated 2039dc20a302Sas200622 * memory for out_members by calling free(). 2040dc20a302Sas200622 * 2041dc20a302Sas200622 * in_members and out_members are hex strings. 2042dc20a302Sas200622 */ 2043dc20a302Sas200622 static int 2044dc20a302Sas200622 smb_lgrp_mlist_del(smb_lgmlist_t *in_members, smb_lgmid_t *mid, 2045dc20a302Sas200622 smb_lgmlist_t *out_members) 2046dc20a302Sas200622 { 2047dc20a302Sas200622 char mid_hex[SMB_LGRP_MID_HEXSZ]; 2048dc20a302Sas200622 char *in_list; 2049dc20a302Sas200622 char *out_list; 2050dc20a302Sas200622 int in_size; 2051dc20a302Sas200622 int out_size; 2052dc20a302Sas200622 int mid_hexsz; 2053dc20a302Sas200622 int out_cnt; 2054dc20a302Sas200622 int i; 2055dc20a302Sas200622 2056dc20a302Sas200622 out_members->m_cnt = 0; 2057dc20a302Sas200622 out_members->m_ids = NULL; 2058dc20a302Sas200622 2059dc20a302Sas200622 if ((in_members == NULL) || (in_members->m_cnt == 0)) 2060dc20a302Sas200622 return (SMB_LGRP_MEMBER_NOT_IN_GROUP); 2061dc20a302Sas200622 2062dc20a302Sas200622 in_size = strlen(in_members->m_ids); 2063dc20a302Sas200622 out_size = in_size + sizeof (mid_hex) + 1; 2064dc20a302Sas200622 out_list = malloc(out_size); 2065dc20a302Sas200622 if (out_list == NULL) 2066dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2067dc20a302Sas200622 2068dc20a302Sas200622 *out_list = '\0'; 2069dc20a302Sas200622 2070dc20a302Sas200622 bzero(mid_hex, sizeof (mid_hex)); 2071dc20a302Sas200622 mid_hexsz = bintohex((const char *)mid, sizeof (smb_lgmid_t), 2072dc20a302Sas200622 mid_hex, sizeof (mid_hex)); 2073dc20a302Sas200622 2074dc20a302Sas200622 in_list = in_members->m_ids; 2075dc20a302Sas200622 for (i = 0, out_cnt = 0; i < in_members->m_cnt; i++) { 2076dc20a302Sas200622 if (strncmp(in_list, mid_hex, mid_hexsz)) { 2077dc20a302Sas200622 (void) strncat(out_list, in_list, mid_hexsz); 2078dc20a302Sas200622 out_cnt++; 2079dc20a302Sas200622 } 2080dc20a302Sas200622 in_list += mid_hexsz; 2081dc20a302Sas200622 } 2082dc20a302Sas200622 2083dc20a302Sas200622 if (out_cnt == in_members->m_cnt) { 2084dc20a302Sas200622 free(out_list); 2085dc20a302Sas200622 return (SMB_LGRP_MEMBER_NOT_IN_GROUP); 2086dc20a302Sas200622 } 2087dc20a302Sas200622 2088dc20a302Sas200622 out_members->m_cnt = out_cnt; 2089dc20a302Sas200622 out_members->m_ids = out_list; 2090dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2091dc20a302Sas200622 } 2092dc20a302Sas200622 2093dc20a302Sas200622 /* 2094dc20a302Sas200622 * smb_lgrp_plist_add 2095dc20a302Sas200622 * 2096dc20a302Sas200622 * Adds the given privilege to the input list (in_privs) 2097dc20a302Sas200622 * if it's not already there. The result list is returned 2098dc20a302Sas200622 * in out_privs. The caller must free the allocated memory 2099dc20a302Sas200622 * for out_privs by calling free(). 2100dc20a302Sas200622 */ 2101dc20a302Sas200622 static int 2102dc20a302Sas200622 smb_lgrp_plist_add(smb_lgplist_t *in_privs, smb_lgpid_t priv_id, 2103dc20a302Sas200622 smb_lgplist_t *out_privs) 2104dc20a302Sas200622 { 2105dc20a302Sas200622 int i, size; 2106dc20a302Sas200622 smb_lgpid_t *pbuf; 2107dc20a302Sas200622 2108dc20a302Sas200622 out_privs->p_cnt = 0; 2109dc20a302Sas200622 out_privs->p_ids = NULL; 2110dc20a302Sas200622 2111dc20a302Sas200622 for (i = 0; i < in_privs->p_cnt; i++) { 2112dc20a302Sas200622 if (in_privs->p_ids[i] == priv_id) 2113dc20a302Sas200622 return (SMB_LGRP_PRIV_HELD); 2114dc20a302Sas200622 } 2115dc20a302Sas200622 2116dc20a302Sas200622 size = (in_privs->p_cnt + 1) * sizeof (smb_lgpid_t) + 1; 2117dc20a302Sas200622 pbuf = malloc(size); 2118dc20a302Sas200622 if (pbuf == NULL) 2119dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2120dc20a302Sas200622 2121dc20a302Sas200622 bzero(pbuf, size); 2122dc20a302Sas200622 bcopy(in_privs->p_ids, pbuf, in_privs->p_cnt * sizeof (smb_lgpid_t)); 2123dc20a302Sas200622 pbuf[in_privs->p_cnt] = priv_id; 2124dc20a302Sas200622 2125dc20a302Sas200622 out_privs->p_cnt = in_privs->p_cnt + 1; 2126dc20a302Sas200622 out_privs->p_ids = pbuf; 2127dc20a302Sas200622 2128dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2129dc20a302Sas200622 } 2130dc20a302Sas200622 2131dc20a302Sas200622 /* 2132dc20a302Sas200622 * smb_lgrp_plist_del 2133dc20a302Sas200622 * 2134dc20a302Sas200622 * Removes the given privilege from the input list (in_privs) 2135dc20a302Sas200622 * if it's already there. The result list is returned 2136dc20a302Sas200622 * in out_privs. The caller must free the allocated memory 2137dc20a302Sas200622 * for out_privs by calling free(). 2138dc20a302Sas200622 */ 2139dc20a302Sas200622 static int 2140dc20a302Sas200622 smb_lgrp_plist_del(smb_lgplist_t *in_privs, smb_lgpid_t priv_id, 2141dc20a302Sas200622 smb_lgplist_t *out_privs) 2142dc20a302Sas200622 { 2143dc20a302Sas200622 int i, size; 2144dc20a302Sas200622 2145dc20a302Sas200622 out_privs->p_cnt = 0; 2146dc20a302Sas200622 out_privs->p_ids = NULL; 2147dc20a302Sas200622 2148dc20a302Sas200622 if ((in_privs == NULL) || (in_privs->p_cnt == 0)) 2149dc20a302Sas200622 return (SMB_LGRP_PRIV_NOT_HELD); 2150dc20a302Sas200622 2151dc20a302Sas200622 size = (in_privs->p_cnt - 1) * sizeof (smb_lgpid_t) + 1; 2152dc20a302Sas200622 out_privs->p_ids = malloc(size); 2153dc20a302Sas200622 if (out_privs->p_ids == NULL) 2154dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2155dc20a302Sas200622 2156dc20a302Sas200622 bzero(out_privs->p_ids, size); 2157dc20a302Sas200622 2158dc20a302Sas200622 for (i = 0; i < in_privs->p_cnt; i++) { 2159dc20a302Sas200622 if (in_privs->p_ids[i] != priv_id) 2160dc20a302Sas200622 out_privs->p_ids[out_privs->p_cnt++] = 2161dc20a302Sas200622 in_privs->p_ids[i]; 2162dc20a302Sas200622 } 2163dc20a302Sas200622 2164dc20a302Sas200622 if (out_privs->p_cnt == in_privs->p_cnt) { 2165dc20a302Sas200622 free(out_privs->p_ids); 2166dc20a302Sas200622 out_privs->p_cnt = 0; 2167dc20a302Sas200622 out_privs->p_ids = NULL; 2168dc20a302Sas200622 return (SMB_LGRP_PRIV_NOT_HELD); 2169dc20a302Sas200622 } 2170dc20a302Sas200622 2171dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2172dc20a302Sas200622 } 2173dc20a302Sas200622 2174dc20a302Sas200622 /* 2175dc20a302Sas200622 * smb_lgrp_encode_privset 2176dc20a302Sas200622 * 2177dc20a302Sas200622 * Encodes given privilege set into a buffer to be stored in the group 2178dc20a302Sas200622 * database. Each entry of the encoded buffer contains the privilege ID 2179dc20a302Sas200622 * of an enable privilege. The returned buffer is null-terminated. 2180dc20a302Sas200622 */ 2181dc20a302Sas200622 static void 2182dc20a302Sas200622 smb_lgrp_encode_privset(smb_group_t *grp, smb_lgplist_t *plist) 2183dc20a302Sas200622 { 2184dc20a302Sas200622 smb_privset_t *privs; 2185dc20a302Sas200622 uint32_t pcnt = plist->p_cnt; 2186dc20a302Sas200622 int i; 2187dc20a302Sas200622 2188dc20a302Sas200622 bzero(plist->p_ids, sizeof (smb_lgpid_t) * plist->p_cnt); 2189dc20a302Sas200622 plist->p_cnt = 0; 2190dc20a302Sas200622 2191dc20a302Sas200622 privs = grp->sg_privs; 2192dc20a302Sas200622 if ((privs == NULL) || (privs->priv_cnt == 0)) 2193dc20a302Sas200622 return; 2194dc20a302Sas200622 2195dc20a302Sas200622 if (pcnt < privs->priv_cnt) { 2196dc20a302Sas200622 assert(0); 2197dc20a302Sas200622 } 2198dc20a302Sas200622 2199dc20a302Sas200622 for (i = 0; i < privs->priv_cnt; i++) { 2200dc20a302Sas200622 if (privs->priv[i].attrs == SE_PRIVILEGE_ENABLED) { 2201dc20a302Sas200622 plist->p_ids[plist->p_cnt++] = 2202dc20a302Sas200622 (uint8_t)privs->priv[i].luid.lo_part; 2203dc20a302Sas200622 } 2204dc20a302Sas200622 } 2205dc20a302Sas200622 } 2206dc20a302Sas200622 2207dc20a302Sas200622 /* 2208dc20a302Sas200622 * smb_lgrp_decode_privset 2209dc20a302Sas200622 * 2210dc20a302Sas200622 * Decodes the privilege information read from group table 2211dc20a302Sas200622 * (nprivs, privs) into a binray format specified by the 2212dc20a302Sas200622 * privilege field of smb_group_t 2213dc20a302Sas200622 */ 2214dc20a302Sas200622 static int 2215dc20a302Sas200622 smb_lgrp_decode_privset(smb_group_t *grp, char *nprivs, char *privs) 2216dc20a302Sas200622 { 2217dc20a302Sas200622 smb_lgplist_t plist; 2218dc20a302Sas200622 int i; 2219dc20a302Sas200622 2220dc20a302Sas200622 plist.p_cnt = atoi(nprivs); 2221dc20a302Sas200622 if (strlen(privs) != plist.p_cnt) 2222dc20a302Sas200622 return (SMB_LGRP_BAD_DATA); 2223dc20a302Sas200622 2224dc20a302Sas200622 plist.p_ids = (smb_lgpid_t *)privs; 2225dc20a302Sas200622 grp->sg_privs = smb_privset_new(); 2226dc20a302Sas200622 if (grp->sg_privs == NULL) 2227dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2228dc20a302Sas200622 2229dc20a302Sas200622 for (i = 0; i < plist.p_cnt; i++) 2230dc20a302Sas200622 smb_privset_enable(grp->sg_privs, plist.p_ids[i]); 2231dc20a302Sas200622 2232dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2233dc20a302Sas200622 } 2234dc20a302Sas200622 2235dc20a302Sas200622 /* 2236dc20a302Sas200622 * smb_lgrp_decode_members 2237dc20a302Sas200622 * 2238dc20a302Sas200622 * Decodes the members information read from group table 22396537f381Sas200622 * (nmembers, members) into a binary format specified by the 2240dc20a302Sas200622 * member fields of smb_group_t 2241dc20a302Sas200622 */ 2242dc20a302Sas200622 static int 2243dc20a302Sas200622 smb_lgrp_decode_members(smb_group_t *grp, char *nmembers, char *members, 2244dc20a302Sas200622 sqlite *db) 2245dc20a302Sas200622 { 22466537f381Sas200622 smb_lgmid_t *m_id; 2247dc20a302Sas200622 smb_lgmid_t *m_ids; 22486537f381Sas200622 smb_gsid_t *m_sid; 22496537f381Sas200622 smb_gsid_t *m_sids; 22506537f381Sas200622 int m_num; 2251dc20a302Sas200622 int mids_size; 2252dc20a302Sas200622 int i, rc; 2253dc20a302Sas200622 22546537f381Sas200622 grp->sg_nmembers = 0; 22556537f381Sas200622 grp->sg_members = NULL; 22566537f381Sas200622 22576537f381Sas200622 m_num = atoi(nmembers); 22586537f381Sas200622 mids_size = m_num * sizeof (smb_lgmid_t); 22596537f381Sas200622 if ((m_ids = malloc(mids_size)) == NULL) 2260dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2261dc20a302Sas200622 22629fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States m_sids = calloc(m_num, sizeof (smb_gsid_t)); 22636537f381Sas200622 if (m_sids == NULL) { 2264dc20a302Sas200622 free(m_ids); 2265dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2266dc20a302Sas200622 } 2267dc20a302Sas200622 2268dc20a302Sas200622 (void) hextobin(members, strlen(members), (char *)m_ids, mids_size); 2269dc20a302Sas200622 22706537f381Sas200622 m_id = m_ids; 22716537f381Sas200622 m_sid = m_sids; 22726537f381Sas200622 for (i = 0; i < m_num; i++, m_id++, m_sid++) { 22736537f381Sas200622 rc = smb_lgrp_getsid(m_id->m_idx, &m_id->m_rid, m_id->m_type, 22746537f381Sas200622 db, &m_sid->gs_sid); 22756537f381Sas200622 2276dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) { 2277dc20a302Sas200622 free(m_ids); 22786537f381Sas200622 for (m_sid = m_sids; m_sid->gs_sid != NULL; m_sid++) 22796537f381Sas200622 smb_sid_free(m_sid->gs_sid); 22806537f381Sas200622 free(m_sids); 22816537f381Sas200622 return (rc); 2282dc20a302Sas200622 } 2283dc20a302Sas200622 22846537f381Sas200622 m_sid->gs_type = m_id->m_type; 2285dc20a302Sas200622 } 2286dc20a302Sas200622 2287dc20a302Sas200622 free(m_ids); 22886537f381Sas200622 22896537f381Sas200622 grp->sg_nmembers = m_num; 22906537f381Sas200622 grp->sg_members = m_sids; 2291dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2292dc20a302Sas200622 } 2293dc20a302Sas200622 2294dc20a302Sas200622 /* 2295dc20a302Sas200622 * smb_lgrp_decode 2296dc20a302Sas200622 * 2297dc20a302Sas200622 * Fills out the fields of the given group (grp) based in the 2298dc20a302Sas200622 * string information read from the group table. infolvl determines 2299dc20a302Sas200622 * which fields are requested and need to be decoded. 2300dc20a302Sas200622 * 2301dc20a302Sas200622 * Allocated memories must be freed by calling smb_lgrp_free() 2302dc20a302Sas200622 * upon successful return. 2303dc20a302Sas200622 */ 2304dc20a302Sas200622 static int 2305dc20a302Sas200622 smb_lgrp_decode(smb_group_t *grp, char **values, int infolvl, sqlite *db) 2306dc20a302Sas200622 { 2307dc20a302Sas200622 uint32_t sid_idx; 2308dc20a302Sas200622 int rc; 2309dc20a302Sas200622 2310dc20a302Sas200622 if (infolvl == SMB_LGRP_INFO_NONE) 2311dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2312dc20a302Sas200622 2313dc20a302Sas200622 if (infolvl & SMB_LGRP_INFO_NAME) { 2314dc20a302Sas200622 grp->sg_name = strdup(values[SMB_LGRP_GTBL_NAME]); 2315dc20a302Sas200622 if (grp->sg_name == NULL) 2316dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2317dc20a302Sas200622 } 2318dc20a302Sas200622 2319dc20a302Sas200622 if (infolvl & SMB_LGRP_INFO_CMNT) { 2320dc20a302Sas200622 grp->sg_cmnt = strdup(values[SMB_LGRP_GTBL_CMNT]); 2321dc20a302Sas200622 if (grp->sg_cmnt == NULL) { 2322dc20a302Sas200622 smb_lgrp_free(grp); 2323dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 2324dc20a302Sas200622 } 2325dc20a302Sas200622 } 2326dc20a302Sas200622 2327dc20a302Sas200622 2328dc20a302Sas200622 if (infolvl & SMB_LGRP_INFO_SID) { 2329dc20a302Sas200622 sid_idx = atoi(values[SMB_LGRP_GTBL_SIDIDX]); 2330dc20a302Sas200622 grp->sg_rid = atoi(values[SMB_LGRP_GTBL_SIDRID]); 2331dc20a302Sas200622 grp->sg_attr = atoi(values[SMB_LGRP_GTBL_SIDATR]); 2332dc20a302Sas200622 grp->sg_id.gs_type = atoi(values[SMB_LGRP_GTBL_SIDTYP]); 2333dc20a302Sas200622 rc = smb_lgrp_getsid(sid_idx, &grp->sg_rid, grp->sg_id.gs_type, 2334dc20a302Sas200622 db, &grp->sg_id.gs_sid); 2335dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) { 2336dc20a302Sas200622 smb_lgrp_free(grp); 23379fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States return (rc); 2338dc20a302Sas200622 } 2339dc20a302Sas200622 grp->sg_domain = (sid_idx == SMB_LGRP_LOCAL_IDX) 23409fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States ? SMB_DOMAIN_LOCAL : SMB_DOMAIN_BUILTIN; 2341dc20a302Sas200622 } 2342dc20a302Sas200622 2343dc20a302Sas200622 if (infolvl & SMB_LGRP_INFO_PRIV) { 2344dc20a302Sas200622 rc = smb_lgrp_decode_privset(grp, values[SMB_LGRP_GTBL_NPRIVS], 2345dc20a302Sas200622 values[SMB_LGRP_GTBL_PRIVS]); 2346dc20a302Sas200622 2347dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) { 2348dc20a302Sas200622 smb_lgrp_free(grp); 2349dc20a302Sas200622 return (rc); 2350dc20a302Sas200622 } 2351dc20a302Sas200622 } 2352dc20a302Sas200622 2353dc20a302Sas200622 if (infolvl & SMB_LGRP_INFO_MEMB) { 2354dc20a302Sas200622 rc = smb_lgrp_decode_members(grp, values[SMB_LGRP_GTBL_NMEMBS], 2355dc20a302Sas200622 values[SMB_LGRP_GTBL_MEMBS], db); 2356dc20a302Sas200622 if (rc != SMB_LGRP_SUCCESS) { 2357dc20a302Sas200622 smb_lgrp_free(grp); 2358dc20a302Sas200622 return (rc); 2359dc20a302Sas200622 } 2360dc20a302Sas200622 } 2361dc20a302Sas200622 2362dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2363dc20a302Sas200622 } 2364dc20a302Sas200622 2365dc20a302Sas200622 /* 2366fe1c642dSBill Krier * smb_lgrp_normalize_name 2367dc20a302Sas200622 * 2368fe1c642dSBill Krier * Trim whitespace, validate the group name and convert it to lowercase. 2369dc20a302Sas200622 */ 2370dc20a302Sas200622 static boolean_t 2371fe1c642dSBill Krier smb_lgrp_normalize_name(char *name) 2372dc20a302Sas200622 { 2373fe1c642dSBill Krier (void) trim_whitespace(name); 2374dc20a302Sas200622 2375fe1c642dSBill Krier if (smb_name_validate_account(name) != ERROR_SUCCESS) 2376dc20a302Sas200622 return (B_FALSE); 2377dc20a302Sas200622 2378bbf6f00cSJordan Brown (void) smb_strlwr(name); 2379dc20a302Sas200622 return (B_TRUE); 2380dc20a302Sas200622 } 2381dc20a302Sas200622 2382dc20a302Sas200622 /* 2383dc20a302Sas200622 * smb_lgrp_set_default_privs 2384dc20a302Sas200622 * 2385dc20a302Sas200622 * set default privileges for Administrators and Backup Operators 2386dc20a302Sas200622 */ 2387dc20a302Sas200622 static void 2388dc20a302Sas200622 smb_lgrp_set_default_privs(smb_group_t *grp) 2389dc20a302Sas200622 { 2390bbf6f00cSJordan Brown if (smb_strcasecmp(grp->sg_name, "Administrators", 0) == 0) { 2391dc20a302Sas200622 smb_privset_enable(grp->sg_privs, SE_TAKE_OWNERSHIP_LUID); 2392dc20a302Sas200622 return; 2393dc20a302Sas200622 } 2394dc20a302Sas200622 2395bbf6f00cSJordan Brown if (smb_strcasecmp(grp->sg_name, "Backup Operators", 0) == 0) { 2396dc20a302Sas200622 smb_privset_enable(grp->sg_privs, SE_BACKUP_LUID); 2397dc20a302Sas200622 smb_privset_enable(grp->sg_privs, SE_RESTORE_LUID); 2398dc20a302Sas200622 return; 2399dc20a302Sas200622 } 2400dc20a302Sas200622 } 2401dc20a302Sas200622 2402dc20a302Sas200622 /* 2403dc20a302Sas200622 * smb_lgrp_getsid 2404dc20a302Sas200622 * 2405dc20a302Sas200622 * Returns a SID based on the provided information 2406dc20a302Sas200622 * If dom_idx is 0, it means 'rid' contains a UID/GID and the 2407dc20a302Sas200622 * returned SID will be a local SID. If dom_idx is not 0 then 2408dc20a302Sas200622 * the domain SID will be fetched from the domain table. 2409dc20a302Sas200622 */ 2410dc20a302Sas200622 static int 2411dc20a302Sas200622 smb_lgrp_getsid(int dom_idx, uint32_t *rid, uint16_t sid_type, 24126537f381Sas200622 sqlite *db, smb_sid_t **sid) 2413dc20a302Sas200622 { 24146537f381Sas200622 smb_sid_t *dom_sid = NULL; 24156537f381Sas200622 smb_sid_t *res_sid = NULL; 24169fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States idmap_stat stat; 2417dc20a302Sas200622 int id_type; 2418dc20a302Sas200622 int rc; 2419dc20a302Sas200622 2420dc20a302Sas200622 *sid = NULL; 2421dc20a302Sas200622 if (dom_idx == SMB_LGRP_LOCAL_IDX) { 2422dc20a302Sas200622 id_type = (sid_type == SidTypeUser) 2423dc20a302Sas200622 ? SMB_IDMAP_USER : SMB_IDMAP_GROUP; 24249fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States stat = smb_idmap_getsid(*rid, id_type, &res_sid); 24259fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (stat != IDMAP_SUCCESS) { 24269fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States syslog(LOG_ERR, "smb_lgrp_getsid: " 24279fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States "failed to get a SID for %s id=%u (%d)", 24289fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (id_type == SMB_IDMAP_USER) ? "user" : "group", 24299fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States *rid, stat); 2430dc20a302Sas200622 return (SMB_LGRP_NO_SID); 24319fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 2432dc20a302Sas200622 2433dc20a302Sas200622 /* 2434dc20a302Sas200622 * Make sure the returned SID is local 2435dc20a302Sas200622 */ 24369fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (!smb_sid_indomain(smb_localgrp.lg_machine_sid, res_sid)) { 24379fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States syslog(LOG_ERR, "smb_lgrp_getsid: " 24389fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States "local %s (%u) is mapped to a non-local SID", 24399fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States (id_type == SMB_IDMAP_USER) ? "user" : "group", 24409fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States *rid); 24416537f381Sas200622 smb_sid_free(res_sid); 2442dc20a302Sas200622 return (SMB_LGRP_SID_NOTLOCAL); 2443dc20a302Sas200622 } 2444dc20a302Sas200622 24456537f381Sas200622 (void) smb_sid_getrid(res_sid, rid); 2446dc20a302Sas200622 *sid = res_sid; 2447dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2448dc20a302Sas200622 } 2449dc20a302Sas200622 2450dc20a302Sas200622 rc = smb_lgrp_dtbl_getsid(db, dom_idx, &dom_sid); 24519fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (rc != SMB_LGRP_SUCCESS) { 24529fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States syslog(LOG_ERR, "smb_lgrp_getsid: %s", smb_lgrp_strerror(rc)); 2453dc20a302Sas200622 return (SMB_LGRP_DB_ERROR); 24549fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 2455dc20a302Sas200622 24566537f381Sas200622 res_sid = smb_sid_splice(dom_sid, *rid); 24576537f381Sas200622 smb_sid_free(dom_sid); 24589fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if (res_sid == NULL) { 24599fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States syslog(LOG_ERR, "smb_lgrp_getsid: %s", smb_lgrp_strerror(rc)); 2460dc20a302Sas200622 return (SMB_LGRP_NO_MEMORY); 24619fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States } 2462dc20a302Sas200622 2463dc20a302Sas200622 *sid = res_sid; 2464dc20a302Sas200622 return (SMB_LGRP_SUCCESS); 2465dc20a302Sas200622 } 2466c8ec8eeaSjose borrego 2467c8ec8eeaSjose borrego /* 2468c8ec8eeaSjose borrego * smb_lgrp_getgid 2469c8ec8eeaSjose borrego * 2470c8ec8eeaSjose borrego * Converts given local RID to a local gid since for user 2471c8ec8eeaSjose borrego * defined local groups, gid is stored in the table. 2472c8ec8eeaSjose borrego */ 2473c8ec8eeaSjose borrego static int 2474c8ec8eeaSjose borrego smb_lgrp_getgid(uint32_t rid, gid_t *gid) 2475c8ec8eeaSjose borrego { 2476c8ec8eeaSjose borrego smb_sid_t *sid; 2477c8ec8eeaSjose borrego int idtype; 2478c8ec8eeaSjose borrego int rc; 2479c8ec8eeaSjose borrego 24809fb67ea3Safshin salek ardakani - Sun Microsystems - Irvine United States if ((sid = smb_sid_splice(smb_localgrp.lg_machine_sid, rid)) == NULL) 2481c8ec8eeaSjose borrego return (SMB_LGRP_NO_MEMORY); 2482c8ec8eeaSjose borrego 2483c8ec8eeaSjose borrego idtype = SMB_IDMAP_GROUP; 2484c8ec8eeaSjose borrego rc = smb_idmap_getid(sid, gid, &idtype); 2485c8ec8eeaSjose borrego smb_sid_free(sid); 2486c8ec8eeaSjose borrego 2487c8ec8eeaSjose borrego return ((rc == IDMAP_SUCCESS) ? SMB_LGRP_SUCCESS : SMB_LGRP_NOT_FOUND); 2488c8ec8eeaSjose borrego } 248929bd2886SAlan Wright 249029bd2886SAlan Wright /* 249129bd2886SAlan Wright * smb_lgrp_exists 249229bd2886SAlan Wright * 249329bd2886SAlan Wright * Returns B_TRUE if the local group with the given name exists. 249429bd2886SAlan Wright * Otherwise, returns B_FALSE. 249529bd2886SAlan Wright */ 249629bd2886SAlan Wright static boolean_t 249729bd2886SAlan Wright smb_lgrp_exists(char *gname) 249829bd2886SAlan Wright { 249929bd2886SAlan Wright sqlite *db; 250029bd2886SAlan Wright boolean_t rc; 250129bd2886SAlan Wright 2502fe1c642dSBill Krier if (!smb_lgrp_normalize_name(gname)) 250329bd2886SAlan Wright return (B_FALSE); 250429bd2886SAlan Wright 250529bd2886SAlan Wright db = smb_lgrp_db_open(SMB_LGRP_DB_ORD); 250629bd2886SAlan Wright if (db == NULL) 250729bd2886SAlan Wright return (B_FALSE); 250829bd2886SAlan Wright 250929bd2886SAlan Wright rc = smb_lgrp_gtbl_exists(db, gname); 251029bd2886SAlan Wright smb_lgrp_db_close(db); 251129bd2886SAlan Wright 251229bd2886SAlan Wright return (rc); 251329bd2886SAlan Wright } 2514148c5f43SAlan Wright 2515148c5f43SAlan Wright /* 2516148c5f43SAlan Wright * smb_lgrp_pgrp_valid_gname 2517148c5f43SAlan Wright * 2518148c5f43SAlan Wright * Validate posix group name string. 2519148c5f43SAlan Wright */ 2520148c5f43SAlan Wright static int 2521148c5f43SAlan Wright smb_lgrp_pgrp_valid_gname(char *group) 2522148c5f43SAlan Wright { 2523148c5f43SAlan Wright char *ptr = group; 2524148c5f43SAlan Wright char c; 2525148c5f43SAlan Wright int len = 0; 2526148c5f43SAlan Wright int badchar = 0; 2527148c5f43SAlan Wright 2528148c5f43SAlan Wright if (!group || !*group) 2529148c5f43SAlan Wright return (SMB_LGRP_PGRP_INVALID); 2530148c5f43SAlan Wright 2531148c5f43SAlan Wright for (c = *ptr; c != NULL; ptr++, c = *ptr) { 2532148c5f43SAlan Wright len++; 2533148c5f43SAlan Wright if (!isprint(c) || (c == ':') || (c == '\n')) 2534148c5f43SAlan Wright return (SMB_LGRP_PGRP_INVALID); 2535148c5f43SAlan Wright 2536148c5f43SAlan Wright if (!(islower(c) || isdigit(c))) 2537148c5f43SAlan Wright badchar++; 2538148c5f43SAlan Wright } 2539148c5f43SAlan Wright 2540148c5f43SAlan Wright if ((len > SMB_LGRP_PGRP_MAXGLEN - 1) || (badchar != 0)) 2541148c5f43SAlan Wright return (SMB_LGRP_PGRP_INVALID); 2542148c5f43SAlan Wright 2543148c5f43SAlan Wright if (getgrnam(group) != NULL) 2544148c5f43SAlan Wright return (SMB_LGRP_PGRP_NOTUNIQUE); 2545148c5f43SAlan Wright 2546148c5f43SAlan Wright return (SMB_LGRP_PGRP_UNIQUE); 2547148c5f43SAlan Wright } 2548148c5f43SAlan Wright 2549148c5f43SAlan Wright /* 2550148c5f43SAlan Wright * smb_lgrp_pgrp_add 2551148c5f43SAlan Wright * 2552148c5f43SAlan Wright * Create a posix group with the given name. 2553148c5f43SAlan Wright * This group will be added to the /etc/group file. 2554148c5f43SAlan Wright */ 2555148c5f43SAlan Wright static int 2556148c5f43SAlan Wright smb_lgrp_pgrp_add(char *group) 2557148c5f43SAlan Wright { 2558148c5f43SAlan Wright FILE *etcgrp; 2559148c5f43SAlan Wright FILE *etctmp; 2560*a7fe1d5bSAndy Stormont int o_mask; 2561148c5f43SAlan Wright int newdone = 0; 2562148c5f43SAlan Wright struct stat sb; 2563148c5f43SAlan Wright char buf[SMB_LGRP_PGRP_GRPBUFSIZ]; 2564148c5f43SAlan Wright gid_t gid; 2565148c5f43SAlan Wright int rc = 0; 2566148c5f43SAlan Wright 2567148c5f43SAlan Wright rc = smb_lgrp_pgrp_valid_gname(group); 2568148c5f43SAlan Wright if ((rc == SMB_LGRP_PGRP_INVALID) || (rc == SMB_LGRP_PGRP_NOTUNIQUE)) 2569148c5f43SAlan Wright return (-1); 2570148c5f43SAlan Wright 2571*a7fe1d5bSAndy Stormont if ((findnextgid(SMB_LGRP_PGRP_DEFRID, MAXUID, &gid)) != 0) 2572148c5f43SAlan Wright return (-1); 2573148c5f43SAlan Wright 2574148c5f43SAlan Wright if ((etcgrp = fopen(SMB_LGRP_PGRP_GROUP, "r")) == NULL) 2575148c5f43SAlan Wright return (-1); 2576148c5f43SAlan Wright 2577148c5f43SAlan Wright if (fstat(fileno(etcgrp), &sb) < 0) 2578148c5f43SAlan Wright sb.st_mode = S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH; 2579148c5f43SAlan Wright 2580148c5f43SAlan Wright o_mask = umask(077); 2581148c5f43SAlan Wright etctmp = fopen(SMB_LGRP_PGRP_GRPTMP, "w+"); 2582148c5f43SAlan Wright (void) umask(o_mask); 2583148c5f43SAlan Wright 2584148c5f43SAlan Wright if (etctmp == NULL) { 2585148c5f43SAlan Wright (void) fclose(etcgrp); 2586148c5f43SAlan Wright return (-1); 2587148c5f43SAlan Wright } 2588148c5f43SAlan Wright 2589148c5f43SAlan Wright if (lockf(fileno(etctmp), F_LOCK, 0) != 0) { 2590148c5f43SAlan Wright (void) fclose(etcgrp); 2591148c5f43SAlan Wright (void) fclose(etctmp); 2592148c5f43SAlan Wright (void) unlink(SMB_LGRP_PGRP_GRPTMP); 2593148c5f43SAlan Wright return (-1); 2594148c5f43SAlan Wright } 2595148c5f43SAlan Wright 2596148c5f43SAlan Wright if (fchmod(fileno(etctmp), sb.st_mode) != 0 || 2597148c5f43SAlan Wright fchown(fileno(etctmp), sb.st_uid, sb.st_gid) != 0) { 2598148c5f43SAlan Wright (void) lockf(fileno(etctmp), F_ULOCK, 0); 2599148c5f43SAlan Wright (void) fclose(etcgrp); 2600148c5f43SAlan Wright (void) fclose(etctmp); 2601148c5f43SAlan Wright (void) unlink(SMB_LGRP_PGRP_GRPTMP); 2602148c5f43SAlan Wright return (-1); 2603148c5f43SAlan Wright } 2604148c5f43SAlan Wright 2605148c5f43SAlan Wright while (fgets(buf, SMB_LGRP_PGRP_GRPBUFSIZ, etcgrp) != NULL) { 2606148c5f43SAlan Wright /* Check for NameService reference */ 2607148c5f43SAlan Wright if (!newdone && (buf[0] == '+' || buf[0] == '-')) { 2608148c5f43SAlan Wright (void) fprintf(etctmp, "%s::%u:\n", group, gid); 2609148c5f43SAlan Wright newdone = 1; 2610148c5f43SAlan Wright } 2611148c5f43SAlan Wright 2612148c5f43SAlan Wright (void) fputs(buf, etctmp); 2613148c5f43SAlan Wright } 2614148c5f43SAlan Wright (void) fclose(etcgrp); 2615148c5f43SAlan Wright 2616148c5f43SAlan Wright if (!newdone) 2617148c5f43SAlan Wright (void) fprintf(etctmp, "%s::%u:\n", group, gid); 2618148c5f43SAlan Wright 2619148c5f43SAlan Wright if (rename(SMB_LGRP_PGRP_GRPTMP, SMB_LGRP_PGRP_GROUP) < 0) { 2620148c5f43SAlan Wright (void) lockf(fileno(etctmp), F_ULOCK, 0); 2621148c5f43SAlan Wright (void) fclose(etctmp); 2622148c5f43SAlan Wright (void) unlink(SMB_LGRP_PGRP_GRPTMP); 2623148c5f43SAlan Wright return (-1); 2624148c5f43SAlan Wright } 2625148c5f43SAlan Wright 2626148c5f43SAlan Wright (void) lockf(fileno(etctmp), F_ULOCK, 0); 2627148c5f43SAlan Wright (void) fclose(etctmp); 2628148c5f43SAlan Wright return (0); 2629148c5f43SAlan Wright } 2630