diff options
Diffstat (limited to 'source4/lib')
| -rw-r--r-- | source4/lib/account_pol.c | 169 | ||||
| -rw-r--r-- | source4/lib/adt_tree.c | 464 | ||||
| -rw-r--r-- | source4/lib/basic.mk | 2 | ||||
| -rw-r--r-- | source4/lib/genrand.c | 17 | ||||
| -rw-r--r-- | source4/lib/sysacls.c | 3198 | ||||
| -rw-r--r-- | source4/lib/username.c | 318 | 
6 files changed, 0 insertions, 4168 deletions
diff --git a/source4/lib/account_pol.c b/source4/lib/account_pol.c deleted file mode 100644 index df1479da3a..0000000000 --- a/source4/lib/account_pol.c +++ /dev/null @@ -1,169 +0,0 @@ -/*  - *  Unix SMB/CIFS implementation. - *  account policy storage - *  Copyright (C) Jean Fran�ois Micouleau      1998-2001. - *  Copyright (C) Andrew Bartlett              2002 - *   - *  This program is free software; you can redistribute it and/or modify - *  it under the terms of the GNU General Public License as published by - *  the Free Software Foundation; either version 2 of the License, or - *  (at your option) any later version. - *   - *  This program is distributed in the hope that it will be useful, - *  but WITHOUT ANY WARRANTY; without even the implied warranty of - *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the - *  GNU General Public License for more details. - *   - *  You should have received a copy of the GNU General Public License - *  along with this program; if not, write to the Free Software - *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - */ - -#include "includes.h" -static TDB_CONTEXT *tdb; /* used for driver files */ - -#define DATABASE_VERSION 1 - -/**************************************************************************** - Open the account policy tdb. -****************************************************************************/ - -BOOL init_account_policy(void) -{ -	static pid_t local_pid; -	const char *vstring = "INFO/version"; -	uint32 version; -	TALLOC_CTX *mem_ctx; - -	if (tdb && local_pid == getpid()) -		return True; -	mem_ctx = talloc_init("init_account_policy"); -	if (!mem_ctx) { -		DEBUG(0,("No memory to open account policy database\n")); -		return False; -	} -	tdb = tdb_open_log(lock_path(mem_ctx, "account_policy.tdb"), 0, TDB_DEFAULT, O_RDWR|O_CREAT, 0600); -	talloc_destroy(mem_ctx); -	if (!tdb) { -		DEBUG(0,("Failed to open account policy database\n")); -		return False; -	} - -	local_pid = getpid(); - -	/* handle a Samba upgrade */ -	tdb_lock_bystring(tdb, vstring,0); -	if (!tdb_fetch_uint32(tdb, vstring, &version) || version != DATABASE_VERSION) { -		tdb_traverse(tdb, tdb_traverse_delete_fn, NULL); -		tdb_store_uint32(tdb, vstring, DATABASE_VERSION); -		 -		account_policy_set(AP_MIN_PASSWORD_LEN, MINPASSWDLENGTH);   /* 5 chars minimum             */ -		account_policy_set(AP_PASSWORD_HISTORY, 0);		    /* don't keep any old password */ -		account_policy_set(AP_USER_MUST_LOGON_TO_CHG_PASS, 0);	    /* don't force user to logon   */ -		account_policy_set(AP_MAX_PASSWORD_AGE, MAX_PASSWORD_AGE);  /* 21 days                     */ -		account_policy_set(AP_MIN_PASSWORD_AGE, 0);		    /* 0 days                      */ -		account_policy_set(AP_LOCK_ACCOUNT_DURATION, 0);	    /* lockout for 0 minutes       */ -		account_policy_set(AP_RESET_COUNT_TIME, 0);		    /* reset immediatly            */ -		account_policy_set(AP_BAD_ATTEMPT_LOCKOUT, 0);		    /* don't lockout               */ -		account_policy_set(AP_TIME_TO_LOGOUT, -1);		    /* don't force logout          */ -	} -	tdb_unlock_bystring(tdb, vstring); - -	return True; -} - -static const struct { -	int field; -	const char *string; -} account_policy_names[] = { -	{AP_MIN_PASSWORD_LEN, "min password length"}, -	{AP_PASSWORD_HISTORY, "password history"}, -	{AP_USER_MUST_LOGON_TO_CHG_PASS, "user must logon to change password"}, -	{AP_MAX_PASSWORD_AGE, "maximum password age"}, -	{AP_MIN_PASSWORD_AGE,"minimum password age"}, -	{AP_LOCK_ACCOUNT_DURATION, "lockout duration"}, -	{AP_RESET_COUNT_TIME, "reset count minutes"}, -	{AP_BAD_ATTEMPT_LOCKOUT, "bad lockout attempt"}, -	{AP_TIME_TO_LOGOUT, "disconnect time"}, -	{0, NULL} -}; - -/**************************************************************************** -Get the account policy name as a string from its #define'ed number -****************************************************************************/ - -static const char *decode_account_policy_name(int field) -{ -	int i; -	for (i=0; account_policy_names[i].string; i++) { -		if (field == account_policy_names[i].field) -			return account_policy_names[i].string; -	} -	return NULL; - -} - -/**************************************************************************** -Get the account policy name as a string from its #define'ed number -****************************************************************************/ - -int account_policy_name_to_fieldnum(const char *name) -{ -	int i; -	for (i=0; account_policy_names[i].string; i++) { -		if (strcmp(name, account_policy_names[i].string) == 0) -			return account_policy_names[i].field; -	} -	return 0; - -} - - -/**************************************************************************** -****************************************************************************/ -BOOL account_policy_get(int field, uint32 *value) -{ -	fstring name; - -	init_account_policy(); - -	*value = 0; - -	fstrcpy(name, decode_account_policy_name(field)); -	if (!*name) { -		DEBUG(1, ("account_policy_get: Field %d is not a valid account policy type!  Cannot get, returning 0.\n", field)); -		return False; -	} -	if (!tdb_fetch_uint32(tdb, name, value)) { -		DEBUG(1, ("account_policy_get: tdb_fetch_uint32 failed for efild %d (%s), returning 0", field, name)); -		return False; -	} -	DEBUG(10,("account_policy_get: %s:%d\n", name, *value)); -	return True; -} - - -/**************************************************************************** -****************************************************************************/ -BOOL account_policy_set(int field, uint32 value) -{ -	fstring name; - -	init_account_policy(); - -	fstrcpy(name, decode_account_policy_name(field)); -	if (!*name) { -		DEBUG(1, ("Field %d is not a valid account policy type!  Cannot set.\n", field)); -		return False; -	} - -	if (!tdb_store_uint32(tdb, name, value)) { -		DEBUG(1, ("tdb_store_uint32 failed for field %d (%s) on value %u", field, name, value)); -		return False; -	} - -	DEBUG(10,("account_policy_set: %s:%d\n", name, value)); -	 -	return True; -} - diff --git a/source4/lib/adt_tree.c b/source4/lib/adt_tree.c deleted file mode 100644 index 0bc224ec23..0000000000 --- a/source4/lib/adt_tree.c +++ /dev/null @@ -1,464 +0,0 @@ -/*  - *  Unix SMB/CIFS implementation. - *  Generic Abstract Data Types - *  Copyright (C) Gerald Carter                     2002. - * - *  This program is free software; you can redistribute it and/or modify - *  it under the terms of the GNU General Public License as published by - *  the Free Software Foundation; either version 2 of the License, or - *  (at your option) any later version. - *   - *  This program is distributed in the hope that it will be useful, - *  but WITHOUT ANY WARRANTY; without even the implied warranty of - *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the - *  GNU General Public License for more details. - *   - *  You should have received a copy of the GNU General Public License - *  along with this program; if not, write to the Free Software - *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - */ - -#include "includes.h" - - -/************************************************************************** - Initialize the tree's root.  The cmp_fn is a callback function used - for comparision of two children - *************************************************************************/ - -static BOOL trim_tree_keypath( char *path, char **base, char **new_path ) -{ -	char *p; -	 -	*new_path = *base = NULL; -	 -	if ( !path ) -		return False; -	 -	*base = path; -	 -	p = strchr( path, '/' ); -	 -	if ( p ) { -		*p = '\0'; -		*new_path = p+1; -	} -	 -	return True; -} - -  -/************************************************************************** - Initialize the tree's root.  The cmp_fn is a callback function used - for comparision of two children - *************************************************************************/ - -SORTED_TREE* sorted_tree_init( void *data_p, -                               int (cmp_fn)(void*, void*), -                               void (free_fn)(void*) ) -{ -	SORTED_TREE *tree = NULL; -	 -	if ( !(tree = (SORTED_TREE*)malloc( sizeof(SORTED_TREE) )) ) -		return NULL; -		 -	ZERO_STRUCTP( tree ); -	 -	tree->compare = cmp_fn; -	tree->free    = free_fn; -	 -	if ( !(tree->root = (TREE_NODE*)malloc( sizeof(TREE_NODE) )) ) { -		SAFE_FREE( tree ); -		return NULL; -	} -	 -	ZERO_STRUCTP( tree->root ); -	tree->root->data_p = data_p; -	 -	return tree; -} - - -/************************************************************************** - Delete a tree and free all allocated memory - *************************************************************************/ - -static void sorted_tree_destroy_children( TREE_NODE *root ) -{ -	int i; -	 -	if ( !root ) -		return; -	 -	for ( i=0; i<root->num_children; i++ ) -	{ -		sorted_tree_destroy_children( root->children[i] );	 -	} -	 -	SAFE_FREE( root->children ); -	SAFE_FREE( root->key ); -	 -	return; -} - -/************************************************************************** - Delete a tree and free all allocated memory - *************************************************************************/ - -void sorted_tree_destroy( SORTED_TREE *tree ) -{ -	if ( tree->root ) -		sorted_tree_destroy_children( tree->root );	 -	 -	if ( tree->free ) -		tree->free( tree->root ); -	 -	SAFE_FREE( tree ); -} - -/************************************************************************** - Find the next child given a key string - *************************************************************************/ - -static TREE_NODE* sorted_tree_birth_child( TREE_NODE *node, char* key ) -{ -	TREE_NODE *infant = NULL; -	TREE_NODE **siblings; -	int i; -	 -	if ( !(infant = (TREE_NODE*)malloc( sizeof(TREE_NODE) )) ) -		return NULL; -	 -	ZERO_STRUCTP( infant ); -		 -	infant->key = strdup( key ); -	infant->parent = node; -	 -	siblings = Realloc( node->children, sizeof(TREE_NODE*)*(node->num_children+1) ); -	 -	if ( siblings ) -		node->children = siblings; -	 -	node->num_children++; -	 -	/* first child */ -	 -	if ( node->num_children == 1 ) { -		DEBUG(11,("sorted_tree_birth_child: First child of node [%s]! [%s]\n",  -			node->key ? node->key : "NULL", infant->key )); -		node->children[0] = infant; -	} -	else  -	{ -		/*  -		 * multiple siblings .... (at least 2 children) -		 *  -		 * work from the end of the list forward  -		 * The last child is not set at this point  -		 * Insert the new infanct in ascending order  -		 * from left to right -		 */ -	 -		for ( i = node->num_children-1; i>=1; i-- ) -		{ -			DEBUG(11,("sorted_tree_birth_child: Looking for crib; infant -> [%s], child -> [%s]\n", -				infant->key, node->children[i-1]->key)); -			 -			/* the strings should never match assuming that we  -			   have called sorted_tree_find_child() first */ -		 -			if ( StrCaseCmp( infant->key, node->children[i-1]->key ) > 0 ) { -				DEBUG(11,("sorted_tree_birth_child: storing infant in i == [%d]\n",  -					i)); -				node->children[i] = infant; -				break; -			} -			 -			/* bump everything towards the end on slot */ -			 -			node->children[i] = node->children[i-1]; -		} - -		DEBUG(11,("sorted_tree_birth_child: Exiting loop (i == [%d])\n", i )); -		 -		/* if we haven't found the correct slot yet, the child  -		   will be first in the list */ -		    -		if ( i == 0 ) -			node->children[0] = infant; -	} - -	return infant; -} - -/************************************************************************** - Find the next child given a key string - *************************************************************************/ - -static TREE_NODE* sorted_tree_find_child( TREE_NODE *node, char* key ) -{ -	TREE_NODE *next = NULL; -	int i, result; -	 -	if ( !node ) { -		DEBUG(0,("sorted_tree_find_child: NULL node passed into function!\n")); -		return NULL; -	} -	 -	if ( !key ) { -		DEBUG(0,("sorted_tree_find_child: NULL key string passed into function!\n")); -		return NULL; -	} -	 -	for ( i=0; i<node->num_children; i++ ) -	{	 -		DEBUG(11,("sorted_tree_find_child: child key => [%s]\n", -			node->children[i]->key)); -			 -		result = StrCaseCmp( node->children[i]->key, key ); -		 -		if ( result == 0 ) -			next = node->children[i]; -		 -		/* if result > 0 then we've gone to far because -		   the list of children is sorted by key name  -		   If result == 0, then we have a match         */ -		    -		if ( result > 0 ) -			break; -	} - -	DEBUG(11,("sorted_tree_find_child: %s [%s]\n", -		next ? "Found" : "Did not find", key ));	 -	 -	return next; -} - -/************************************************************************** - Add a new node into the tree given a key path and a blob of data - *************************************************************************/ - -BOOL sorted_tree_add( SORTED_TREE *tree, const char *path, void *data_p ) -{ -	char *str, *base, *path2; -	TREE_NODE *current, *next; -	BOOL ret = True; -	 -	DEBUG(8,("sorted_tree_add: Enter\n")); -		 -	if ( !path || *path != '/' ) { -		DEBUG(0,("sorted_tree_add: Attempt to add a node with a bad path [%s]\n", -			path ? path : "NULL" )); -		return False; -	} -	 -	if ( !tree ) { -		DEBUG(0,("sorted_tree_add: Attempt to add a node to an uninitialized tree!\n")); -		return False; -	} -	 -	/* move past the first '/' */ -	 -	path++;	 -	path2 = strdup( path ); -	if ( !path2 ) { -		DEBUG(0,("sorted_tree_add: strdup() failed on string [%s]!?!?!\n", path)); -		return False; -	} -	 - -	/*  -	 * this works sort of like a 'mkdir -p'	call, possibly  -	 * creating an entire path to the new node at once -	 * The path should be of the form /<key1>/<key2>/... -	 */ -	 -	base = path2; -	str  = path2; -	current = tree->root; -	 -	do { -		/* break off the remaining part of the path */ -		 -		str = strchr( str, '/' ); -		if ( str ) -			*str = '\0'; -			 -		/* iterate to the next child--birth it if necessary */ -		 -		next = sorted_tree_find_child( current, base ); -		if ( !next ) { -			next = sorted_tree_birth_child( current, base ); -			if ( !next ) { -				DEBUG(0,("sorted_tree_add: Failed to create new child!\n")); -				ret =  False; -				goto done; -			} -		} -		current = next; -		 -		/* setup the next part of the path */ -		 -		base = str; -		if ( base ) { -			*base = '/'; -			base++; -			str = base; -		} -	 -	} while ( base != NULL ); -	 -	current->data_p = data_p; -	 -	DEBUG(10,("sorted_tree_add: Successfully added node [%s] to tree\n", -		path )); - -	DEBUG(8,("sorted_tree_add: Exit\n")); - -done: -	SAFE_FREE( path2 ); -	return ret; -} - - -/************************************************************************** - Recursive routine to print out all children of a TREE_NODE - *************************************************************************/ - -static void sorted_tree_print_children( TREE_NODE *node, int debug, const char *path ) -{ -	int i; -	int num_children; -	pstring path2; -	 -	if ( !node ) -		return; -	 -	 -	if ( node->key ) -		DEBUG(debug,("%s: [%s] (%s)\n", path ? path : "NULL", node->key, -			node->data_p ? "data" : "NULL" )); - -	*path2 = '\0'; -	if ( path ) -		pstrcpy( path2, path ); -	pstrcat( path2, node->key ? node->key : "NULL" ); -	pstrcat( path2, "/" ); -		 -	num_children = node->num_children; -	for ( i=0; i<num_children; i++ ) -		sorted_tree_print_children( node->children[i], debug, path2 ); -	 - -} - -/************************************************************************** - Dump the kys for a tree to the log file - *************************************************************************/ - -void sorted_tree_print_keys( SORTED_TREE *tree, int debug ) -{ -	int i; -	int num_children = tree->root->num_children; -	 -	if ( tree->root->key ) -		DEBUG(debug,("ROOT/: [%s] (%s)\n", tree->root->key, -			tree->root->data_p ? "data" : "NULL" )); -	 -	for ( i=0; i<num_children; i++ ) { -		sorted_tree_print_children( tree->root->children[i], debug,  -			tree->root->key ? tree->root->key : "ROOT/" ); -	} -	 -} - -/************************************************************************** - return the data_p for for the node in tree matching the key string - The key string is the full path.  We must break it apart and walk  - the tree - *************************************************************************/ - -void* sorted_tree_find( SORTED_TREE *tree, char *key ) -{ -	char *keystr, *base, *str, *p; -	TREE_NODE *current; -	void *result = NULL; -	 -	DEBUG(10,("sorted_tree_find: Enter [%s]\n", key ? key : "NULL" )); - -	/* sanity checks first */ -	 -	if ( !key ) { -		DEBUG(0,("sorted_tree_find: Attempt to search tree using NULL search string!\n")); -		return NULL; -	} -	 -	if ( !tree ) { -		DEBUG(0,("sorted_tree_find: Attempt to search an uninitialized tree using string [%s]!\n", -			key ? key : "NULL" )); -		return NULL; -	} -	 -	if ( !tree->root ) -		return NULL; -	 -	/* make a copy to play with */ -	 -	if ( *key == '/' ) -		keystr = strdup( key+1 ); -	else -		keystr = strdup( key ); -	 -	if ( !keystr ) { -		DEBUG(0,("sorted_tree_find: strdup() failed on string [%s]!?!?!\n", key)); -		return NULL; -	} - -	/* start breaking the path apart */ -	 -	p = keystr; -	current = tree->root; -	 -	if ( tree->root->data_p ) -		result = tree->root->data_p; -		 -	do -	{ -		/* break off the remaining part of the path */ - -		trim_tree_keypath( p, &base, &str ); -			 -		DEBUG(11,("sorted_tree_find: [loop] base => [%s], new_path => [%s]\n",  -			base, str)); - -		/* iterate to the next child */ -		 -		current = sorted_tree_find_child( current, base ); -	 -		/*  -		 * the idea is that the data_p for a parent should  -		 * be inherited by all children, but allow it to be  -		 * overridden farther down -		 */ -		 -		if ( current && current->data_p ) -			result = current->data_p; - -		/* reset the path pointer 'p' to the remaining part of the key string */ - -		p = str; -	    -	} while ( str && current ); -	 -	/* result should be the data_p from the lowest match node in the tree */ -	if ( result ) -		DEBUG(11,("sorted_tree_find: Found data_p!\n")); -	 -	SAFE_FREE( keystr ); -	 -	DEBUG(10,("sorted_tree_find: Exit\n")); -	 -	return result; -} - - diff --git a/source4/lib/basic.mk b/source4/lib/basic.mk index 698c09a563..3a1f127853 100644 --- a/source4/lib/basic.mk +++ b/source4/lib/basic.mk @@ -18,8 +18,6 @@ ADD_OBJ_FILES = \  		lib/time.o \  		lib/genrand.o \  		lib/username.o \ -		lib/util_getent.o \ -		lib/util_pw.o \  		lib/smbrun.o \  		lib/bitmap.o \  		lib/snprintf.o \ diff --git a/source4/lib/genrand.c b/source4/lib/genrand.c index fdd4bb14fc..9645dd7999 100644 --- a/source4/lib/genrand.c +++ b/source4/lib/genrand.c @@ -135,7 +135,6 @@ static int do_reseed(BOOL use_fd, int fd)  {  	unsigned char seed_inbuf[40];  	uint32 v1, v2; struct timeval tval; pid_t mypid; -	struct passwd *pw;  	if (use_fd) {  		if (fd != -1) @@ -152,22 +151,6 @@ static int do_reseed(BOOL use_fd, int fd)  	do_filehash(lp_smb_passwd_file(), &seed_inbuf[16]);  	/* -	 * Add in the root encrypted password. -	 * On any system where security is taken -	 * seriously this will be secret. -	 */ - -	pw = getpwnam_alloc("root"); -	if (pw && pw->pw_passwd) { -		size_t i; -		unsigned char md4_tmp[16]; -		mdfour(md4_tmp, (unsigned char *)pw->pw_passwd, strlen(pw->pw_passwd)); -		for (i=0;i<16;i++) -			seed_inbuf[8+i] ^= md4_tmp[i]; -		passwd_free(&pw); -	} - -	/*  	 * Add the counter, time of day, and pid.  	 */ diff --git a/source4/lib/sysacls.c b/source4/lib/sysacls.c deleted file mode 100644 index fe85b9e72f..0000000000 --- a/source4/lib/sysacls.c +++ /dev/null @@ -1,3198 +0,0 @@ -/*  -   Unix SMB/CIFS implementation. -   Samba system utilities for ACL support. -   Copyright (C) Jeremy Allison 2000. -    -   This program is free software; you can redistribute it and/or modify -   it under the terms of the GNU General Public License as published by -   the Free Software Foundation; either version 2 of the License, or -   (at your option) any later version. -    -   This program is distributed in the hope that it will be useful, -   but WITHOUT ANY WARRANTY; without even the implied warranty of -   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the -   GNU General Public License for more details. -    -   You should have received a copy of the GNU General Public License -   along with this program; if not, write to the Free Software -   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. -*/ - -#include "includes.h" - -/* - This file wraps all differing system ACL interfaces into a consistent - one based on the POSIX interface. It also returns the correct errors - for older UNIX systems that don't support ACLs. - - The interfaces that each ACL implementation must support are as follows : - - int sys_acl_get_entry( SMB_ACL_T theacl, int entry_id, SMB_ACL_ENTRY_T *entry_p) - int sys_acl_get_tag_type( SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *tag_type_p) - int sys_acl_get_permset( SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p - void *sys_acl_get_qualifier( SMB_ACL_ENTRY_T entry_d) - SMB_ACL_T sys_acl_get_file( const char *path_p, SMB_ACL_TYPE_T type) - SMB_ACL_T sys_acl_get_fd(int fd) - int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset); - int sys_acl_add_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm); - char *sys_acl_to_text( SMB_ACL_T theacl, ssize_t *plen) - SMB_ACL_T sys_acl_init( int count) - int sys_acl_create_entry( SMB_ACL_T *pacl, SMB_ACL_ENTRY_T *pentry) - int sys_acl_set_tag_type( SMB_ACL_ENTRY_T entry, SMB_ACL_TAG_T tagtype) - int sys_acl_set_qualifier( SMB_ACL_ENTRY_T entry, void *qual) - int sys_acl_set_permset( SMB_ACL_ENTRY_T entry, SMB_ACL_PERMSET_T permset) - int sys_acl_valid( SMB_ACL_T theacl ) - int sys_acl_set_file( const char *name, SMB_ACL_TYPE_T acltype, SMB_ACL_T theacl) - int sys_acl_set_fd( int fd, SMB_ACL_T theacl) - int sys_acl_delete_def_file(const char *path) - - This next one is not POSIX complient - but we *have* to have it ! - More POSIX braindamage. - - int sys_acl_get_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) - - The generic POSIX free is the following call. We split this into - several different free functions as we may need to add tag info - to structures when emulating the POSIX interface. - - int sys_acl_free( void *obj_p) - - The calls we actually use are : - - int sys_acl_free_text(char *text) - free acl_to_text - int sys_acl_free_acl(SMB_ACL_T posix_acl) - int sys_acl_free_qualifier(void *qualifier, SMB_ACL_TAG_T tagtype) - -*/ - -#if defined(HAVE_POSIX_ACLS) - -/* Identity mapping - easy. */ - -int sys_acl_get_entry( SMB_ACL_T the_acl, int entry_id, SMB_ACL_ENTRY_T *entry_p) -{ -	return acl_get_entry( the_acl, entry_id, entry_p); -} - -int sys_acl_get_tag_type( SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *tag_type_p) -{ -	return acl_get_tag_type( entry_d, tag_type_p); -} - -int sys_acl_get_permset( SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p) -{ -	return acl_get_permset( entry_d, permset_p); -} - -void *sys_acl_get_qualifier( SMB_ACL_ENTRY_T entry_d) -{ -	return acl_get_qualifier( entry_d); -} - -SMB_ACL_T sys_acl_get_file( const char *path_p, SMB_ACL_TYPE_T type) -{ -	return acl_get_file( path_p, type); -} - -SMB_ACL_T sys_acl_get_fd(int fd) -{ -	return acl_get_fd(fd); -} - -int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset) -{ -	return acl_clear_perms(permset); -} - -int sys_acl_add_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -	return acl_add_perm(permset, perm); -} - -int sys_acl_get_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -#if defined(HAVE_ACL_GET_PERM_NP) -	/* -	 * Required for TrustedBSD-based ACL implementations where -	 * non-POSIX.1e functions are denoted by a _np (non-portable) -	 * suffix. -	 */ -	return acl_get_perm_np(permset, perm); -#else -	return acl_get_perm(permset, perm); -#endif -} - -char *sys_acl_to_text( SMB_ACL_T the_acl, ssize_t *plen) -{ -	return acl_to_text( the_acl, plen); -} - -SMB_ACL_T sys_acl_init( int count) -{ -	return acl_init(count); -} - -int sys_acl_create_entry( SMB_ACL_T *pacl, SMB_ACL_ENTRY_T *pentry) -{ -	return acl_create_entry(pacl, pentry); -} - -int sys_acl_set_tag_type( SMB_ACL_ENTRY_T entry, SMB_ACL_TAG_T tagtype) -{ -	return acl_set_tag_type(entry, tagtype); -} - -int sys_acl_set_qualifier( SMB_ACL_ENTRY_T entry, void *qual) -{ -	return acl_set_qualifier(entry, qual); -} - -int sys_acl_set_permset( SMB_ACL_ENTRY_T entry, SMB_ACL_PERMSET_T permset) -{ -	return acl_set_permset(entry, permset); -} - -int sys_acl_valid( SMB_ACL_T theacl ) -{ -	return acl_valid(theacl); -} - -int sys_acl_set_file(const char *name, SMB_ACL_TYPE_T acltype, SMB_ACL_T theacl) -{ -	return acl_set_file(name, acltype, theacl); -} - -int sys_acl_set_fd( int fd, SMB_ACL_T theacl) -{ -	return acl_set_fd(fd, theacl); -} - -int sys_acl_delete_def_file(const char *name) -{ -	return acl_delete_def_file(name); -} - -int sys_acl_free_text(char *text) -{ -	return acl_free(text); -} - -int sys_acl_free_acl(SMB_ACL_T the_acl)  -{ -	return acl_free(the_acl); -} - -int sys_acl_free_qualifier(void *qual, SMB_ACL_TAG_T tagtype) -{ -	return acl_free(qual); -} - -#elif defined(HAVE_TRU64_ACLS) -/* - * The interface to DEC/Compaq Tru64 UNIX ACLs - * is based on Draft 13 of the POSIX spec which is - * slightly different from the Draft 16 interface. - *  - * Also, some of the permset manipulation functions - * such as acl_clear_perm() and acl_add_perm() appear - * to be broken on Tru64 so we have to manipulate - * the permission bits in the permset directly. - */ -int sys_acl_get_entry( SMB_ACL_T the_acl, int entry_id, SMB_ACL_ENTRY_T *entry_p) -{ -	SMB_ACL_ENTRY_T	entry; - -	if (entry_id == SMB_ACL_FIRST_ENTRY && acl_first_entry(the_acl) != 0) { -		return -1; -	} - -	errno = 0; -	if ((entry = acl_get_entry(the_acl)) != NULL) { -		*entry_p = entry; -		return 1; -	} - -	return errno ? -1 : 0; -} - -int sys_acl_get_tag_type( SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *tag_type_p) -{ -	return acl_get_tag_type( entry_d, tag_type_p); -} - -int sys_acl_get_permset( SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p) -{ -	return acl_get_permset( entry_d, permset_p); -} - -void *sys_acl_get_qualifier( SMB_ACL_ENTRY_T entry_d) -{ -	return acl_get_qualifier( entry_d); -} - -SMB_ACL_T sys_acl_get_file( const char *path_p, SMB_ACL_TYPE_T type) -{ -	return acl_get_file((char *)path_p, type); -} - -SMB_ACL_T sys_acl_get_fd(int fd) -{ -	return acl_get_fd(fd, ACL_TYPE_ACCESS); -} - -int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset) -{ -	*permset = 0;		/* acl_clear_perm() is broken on Tru64	*/ - -	return 0; -} - -int sys_acl_add_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -	if (perm & ~(SMB_ACL_READ | SMB_ACL_WRITE | SMB_ACL_EXECUTE)) { -		errno = EINVAL; -		return -1; -	} - -	*permset |= perm;	/* acl_add_perm() is broken on Tru64	*/ - -	return 0; -} - -int sys_acl_get_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -	return *permset & perm;	/* Tru64 doesn't have acl_get_perm() */ -} - -char *sys_acl_to_text( SMB_ACL_T the_acl, ssize_t *plen) -{ -	return acl_to_text( the_acl, plen); -} - -SMB_ACL_T sys_acl_init( int count) -{ -	return acl_init(count); -} - -int sys_acl_create_entry( SMB_ACL_T *pacl, SMB_ACL_ENTRY_T *pentry) -{ -	SMB_ACL_ENTRY_T entry; - -	if ((entry = acl_create_entry(pacl)) == NULL) { -		return -1; -	} - -	*pentry = entry; -	return 0; -} - -int sys_acl_set_tag_type( SMB_ACL_ENTRY_T entry, SMB_ACL_TAG_T tagtype) -{ -	return acl_set_tag_type(entry, tagtype); -} - -int sys_acl_set_qualifier( SMB_ACL_ENTRY_T entry, void *qual) -{ -	return acl_set_qualifier(entry, qual); -} - -int sys_acl_set_permset( SMB_ACL_ENTRY_T entry, SMB_ACL_PERMSET_T permset) -{ -	return acl_set_permset(entry, permset); -} - -int sys_acl_valid( SMB_ACL_T theacl ) -{ -	acl_entry_t	entry; - -	return acl_valid(theacl, &entry); -} - -int sys_acl_set_file( const char *name, SMB_ACL_TYPE_T acltype, SMB_ACL_T theacl) -{ -	return acl_set_file((char *)name, acltype, theacl); -} - -int sys_acl_set_fd( int fd, SMB_ACL_T theacl) -{ -	return acl_set_fd(fd, ACL_TYPE_ACCESS, theacl); -} - -int sys_acl_delete_def_file(const char *name) -{ -	return acl_delete_def_file((char *)name); -} - -int sys_acl_free_text(char *text) -{ -	/* -	 * (void) cast and explicit return 0 are for DEC UNIX -	 *  which just #defines acl_free_text() to be free() -	 */ -	(void) acl_free_text(text); -	return 0; -} - -int sys_acl_free_acl(SMB_ACL_T the_acl)  -{ -	return acl_free(the_acl); -} - -int sys_acl_free_qualifier(void *qual, SMB_ACL_TAG_T tagtype) -{ -	return acl_free_qualifier(qual, tagtype); -} - -#elif defined(HAVE_UNIXWARE_ACLS) || defined(HAVE_SOLARIS_ACLS) - -/* - * Donated by Michael Davidson <md@sco.COM> for UnixWare / OpenUNIX. - * Modified by Toomas Soome <tsoome@ut.ee> for Solaris. - */ - -/* - * Note that while this code implements sufficient functionality - * to support the sys_acl_* interfaces it does not provide all - * of the semantics of the POSIX ACL interfaces. - * - * In particular, an ACL entry descriptor (SMB_ACL_ENTRY_T) returned - * from a call to sys_acl_get_entry() should not be assumed to be - * valid after calling any of the following functions, which may - * reorder the entries in the ACL. - * - *	sys_acl_valid() - *	sys_acl_set_file() - *	sys_acl_set_fd() - */ - -/* - * The only difference between Solaris and UnixWare / OpenUNIX is - * that the #defines for the ACL operations have different names - */ -#if defined(HAVE_UNIXWARE_ACLS) - -#define	SETACL		ACL_SET -#define	GETACL		ACL_GET -#define	GETACLCNT	ACL_CNT - -#endif - - -int sys_acl_get_entry(SMB_ACL_T acl_d, int entry_id, SMB_ACL_ENTRY_T *entry_p) -{ -	if (entry_id != SMB_ACL_FIRST_ENTRY && entry_id != SMB_ACL_NEXT_ENTRY) { -		errno = EINVAL; -		return -1; -	} - -	if (entry_p == NULL) { -		errno = EINVAL; -		return -1; -	} - -	if (entry_id == SMB_ACL_FIRST_ENTRY) { -		acl_d->next = 0; -	} - -	if (acl_d->next < 0) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_d->next >= acl_d->count) { -		return 0; -	} - -	*entry_p = &acl_d->acl[acl_d->next++]; - -	return 1; -} - -int sys_acl_get_tag_type(SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *type_p) -{ -	*type_p = entry_d->a_type; - -	return 0; -} - -int sys_acl_get_permset(SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p) -{ -	*permset_p = &entry_d->a_perm; - -	return 0; -} - -void *sys_acl_get_qualifier(SMB_ACL_ENTRY_T entry_d) -{ -	if (entry_d->a_type != SMB_ACL_USER -	    && entry_d->a_type != SMB_ACL_GROUP) { -		errno = EINVAL; -		return NULL; -	} - -	return &entry_d->a_id; -} - -/* - * There is no way of knowing what size the ACL returned by - * GETACL will be unless you first call GETACLCNT which means - * making an additional system call. - * - * In the hope of avoiding the cost of the additional system - * call in most cases, we initially allocate enough space for - * an ACL with INITIAL_ACL_SIZE entries. If this turns out to - * be too small then we use GETACLCNT to find out the actual - * size, reallocate the ACL buffer, and then call GETACL again. - */ - -#define	INITIAL_ACL_SIZE	16 - -SMB_ACL_T sys_acl_get_file(const char *path_p, SMB_ACL_TYPE_T type) -{ -	SMB_ACL_T	acl_d; -	int		count;		/* # of ACL entries allocated	*/ -	int		naccess;	/* # of access ACL entries	*/ -	int		ndefault;	/* # of default ACL entries	*/ - -	if (type != SMB_ACL_TYPE_ACCESS && type != SMB_ACL_TYPE_DEFAULT) { -		errno = EINVAL; -		return NULL; -	} - -	count = INITIAL_ACL_SIZE; -	if ((acl_d = sys_acl_init(count)) == NULL) { -		return NULL; -	} - -	/* -	 * If there isn't enough space for the ACL entries we use -	 * GETACLCNT to determine the actual number of ACL entries -	 * reallocate and try again. This is in a loop because it -	 * is possible that someone else could modify the ACL and -	 * increase the number of entries between the call to -	 * GETACLCNT and the call to GETACL. -	 */ -	while ((count = acl(path_p, GETACL, count, &acl_d->acl[0])) < 0 -	    && errno == ENOSPC) { - -		sys_acl_free_acl(acl_d); - -		if ((count = acl(path_p, GETACLCNT, 0, NULL)) < 0) { -			return NULL; -		} - -		if ((acl_d = sys_acl_init(count)) == NULL) { -			return NULL; -		} -	} - -	if (count < 0) { -		sys_acl_free_acl(acl_d); -		return NULL; -	} - -	/* -	 * calculate the number of access and default ACL entries -	 * -	 * Note: we assume that the acl() system call returned a -	 * well formed ACL which is sorted so that all of the -	 * access ACL entries preceed any default ACL entries -	 */ -	for (naccess = 0; naccess < count; naccess++) { -		if (acl_d->acl[naccess].a_type & ACL_DEFAULT) -			break; -	} -	ndefault = count - naccess; -	 -	/* -	 * if the caller wants the default ACL we have to copy -	 * the entries down to the start of the acl[] buffer -	 * and mask out the ACL_DEFAULT flag from the type field -	 */ -	if (type == SMB_ACL_TYPE_DEFAULT) { -		int	i, j; - -		for (i = 0, j = naccess; i < ndefault; i++, j++) { -			acl_d->acl[i] = acl_d->acl[j]; -			acl_d->acl[i].a_type &= ~ACL_DEFAULT; -		} - -		acl_d->count = ndefault; -	} else { -		acl_d->count = naccess; -	} - -	return acl_d; -} - -SMB_ACL_T sys_acl_get_fd(int fd) -{ -	SMB_ACL_T	acl_d; -	int		count;		/* # of ACL entries allocated	*/ -	int		naccess;	/* # of access ACL entries	*/ - -	count = INITIAL_ACL_SIZE; -	if ((acl_d = sys_acl_init(count)) == NULL) { -		return NULL; -	} - -	while ((count = facl(fd, GETACL, count, &acl_d->acl[0])) < 0 -	    && errno == ENOSPC) { - -		sys_acl_free_acl(acl_d); - -		if ((count = facl(fd, GETACLCNT, 0, NULL)) < 0) { -			return NULL; -		} - -		if ((acl_d = sys_acl_init(count)) == NULL) { -			return NULL; -		} -	} - -	if (count < 0) { -		sys_acl_free_acl(acl_d); -		return NULL; -	} - -	/* -	 * calculate the number of access ACL entries -	 */ -	for (naccess = 0; naccess < count; naccess++) { -		if (acl_d->acl[naccess].a_type & ACL_DEFAULT) -			break; -	} -	 -	acl_d->count = naccess; - -	return acl_d; -} - -int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset_d) -{ -	*permset_d = 0; - -	return 0; -} - -int sys_acl_add_perm(SMB_ACL_PERMSET_T permset_d, SMB_ACL_PERM_T perm) -{ -	if (perm != SMB_ACL_READ && perm != SMB_ACL_WRITE -	    && perm != SMB_ACL_EXECUTE) { -		errno = EINVAL; -		return -1; -	} - -	if (permset_d == NULL) { -		errno = EINVAL; -		return -1; -	} - -	*permset_d |= perm; - -	return 0; -} - -int sys_acl_get_perm(SMB_ACL_PERMSET_T permset_d, SMB_ACL_PERM_T perm) -{ -	return *permset_d & perm; -} - -char *sys_acl_to_text(SMB_ACL_T acl_d, ssize_t *len_p) -{ -	int	i; -	int	len, maxlen; -	char	*text; - -	/* -	 * use an initial estimate of 20 bytes per ACL entry -	 * when allocating memory for the text representation -	 * of the ACL -	 */ -	len	= 0; -	maxlen	= 20 * acl_d->count; -	if ((text = malloc(maxlen)) == NULL) { -		errno = ENOMEM; -		return NULL; -	} - -	for (i = 0; i < acl_d->count; i++) { -		struct acl	*ap	= &acl_d->acl[i]; -		struct passwd	*pw; -		struct group	*gr; -		char		tagbuf[12]; -		char		idbuf[12]; -		char		*tag; -		char		*id	= ""; -		char		perms[4]; -		int		nbytes; - -		switch (ap->a_type) { -			/* -			 * for debugging purposes it's probably more -			 * useful to dump unknown tag types rather -			 * than just returning an error -			 */ -			default: -				slprintf(tagbuf, sizeof(tagbuf)-1, "0x%x", -					ap->a_type); -				tag = tagbuf; -				slprintf(idbuf, sizeof(idbuf)-1, "%ld", -					(long)ap->a_id); -				id = idbuf; -				break; - -			case SMB_ACL_USER: -				id = uidtoname(ap->a_id); -			case SMB_ACL_USER_OBJ: -				tag = "user"; -				break; - -			case SMB_ACL_GROUP: -				if ((gr = getgrgid(ap->a_id)) == NULL) { -					slprintf(idbuf, sizeof(idbuf)-1, "%ld", -						(long)ap->a_id); -					id = idbuf; -				} else { -					id = gr->gr_name; -				} -			case SMB_ACL_GROUP_OBJ: -				tag = "group"; -				break; - -			case SMB_ACL_OTHER: -				tag = "other"; -				break; - -			case SMB_ACL_MASK: -				tag = "mask"; -				break; - -		} - -		perms[0] = (ap->a_perm & SMB_ACL_READ) ? 'r' : '-'; -		perms[1] = (ap->a_perm & SMB_ACL_WRITE) ? 'w' : '-'; -		perms[2] = (ap->a_perm & SMB_ACL_EXECUTE) ? 'x' : '-'; -		perms[3] = '\0'; - -		/*          <tag>      :  <qualifier>   :  rwx \n  \0 */ -		nbytes = strlen(tag) + 1 + strlen(id) + 1 + 3 + 1 + 1; - -		/* -		 * If this entry would overflow the buffer -		 * allocate enough additional memory for this -		 * entry and an estimate of another 20 bytes -		 * for each entry still to be processed -		 */ -		if ((len + nbytes) > maxlen) { -			char *oldtext = text; - -			maxlen += nbytes + 20 * (acl_d->count - i); - -			if ((text = Realloc(oldtext, maxlen)) == NULL) { -				SAFE_FREE(oldtext); -				errno = ENOMEM; -				return NULL; -			} -		} - -		slprintf(&text[len], nbytes-1, "%s:%s:%s\n", tag, id, perms); -		len += nbytes - 1; -	} - -	if (len_p) -		*len_p = len; - -	return text; -} - -SMB_ACL_T sys_acl_init(int count) -{ -	SMB_ACL_T	a; - -	if (count < 0) { -		errno = EINVAL; -		return NULL; -	} - -	/* -	 * note that since the definition of the structure pointed -	 * to by the SMB_ACL_T includes the first element of the -	 * acl[] array, this actually allocates an ACL with room -	 * for (count+1) entries -	 */ -	if ((a = malloc(sizeof(*a) + count * sizeof(struct acl))) == NULL) { -		errno = ENOMEM; -		return NULL; -	} - -	a->size = count + 1; -	a->count = 0; -	a->next = -1; - -	return a; -} - - -int sys_acl_create_entry(SMB_ACL_T *acl_p, SMB_ACL_ENTRY_T *entry_p) -{ -	SMB_ACL_T	acl_d; -	SMB_ACL_ENTRY_T	entry_d; - -	if (acl_p == NULL || entry_p == NULL || (acl_d = *acl_p) == NULL) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_d->count >= acl_d->size) { -		errno = ENOSPC; -		return -1; -	} - -	entry_d		= &acl_d->acl[acl_d->count++]; -	entry_d->a_type	= 0; -	entry_d->a_id	= -1; -	entry_d->a_perm	= 0; -	*entry_p	= entry_d; - -	return 0; -} - -int sys_acl_set_tag_type(SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T tag_type) -{ -	switch (tag_type) { -		case SMB_ACL_USER: -		case SMB_ACL_USER_OBJ: -		case SMB_ACL_GROUP: -		case SMB_ACL_GROUP_OBJ: -		case SMB_ACL_OTHER: -		case SMB_ACL_MASK: -			entry_d->a_type = tag_type; -			break; -		default: -			errno = EINVAL; -			return -1; -	} - -	return 0; -} - -int sys_acl_set_qualifier(SMB_ACL_ENTRY_T entry_d, void *qual_p) -{ -	if (entry_d->a_type != SMB_ACL_GROUP -	    && entry_d->a_type != SMB_ACL_USER) { -		errno = EINVAL; -		return -1; -	} - -	entry_d->a_id = *((id_t *)qual_p); - -	return 0; -} - -int sys_acl_set_permset(SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T permset_d) -{ -	if (*permset_d & ~(SMB_ACL_READ|SMB_ACL_WRITE|SMB_ACL_EXECUTE)) { -		return EINVAL; -	} - -	entry_d->a_perm = *permset_d; - -	return 0; -} - -/* - * sort the ACL and check it for validity - * - * if it's a minimal ACL with only 4 entries then we - * need to recalculate the mask permissions to make - * sure that they are the same as the GROUP_OBJ - * permissions as required by the UnixWare acl() system call. - * - * (note: since POSIX allows minimal ACLs which only contain - * 3 entries - ie there is no mask entry - we should, in theory, - * check for this and add a mask entry if necessary - however - * we "know" that the caller of this interface always specifies - * a mask so, in practice "this never happens" (tm) - if it *does* - * happen aclsort() will fail and return an error and someone will - * have to fix it ...) - */ - -static int acl_sort(SMB_ACL_T acl_d) -{ -	int     fixmask = (acl_d->count <= 4); - -	if (aclsort(acl_d->count, fixmask, acl_d->acl) != 0) { -		errno = EINVAL; -		return -1; -	} -	return 0; -} -  -int sys_acl_valid(SMB_ACL_T acl_d) -{ -	return acl_sort(acl_d); -} - -int sys_acl_set_file(const char *name, SMB_ACL_TYPE_T type, SMB_ACL_T acl_d) -{ -	struct stat	s; -	struct acl	*acl_p; -	int		acl_count; -	struct acl	*acl_buf	= NULL; -	int		ret; - -	if (type != SMB_ACL_TYPE_ACCESS && type != SMB_ACL_TYPE_DEFAULT) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_sort(acl_d) != 0) { -		return -1; -	} - -	acl_p		= &acl_d->acl[0]; -	acl_count	= acl_d->count; - -	/* -	 * if it's a directory there is extra work to do -	 * since the acl() system call will replace both -	 * the access ACLs and the default ACLs (if any) -	 */ -	if (stat(name, &s) != 0) { -		return -1; -	} -	if (S_ISDIR(s.st_mode)) { -		SMB_ACL_T	acc_acl; -		SMB_ACL_T	def_acl; -		SMB_ACL_T	tmp_acl; -		int		i; - -		if (type == SMB_ACL_TYPE_ACCESS) { -			acc_acl = acl_d; -			def_acl = tmp_acl = sys_acl_get_file(name, SMB_ACL_TYPE_DEFAULT); - -		} else { -			def_acl = acl_d; -			acc_acl = tmp_acl = sys_acl_get_file(name, SMB_ACL_TYPE_ACCESS); -		} - -		if (tmp_acl == NULL) { -			return -1; -		} - -		/* -		 * allocate a temporary buffer for the complete ACL -		 */ -		acl_count = acc_acl->count + def_acl->count; -		acl_p = acl_buf = malloc(acl_count * sizeof(acl_buf[0])); - -		if (acl_buf == NULL) { -			sys_acl_free_acl(tmp_acl); -			errno = ENOMEM; -			return -1; -		} - -		/* -		 * copy the access control and default entries into the buffer -		 */ -		memcpy(&acl_buf[0], &acc_acl->acl[0], -			acc_acl->count * sizeof(acl_buf[0])); - -		memcpy(&acl_buf[acc_acl->count], &def_acl->acl[0], -			def_acl->count * sizeof(acl_buf[0])); - -		/* -		 * set the ACL_DEFAULT flag on the default entries -		 */ -		for (i = acc_acl->count; i < acl_count; i++) { -			acl_buf[i].a_type |= ACL_DEFAULT; -		} - -		sys_acl_free_acl(tmp_acl); - -	} else if (type != SMB_ACL_TYPE_ACCESS) { -		errno = EINVAL; -		return -1; -	} - -	ret = acl(name, SETACL, acl_count, acl_p); - -	SAFE_FREE(acl_buf); - -	return ret; -} - -int sys_acl_set_fd(int fd, SMB_ACL_T acl_d) -{ -	if (acl_sort(acl_d) != 0) { -		return -1; -	} - -	return facl(fd, SETACL, acl_d->count, &acl_d->acl[0]); -} - -int sys_acl_delete_def_file(const char *path) -{ -	SMB_ACL_T	acl_d; -	int		ret; - -	/* -	 * fetching the access ACL and rewriting it has -	 * the effect of deleting the default ACL -	 */ -	if ((acl_d = sys_acl_get_file(path, SMB_ACL_TYPE_ACCESS)) == NULL) { -		return -1; -	} - -	ret = acl(path, SETACL, acl_d->count, acl_d->acl); - -	sys_acl_free_acl(acl_d); -	 -	return ret; -} - -int sys_acl_free_text(char *text) -{ -	SAFE_FREE(text); -	return 0; -} - -int sys_acl_free_acl(SMB_ACL_T acl_d)  -{ -	SAFE_FREE(acl_d); -	return 0; -} - -int sys_acl_free_qualifier(void *qual, SMB_ACL_TAG_T tagtype) -{ -	return 0; -} - -#elif defined(HAVE_HPUX_ACLS) -#include <dl.h> - -/* - * Based on the Solaris/SCO code - with modifications. - */ - -/* - * Note that while this code implements sufficient functionality - * to support the sys_acl_* interfaces it does not provide all - * of the semantics of the POSIX ACL interfaces. - * - * In particular, an ACL entry descriptor (SMB_ACL_ENTRY_T) returned - * from a call to sys_acl_get_entry() should not be assumed to be - * valid after calling any of the following functions, which may - * reorder the entries in the ACL. - * - *	sys_acl_valid() - *	sys_acl_set_file() - *	sys_acl_set_fd() - */ - -/* This checks if the POSIX ACL system call is defined */ -/* which basically corresponds to whether JFS 3.3 or   */ -/* higher is installed. If acl() was called when it    */ -/* isn't defined, it causes the process to core dump   */ -/* so it is important to check this and avoid acl()    */ -/* calls if it isn't there.                            */ - -static BOOL hpux_acl_call_presence(void) -{ - -	shl_t handle = NULL; -	void *value; -	int ret_val=0; -	//static BOOL already_checked=0; -	// REWRITE: add this back in?? -	//if(already_checked) -	//	return True; - - -	ret_val = shl_findsym(&handle, "acl", TYPE_PROCEDURE, &value); - -	if(ret_val != 0) { -		DEBUG(5, ("hpux_acl_call_presence: shl_findsym() returned %d, errno = %d, error %s\n", -			ret_val, errno, strerror(errno))); -		DEBUG(5,("hpux_acl_call_presence: acl() system call is not present. Check if you have JFS 3.3 and above?\n")); -		return False; -	} - -	DEBUG(10,("hpux_acl_call_presence: acl() system call is present. We have JFS 3.3 or above \n")); - -	already_checked = True; -	return True; -} - -int sys_acl_get_entry(SMB_ACL_T acl_d, int entry_id, SMB_ACL_ENTRY_T *entry_p) -{ -	if (entry_id != SMB_ACL_FIRST_ENTRY && entry_id != SMB_ACL_NEXT_ENTRY) { -		errno = EINVAL; -		return -1; -	} - -	if (entry_p == NULL) { -		errno = EINVAL; -		return -1; -	} - -	if (entry_id == SMB_ACL_FIRST_ENTRY) { -		acl_d->next = 0; -	} - -	if (acl_d->next < 0) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_d->next >= acl_d->count) { -		return 0; -	} - -	*entry_p = &acl_d->acl[acl_d->next++]; - -	return 1; -} - -int sys_acl_get_tag_type(SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *type_p) -{ -	*type_p = entry_d->a_type; - -	return 0; -} - -int sys_acl_get_permset(SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p) -{ -	*permset_p = &entry_d->a_perm; - -	return 0; -} - -void *sys_acl_get_qualifier(SMB_ACL_ENTRY_T entry_d) -{ -	if (entry_d->a_type != SMB_ACL_USER -	    && entry_d->a_type != SMB_ACL_GROUP) { -		errno = EINVAL; -		return NULL; -	} - -	return &entry_d->a_id; -} - -/* - * There is no way of knowing what size the ACL returned by - * ACL_GET will be unless you first call ACL_CNT which means - * making an additional system call. - * - * In the hope of avoiding the cost of the additional system - * call in most cases, we initially allocate enough space for - * an ACL with INITIAL_ACL_SIZE entries. If this turns out to - * be too small then we use ACL_CNT to find out the actual - * size, reallocate the ACL buffer, and then call ACL_GET again. - */ - -#define	INITIAL_ACL_SIZE	16 - -SMB_ACL_T sys_acl_get_file(const char *path_p, SMB_ACL_TYPE_T type) -{ -	SMB_ACL_T	acl_d; -	int		count;		/* # of ACL entries allocated	*/ -	int		naccess;	/* # of access ACL entries	*/ -	int		ndefault;	/* # of default ACL entries	*/ - -	if(hpux_acl_call_presence() == False) { -		/* Looks like we don't have the acl() system call on HPUX.  -		 * May be the system doesn't have the latest version of JFS. -		 */ -		return NULL;  -	} - -	if (type != SMB_ACL_TYPE_ACCESS && type != SMB_ACL_TYPE_DEFAULT) { -		errno = EINVAL; -		return NULL; -	} - -	count = INITIAL_ACL_SIZE; -	if ((acl_d = sys_acl_init(count)) == NULL) { -		return NULL; -	} - -	/* -	 * If there isn't enough space for the ACL entries we use -	 * ACL_CNT to determine the actual number of ACL entries -	 * reallocate and try again. This is in a loop because it -	 * is possible that someone else could modify the ACL and -	 * increase the number of entries between the call to -	 * ACL_CNT and the call to ACL_GET. -	 */ -	while ((count = acl(path_p, ACL_GET, count, &acl_d->acl[0])) < 0 && errno == ENOSPC) { - -		sys_acl_free_acl(acl_d); - -		if ((count = acl(path_p, ACL_CNT, 0, NULL)) < 0) { -			return NULL; -		} - -		if ((acl_d = sys_acl_init(count)) == NULL) { -			return NULL; -		} -	} - -	if (count < 0) { -		sys_acl_free_acl(acl_d); -		return NULL; -	} - -	/* -	 * calculate the number of access and default ACL entries -	 * -	 * Note: we assume that the acl() system call returned a -	 * well formed ACL which is sorted so that all of the -	 * access ACL entries preceed any default ACL entries -	 */ -	for (naccess = 0; naccess < count; naccess++) { -		if (acl_d->acl[naccess].a_type & ACL_DEFAULT) -			break; -	} -	ndefault = count - naccess; -	 -	/* -	 * if the caller wants the default ACL we have to copy -	 * the entries down to the start of the acl[] buffer -	 * and mask out the ACL_DEFAULT flag from the type field -	 */ -	if (type == SMB_ACL_TYPE_DEFAULT) { -		int	i, j; - -		for (i = 0, j = naccess; i < ndefault; i++, j++) { -			acl_d->acl[i] = acl_d->acl[j]; -			acl_d->acl[i].a_type &= ~ACL_DEFAULT; -		} - -		acl_d->count = ndefault; -	} else { -		acl_d->count = naccess; -	} - -	return acl_d; -} - -SMB_ACL_T sys_acl_get_fd(int fd) -{ -	/* -	 * HPUX doesn't have the facl call. Fake it using the path.... JRA. -	 */ - -	files_struct *fsp = file_find_fd(fd); - -	if (fsp == NULL) { -		errno = EBADF; -		return NULL; -	} - -	/* -	 * We know we're in the same conn context. So we -	 * can use the relative path. -	 */ - -	return sys_acl_get_file(fsp->fsp_name, SMB_ACL_TYPE_ACCESS); -} - -int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset_d) -{ -	*permset_d = 0; - -	return 0; -} - -int sys_acl_add_perm(SMB_ACL_PERMSET_T permset_d, SMB_ACL_PERM_T perm) -{ -	if (perm != SMB_ACL_READ && perm != SMB_ACL_WRITE -	    && perm != SMB_ACL_EXECUTE) { -		errno = EINVAL; -		return -1; -	} - -	if (permset_d == NULL) { -		errno = EINVAL; -		return -1; -	} - -	*permset_d |= perm; - -	return 0; -} - -int sys_acl_get_perm(SMB_ACL_PERMSET_T permset_d, SMB_ACL_PERM_T perm) -{ -	return *permset_d & perm; -} - -char *sys_acl_to_text(SMB_ACL_T acl_d, ssize_t *len_p) -{ -	int	i; -	int	len, maxlen; -	char	*text; - -	/* -	 * use an initial estimate of 20 bytes per ACL entry -	 * when allocating memory for the text representation -	 * of the ACL -	 */ -	len	= 0; -	maxlen	= 20 * acl_d->count; -	if ((text = malloc(maxlen)) == NULL) { -		errno = ENOMEM; -		return NULL; -	} - -	for (i = 0; i < acl_d->count; i++) { -		struct acl	*ap	= &acl_d->acl[i]; -		struct passwd	*pw; -		struct group	*gr; -		char		tagbuf[12]; -		char		idbuf[12]; -		char		*tag; -		char		*id	= ""; -		char		perms[4]; -		int		nbytes; - -		switch (ap->a_type) { -			/* -			 * for debugging purposes it's probably more -			 * useful to dump unknown tag types rather -			 * than just returning an error -			 */ -			default: -				slprintf(tagbuf, sizeof(tagbuf)-1, "0x%x", -					ap->a_type); -				tag = tagbuf; -				slprintf(idbuf, sizeof(idbuf)-1, "%ld", -					(long)ap->a_id); -				id = idbuf; -				break; - -			case SMB_ACL_USER: -				id = uidtoname(ap->a_id); -			case SMB_ACL_USER_OBJ: -				tag = "user"; -				break; - -			case SMB_ACL_GROUP: -				if ((gr = getgrgid(ap->a_id)) == NULL) { -					slprintf(idbuf, sizeof(idbuf)-1, "%ld", -						(long)ap->a_id); -					id = idbuf; -				} else { -					id = gr->gr_name; -				} -			case SMB_ACL_GROUP_OBJ: -				tag = "group"; -				break; - -			case SMB_ACL_OTHER: -				tag = "other"; -				break; - -			case SMB_ACL_MASK: -				tag = "mask"; -				break; - -		} - -		perms[0] = (ap->a_perm & SMB_ACL_READ) ? 'r' : '-'; -		perms[1] = (ap->a_perm & SMB_ACL_WRITE) ? 'w' : '-'; -		perms[2] = (ap->a_perm & SMB_ACL_EXECUTE) ? 'x' : '-'; -		perms[3] = '\0'; - -		/*          <tag>      :  <qualifier>   :  rwx \n  \0 */ -		nbytes = strlen(tag) + 1 + strlen(id) + 1 + 3 + 1 + 1; - -		/* -		 * If this entry would overflow the buffer -		 * allocate enough additional memory for this -		 * entry and an estimate of another 20 bytes -		 * for each entry still to be processed -		 */ -		if ((len + nbytes) > maxlen) { -			char *oldtext = text; - -			maxlen += nbytes + 20 * (acl_d->count - i); - -			if ((text = Realloc(oldtext, maxlen)) == NULL) { -				free(oldtext); -				errno = ENOMEM; -				return NULL; -			} -		} - -		slprintf(&text[len], nbytes-1, "%s:%s:%s\n", tag, id, perms); -		len += nbytes - 1; -	} - -	if (len_p) -		*len_p = len; - -	return text; -} - -SMB_ACL_T sys_acl_init(int count) -{ -	SMB_ACL_T	a; - -	if (count < 0) { -		errno = EINVAL; -		return NULL; -	} - -	/* -	 * note that since the definition of the structure pointed -	 * to by the SMB_ACL_T includes the first element of the -	 * acl[] array, this actually allocates an ACL with room -	 * for (count+1) entries -	 */ -	if ((a = malloc(sizeof(*a) + count * sizeof(struct acl))) == NULL) { -		errno = ENOMEM; -		return NULL; -	} - -	a->size = count + 1; -	a->count = 0; -	a->next = -1; - -	return a; -} - - -int sys_acl_create_entry(SMB_ACL_T *acl_p, SMB_ACL_ENTRY_T *entry_p) -{ -	SMB_ACL_T	acl_d; -	SMB_ACL_ENTRY_T	entry_d; - -	if (acl_p == NULL || entry_p == NULL || (acl_d = *acl_p) == NULL) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_d->count >= acl_d->size) { -		errno = ENOSPC; -		return -1; -	} - -	entry_d		= &acl_d->acl[acl_d->count++]; -	entry_d->a_type	= 0; -	entry_d->a_id	= -1; -	entry_d->a_perm	= 0; -	*entry_p	= entry_d; - -	return 0; -} - -int sys_acl_set_tag_type(SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T tag_type) -{ -	switch (tag_type) { -		case SMB_ACL_USER: -		case SMB_ACL_USER_OBJ: -		case SMB_ACL_GROUP: -		case SMB_ACL_GROUP_OBJ: -		case SMB_ACL_OTHER: -		case SMB_ACL_MASK: -			entry_d->a_type = tag_type; -			break; -		default: -			errno = EINVAL; -			return -1; -	} - -	return 0; -} - -int sys_acl_set_qualifier(SMB_ACL_ENTRY_T entry_d, void *qual_p) -{ -	if (entry_d->a_type != SMB_ACL_GROUP -	    && entry_d->a_type != SMB_ACL_USER) { -		errno = EINVAL; -		return -1; -	} - -	entry_d->a_id = *((id_t *)qual_p); - -	return 0; -} - -int sys_acl_set_permset(SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T permset_d) -{ -	if (*permset_d & ~(SMB_ACL_READ|SMB_ACL_WRITE|SMB_ACL_EXECUTE)) { -		return EINVAL; -	} - -	entry_d->a_perm = *permset_d; - -	return 0; -} - -/* Structure to capture the count for each type of ACE. */ - -struct hpux_acl_types { -	int n_user; -	int n_def_user; -	int n_user_obj; -	int n_def_user_obj; - -	int n_group; -	int n_def_group; -	int n_group_obj; -	int n_def_group_obj; - -	int n_other; -	int n_other_obj; -	int n_def_other_obj; - -	int n_class_obj; -	int n_def_class_obj; - -	int n_illegal_obj; -}; - -/* count_obj: - * Counts the different number of objects in a given array of ACL - * structures. - * Inputs: - * - * acl_count      - Count of ACLs in the array of ACL strucutres. - * aclp           - Array of ACL structures. - * acl_type_count - Pointer to acl_types structure. Should already be - *                  allocated. - * Output:  - * - * acl_type_count - This structure is filled up with counts of various  - *                  acl types. - */ - -static int hpux_count_obj(int acl_count, struct acl *aclp, struct hpux_acl_types *acl_type_count) -{ -	int i; - -	memset(acl_type_count, 0, sizeof(struct hpux_acl_types)); - -	for(i=0;i<acl_count;i++) { -		switch(aclp[i].a_type) { -		case USER:  -			acl_type_count->n_user++; -			break; -		case USER_OBJ:  -			acl_type_count->n_user_obj++; -			break; -		case DEF_USER_OBJ:  -			acl_type_count->n_def_user_obj++; -			break; -		case GROUP:  -			acl_type_count->n_group++; -			break; -		case GROUP_OBJ:  -			acl_type_count->n_group_obj++; -			break; -		case DEF_GROUP_OBJ:  -			acl_type_count->n_def_group_obj++; -			break; -		case OTHER_OBJ:  -			acl_type_count->n_other_obj++; -			break; -		case DEF_OTHER_OBJ:  -			acl_type_count->n_def_other_obj++; -			break; -		case CLASS_OBJ: -			acl_type_count->n_class_obj++; -			break; -		case DEF_CLASS_OBJ: -			acl_type_count->n_def_class_obj++; -			break; -		case DEF_USER: -			acl_type_count->n_def_user++; -			break; -		case DEF_GROUP: -			acl_type_count->n_def_group++; -			break; -		default:  -			acl_type_count->n_illegal_obj++; -			break; -		} -	} -} - -/* swap_acl_entries:  Swaps two ACL entries.  - * - * Inputs: aclp0, aclp1 - ACL entries to be swapped. - */ - -static void hpux_swap_acl_entries(struct acl *aclp0, struct acl *aclp1) -{ -	struct acl temp_acl; - -	temp_acl.a_type = aclp0->a_type; -	temp_acl.a_id = aclp0->a_id; -	temp_acl.a_perm = aclp0->a_perm; - -	aclp0->a_type = aclp1->a_type; -	aclp0->a_id = aclp1->a_id; -	aclp0->a_perm = aclp1->a_perm; - -	aclp1->a_type = temp_acl.a_type; -	aclp1->a_id = temp_acl.a_id; -	aclp1->a_perm = temp_acl.a_perm; -} - -/* prohibited_duplicate_type - * Identifies if given ACL type can have duplicate entries or  - * not. - * - * Inputs: acl_type - ACL Type. - * - * Outputs:  - * - * Return..  - * - * True - If the ACL type matches any of the prohibited types. - * False - If the ACL type doesn't match any of the prohibited types. - */  - -static BOOL hpux_prohibited_duplicate_type(int acl_type) -{ -	switch(acl_type) { -		case USER: -		case GROUP: -		case DEF_USER:  -		case DEF_GROUP: -			return True; -		default: -			return False; -	} -} - -/* get_needed_class_perm - * Returns the permissions of a ACL structure only if the ACL - * type matches one of the pre-determined types for computing  - * CLASS_OBJ permissions. - * - * Inputs: aclp - Pointer to ACL structure. - */ - -static int hpux_get_needed_class_perm(struct acl *aclp) -{ -	switch(aclp->a_type) { -		case USER:  -		case GROUP_OBJ:  -		case GROUP:  -		case DEF_USER_OBJ:  -		case DEF_USER: -		case DEF_GROUP_OBJ:  -		case DEF_GROUP: -		case DEF_CLASS_OBJ: -		case DEF_OTHER_OBJ:  -			return aclp->a_perm; -		default:  -			return 0; -	} -} - -/* acl_sort for HPUX. - * Sorts the array of ACL structures as per the description in - * aclsort man page. Refer to aclsort man page for more details - * - * Inputs: - * - * acl_count - Count of ACLs in the array of ACL structures. - * calclass  - If this is not zero, then we compute the CLASS_OBJ - *             permissions. - * aclp      - Array of ACL structures. - * - * Outputs: - * - * aclp     - Sorted array of ACL structures. - * - * Outputs: - * - * Returns 0 for success -1 for failure. Prints a message to the Samba - * debug log in case of failure. - */ - -static int hpux_acl_sort(int acl_count, int calclass, struct acl *aclp) -{ -#if !defined(HAVE_HPUX_ACLSORT) -	/* -	 * The aclsort() system call is availabe on the latest HPUX General -	 * Patch Bundles. So for HPUX, we developed our version of acl_sort  -	 * function. Because, we don't want to update to a new  -	 * HPUX GR bundle just for aclsort() call. -	 */ - -	struct hpux_acl_types acl_obj_count; -	int n_class_obj_perm = 0; -	int i, j; -  -	if(!acl_count) { -		DEBUG(10,("Zero acl count passed. Returning Success\n")); -		return 0; -	} - -	if(aclp == NULL) { -		DEBUG(0,("Null ACL pointer in hpux_acl_sort. Returning Failure. \n")); -		return -1; -	} - -	/* Count different types of ACLs in the ACLs array */ - -	hpux_count_obj(acl_count, aclp, &acl_obj_count); - -	/* There should be only one entry each of type USER_OBJ, GROUP_OBJ,  -	 * CLASS_OBJ and OTHER_OBJ  -	 */ - -	if( (acl_obj_count.n_user_obj  != 1) ||  -		(acl_obj_count.n_group_obj != 1) ||  -		(acl_obj_count.n_class_obj != 1) || -		(acl_obj_count.n_other_obj != 1)  -	) { -		DEBUG(0,("hpux_acl_sort: More than one entry or no entries for \ -USER OBJ or GROUP_OBJ or OTHER_OBJ or CLASS_OBJ\n")); -		return -1; -	} - -	/* If any of the default objects are present, there should be only -	 * one of them each. -	 */ - -	if( (acl_obj_count.n_def_user_obj  > 1) || (acl_obj_count.n_def_group_obj > 1) ||  -			(acl_obj_count.n_def_other_obj > 1) || (acl_obj_count.n_def_class_obj > 1) ) { -		DEBUG(0,("hpux_acl_sort: More than one entry for DEF_CLASS_OBJ \ -or DEF_USER_OBJ or DEF_GROUP_OBJ or DEF_OTHER_OBJ\n")); -		return -1; -	} - -	/* We now have proper number of OBJ and DEF_OBJ entries. Now sort the acl  -	 * structures.   -	 * -	 * Sorting crieteria - First sort by ACL type. If there are multiple entries of -	 * same ACL type, sort by ACL id. -	 * -	 * I am using the trival kind of sorting method here because, performance isn't  -	 * really effected by the ACLs feature. More over there aren't going to be more -	 * than 17 entries on HPUX.  -	 */ - -	for(i=0; i<acl_count;i++) { -		for (j=i+1; j<acl_count; j++) { -			if( aclp[i].a_type > aclp[j].a_type ) { -				/* ACL entries out of order, swap them */ - -				hpux_swap_acl_entries((aclp+i), (aclp+j)); - -			} else if ( aclp[i].a_type == aclp[j].a_type ) { - -				/* ACL entries of same type, sort by id */ - -				if(aclp[i].a_id > aclp[j].a_id) { -					hpux_swap_acl_entries((aclp+i), (aclp+j)); -				} else if (aclp[i].a_id == aclp[j].a_id) { -					/* We have a duplicate entry. */ -					if(hpux_prohibited_duplicate_type(aclp[i].a_type)) { -						DEBUG(0, ("hpux_acl_sort: Duplicate entry: Type(hex): %x Id: %d\n", -							aclp[i].a_type, aclp[i].a_id)); -						return -1; -					} -				} - -			} -		} -	} - -	/* set the class obj permissions to the computed one. */ -	if(calclass) { -		int n_class_obj_index = -1; - -		for(i=0;i<acl_count;i++) { -			n_class_obj_perm |= hpux_get_needed_class_perm((aclp+i)); - -			if(aclp[i].a_type == CLASS_OBJ) -				n_class_obj_index = i; -		} -		aclp[n_class_obj_index].a_perm = n_class_obj_perm; -	} - -	return 0; -#else -	return aclsort(acl_count, calclass, aclp); -#endif -} - -/* - * sort the ACL and check it for validity - * - * if it's a minimal ACL with only 4 entries then we - * need to recalculate the mask permissions to make - * sure that they are the same as the GROUP_OBJ - * permissions as required by the UnixWare acl() system call. - * - * (note: since POSIX allows minimal ACLs which only contain - * 3 entries - ie there is no mask entry - we should, in theory, - * check for this and add a mask entry if necessary - however - * we "know" that the caller of this interface always specifies - * a mask so, in practice "this never happens" (tm) - if it *does* - * happen aclsort() will fail and return an error and someone will - * have to fix it ...) - */ - -static int acl_sort(SMB_ACL_T acl_d) -{ -	int fixmask = (acl_d->count <= 4); - -	if (hpux_acl_sort(acl_d->count, fixmask, acl_d->acl) != 0) { -		errno = EINVAL; -		return -1; -	} -	return 0; -} -  -int sys_acl_valid(SMB_ACL_T acl_d) -{ -	return acl_sort(acl_d); -} - -int sys_acl_set_file(const char *name, SMB_ACL_TYPE_T type, SMB_ACL_T acl_d) -{ -	struct stat	s; -	struct acl	*acl_p; -	int		acl_count; -	struct acl	*acl_buf	= NULL; -	int		ret; - -	if(hpux_acl_call_presence() == False) { -		/* Looks like we don't have the acl() system call on HPUX.  -		 * May be the system doesn't have the latest version of JFS. -		 */ -		errno=ENOSYS; -		return -1;  -	} - -	if (type != SMB_ACL_TYPE_ACCESS && type != SMB_ACL_TYPE_DEFAULT) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_sort(acl_d) != 0) { -		return -1; -	} - -	acl_p		= &acl_d->acl[0]; -	acl_count	= acl_d->count; - -	/* -	 * if it's a directory there is extra work to do -	 * since the acl() system call will replace both -	 * the access ACLs and the default ACLs (if any) -	 */ -	if (stat(name, &s) != 0) { -		return -1; -	} -	if (S_ISDIR(s.st_mode)) { -		SMB_ACL_T	acc_acl; -		SMB_ACL_T	def_acl; -		SMB_ACL_T	tmp_acl; -		int		i; - -		if (type == SMB_ACL_TYPE_ACCESS) { -			acc_acl = acl_d; -			def_acl = tmp_acl = sys_acl_get_file(name, SMB_ACL_TYPE_DEFAULT); - -		} else { -			def_acl = acl_d; -			acc_acl = tmp_acl = sys_acl_get_file(name, SMB_ACL_TYPE_ACCESS); -		} - -		if (tmp_acl == NULL) { -			return -1; -		} - -		/* -		 * allocate a temporary buffer for the complete ACL -		 */ -		acl_count = acc_acl->count + def_acl->count; -		acl_p = acl_buf = malloc(acl_count * sizeof(acl_buf[0])); - -		if (acl_buf == NULL) { -			sys_acl_free_acl(tmp_acl); -			errno = ENOMEM; -			return -1; -		} - -		/* -		 * copy the access control and default entries into the buffer -		 */ -		memcpy(&acl_buf[0], &acc_acl->acl[0], -			acc_acl->count * sizeof(acl_buf[0])); - -		memcpy(&acl_buf[acc_acl->count], &def_acl->acl[0], -			def_acl->count * sizeof(acl_buf[0])); - -		/* -		 * set the ACL_DEFAULT flag on the default entries -		 */ -		for (i = acc_acl->count; i < acl_count; i++) { -			acl_buf[i].a_type |= ACL_DEFAULT; -		} - -		sys_acl_free_acl(tmp_acl); - -	} else if (type != SMB_ACL_TYPE_ACCESS) { -		errno = EINVAL; -		return -1; -	} - -	ret = acl(name, ACL_SET, acl_count, acl_p); - -	if (acl_buf) { -		free(acl_buf); -	} - -	return ret; -} - -int sys_acl_set_fd(int fd, SMB_ACL_T acl_d) -{ -	/* -	 * HPUX doesn't have the facl call. Fake it using the path.... JRA. -	 */ - -	files_struct *fsp = file_find_fd(fd); - -	if (fsp == NULL) { -		errno = EBADF; -		return NULL; -	} - -	if (acl_sort(acl_d) != 0) { -		return -1; -	} - -	/* -	 * We know we're in the same conn context. So we -	 * can use the relative path. -	 */ - -	return sys_acl_set_file(fsp->fsp_name, SMB_ACL_TYPE_ACCESS, acl_d); -} - -int sys_acl_delete_def_file(const char *path) -{ -	SMB_ACL_T	acl_d; -	int		ret; - -	/* -	 * fetching the access ACL and rewriting it has -	 * the effect of deleting the default ACL -	 */ -	if ((acl_d = sys_acl_get_file(path, SMB_ACL_TYPE_ACCESS)) == NULL) { -		return -1; -	} - -	ret = acl(path, ACL_SET, acl_d->count, acl_d->acl); - -	sys_acl_free_acl(acl_d); -	 -	return ret; -} - -int sys_acl_free_text(char *text) -{ -	free(text); -	return 0; -} - -int sys_acl_free_acl(SMB_ACL_T acl_d)  -{ -	free(acl_d); -	return 0; -} - -int sys_acl_free_qualifier(void *qual, SMB_ACL_TAG_T tagtype) -{ -	return 0; -} - -#elif defined(HAVE_IRIX_ACLS) - -int sys_acl_get_entry(SMB_ACL_T acl_d, int entry_id, SMB_ACL_ENTRY_T *entry_p) -{ -	if (entry_id != SMB_ACL_FIRST_ENTRY && entry_id != SMB_ACL_NEXT_ENTRY) { -		errno = EINVAL; -		return -1; -	} - -	if (entry_p == NULL) { -		errno = EINVAL; -		return -1; -	} - -	if (entry_id == SMB_ACL_FIRST_ENTRY) { -		acl_d->next = 0; -	} - -	if (acl_d->next < 0) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_d->next >= acl_d->aclp->acl_cnt) { -		return 0; -	} - -	*entry_p = &acl_d->aclp->acl_entry[acl_d->next++]; - -	return 1; -} - -int sys_acl_get_tag_type(SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *type_p) -{ -	*type_p = entry_d->ae_tag; - -	return 0; -} - -int sys_acl_get_permset(SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p) -{ -	*permset_p = entry_d; - -	return 0; -} - -void *sys_acl_get_qualifier(SMB_ACL_ENTRY_T entry_d) -{ -	if (entry_d->ae_tag != SMB_ACL_USER -	    && entry_d->ae_tag != SMB_ACL_GROUP) { -		errno = EINVAL; -		return NULL; -	} - -	return &entry_d->ae_id; -} - -SMB_ACL_T sys_acl_get_file(const char *path_p, SMB_ACL_TYPE_T type) -{ -	SMB_ACL_T	a; - -	if ((a = malloc(sizeof(*a))) == NULL) { -		errno = ENOMEM; -		return NULL; -	} -	if ((a->aclp = acl_get_file(path_p, type)) == NULL) { -		SAFE_FREE(a); -		return NULL; -	} -	a->next = -1; -	a->freeaclp = True; -	return a; -} - -SMB_ACL_T sys_acl_get_fd(int fd) -{ -	SMB_ACL_T	a; - -	if ((a = malloc(sizeof(*a))) == NULL) { -		errno = ENOMEM; -		return NULL; -	} -	if ((a->aclp = acl_get_fd(fd)) == NULL) { -		SAFE_FREE(a); -		return NULL; -	} -	a->next = -1; -	a->freeaclp = True; -	return a; -} - -int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset_d) -{ -	permset_d->ae_perm = 0; - -	return 0; -} - -int sys_acl_add_perm(SMB_ACL_PERMSET_T permset_d, SMB_ACL_PERM_T perm) -{ -	if (perm != SMB_ACL_READ && perm != SMB_ACL_WRITE -	    && perm != SMB_ACL_EXECUTE) { -		errno = EINVAL; -		return -1; -	} - -	if (permset_d == NULL) { -		errno = EINVAL; -		return -1; -	} - -	permset_d->ae_perm |= perm; - -	return 0; -} - -int sys_acl_get_perm(SMB_ACL_PERMSET_T permset_d, SMB_ACL_PERM_T perm) -{ -	return permset_d->ae_perm & perm; -} - -char *sys_acl_to_text(SMB_ACL_T acl_d, ssize_t *len_p) -{ -	return acl_to_text(acl_d->aclp, len_p); -} - -SMB_ACL_T sys_acl_init(int count) -{ -	SMB_ACL_T	a; - -	if (count < 0) { -		errno = EINVAL; -		return NULL; -	} - -	if ((a = malloc(sizeof(*a) + sizeof(struct acl))) == NULL) { -		errno = ENOMEM; -		return NULL; -	} - -	a->next = -1; -	a->freeaclp = False; -	a->aclp = (struct acl *)(&a->aclp + sizeof(struct acl *)); -	a->aclp->acl_cnt = 0; - -	return a; -} - - -int sys_acl_create_entry(SMB_ACL_T *acl_p, SMB_ACL_ENTRY_T *entry_p) -{ -	SMB_ACL_T	acl_d; -	SMB_ACL_ENTRY_T	entry_d; - -	if (acl_p == NULL || entry_p == NULL || (acl_d = *acl_p) == NULL) { -		errno = EINVAL; -		return -1; -	} - -	if (acl_d->aclp->acl_cnt >= ACL_MAX_ENTRIES) { -		errno = ENOSPC; -		return -1; -	} - -	entry_d		= &acl_d->aclp->acl_entry[acl_d->aclp->acl_cnt++]; -	entry_d->ae_tag	= 0; -	entry_d->ae_id	= 0; -	entry_d->ae_perm	= 0; -	*entry_p	= entry_d; - -	return 0; -} - -int sys_acl_set_tag_type(SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T tag_type) -{ -	switch (tag_type) { -		case SMB_ACL_USER: -		case SMB_ACL_USER_OBJ: -		case SMB_ACL_GROUP: -		case SMB_ACL_GROUP_OBJ: -		case SMB_ACL_OTHER: -		case SMB_ACL_MASK: -			entry_d->ae_tag = tag_type; -			break; -		default: -			errno = EINVAL; -			return -1; -	} - -	return 0; -} - -int sys_acl_set_qualifier(SMB_ACL_ENTRY_T entry_d, void *qual_p) -{ -	if (entry_d->ae_tag != SMB_ACL_GROUP -	    && entry_d->ae_tag != SMB_ACL_USER) { -		errno = EINVAL; -		return -1; -	} - -	entry_d->ae_id = *((id_t *)qual_p); - -	return 0; -} - -int sys_acl_set_permset(SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T permset_d) -{ -	if (permset_d->ae_perm & ~(SMB_ACL_READ|SMB_ACL_WRITE|SMB_ACL_EXECUTE)) { -		return EINVAL; -	} - -	entry_d->ae_perm = permset_d->ae_perm; - -	return 0; -} - -int sys_acl_valid(SMB_ACL_T acl_d) -{ -	return acl_valid(acl_d->aclp); -} - -int sys_acl_set_file(const char *name, SMB_ACL_TYPE_T type, SMB_ACL_T acl_d) -{ -	return acl_set_file(name, type, acl_d->aclp); -} - -int sys_acl_set_fd(int fd, SMB_ACL_T acl_d) -{ -	return acl_set_fd(fd, acl_d->aclp); -} - -int sys_acl_delete_def_file(const char *name) -{ -	return acl_delete_def_file(name); -} - -int sys_acl_free_text(char *text) -{ -	return acl_free(text); -} - -int sys_acl_free_acl(SMB_ACL_T acl_d)  -{ -	if (acl_d->freeaclp) { -		acl_free(acl_d->aclp); -	} -	acl_free(acl_d); -	return 0; -} - -int sys_acl_free_qualifier(void *qual, SMB_ACL_TAG_T tagtype) -{ -	return 0; -} - -#elif defined(HAVE_AIX_ACLS) - -/* Donated by Medha Date, mdate@austin.ibm.com, for IBM */ - -int sys_acl_get_entry( SMB_ACL_T theacl, int entry_id, SMB_ACL_ENTRY_T *entry_p) -{ -	struct acl_entry_link *link; -	struct new_acl_entry *entry; -	int keep_going; - -	DEBUG(10,("This is the count: %d\n",theacl->count)); - -	/* Check if count was previously set to -1. * -	 * If it was, that means we reached the end * -	 * of the acl last time.                    */ -	if(theacl->count == -1) -		return(0); - -	link = theacl; -	/* To get to the next acl, traverse linked list until index * -	 * of acl matches the count we are keeping.  This count is  * -	 * incremented each time we return an acl entry.            */ - -	for(keep_going = 0; keep_going < theacl->count; keep_going++) -		link = link->nextp; - -	entry = *entry_p =  link->entryp; - -	DEBUG(10,("*entry_p is %d\n",entry_p)); -	DEBUG(10,("*entry_p->ace_access is %d\n",entry->ace_access)); - -	/* Increment count */ -	theacl->count++; -	if(link->nextp == NULL) -		theacl->count = -1; - -	return(1); -} - -int sys_acl_get_tag_type( SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *tag_type_p) -{ -	/* Initialize tag type */ - -	*tag_type_p = -1; -	DEBUG(10,("the tagtype is %d\n",entry_d->ace_id->id_type)); - -	/* Depending on what type of entry we have, * -	 * return tag type.                         */ -	switch(entry_d->ace_id->id_type) { -	case ACEID_USER: -		*tag_type_p = SMB_ACL_USER; -		break; -	case ACEID_GROUP: -		*tag_type_p = SMB_ACL_GROUP; -		break; - -	case SMB_ACL_USER_OBJ: -	case SMB_ACL_GROUP_OBJ: -	case SMB_ACL_OTHER: -		*tag_type_p = entry_d->ace_id->id_type; -		break; -  -	default: -		return(-1); -	} - -	return(0); -} - -int sys_acl_get_permset( SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p) -{ -	DEBUG(10,("Starting AIX sys_acl_get_permset\n")); -	*permset_p = &entry_d->ace_access; -	DEBUG(10,("**permset_p is %d\n",**permset_p)); -	if(!(**permset_p & S_IXUSR) && -		!(**permset_p & S_IWUSR) && -		!(**permset_p & S_IRUSR) && -		(**permset_p != 0)) -			return(-1); - -	DEBUG(10,("Ending AIX sys_acl_get_permset\n")); -	return(0); -} - -void *sys_acl_get_qualifier( SMB_ACL_ENTRY_T entry_d) -{ -	return(entry_d->ace_id->id_data); -} - -SMB_ACL_T sys_acl_get_file( const char *path_p, SMB_ACL_TYPE_T type) -{ -	struct acl *file_acl = (struct acl *)NULL; -	struct acl_entry *acl_entry; -	struct new_acl_entry *new_acl_entry; -	struct ace_id *idp; -	struct acl_entry_link *acl_entry_link; -	struct acl_entry_link *acl_entry_link_head; -	int i; -	int rc = 0; -	uid_t user_id; - -	/* Get the acl using statacl */ -  -	DEBUG(10,("Entering sys_acl_get_file\n")); -	DEBUG(10,("path_p is %s\n",path_p)); - -	file_acl = (struct acl *)malloc(BUFSIZ); -  -	if(file_acl == NULL) { -		errno=ENOMEM; -		DEBUG(0,("Error in AIX sys_acl_get_file: %d\n",errno)); -		return(NULL); -	} - -	memset(file_acl,0,BUFSIZ); - -	rc = statacl((char *)path_p,0,file_acl,BUFSIZ); -	if(rc == -1) { -		DEBUG(0,("statacl returned %d with errno %d\n",rc,errno)); -		SAFE_FREE(file_acl); -		return(NULL); -	} - -	DEBUG(10,("Got facl and returned it\n")); - -	/* Point to the first acl entry in the acl */ -	acl_entry =  file_acl->acl_ext; - -	/* Begin setting up the head of the linked list * -	 * that will be used for the storing the acl    * -	 * in a way that is useful for the posix_acls.c * -	 * code.                                          */ - -	acl_entry_link_head = acl_entry_link = sys_acl_init(0); -	if(acl_entry_link_head == NULL) -		return(NULL); - -	acl_entry_link->entryp = (struct new_acl_entry *)malloc(sizeof(struct new_acl_entry)); -	if(acl_entry_link->entryp == NULL) { -		SAFE_FREE(file_acl); -		errno = ENOMEM; -		DEBUG(0,("Error in AIX sys_acl_get_file is %d\n",errno)); -		return(NULL); -	} - -	DEBUG(10,("acl_entry is %d\n",acl_entry)); -	DEBUG(10,("acl_last(file_acl) id %d\n",acl_last(file_acl))); - -	/* Check if the extended acl bit is on.   * -	 * If it isn't, do not show the           * -	 * contents of the acl since AIX intends * -	 * the extended info to remain unused     */ - -	if(file_acl->acl_mode & S_IXACL){ -		/* while we are not pointing to the very end */ -		while(acl_entry < acl_last(file_acl)) { -			/* before we malloc anything, make sure this is  */ -			/* a valid acl entry and one that we want to map */ -			idp = id_nxt(acl_entry->ace_id); -			if((acl_entry->ace_type == ACC_SPECIFY || -				(acl_entry->ace_type == ACC_PERMIT)) && (idp != id_last(acl_entry))) { -					acl_entry = acl_nxt(acl_entry); -					continue; -			} - -			idp = acl_entry->ace_id; - -			/* Check if this is the first entry in the linked list. * -			 * The first entry needs to keep prevp pointing to NULL * -			 * and already has entryp allocated.                  */ - -			if(acl_entry_link_head->count != 0) { -				acl_entry_link->nextp = (struct acl_entry_link *) -											malloc(sizeof(struct acl_entry_link)); - -				if(acl_entry_link->nextp == NULL) { -					SAFE_FREE(file_acl); -					errno = ENOMEM; -					DEBUG(0,("Error in AIX sys_acl_get_file is %d\n",errno)); -					return(NULL); -				} - -				acl_entry_link->nextp->prevp = acl_entry_link; -				acl_entry_link = acl_entry_link->nextp; -				acl_entry_link->entryp = (struct new_acl_entry *)malloc(sizeof(struct new_acl_entry)); -				if(acl_entry_link->entryp == NULL) { -					SAFE_FREE(file_acl); -					errno = ENOMEM; -					DEBUG(0,("Error in AIX sys_acl_get_file is %d\n",errno)); -					return(NULL); -				} -				acl_entry_link->nextp = NULL; -			} - -			acl_entry_link->entryp->ace_len = acl_entry->ace_len; - -			/* Don't really need this since all types are going * -			 * to be specified but, it's better than leaving it 0 */ - -			acl_entry_link->entryp->ace_type = acl_entry->ace_type; -  -			acl_entry_link->entryp->ace_access = acl_entry->ace_access; -  -			memcpy(acl_entry_link->entryp->ace_id,idp,sizeof(struct ace_id)); - -			/* The access in the acl entries must be left shifted by * -			 * three bites, because they will ultimately be compared * -			 * to S_IRUSR, S_IWUSR, and S_IXUSR.                  */ - -			switch(acl_entry->ace_type){ -			case ACC_PERMIT: -			case ACC_SPECIFY: -				acl_entry_link->entryp->ace_access = acl_entry->ace_access; -				acl_entry_link->entryp->ace_access <<= 6; -				acl_entry_link_head->count++; -				break; -			case ACC_DENY: -				/* Since there is no way to return a DENY acl entry * -				 * change to PERMIT and then shift.                 */ -				DEBUG(10,("acl_entry->ace_access is %d\n",acl_entry->ace_access)); -				acl_entry_link->entryp->ace_access = ~acl_entry->ace_access & 7; -				DEBUG(10,("acl_entry_link->entryp->ace_access is %d\n",acl_entry_link->entryp->ace_access)); -				acl_entry_link->entryp->ace_access <<= 6; -				acl_entry_link_head->count++; -				break; -			default: -				return(0); -			} - -			DEBUG(10,("acl_entry = %d\n",acl_entry)); -			DEBUG(10,("The ace_type is %d\n",acl_entry->ace_type)); -  -			acl_entry = acl_nxt(acl_entry); -		} -	} /* end of if enabled */ - -	/* Since owner, group, other acl entries are not * -	 * part of the acl entries in an acl, they must  * -	 * be dummied up to become part of the list.     */ - -	for( i = 1; i < 4; i++) { -		DEBUG(10,("i is %d\n",i)); -		if(acl_entry_link_head->count != 0) { -			acl_entry_link->nextp = (struct acl_entry_link *)malloc(sizeof(struct acl_entry_link)); -			if(acl_entry_link->nextp == NULL) { -				SAFE_FREE(file_acl); -				errno = ENOMEM; -				DEBUG(0,("Error in AIX sys_acl_get_file is %d\n",errno)); -				return(NULL); -			} - -			acl_entry_link->nextp->prevp = acl_entry_link; -			acl_entry_link = acl_entry_link->nextp; -			acl_entry_link->entryp = (struct new_acl_entry *)malloc(sizeof(struct new_acl_entry)); -			if(acl_entry_link->entryp == NULL) { -				SAFE_FREE(file_acl); -				errno = ENOMEM; -				DEBUG(0,("Error in AIX sys_acl_get_file is %d\n",errno)); -				return(NULL); -			} -		} - -		acl_entry_link->nextp = NULL; - -		new_acl_entry = acl_entry_link->entryp; -		idp = new_acl_entry->ace_id; - -		new_acl_entry->ace_len = sizeof(struct acl_entry); -		new_acl_entry->ace_type = ACC_PERMIT; -		idp->id_len = sizeof(struct ace_id); -		DEBUG(10,("idp->id_len = %d\n",idp->id_len)); -		memset(idp->id_data,0,sizeof(uid_t)); - -		switch(i) { -		case 2: -			new_acl_entry->ace_access = file_acl->g_access << 6; -			idp->id_type = SMB_ACL_GROUP_OBJ; -			break; - -		case 3: -			new_acl_entry->ace_access = file_acl->o_access << 6; -			idp->id_type = SMB_ACL_OTHER; -			break; -  -		case 1: -			new_acl_entry->ace_access = file_acl->u_access << 6; -			idp->id_type = SMB_ACL_USER_OBJ; -			break; -  -		default: -			return(NULL); - -		} - -		acl_entry_link_head->count++; -		DEBUG(10,("new_acl_entry->ace_access = %d\n",new_acl_entry->ace_access)); -	} - -	acl_entry_link_head->count = 0; -	SAFE_FREE(file_acl); - -	return(acl_entry_link_head); -} - -SMB_ACL_T sys_acl_get_fd(int fd) -{ -	struct acl *file_acl = (struct acl *)NULL; -	struct acl_entry *acl_entry; -	struct new_acl_entry *new_acl_entry; -	struct ace_id *idp; -	struct acl_entry_link *acl_entry_link; -	struct acl_entry_link *acl_entry_link_head; -	int i; -	int rc = 0; -	uid_t user_id; - -	/* Get the acl using fstatacl */ -    -	DEBUG(10,("Entering sys_acl_get_fd\n")); -	DEBUG(10,("fd is %d\n",fd)); -	file_acl = (struct acl *)malloc(BUFSIZ); - -	if(file_acl == NULL) { -		errno=ENOMEM; -		DEBUG(0,("Error in sys_acl_get_fd is %d\n",errno)); -		return(NULL); -	} - -	memset(file_acl,0,BUFSIZ); - -	rc = fstatacl(fd,0,file_acl,BUFSIZ); -	if(rc == -1) { -		DEBUG(0,("The fstatacl call returned %d with errno %d\n",rc,errno)); -		SAFE_FREE(file_acl); -		return(NULL); -	} - -	DEBUG(10,("Got facl and returned it\n")); - -	/* Point to the first acl entry in the acl */ - -	acl_entry =  file_acl->acl_ext; -	/* Begin setting up the head of the linked list * -	 * that will be used for the storing the acl    * -	 * in a way that is useful for the posix_acls.c * -	 * code.                                        */ - -	acl_entry_link_head = acl_entry_link = sys_acl_init(0); -	if(acl_entry_link_head == NULL){ -		SAFE_FREE(file_acl); -		return(NULL); -	} - -	acl_entry_link->entryp = (struct new_acl_entry *)malloc(sizeof(struct new_acl_entry)); - -	if(acl_entry_link->entryp == NULL) { -		errno = ENOMEM; -		DEBUG(0,("Error in sys_acl_get_fd is %d\n",errno)); -		SAFE_FREE(file_acl); -		return(NULL); -	} - -	DEBUG(10,("acl_entry is %d\n",acl_entry)); -	DEBUG(10,("acl_last(file_acl) id %d\n",acl_last(file_acl))); -  -	/* Check if the extended acl bit is on.   * -	 * If it isn't, do not show the           * -	 * contents of the acl since AIX intends  * -	 * the extended info to remain unused     */ -  -	if(file_acl->acl_mode & S_IXACL){ -		/* while we are not pointing to the very end */ -		while(acl_entry < acl_last(file_acl)) { -			/* before we malloc anything, make sure this is  */ -			/* a valid acl entry and one that we want to map */ - -			idp = id_nxt(acl_entry->ace_id); -			if((acl_entry->ace_type == ACC_SPECIFY || -				(acl_entry->ace_type == ACC_PERMIT)) && (idp != id_last(acl_entry))) { -					acl_entry = acl_nxt(acl_entry); -					continue; -			} - -			idp = acl_entry->ace_id; -  -			/* Check if this is the first entry in the linked list. * -			 * The first entry needs to keep prevp pointing to NULL * -			 * and already has entryp allocated.                 */ - -			if(acl_entry_link_head->count != 0) { -				acl_entry_link->nextp = (struct acl_entry_link *)malloc(sizeof(struct acl_entry_link)); -				if(acl_entry_link->nextp == NULL) { -					errno = ENOMEM; -					DEBUG(0,("Error in sys_acl_get_fd is %d\n",errno)); -					SAFE_FREE(file_acl); -					return(NULL); -				} -				acl_entry_link->nextp->prevp = acl_entry_link; -				acl_entry_link = acl_entry_link->nextp; -				acl_entry_link->entryp = (struct new_acl_entry *)malloc(sizeof(struct new_acl_entry)); -				if(acl_entry_link->entryp == NULL) { -					errno = ENOMEM; -					DEBUG(0,("Error in sys_acl_get_fd is %d\n",errno)); -					SAFE_FREE(file_acl); -					return(NULL); -				} - -				acl_entry_link->nextp = NULL; -			} - -			acl_entry_link->entryp->ace_len = acl_entry->ace_len; - -			/* Don't really need this since all types are going * -			 * to be specified but, it's better than leaving it 0 */ - -			acl_entry_link->entryp->ace_type = acl_entry->ace_type; -			acl_entry_link->entryp->ace_access = acl_entry->ace_access; - -			memcpy(acl_entry_link->entryp->ace_id, idp, sizeof(struct ace_id)); - -			/* The access in the acl entries must be left shifted by * -			 * three bites, because they will ultimately be compared * -			 * to S_IRUSR, S_IWUSR, and S_IXUSR.                  */ - -			switch(acl_entry->ace_type){ -			case ACC_PERMIT: -			case ACC_SPECIFY: -				acl_entry_link->entryp->ace_access = acl_entry->ace_access; -				acl_entry_link->entryp->ace_access <<= 6; -				acl_entry_link_head->count++; -				break; -			case ACC_DENY: -				/* Since there is no way to return a DENY acl entry * -				 * change to PERMIT and then shift.                 */ -				DEBUG(10,("acl_entry->ace_access is %d\n",acl_entry->ace_access)); -				acl_entry_link->entryp->ace_access = ~acl_entry->ace_access & 7; -				DEBUG(10,("acl_entry_link->entryp->ace_access is %d\n",acl_entry_link->entryp->ace_access)); -				acl_entry_link->entryp->ace_access <<= 6; -				acl_entry_link_head->count++; -				break; -			default: -				return(0); -			} - -			DEBUG(10,("acl_entry = %d\n",acl_entry)); -			DEBUG(10,("The ace_type is %d\n",acl_entry->ace_type)); -  -			acl_entry = acl_nxt(acl_entry); -		} -	} /* end of if enabled */ - -	/* Since owner, group, other acl entries are not * -	 * part of the acl entries in an acl, they must  * -	 * be dummied up to become part of the list.     */ - -	for( i = 1; i < 4; i++) { -		DEBUG(10,("i is %d\n",i)); -		if(acl_entry_link_head->count != 0){ -			acl_entry_link->nextp = (struct acl_entry_link *)malloc(sizeof(struct acl_entry_link)); -			if(acl_entry_link->nextp == NULL) { -				errno = ENOMEM; -				DEBUG(0,("Error in sys_acl_get_fd is %d\n",errno)); -				SAFE_FREE(file_acl); -				return(NULL); -			} - -			acl_entry_link->nextp->prevp = acl_entry_link; -			acl_entry_link = acl_entry_link->nextp; -			acl_entry_link->entryp = (struct new_acl_entry *)malloc(sizeof(struct new_acl_entry)); - -			if(acl_entry_link->entryp == NULL) { -				SAFE_FREE(file_acl); -				errno = ENOMEM; -				DEBUG(0,("Error in sys_acl_get_fd is %d\n",errno)); -				return(NULL); -			} -		} - -		acl_entry_link->nextp = NULL; -  -		new_acl_entry = acl_entry_link->entryp; -		idp = new_acl_entry->ace_id; -  -		new_acl_entry->ace_len = sizeof(struct acl_entry); -		new_acl_entry->ace_type = ACC_PERMIT; -		idp->id_len = sizeof(struct ace_id); -		DEBUG(10,("idp->id_len = %d\n",idp->id_len)); -		memset(idp->id_data,0,sizeof(uid_t)); -  -		switch(i) { -		case 2: -			new_acl_entry->ace_access = file_acl->g_access << 6; -			idp->id_type = SMB_ACL_GROUP_OBJ; -			break; -  -		case 3: -			new_acl_entry->ace_access = file_acl->o_access << 6; -			idp->id_type = SMB_ACL_OTHER; -			break; -  -		case 1: -			new_acl_entry->ace_access = file_acl->u_access << 6; -			idp->id_type = SMB_ACL_USER_OBJ; -			break; -  -		default: -			return(NULL); -		} -  -		acl_entry_link_head->count++; -		DEBUG(10,("new_acl_entry->ace_access = %d\n",new_acl_entry->ace_access)); -	} - -	acl_entry_link_head->count = 0; -	SAFE_FREE(file_acl); -  -	return(acl_entry_link_head); -} - -int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset) -{ -	*permset = *permset & ~0777; -	return(0); -} - -int sys_acl_add_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -	if((perm != 0) && -			(perm & (S_IXUSR | S_IWUSR | S_IRUSR)) == 0) -		return(-1); - -	*permset |= perm; -	DEBUG(10,("This is the permset now: %d\n",*permset)); -	return(0); -} - -char *sys_acl_to_text( SMB_ACL_T theacl, ssize_t *plen) -{ -	return(NULL); -} - -SMB_ACL_T sys_acl_init( int count) -{ -	struct acl_entry_link *theacl = NULL; -  -	DEBUG(10,("Entering sys_acl_init\n")); - -	theacl = (struct acl_entry_link *)malloc(sizeof(struct acl_entry_link)); -	if(theacl == NULL) { -		errno = ENOMEM; -		DEBUG(0,("Error in sys_acl_init is %d\n",errno)); -		return(NULL); -	} - -	theacl->count = 0; -	theacl->nextp = NULL; -	theacl->prevp = NULL; -	theacl->entryp = NULL; -	DEBUG(10,("Exiting sys_acl_init\n")); -	return(theacl); -} - -int sys_acl_create_entry( SMB_ACL_T *pacl, SMB_ACL_ENTRY_T *pentry) -{ -	struct acl_entry_link *theacl; -	struct acl_entry_link *acl_entryp; -	struct acl_entry_link *temp_entry; -	int counting; - -	DEBUG(10,("Entering the sys_acl_create_entry\n")); - -	theacl = acl_entryp = *pacl; - -	/* Get to the end of the acl before adding entry */ - -	for(counting=0; counting < theacl->count; counting++){ -		DEBUG(10,("The acl_entryp is %d\n",acl_entryp)); -		temp_entry = acl_entryp; -		acl_entryp = acl_entryp->nextp; -	} - -	if(theacl->count != 0){ -		temp_entry->nextp = acl_entryp = (struct acl_entry_link *)malloc(sizeof(struct acl_entry_link)); -		if(acl_entryp == NULL) { -			errno = ENOMEM; -			DEBUG(0,("Error in sys_acl_create_entry is %d\n",errno)); -			return(-1); -		} - -		DEBUG(10,("The acl_entryp is %d\n",acl_entryp)); -		acl_entryp->prevp = temp_entry; -		DEBUG(10,("The acl_entryp->prevp is %d\n",acl_entryp->prevp)); -	} - -	*pentry = acl_entryp->entryp = (struct new_acl_entry *)malloc(sizeof(struct new_acl_entry)); -	if(*pentry == NULL) { -		errno = ENOMEM; -		DEBUG(0,("Error in sys_acl_create_entry is %d\n",errno)); -		return(-1); -	} - -	memset(*pentry,0,sizeof(struct new_acl_entry)); -	acl_entryp->entryp->ace_len = sizeof(struct acl_entry); -	acl_entryp->entryp->ace_type = ACC_PERMIT; -	acl_entryp->entryp->ace_id->id_len = sizeof(struct ace_id); -	acl_entryp->nextp = NULL; -	theacl->count++; -	DEBUG(10,("Exiting sys_acl_create_entry\n")); -	return(0); -} - -int sys_acl_set_tag_type( SMB_ACL_ENTRY_T entry, SMB_ACL_TAG_T tagtype) -{ -	DEBUG(10,("Starting AIX sys_acl_set_tag_type\n")); -	entry->ace_id->id_type = tagtype; -	DEBUG(10,("The tag type is %d\n",entry->ace_id->id_type)); -	DEBUG(10,("Ending AIX sys_acl_set_tag_type\n")); -} - -int sys_acl_set_qualifier( SMB_ACL_ENTRY_T entry, void *qual) -{ -	DEBUG(10,("Starting AIX sys_acl_set_qualifier\n")); -	memcpy(entry->ace_id->id_data,qual,sizeof(uid_t)); -	DEBUG(10,("Ending AIX sys_acl_set_qualifier\n")); -	return(0); -} - -int sys_acl_set_permset( SMB_ACL_ENTRY_T entry, SMB_ACL_PERMSET_T permset) -{ -	DEBUG(10,("Starting AIX sys_acl_set_permset\n")); -	if(!(*permset & S_IXUSR) && -		!(*permset & S_IWUSR) && -		!(*permset & S_IRUSR) && -		(*permset != 0)) -			return(-1); - -	entry->ace_access = *permset; -	DEBUG(10,("entry->ace_access = %d\n",entry->ace_access)); -	DEBUG(10,("Ending AIX sys_acl_set_permset\n")); -	return(0); -} - -int sys_acl_valid( SMB_ACL_T theacl ) -{ -	int user_obj = 0; -	int group_obj = 0; -	int other_obj = 0; -	struct acl_entry_link *acl_entry; - -	for(acl_entry=theacl; acl_entry != NULL; acl_entry = acl_entry->nextp) { -		user_obj += (acl_entry->entryp->ace_id->id_type == SMB_ACL_USER_OBJ); -		group_obj += (acl_entry->entryp->ace_id->id_type == SMB_ACL_GROUP_OBJ); -		other_obj += (acl_entry->entryp->ace_id->id_type == SMB_ACL_OTHER); -	} - -	DEBUG(10,("user_obj=%d, group_obj=%d, other_obj=%d\n",user_obj,group_obj,other_obj)); -  -	if(user_obj != 1 || group_obj != 1 || other_obj != 1) -		return(-1);  - -	return(0); -} - -int sys_acl_set_file( const char *name, SMB_ACL_TYPE_T acltype, SMB_ACL_T theacl) -{ -	struct acl_entry_link *acl_entry_link = NULL; -	struct acl *file_acl = NULL; -	struct acl *file_acl_temp = NULL; -	struct acl_entry *acl_entry = NULL; -	struct ace_id *ace_id = NULL; -	uint id_type; -	uint ace_access; -	uint user_id; -	uint acl_length; -	uint rc; - -	DEBUG(10,("Entering sys_acl_set_file\n")); -	DEBUG(10,("File name is %s\n",name)); -  -	/* AIX has no default ACL */ -	if(acltype == SMB_ACL_TYPE_DEFAULT) -		return(0); - -	acl_length = BUFSIZ; -	file_acl = (struct acl *)malloc(BUFSIZ); - -	if(file_acl == NULL) { -		errno = ENOMEM; -		DEBUG(0,("Error in sys_acl_set_file is %d\n",errno)); -		return(-1); -	} - -	memset(file_acl,0,BUFSIZ); - -	file_acl->acl_len = ACL_SIZ; -	file_acl->acl_mode = S_IXACL; - -	for(acl_entry_link=theacl; acl_entry_link != NULL; acl_entry_link = acl_entry_link->nextp) { -		acl_entry_link->entryp->ace_access >>= 6; -		id_type = acl_entry_link->entryp->ace_id->id_type; - -		switch(id_type) { -		case SMB_ACL_USER_OBJ: -			file_acl->u_access = acl_entry_link->entryp->ace_access; -			continue; -		case SMB_ACL_GROUP_OBJ: -			file_acl->g_access = acl_entry_link->entryp->ace_access; -			continue; -		case SMB_ACL_OTHER: -			file_acl->o_access = acl_entry_link->entryp->ace_access; -			continue; -		case SMB_ACL_MASK: -			continue; -		} - -		if((file_acl->acl_len + sizeof(struct acl_entry)) > acl_length) { -			acl_length += sizeof(struct acl_entry); -			file_acl_temp = (struct acl *)malloc(acl_length); -			if(file_acl_temp == NULL) { -				SAFE_FREE(file_acl); -				errno = ENOMEM; -				DEBUG(0,("Error in sys_acl_set_file is %d\n",errno)); -				return(-1); -			}   - -			memcpy(file_acl_temp,file_acl,file_acl->acl_len); -			SAFE_FREE(file_acl); -			file_acl = file_acl_temp; -		} - -		acl_entry = (struct acl_entry *)((char *)file_acl + file_acl->acl_len); -		file_acl->acl_len += sizeof(struct acl_entry); -		acl_entry->ace_len = acl_entry_link->entryp->ace_len; -		acl_entry->ace_access = acl_entry_link->entryp->ace_access; -  -		/* In order to use this, we'll need to wait until we can get denies */ -		/* if(!acl_entry->ace_access && acl_entry->ace_type == ACC_PERMIT) -		acl_entry->ace_type = ACC_SPECIFY; */ - -		acl_entry->ace_type = ACC_SPECIFY; -  -		ace_id = acl_entry->ace_id; -  -		ace_id->id_type = acl_entry_link->entryp->ace_id->id_type; -		DEBUG(10,("The id type is %d\n",ace_id->id_type)); -		ace_id->id_len = acl_entry_link->entryp->ace_id->id_len; -		memcpy(&user_id, acl_entry_link->entryp->ace_id->id_data, sizeof(uid_t)); -		memcpy(acl_entry->ace_id->id_data, &user_id, sizeof(uid_t)); -	} - -	rc = chacl(name,file_acl,file_acl->acl_len); -	DEBUG(10,("errno is %d\n",errno)); -	DEBUG(10,("return code is %d\n",rc)); -	SAFE_FREE(file_acl); -	DEBUG(10,("Exiting the sys_acl_set_file\n")); -	return(rc); -} - -int sys_acl_set_fd( int fd, SMB_ACL_T theacl) -{ -	struct acl_entry_link *acl_entry_link = NULL; -	struct acl *file_acl = NULL; -	struct acl *file_acl_temp = NULL; -	struct acl_entry *acl_entry = NULL; -	struct ace_id *ace_id = NULL; -	uint id_type; -	uint user_id; -	uint acl_length; -	uint rc; -  -	DEBUG(10,("Entering sys_acl_set_fd\n")); -	acl_length = BUFSIZ; -	file_acl = (struct acl *)malloc(BUFSIZ); - -	if(file_acl == NULL) { -		errno = ENOMEM; -		DEBUG(0,("Error in sys_acl_set_fd is %d\n",errno)); -		return(-1); -	} - -	memset(file_acl,0,BUFSIZ); -  -	file_acl->acl_len = ACL_SIZ; -	file_acl->acl_mode = S_IXACL; - -	for(acl_entry_link=theacl; acl_entry_link != NULL; acl_entry_link = acl_entry_link->nextp) { -		acl_entry_link->entryp->ace_access >>= 6; -		id_type = acl_entry_link->entryp->ace_id->id_type; -		DEBUG(10,("The id_type is %d\n",id_type)); - -		switch(id_type) { -		case SMB_ACL_USER_OBJ: -			file_acl->u_access = acl_entry_link->entryp->ace_access; -			continue; -		case SMB_ACL_GROUP_OBJ: -			file_acl->g_access = acl_entry_link->entryp->ace_access; -			continue; -		case SMB_ACL_OTHER: -			file_acl->o_access = acl_entry_link->entryp->ace_access; -			continue; -		case SMB_ACL_MASK: -			continue; -		} - -		if((file_acl->acl_len + sizeof(struct acl_entry)) > acl_length) { -			acl_length += sizeof(struct acl_entry); -			file_acl_temp = (struct acl *)malloc(acl_length); -			if(file_acl_temp == NULL) { -				SAFE_FREE(file_acl); -				errno = ENOMEM; -				DEBUG(0,("Error in sys_acl_set_fd is %d\n",errno)); -				return(-1); -			} - -			memcpy(file_acl_temp,file_acl,file_acl->acl_len); -			SAFE_FREE(file_acl); -			file_acl = file_acl_temp; -		} - -		acl_entry = (struct acl_entry *)((char *)file_acl + file_acl->acl_len); -		file_acl->acl_len += sizeof(struct acl_entry); -		acl_entry->ace_len = acl_entry_link->entryp->ace_len; -		acl_entry->ace_access = acl_entry_link->entryp->ace_access; -  -		/* In order to use this, we'll need to wait until we can get denies */ -		/* if(!acl_entry->ace_access && acl_entry->ace_type == ACC_PERMIT) -			acl_entry->ace_type = ACC_SPECIFY; */ -  -		acl_entry->ace_type = ACC_SPECIFY; -  -		ace_id = acl_entry->ace_id; -  -		ace_id->id_type = acl_entry_link->entryp->ace_id->id_type; -		DEBUG(10,("The id type is %d\n",ace_id->id_type)); -		ace_id->id_len = acl_entry_link->entryp->ace_id->id_len; -		memcpy(&user_id, acl_entry_link->entryp->ace_id->id_data, sizeof(uid_t)); -		memcpy(ace_id->id_data, &user_id, sizeof(uid_t)); -	} -  -	rc = fchacl(fd,file_acl,file_acl->acl_len); -	DEBUG(10,("errno is %d\n",errno)); -	DEBUG(10,("return code is %d\n",rc)); -	SAFE_FREE(file_acl); -	DEBUG(10,("Exiting sys_acl_set_fd\n")); -	return(rc); -} - -int sys_acl_delete_def_file(const char *name) -{ -	/* AIX has no default ACL */ -	return 0; -} - -int sys_acl_get_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -	return(*permset & perm); -} - -int sys_acl_free_text(char *text) -{ -	return(0); -} - -int sys_acl_free_acl(SMB_ACL_T posix_acl) -{ -	struct acl_entry_link *acl_entry_link; - -	for(acl_entry_link = posix_acl->nextp; acl_entry_link->nextp != NULL; acl_entry_link = acl_entry_link->nextp) { -		SAFE_FREE(acl_entry_link->prevp->entryp); -		SAFE_FREE(acl_entry_link->prevp); -	} - -	SAFE_FREE(acl_entry_link->prevp->entryp); -	SAFE_FREE(acl_entry_link->prevp); -	SAFE_FREE(acl_entry_link->entryp); -	SAFE_FREE(acl_entry_link); -  -	return(0); -} - -int sys_acl_free_qualifier(void *qual, SMB_ACL_TAG_T tagtype) -{ -	return(0); -} - -#else /* No ACLs. */ - -int sys_acl_get_entry( SMB_ACL_T the_acl, int entry_id, SMB_ACL_ENTRY_T *entry_p) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_get_tag_type( SMB_ACL_ENTRY_T entry_d, SMB_ACL_TAG_T *tag_type_p) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_get_permset( SMB_ACL_ENTRY_T entry_d, SMB_ACL_PERMSET_T *permset_p) -{ -	errno = ENOSYS; -	return -1; -} - -void *sys_acl_get_qualifier( SMB_ACL_ENTRY_T entry_d) -{ -	errno = ENOSYS; -	return NULL; -} - -SMB_ACL_T sys_acl_get_file( const char *path_p, SMB_ACL_TYPE_T type) -{ -	errno = ENOSYS; -	return (SMB_ACL_T)NULL; -} - -SMB_ACL_T sys_acl_get_fd(int fd) -{ -	errno = ENOSYS; -	return (SMB_ACL_T)NULL; -} - -int sys_acl_clear_perms(SMB_ACL_PERMSET_T permset) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_add_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_get_perm( SMB_ACL_PERMSET_T permset, SMB_ACL_PERM_T perm) -{ -	errno = ENOSYS; -	return (permset & perm) ? 1 : 0; -} - -char *sys_acl_to_text( SMB_ACL_T the_acl, ssize_t *plen) -{ -	errno = ENOSYS; -	return NULL; -} - -int sys_acl_free_text(char *text) -{ -	errno = ENOSYS; -	return -1; -} - -SMB_ACL_T sys_acl_init( int count) -{ -	errno = ENOSYS; -	return NULL; -} - -int sys_acl_create_entry( SMB_ACL_T *pacl, SMB_ACL_ENTRY_T *pentry) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_set_tag_type( SMB_ACL_ENTRY_T entry, SMB_ACL_TAG_T tagtype) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_set_qualifier( SMB_ACL_ENTRY_T entry, void *qual) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_set_permset( SMB_ACL_ENTRY_T entry, SMB_ACL_PERMSET_T permset) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_valid( SMB_ACL_T theacl ) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_set_file( const char *name, SMB_ACL_TYPE_T acltype, SMB_ACL_T theacl) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_set_fd( int fd, SMB_ACL_T theacl) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_delete_def_file(const char *name) -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_free_acl(SMB_ACL_T the_acl)  -{ -	errno = ENOSYS; -	return -1; -} - -int sys_acl_free_qualifier(void *qual, SMB_ACL_TAG_T tagtype) -{ -	errno = ENOSYS; -	return -1; -} - -#endif /* No ACLs. */ diff --git a/source4/lib/username.c b/source4/lib/username.c index 2d9d212858..1c8e5aa2bb 100644 --- a/source4/lib/username.c +++ b/source4/lib/username.c @@ -21,10 +21,6 @@  #include "includes.h" -/* internal functions */ -static struct passwd *uname_string_combinations(char *s, struct passwd * (*fn) (const char *), int N); -static struct passwd *uname_string_combinations2(char *s, int offset, struct passwd * (*fn) (const char *), int N); -  /*****************************************************************   Splits passed user or group name to domain and user/group name parts   Returns True if name was splitted and False otherwise. @@ -52,317 +48,3 @@ BOOL split_domain_and_name(const char *name, char *domain, char* username)  	DEBUG(10,("split_domain_and_name: all is fine, domain is |%s| and name is |%s|\n", domain, username));  	return True;  } - -/**************************************************************************** - Get a users home directory. -****************************************************************************/ - -char *get_user_home_dir(const char *user) -{ -	struct passwd *pass; - -	/* Ensure the user exists. */ - -	pass = Get_Pwnam(user); - -	if (!pass) -		return(NULL); -	/* Return home directory from struct passwd. */ - -	return(pass->pw_dir);       -} - - -/**************************************************************************** - * A wrapper for sys_getpwnam().  The following variations are tried: - *   - as transmitted - *   - in all lower case if this differs from transmitted - *   - in all upper case if this differs from transmitted - *   - using lp_usernamelevel() for permutations. -****************************************************************************/ - -static struct passwd *Get_Pwnam_ret = NULL; - -static struct passwd *Get_Pwnam_internals(const char *user, char *user2) -{ -	struct passwd *ret = NULL; - -	if (!user2 || !(*user2)) -		return(NULL); - -	if (!user || !(*user)) -		return(NULL); - -	/* Try in all lower case first as this is the most  -	   common case on UNIX systems */ -	strlower(user2); -	DEBUG(5,("Trying _Get_Pwnam(), username as lowercase is %s\n",user2)); -	ret = getpwnam_alloc(user2); -	if(ret) -		goto done; - -	/* Try as given, if username wasn't originally lowercase */ -	if(strcmp(user, user2) != 0) { -		DEBUG(5,("Trying _Get_Pwnam(), username as given is %s\n", user)); -		ret = getpwnam_alloc(user); -		if(ret) -			goto done; -	} - -	/* Try as uppercase, if username wasn't originally uppercase */ -	strupper(user2); -	if(strcmp(user, user2) != 0) { -		DEBUG(5,("Trying _Get_Pwnam(), username as uppercase is %s\n", user2)); -		ret = getpwnam_alloc(user2); -		if(ret) -			goto done; -	} - -	/* Try all combinations up to usernamelevel */ -	strlower(user2); -	DEBUG(5,("Checking combinations of %d uppercase letters in %s\n", lp_usernamelevel(), user2)); -	ret = uname_string_combinations(user2, getpwnam_alloc, lp_usernamelevel()); - -done: -	DEBUG(5,("Get_Pwnam_internals %s find user [%s]!\n",ret ? "did":"didn't", user)); - -	/* This call used to just return the 'passwd' static buffer. -	   This could then have accidental reuse implications, so  -	   we now malloc a copy, and free it in the next use. - -	   This should cause the (ab)user to segfault if it  -	   uses an old struct.  -	    -	   This is better than useing the wrong data in security -	   critical operations. - -	   The real fix is to make the callers free the returned  -	   malloc'ed data. -	*/ - -	if (Get_Pwnam_ret) { -		passwd_free(&Get_Pwnam_ret); -	} -	 -	Get_Pwnam_ret = ret; - -	return ret; -} - -/**************************************************************************** - Get_Pwnam wrapper without modification. -  NOTE: This with NOT modify 'user'!  -****************************************************************************/ - -struct passwd *Get_Pwnam(const char *user) -{ -	fstring user2; -	struct passwd *ret; - -	fstrcpy(user2, user); - -	DEBUG(5,("Finding user %s\n", user)); - -	ret = Get_Pwnam_internals(user, user2); -	 -	return ret;   -} - -/**************************************************************************** - Check if a user is in a UNIX group. -****************************************************************************/ -static BOOL user_in_unix_group_list(const char *user,const char *gname) -{ -	struct passwd *pass = Get_Pwnam(user); -	struct sys_userlist *user_list; -	struct sys_userlist *member; -	TALLOC_CTX *mem_ctx; - -	DEBUG(10,("user_in_unix_group_list: checking user %s in group %s\n", user, gname)); - - 	/* - 	 * We need to check the users primary group as this - 	 * group is implicit and often not listed in the group database. - 	 */ -  - 	mem_ctx = talloc_init("smbgroupedit talloc"); -	if (!mem_ctx) return -1; - 	if (pass) { - 		if (strequal(gname,gidtoname(mem_ctx, pass->pw_gid))) { - 			DEBUG(10,("user_in_unix_group_list: group %s is primary group.\n", gname )); - 			goto exit; - 		} - 	} -  -	user_list = get_users_in_group(gname); - 	if (user_list == NULL) { - 		DEBUG(10,("user_in_unix_group_list: no such group %s\n", gname )); - 		return False; - 	} - -	for (member = user_list; member; member = member->next) { - 		DEBUG(10,("user_in_unix_group_list: checking user %s against member %s\n", -			user, member->unix_name )); -  		if (strequal(member->unix_name,user)) { -			free_userlist(user_list); -  			goto exit; -  		} -	} - -	free_userlist(user_list); -	talloc_destroy(mem_ctx); -	return False; -exit: -	talloc_destroy(mem_ctx); -	return True; -}	       - -/**************************************************************************** - Check if a user is in a group list. Ask winbind first, then use UNIX. -****************************************************************************/ -static BOOL user_in_group_list(const char *user, const char *gname, gid_t *groups, size_t n_groups) -{ -	BOOL ret; -	gid_t gid; -	unsigned i; - -	gid = nametogid(gname); -	if (gid == (gid_t)-1)  -		return False; - -	if (groups && n_groups > 0) { -		for (i=0; i < n_groups; i++) { -			if (groups[i] == gid) { -				return True; -			} -		} -		return False; -	} - -	/* fallback if we don't yet have the group list */ -	ret = user_in_unix_group_list(user, gname); -	if (ret) -		DEBUG(10,("user_in_group_list: user |%s| is in group |%s|\n", user, gname)); -	return ret; -} - -/**************************************************************************** - Check if a user is in a user list - can check combinations of UNIX - and netgroup lists. -****************************************************************************/ - -BOOL user_in_list(const char *user,const char **list, gid_t *groups, size_t n_groups) -{ -	if (!list || !*list) -		return False; - -	DEBUG(10,("user_in_list: checking user %s in list\n", user)); - -	while (*list) { - -		DEBUG(10,("user_in_list: checking user |%s| against |%s|\n", user, *list)); - -		/* -		 * Check raw username. -		 */ -		if (strequal(user, *list)) -			return(True); - -		/* -		 * Now check to see if any combination -		 * of UNIX and netgroups has been specified. -		 */ - -		if(**list == '@') { -			/* -			 * Old behaviour. Check netgroup list -			 * followed by UNIX list. -			 */ -			if(user_in_group_list(user, *list +1, groups, n_groups)) -				return True; -		} else if (**list == '+') { - -			if((*(*list +1)) == '&') { -				/* -				 * Search UNIX list followed by netgroup. -				 */ -				if(user_in_group_list(user, *list +2, groups, n_groups)) -					return True; -			} else { - -				/* -				 * Just search UNIX list. -				 */ - -				if(user_in_group_list(user, *list +1, groups, n_groups)) -					return True; -			} - -		} else if (**list == '&') { - -			if(*(*list +1) == '+') { -				/* -				 * Search netgroup list followed by UNIX list. -				 */ -				if(user_in_group_list(user, *list +2, groups, n_groups)) -					return True; -			} -		} -     -		list++; -	} -	return(False); -} - -/* The functions below have been taken from password.c and slightly modified */ -/**************************************************************************** - Apply a function to upper/lower case combinations - of a string and return true if one of them returns true. - Try all combinations with N uppercase letters. - offset is the first char to try and change (start with 0) - it assumes the string starts lowercased -****************************************************************************/ - -static struct passwd *uname_string_combinations2(char *s,int offset,struct passwd *(*fn)(const char *),int N) -{ -	ssize_t len = (ssize_t)strlen(s); -	int i; -	struct passwd *ret; - -	if (N <= 0 || offset >= len) -		return(fn(s)); - -	for (i=offset;i<(len-(N-1));i++) { -		char c = s[i]; -		if (!islower((int)c)) -			continue; -		s[i] = toupper(c); -		ret = uname_string_combinations2(s,i+1,fn,N-1); -		if(ret) -			return(ret); -		s[i] = c; -	} -	return(NULL); -} - -/**************************************************************************** - Apply a function to upper/lower case combinations - of a string and return true if one of them returns true. - Try all combinations with up to N uppercase letters. - offset is the first char to try and change (start with 0) - it assumes the string starts lowercased -****************************************************************************/ - -static struct passwd * uname_string_combinations(char *s,struct passwd * (*fn)(const char *),int N) -{ -	int n; -	struct passwd *ret; - -	for (n=1;n<=N;n++) { -		ret = uname_string_combinations2(s,0,fn,n); -		if(ret) -			return(ret); -	}   -	return(NULL); -} -  | 
