15331Samw /* 25331Samw * CDDL HEADER START 35331Samw * 45331Samw * The contents of this file are subject to the terms of the 55331Samw * Common Development and Distribution License (the "License"). 65331Samw * You may not use this file except in compliance with the License. 75331Samw * 85331Samw * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 95331Samw * or http://www.opensolaris.org/os/licensing. 105331Samw * See the License for the specific language governing permissions 115331Samw * and limitations under the License. 125331Samw * 135331Samw * When distributing Covered Code, include this CDDL HEADER in each 145331Samw * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 155331Samw * If applicable, add the following below this CDDL HEADER, with the 165331Samw * fields enclosed by brackets "[]" replaced with your own identifying 175331Samw * information: Portions Copyright [yyyy] [name of copyright owner] 185331Samw * 195331Samw * CDDL HEADER END 205331Samw */ 215331Samw /* 225331Samw * Copyright 2007 Sun Microsystems, Inc. All rights reserved. 235331Samw * Use is subject to license terms. 245331Samw */ 255331Samw 265331Samw #pragma ident "%Z%%M% %I% %E% SMI" 275331Samw 285331Samw /* 295331Samw * Utility functions to support the RPC interface library. 305331Samw */ 315331Samw 325331Samw #include <stdio.h> 335331Samw #include <stdarg.h> 345331Samw #include <strings.h> 355331Samw #include <unistd.h> 365331Samw #include <netdb.h> 375331Samw #include <stdlib.h> 385331Samw #include <pwd.h> 395331Samw #include <grp.h> 405331Samw 415331Samw #include <sys/time.h> 425331Samw #include <sys/systm.h> 435331Samw 445331Samw #include <smbsrv/libsmb.h> 455331Samw #include <smbsrv/libsmbrdr.h> 465331Samw #include <smbsrv/libsmbns.h> 475331Samw #include <smbsrv/libmlsvc.h> 485331Samw 495331Samw #include <smbsrv/smbinfo.h> 505331Samw #include <smbsrv/ntsid.h> 515331Samw #include <smbsrv/lsalib.h> 525331Samw #include <smbsrv/samlib.h> 535331Samw #include <smbsrv/mlsvc_util.h> 545331Samw #include <smbsrv/mlsvc.h> 555331Samw 565331Samw extern int netr_open(char *, char *, mlsvc_handle_t *); 575331Samw extern int netr_close(mlsvc_handle_t *); 585331Samw extern DWORD netlogon_auth(char *, mlsvc_handle_t *, DWORD); 595331Samw extern int mlsvc_user_getauth(char *, char *, smb_auth_info_t *); 605331Samw 615331Samw static int mlsvc_lookup_local_name(char *name, nt_sid_t **sid); 625331Samw static int mlsvc_lookup_nt_name(char *name, nt_sid_t **sid); 635331Samw static int mlsvc_lookup_nt_sid(nt_sid_t *sid, char *buf, int bufsize); 645331Samw 655331Samw /* 665331Samw * Compare the supplied domain name with the local hostname. 675331Samw * We need to deal with both server names and fully-qualified 685331Samw * domain names. 695331Samw * 705331Samw * Returns: 715331Samw * 0 The specified domain is not the local domain, 725331Samw * 1 The Specified domain is the local domain. 735331Samw * -1 Invalid parameter or unable to get the local 745331Samw * system information. 755331Samw */ 765331Samw int 775331Samw mlsvc_is_local_domain(const char *domain) 785331Samw { 795331Samw char hostname[MAXHOSTNAMELEN]; 805331Samw uint32_t mode; 815331Samw int rc; 825331Samw 835331Samw if (strchr(domain, '.') != NULL) 845331Samw rc = smb_getfqhostname(hostname, MAXHOSTNAMELEN); 855331Samw else 865331Samw rc = smb_gethostname(hostname, MAXHOSTNAMELEN, 1); 875331Samw 885331Samw if (rc != 0) 895331Samw return (-1); 905331Samw 915331Samw rc = strcasecmp(domain, hostname); 925331Samw mode = smb_get_security_mode(); 935331Samw 945331Samw if ((rc == 0) || (mode == SMB_SECMODE_WORKGRP)) 955331Samw return (1); 965331Samw 975331Samw return (0); 985331Samw } 995331Samw 1005331Samw /* 1015331Samw * mlsvc_lookup_name 1025331Samw * 1035331Samw * Lookup a name in the specified domain and translate it to a SID. 1045331Samw * If the name is in the NT domain, it may refer to a user, group or 1055331Samw * alias. Otherwise it must refer to a UNIX username. The memory for 1065331Samw * the sid is allocated using malloc so the caller should call free 1075331Samw * when it is no longer required. 1085331Samw * 1095331Samw * On success, 0 will be returned and sid will point to a local domain 1105331Samw * user SID. Otherwise -1 will be returned. 1115331Samw */ 1125331Samw int 1135331Samw mlsvc_lookup_name(char *domain, char *name, nt_sid_t **sid) 1145331Samw { 1155331Samw if (domain == NULL || name == NULL || sid == NULL) 1165331Samw return (-1); 1175331Samw 1185331Samw if (mlsvc_is_local_domain(domain) == 1) 1195331Samw return (mlsvc_lookup_local_name(name, sid)); 1205331Samw else 1215331Samw return (mlsvc_lookup_nt_name(name, sid)); 1225331Samw } 1235331Samw 1245331Samw /* 1255331Samw * mlsvc_lookup_local_name 1265331Samw * 1275331Samw * Lookup a name in the local password file and translate it to a SID. 1285331Samw * The name must refer to a user. This is a private function intended 1295331Samw * to support mlsvc_lookup_name so it doesn't perform any parameter 1305331Samw * validation. The memory for the sid is allocated using malloc so the 1315331Samw * caller must call free when it is no longer required. 1325331Samw * 1335331Samw * On success, 0 will be returned and sid will point to a local domain 1345331Samw * user SID. Otherwise -1 will be returned. 1355331Samw */ 1365331Samw static int 1375331Samw mlsvc_lookup_local_name(char *name, nt_sid_t **sid) 1385331Samw { 1395331Samw struct passwd *pw; 1405331Samw nt_sid_t *domain_sid; 1415331Samw 1425331Samw if ((pw = getpwnam(name)) == NULL) 1435331Samw return (-1); 1445331Samw 1455331Samw if ((domain_sid = nt_domain_local_sid()) == NULL) 1465331Samw return (-1); 1475331Samw 1485331Samw *sid = nt_sid_splice(domain_sid, pw->pw_uid); 1495331Samw return (0); 1505331Samw } 1515331Samw 1525331Samw /* 1535331Samw * mlsvc_lookup_nt_name 1545331Samw * 1555331Samw * Lookup a name in the specified NT domain and translate it to a SID. 1565331Samw * The name may refer to a user, group or alias. This is a private 1575331Samw * function intended to support mlsvc_lookup_name so it doesn't do any 1585331Samw * parameter validation. The memory for the sid is allocated using 1595331Samw * malloc so the caller should call free when it is no longer required. 1605331Samw * 1615331Samw * On success, 0 will be returned and sid will point to an NT domain 1625331Samw * user SID. Otherwise -1 will be returned. 1635331Samw */ 1645331Samw static int 1655331Samw mlsvc_lookup_nt_name(char *name, nt_sid_t **sid) 1665331Samw { 1675331Samw smb_userinfo_t *user_info; 1685331Samw 1695331Samw if ((user_info = mlsvc_alloc_user_info()) == NULL) 1705331Samw return (-1); 1715331Samw 1725331Samw if (lsa_lookup_name(0, 0, name, user_info) != 0) 1735331Samw return (-1); 1745331Samw 1755331Samw *sid = nt_sid_splice(user_info->domain_sid, user_info->rid); 1765331Samw mlsvc_free_user_info(user_info); 1775331Samw return (0); 1785331Samw } 1795331Samw 1805331Samw /* 1815331Samw * mlsvc_lookup_sid 1825331Samw * 1835331Samw * Lookup a SID and translate it to a name. The name returned may refer 1845331Samw * to a domain, user, group or alias dependent on the SID. On success 0 1855331Samw * will be returned. Otherwise -1 will be returned. 1865331Samw */ 1875331Samw int 1885331Samw mlsvc_lookup_sid(nt_sid_t *sid, char *buf, int bufsize) 1895331Samw { 1905331Samw struct passwd *pw; 1915331Samw struct group *gr; 1925331Samw nt_group_t *grp; 1935331Samw DWORD rid; 1945331Samw 1955331Samw if (sid == NULL || buf == NULL) 1965331Samw return (-1); 1975331Samw 1985331Samw if (nt_sid_is_local(sid)) { 1995331Samw (void) nt_sid_get_rid(sid, &rid); 2005331Samw 2015331Samw switch (SAM_RID_TYPE(rid)) { 2025331Samw case SAM_RT_NT_UID: 2035331Samw break; 2045331Samw 2055331Samw case SAM_RT_NT_GID: 2065331Samw if ((grp = nt_groups_lookup_rid(rid)) == NULL) 2075331Samw return (-1); 2085331Samw 2095331Samw (void) strlcpy(buf, grp->name, bufsize); 2105331Samw break; 2115331Samw 2125331Samw case SAM_RT_UNIX_UID: 2135331Samw if ((pw = getpwuid(SAM_DECODE_RID(rid))) == NULL) 2145331Samw return (-1); 2155331Samw 2165331Samw (void) strlcpy(buf, pw->pw_name, bufsize); 2175331Samw break; 2185331Samw 2195331Samw case SAM_RT_UNIX_GID: 2205331Samw if ((gr = getgrgid(SAM_DECODE_RID(rid))) == NULL) 2215331Samw return (-1); 2225331Samw 2235331Samw (void) strlcpy(buf, gr->gr_name, bufsize); 2245331Samw break; 2255331Samw } 2265331Samw 2275331Samw return (0); 2285331Samw } 2295331Samw 2305331Samw return (mlsvc_lookup_nt_sid(sid, buf, bufsize)); 2315331Samw } 2325331Samw 2335331Samw /* 2345331Samw * mlsvc_lookup_nt_sid 2355331Samw * 2365331Samw * Lookup an NT SID and translate it to a name. This is a private 2375331Samw * function intended to support mlsvc_lookup_sid so it doesn't do any 2385331Samw * parameter validation. The input account_name specifies the logon/ 2395331Samw * session to be used for the lookup. It doesn't need to have any 2405331Samw * association with the SID being looked up. The name returned may 2415331Samw * refer to a domain, user, group or alias dependent on the SID. 2425331Samw * 2435331Samw * On success the name will be copied into buf and 0 will be returned. 2445331Samw * Otherwise -1 will be returned. 2455331Samw */ 2465331Samw static int 2475331Samw mlsvc_lookup_nt_sid(nt_sid_t *sid, char *buf, int bufsize) 2485331Samw { 2495331Samw smb_userinfo_t *user_info; 2505331Samw int rc; 2515331Samw 2525331Samw if ((user_info = mlsvc_alloc_user_info()) == NULL) 2535331Samw return (-1); 2545331Samw 2555331Samw if ((rc = lsa_lookup_sid(sid, user_info)) == 0) 2565331Samw (void) strlcpy(buf, user_info->name, bufsize); 2575331Samw 2585331Samw mlsvc_free_user_info(user_info); 2595331Samw return (rc); 2605331Samw } 2615331Samw 2625331Samw /* 2635331Samw * mlsvc_alloc_user_info 2645331Samw * 2655331Samw * Allocate a user_info structure and set the contents to zero. A 2665331Samw * pointer to the user_info structure is returned. 2675331Samw */ 2685331Samw smb_userinfo_t * 2695331Samw mlsvc_alloc_user_info(void) 2705331Samw { 2715331Samw smb_userinfo_t *user_info; 2725331Samw 2735331Samw user_info = (smb_userinfo_t *)malloc(sizeof (smb_userinfo_t)); 2745331Samw if (user_info == NULL) 2755331Samw return (NULL); 2765331Samw 2775331Samw bzero(user_info, sizeof (smb_userinfo_t)); 2785331Samw return (user_info); 2795331Samw } 2805331Samw 2815331Samw /* 2825331Samw * mlsvc_free_user_info 2835331Samw * 2845331Samw * Free a user_info structure. This function ensures that the contents 2855331Samw * of the user_info are freed as well as the user_info itself. 2865331Samw */ 2875331Samw void 2885331Samw mlsvc_free_user_info(smb_userinfo_t *user_info) 2895331Samw { 2905331Samw if (user_info) { 2915331Samw mlsvc_release_user_info(user_info); 2925331Samw free(user_info); 2935331Samw } 2945331Samw } 2955331Samw 2965331Samw /* 2975331Samw * mlsvc_release_user_info 2985331Samw * 2995331Samw * Release the contents of a user_info structure and zero out the 3005331Samw * elements but do not free the user_info structure itself. This 3015331Samw * function cleans out the structure so that it can be reused without 3025331Samw * worrying about stale contents. 3035331Samw */ 3045331Samw void 3055331Samw mlsvc_release_user_info(smb_userinfo_t *user_info) 3065331Samw { 3075331Samw int i; 3085331Samw 3095331Samw if (user_info == NULL) 3105331Samw return; 3115331Samw 3125331Samw free(user_info->name); 3135331Samw free(user_info->domain_sid); 3145331Samw free(user_info->domain_name); 3155331Samw free(user_info->groups); 3165331Samw 3175331Samw if (user_info->n_other_grps) { 3185331Samw for (i = 0; i < user_info->n_other_grps; i++) 3195331Samw free(user_info->other_grps[i].sid); 3205331Samw 3215331Samw free(user_info->other_grps); 3225331Samw } 3235331Samw 3245331Samw free(user_info->user_sid); 3255331Samw free(user_info->pgrp_sid); 3265331Samw bzero(user_info, sizeof (smb_userinfo_t)); 3275331Samw } 3285331Samw 3295331Samw /* 3305331Samw * mlsvc_setadmin_user_info 3315331Samw * 3325331Samw * Determines if the given user is the domain Administrator or a 3335331Samw * member of Domain Admins or Administrators group and set the 3345331Samw * user_info->flags accordingly. 3355331Samw */ 3365331Samw void 3375331Samw mlsvc_setadmin_user_info(smb_userinfo_t *user_info) 3385331Samw { 3395331Samw nt_domain_t *domain; 3405331Samw nt_group_t *grp; 3415331Samw int i; 3425331Samw 3435331Samw if ((domain = nt_domain_lookupbytype(NT_DOMAIN_PRIMARY)) == NULL) 3445331Samw return; 3455331Samw 3465331Samw if (!nt_sid_is_equal((nt_sid_t *)user_info->domain_sid, domain->sid)) 3475331Samw return; 3485331Samw 3495331Samw if (user_info->rid == DOMAIN_USER_RID_ADMIN) 3505331Samw user_info->flags |= SMB_UINFO_FLAG_DADMIN; 3515331Samw else if (user_info->primary_group_rid == DOMAIN_GROUP_RID_ADMINS) 3525331Samw user_info->flags |= SMB_UINFO_FLAG_DADMIN; 3535331Samw else { 3545331Samw for (i = 0; i < user_info->n_groups; i++) 3555331Samw if (user_info->groups[i].rid == DOMAIN_GROUP_RID_ADMINS) 3565331Samw user_info->flags |= SMB_UINFO_FLAG_DADMIN; 3575331Samw } 3585331Samw 3595331Samw grp = nt_group_getinfo("Administrators", RWLOCK_READER); 3605331Samw if (grp) { 3615331Samw i = nt_group_is_member(grp, user_info->user_sid); 3625331Samw nt_group_putinfo(grp); 3635331Samw if (i) 3645331Samw user_info->flags |= SMB_UINFO_FLAG_LADMIN; 3655331Samw } 3665331Samw } 3675331Samw 3685331Samw /* 3695331Samw * mlsvc_string_save 3705331Samw * 3715331Samw * This is a convenience function to prepare strings for an RPC call. 3725331Samw * An ms_string_t is set up with the appropriate lengths and str is 3735331Samw * set up to point to a copy of the original string on the heap. The 3745331Samw * macro MLRPC_HEAP_STRSAVE is an alias for mlrpc_heap_strsave, which 3755331Samw * extends the heap and copies the string into the new area. 3765331Samw */ 3775331Samw int 3785331Samw mlsvc_string_save(ms_string_t *ms, char *str, struct mlrpc_xaction *mxa) 3795331Samw { 380*5521Sas200622 if (str == NULL) 3815331Samw return (0); 3825331Samw 383*5521Sas200622 ms->length = mts_wcequiv_strlen(str); 384*5521Sas200622 ms->allosize = ms->length + sizeof (mts_wchar_t); 3855331Samw 386*5521Sas200622 if ((ms->str = MLRPC_HEAP_STRSAVE(mxa, str)) == NULL) 387*5521Sas200622 return (0); 3885331Samw 3895331Samw return (1); 3905331Samw } 3915331Samw 3925331Samw /* 3935331Samw * mlsvc_sid_save 3945331Samw * 3955331Samw * Expand the heap and copy the sid into the new area. 3965331Samw * Returns a pointer to the copy of the sid on the heap. 3975331Samw */ 3985331Samw nt_sid_t * 3995331Samw mlsvc_sid_save(nt_sid_t *sid, struct mlrpc_xaction *mxa) 4005331Samw { 4015331Samw nt_sid_t *heap_sid; 4025331Samw unsigned size; 4035331Samw 4045331Samw if (sid == NULL) 4055331Samw return (NULL); 4065331Samw 4075331Samw size = nt_sid_length(sid); 4085331Samw 4095331Samw if ((heap_sid = (nt_sid_t *)MLRPC_HEAP_MALLOC(mxa, size)) == NULL) 4105331Samw return (0); 4115331Samw 4125331Samw bcopy(sid, heap_sid, size); 4135331Samw return (heap_sid); 4145331Samw } 4155331Samw 4165331Samw /* 4175331Samw * mlsvc_is_null_handle 4185331Samw * 4195331Samw * Check a handle against a null handle. Returns 1 if the handle is 4205331Samw * null. Otherwise returns 0. 4215331Samw */ 4225331Samw int 4235331Samw mlsvc_is_null_handle(mlsvc_handle_t *handle) 4245331Samw { 4255331Samw static ms_handle_t zero_handle; 4265331Samw 4275331Samw if (handle == NULL || handle->context == NULL) 4285331Samw return (1); 4295331Samw 4305331Samw if (!memcmp(&handle->handle, &zero_handle, sizeof (ms_handle_t))) 4315331Samw return (1); 4325331Samw 4335331Samw return (0); 4345331Samw } 4355331Samw 4365331Samw /* 437*5521Sas200622 * mlsvc_join 4385331Samw * 4395331Samw * Returns NT status codes. 4405331Samw */ 4415331Samw DWORD 442*5521Sas200622 mlsvc_join(char *server, char *domain, char *plain_user, char *plain_text) 4435331Samw { 4445331Samw smb_auth_info_t auth; 4455331Samw smb_ntdomain_t *di; 4465331Samw int erc; 4475331Samw DWORD status; 4485331Samw mlsvc_handle_t netr_handle; 4495331Samw char machine_passwd[MLSVC_MACHINE_ACCT_PASSWD_MAX]; 4505331Samw 4515331Samw machine_passwd[0] = '\0'; 4525331Samw 4535331Samw /* 4545331Samw * Ensure that the domain name is uppercase. 4555331Samw */ 4565331Samw (void) utf8_strupr(domain); 4575331Samw 4585331Samw /* 4595331Samw * There is no point continuing if the domain information is 4605331Samw * not available. Wait for up to 10 seconds and then give up. 4615331Samw */ 4625331Samw if ((di = smb_getdomaininfo(10)) == 0) { 4635331Samw status = NT_STATUS_CANT_ACCESS_DOMAIN_INFO; 4645331Samw return (status); 4655331Samw } 4665331Samw 4675331Samw if (strcasecmp(domain, di->domain) != 0) { 4685331Samw status = NT_STATUS_INVALID_PARAMETER; 4695331Samw return (status); 4705331Samw } 4715331Samw 472*5521Sas200622 erc = mlsvc_logon(server, domain, plain_user); 4735331Samw 4745331Samw if (erc == AUTH_USER_GRANT) { 4755331Samw int isenabled; 4765331Samw 4775331Samw smb_config_rdlock(); 4785331Samw isenabled = smb_config_getyorn(SMB_CI_ADS_ENABLE); 4795331Samw smb_config_unlock(); 4805331Samw if (isenabled) { 481*5521Sas200622 if (ads_join(plain_user, plain_text, machine_passwd, 482*5521Sas200622 sizeof (machine_passwd)) == ADJOIN_SUCCESS) 4835331Samw status = NT_STATUS_SUCCESS; 484*5521Sas200622 else 4855331Samw status = NT_STATUS_UNSUCCESSFUL; 4865331Samw } else { 4875331Samw if (mlsvc_user_getauth(server, plain_user, &auth) 4885331Samw != 0) { 4895331Samw status = NT_STATUS_INVALID_PARAMETER; 4905331Samw return (status); 4915331Samw } 4925331Samw 4935331Samw status = sam_create_trust_account(server, domain, 4945331Samw &auth); 4955331Samw if (status == NT_STATUS_SUCCESS) { 4965331Samw (void) smb_gethostname(machine_passwd, 4975331Samw sizeof (machine_passwd), 0); 4985331Samw (void) utf8_strlwr(machine_passwd); 4995331Samw } 5005331Samw } 5015331Samw 5025331Samw if (status == NT_STATUS_SUCCESS) { 503*5521Sas200622 if (smb_set_machine_pwd(machine_passwd) != 0) 5045331Samw return (NT_STATUS_UNSUCCESSFUL); 5055331Samw 5065331Samw /* 5075331Samw * If we successfully create a trust account, we mark 5085331Samw * ourselves as a domain member in the environment so 5095331Samw * that we use the SAMLOGON version of the NETLOGON 5105331Samw * PDC location protocol. 5115331Samw */ 5125331Samw smb_set_domain_member(1); 5135331Samw 5145331Samw if (netr_open(server, domain, &netr_handle) == 0) { 5155331Samw status = netlogon_auth(server, &netr_handle, 5165331Samw NETR_FLG_INIT); 5175331Samw (void) netr_close(&netr_handle); 5185331Samw } else { 5195331Samw status = NT_STATUS_OPEN_FAILED; 5205331Samw } 5215331Samw } 5225331Samw } else { 5235331Samw status = NT_STATUS_LOGON_FAILURE; 5245331Samw } 5255331Samw 5265331Samw return (status); 5275331Samw } 5285331Samw 5295331Samw /*ARGSUSED*/ 5305331Samw void 5315331Samw nt_group_ht_lock(krwmode_t locktype) 5325331Samw { 5335331Samw } 5345331Samw 5355331Samw void 5365331Samw nt_group_ht_unlock(void) 5375331Samw { 5385331Samw } 5395331Samw 5405331Samw int 5415331Samw nt_group_num_groups(void) 5425331Samw { 5435331Samw return (0); 5445331Samw } 5455331Samw 5465331Samw /*ARGSUSED*/ 5475331Samw uint32_t 5485331Samw nt_group_add(char *gname, char *comment) 5495331Samw { 5505331Samw return (NT_STATUS_NOT_SUPPORTED); 5515331Samw } 5525331Samw 5535331Samw /*ARGSUSED*/ 5545331Samw uint32_t 5555331Samw nt_group_modify(char *gname, char *new_gname, char *comment) 5565331Samw { 5575331Samw return (NT_STATUS_NOT_SUPPORTED); 5585331Samw } 5595331Samw 5605331Samw /*ARGSUSED*/ 5615331Samw uint32_t 5625331Samw nt_group_delete(char *gname) 5635331Samw { 5645331Samw return (NT_STATUS_NOT_SUPPORTED); 5655331Samw } 5665331Samw 5675331Samw /*ARGSUSED*/ 5685331Samw nt_group_t * 5695331Samw nt_group_getinfo(char *gname, krwmode_t locktype) 5705331Samw { 5715331Samw return (NULL); 5725331Samw } 5735331Samw 5745331Samw /*ARGSUSED*/ 5755331Samw void 5765331Samw nt_group_putinfo(nt_group_t *grp) 5775331Samw { 5785331Samw } 5795331Samw 5805331Samw /*ARGSUSED*/ 5815331Samw int 5825331Samw nt_group_getpriv(nt_group_t *grp, uint32_t priv_id) 5835331Samw { 5845331Samw return (SE_PRIVILEGE_DISABLED); 5855331Samw } 5865331Samw 5875331Samw /*ARGSUSED*/ 5885331Samw uint32_t 5895331Samw nt_group_setpriv(nt_group_t *grp, uint32_t priv_id, uint32_t new_attr) 5905331Samw { 5915331Samw return (NT_STATUS_NOT_SUPPORTED); 5925331Samw } 5935331Samw 5945331Samw /*ARGSUSED*/ 5955331Samw int 5965331Samw nt_group_is_member(nt_group_t *grp, nt_sid_t *sid) 5975331Samw { 5985331Samw return (0); 5995331Samw } 6005331Samw 6015331Samw /*ARGSUSED*/ 6025331Samw uint32_t 6035331Samw nt_group_add_member(nt_group_t *grp, nt_sid_t *msid, uint16_t sid_name_use, 6045331Samw char *account) 6055331Samw { 6065331Samw return (NT_STATUS_NOT_SUPPORTED); 6075331Samw } 6085331Samw 6095331Samw /*ARGSUSED*/ 6105331Samw uint32_t 6115331Samw nt_group_del_member(nt_group_t *grp, void *key, int keytype) 6125331Samw { 6135331Samw return (NT_STATUS_NOT_SUPPORTED); 6145331Samw } 6155331Samw 6165331Samw /*ARGSUSED*/ 6175331Samw int 6185331Samw nt_group_num_members(nt_group_t *grp) 6195331Samw { 6205331Samw return (0); 6215331Samw } 6225331Samw 6235331Samw nt_group_iterator_t * 6245331Samw nt_group_open_iterator(void) 6255331Samw { 6265331Samw return (NULL); 6275331Samw } 6285331Samw 6295331Samw /*ARGSUSED*/ 6305331Samw void 6315331Samw nt_group_close_iterator(nt_group_iterator_t *gi) 6325331Samw { 6335331Samw } 6345331Samw 6355331Samw /*ARGSUSED*/ 6365331Samw nt_group_t * 6375331Samw nt_group_iterate(nt_group_iterator_t *gi) 6385331Samw { 6395331Samw return (NULL); 6405331Samw } 6415331Samw 6425331Samw int 6435331Samw nt_group_cache_size(void) 6445331Samw { 6455331Samw return (0); 6465331Samw } 6475331Samw 6485331Samw uint32_t 6495331Samw sam_init(void) 6505331Samw { 6515331Samw return (NT_STATUS_SUCCESS); 6525331Samw } 6535331Samw 6545331Samw /*ARGSUSED*/ 6555331Samw uint32_t 6565331Samw nt_group_add_member_byname(char *gname, char *account) 6575331Samw { 6585331Samw return (NT_STATUS_NOT_SUPPORTED); 6595331Samw } 6605331Samw 6615331Samw /*ARGSUSED*/ 6625331Samw uint32_t 6635331Samw nt_group_del_member_byname(nt_group_t *grp, char *member_name) 6645331Samw { 6655331Samw return (NT_STATUS_NOT_SUPPORTED); 6665331Samw } 6675331Samw 6685331Samw /*ARGSUSED*/ 6695331Samw void 6705331Samw nt_group_add_groupprivs(nt_group_t *grp, smb_privset_t *priv) 6715331Samw { 6725331Samw } 6735331Samw 6745331Samw /*ARGSUSED*/ 6755331Samw uint32_t 6765331Samw nt_groups_member_privs(nt_sid_t *sid, smb_privset_t *priv) 6775331Samw { 6785331Samw return (NT_STATUS_SUCCESS); 6795331Samw } 6805331Samw 6815331Samw /*ARGSUSED*/ 6825331Samw int 6835331Samw nt_groups_member_ngroups(nt_sid_t *sid) 6845331Samw { 6855331Samw return (0); 6865331Samw } 6875331Samw 6885331Samw /*ARGSUSED*/ 6895331Samw uint32_t 6905331Samw nt_groups_member_groups(nt_sid_t *sid, smb_id_t *grps, int ngrps) 6915331Samw { 6925331Samw return (NT_STATUS_SUCCESS); 6935331Samw } 6945331Samw 6955331Samw /*ARGSUSED*/ 6965331Samw nt_group_t * 6975331Samw nt_groups_lookup_rid(uint32_t rid) 6985331Samw { 6995331Samw return (NULL); 7005331Samw } 7015331Samw 7025331Samw /*ARGSUSED*/ 7035331Samw int 7045331Samw nt_groups_count(int cnt_opt) 7055331Samw { 7065331Samw return (0); 7075331Samw } 7085331Samw 7095331Samw /*ARGSUSED*/ 7105331Samw int 7115331Samw nt_group_member_list(int offset, nt_group_t *grp, 7125331Samw ntgrp_member_list_t *rmembers) 7135331Samw { 7145331Samw return (0); 7155331Samw } 7165331Samw 7175331Samw /*ARGSUSED*/ 7185331Samw void 7195331Samw nt_group_list(int offset, char *pattern, ntgrp_list_t *list) 7205331Samw { 7215331Samw } 722