mirror of
https://github.com/samba-team/samba.git
synced 2025-08-03 04:22:09 +03:00
Tidyup of lib/username. Add name_is_local fn to determine if name is
winbindd. Getting ready for efficiency fix in group lookups. Jeremy.
This commit is contained in:
@ -31,15 +31,15 @@ static struct passwd *uname_string_combinations2(char *s, int offset, struct pas
|
|||||||
|
|
||||||
char *get_user_home_dir(const char *user)
|
char *get_user_home_dir(const char *user)
|
||||||
{
|
{
|
||||||
static struct passwd *pass;
|
static struct passwd *pass;
|
||||||
|
|
||||||
pass = Get_Pwnam(user);
|
pass = Get_Pwnam(user);
|
||||||
|
|
||||||
if (!pass) return(NULL);
|
if (!pass)
|
||||||
return(pass->pw_dir);
|
return(NULL);
|
||||||
|
return(pass->pw_dir);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*******************************************************************
|
/*******************************************************************
|
||||||
Map a username from a dos name to a unix name by looking in the username
|
Map a username from a dos name to a unix name by looking in the username
|
||||||
map. Note that this modifies the name in place.
|
map. Note that this modifies the name in place.
|
||||||
@ -53,105 +53,106 @@ char *get_user_home_dir(const char *user)
|
|||||||
|
|
||||||
BOOL map_username(char *user)
|
BOOL map_username(char *user)
|
||||||
{
|
{
|
||||||
static BOOL initialised=False;
|
static BOOL initialised=False;
|
||||||
static fstring last_from,last_to;
|
static fstring last_from,last_to;
|
||||||
XFILE *f;
|
XFILE *f;
|
||||||
char *mapfile = lp_username_map();
|
char *mapfile = lp_username_map();
|
||||||
char *s;
|
char *s;
|
||||||
pstring buf;
|
pstring buf;
|
||||||
BOOL mapped_user = False;
|
BOOL mapped_user = False;
|
||||||
|
|
||||||
if (!*user)
|
if (!*user)
|
||||||
return False;
|
return False;
|
||||||
|
|
||||||
if (!*mapfile)
|
if (!*mapfile)
|
||||||
return False;
|
return False;
|
||||||
|
|
||||||
if (!initialised) {
|
if (!initialised) {
|
||||||
*last_from = *last_to = 0;
|
*last_from = *last_to = 0;
|
||||||
initialised = True;
|
initialised = True;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (strequal(user,last_to))
|
if (strequal(user,last_to))
|
||||||
return False;
|
return False;
|
||||||
|
|
||||||
if (strequal(user,last_from)) {
|
if (strequal(user,last_from)) {
|
||||||
DEBUG(3,("Mapped user %s to %s\n",user,last_to));
|
DEBUG(3,("Mapped user %s to %s\n",user,last_to));
|
||||||
fstrcpy(user,last_to);
|
fstrcpy(user,last_to);
|
||||||
return True;
|
return True;
|
||||||
}
|
}
|
||||||
|
|
||||||
f = x_fopen(mapfile,O_RDONLY, 0);
|
f = x_fopen(mapfile,O_RDONLY, 0);
|
||||||
if (!f) {
|
if (!f) {
|
||||||
DEBUG(0,("can't open username map %s. Error %s\n",mapfile, strerror(errno) ));
|
DEBUG(0,("can't open username map %s. Error %s\n",mapfile, strerror(errno) ));
|
||||||
return False;
|
return False;
|
||||||
}
|
}
|
||||||
|
|
||||||
DEBUG(4,("Scanning username map %s\n",mapfile));
|
DEBUG(4,("Scanning username map %s\n",mapfile));
|
||||||
|
|
||||||
while((s=fgets_slash(buf,sizeof(buf),f))!=NULL) {
|
while((s=fgets_slash(buf,sizeof(buf),f))!=NULL) {
|
||||||
char *unixname = s;
|
char *unixname = s;
|
||||||
char *dosname = strchr_m(unixname,'=');
|
char *dosname = strchr_m(unixname,'=');
|
||||||
char **dosuserlist;
|
char **dosuserlist;
|
||||||
BOOL return_if_mapped = False;
|
BOOL return_if_mapped = False;
|
||||||
|
|
||||||
if (!dosname)
|
if (!dosname)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
*dosname++ = 0;
|
*dosname++ = 0;
|
||||||
|
|
||||||
while (isspace(*unixname))
|
while (isspace(*unixname))
|
||||||
unixname++;
|
unixname++;
|
||||||
if ('!' == *unixname) {
|
|
||||||
return_if_mapped = True;
|
if ('!' == *unixname) {
|
||||||
unixname++;
|
return_if_mapped = True;
|
||||||
while (*unixname && isspace(*unixname))
|
unixname++;
|
||||||
unixname++;
|
while (*unixname && isspace(*unixname))
|
||||||
}
|
unixname++;
|
||||||
|
}
|
||||||
|
|
||||||
if (!*unixname || strchr_m("#;",*unixname))
|
if (!*unixname || strchr_m("#;",*unixname))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
{
|
{
|
||||||
int l = strlen(unixname);
|
int l = strlen(unixname);
|
||||||
while (l && isspace(unixname[l-1])) {
|
while (l && isspace(unixname[l-1])) {
|
||||||
unixname[l-1] = 0;
|
unixname[l-1] = 0;
|
||||||
l--;
|
l--;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
dosuserlist = lp_list_make(dosname);
|
dosuserlist = lp_list_make(dosname);
|
||||||
if (!dosuserlist) {
|
if (!dosuserlist) {
|
||||||
DEBUG(0,("Unable to build user list\n"));
|
DEBUG(0,("Unable to build user list\n"));
|
||||||
return False;
|
return False;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (strchr_m(dosname,'*') || user_in_list(user, dosuserlist)) {
|
if (strchr_m(dosname,'*') || user_in_list(user, dosuserlist)) {
|
||||||
DEBUG(3,("Mapped user %s to %s\n",user,unixname));
|
DEBUG(3,("Mapped user %s to %s\n",user,unixname));
|
||||||
mapped_user = True;
|
mapped_user = True;
|
||||||
fstrcpy(last_from,user);
|
fstrcpy(last_from,user);
|
||||||
sscanf(unixname,"%s",user);
|
sscanf(unixname,"%s",user);
|
||||||
fstrcpy(last_to,user);
|
fstrcpy(last_to,user);
|
||||||
if(return_if_mapped) {
|
if(return_if_mapped) {
|
||||||
lp_list_free (&dosuserlist);
|
lp_list_free (&dosuserlist);
|
||||||
x_fclose(f);
|
x_fclose(f);
|
||||||
return True;
|
return True;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
lp_list_free (&dosuserlist);
|
lp_list_free (&dosuserlist);
|
||||||
}
|
}
|
||||||
|
|
||||||
x_fclose(f);
|
x_fclose(f);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Setup the last_from and last_to as an optimization so
|
* Setup the last_from and last_to as an optimization so
|
||||||
* that we don't scan the file again for the same user.
|
* that we don't scan the file again for the same user.
|
||||||
*/
|
*/
|
||||||
fstrcpy(last_from,user);
|
fstrcpy(last_from,user);
|
||||||
fstrcpy(last_to,user);
|
fstrcpy(last_to,user);
|
||||||
|
|
||||||
return mapped_user;
|
return mapped_user;
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
@ -160,30 +161,30 @@ BOOL map_username(char *user)
|
|||||||
|
|
||||||
static struct passwd *_Get_Pwnam(const char *s)
|
static struct passwd *_Get_Pwnam(const char *s)
|
||||||
{
|
{
|
||||||
struct passwd *ret;
|
struct passwd *ret;
|
||||||
|
|
||||||
ret = sys_getpwnam(s);
|
ret = sys_getpwnam(s);
|
||||||
if (ret) {
|
if (ret) {
|
||||||
#ifdef HAVE_GETPWANAM
|
#ifdef HAVE_GETPWANAM
|
||||||
struct passwd_adjunct *pwret;
|
struct passwd_adjunct *pwret;
|
||||||
pwret = getpwanam(s);
|
pwret = getpwanam(s);
|
||||||
if (pwret && pwret->pwa_passwd) {
|
if (pwret && pwret->pwa_passwd)
|
||||||
pstrcpy(ret->pw_passwd,pwret->pwa_passwd);
|
pstrcpy(ret->pw_passwd,pwret->pwa_passwd);
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
return(ret);
|
return(ret);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/****************************************************************************
|
||||||
* A wrapper for getpwnam(). The following variations are tried:
|
* A wrapper for getpwnam(). The following variations are tried:
|
||||||
* - as transmitted
|
* - as transmitted
|
||||||
* - in all lower case if this differs from transmitted
|
* - in all lower case if this differs from transmitted
|
||||||
* - in all upper case if this differs from transmitted
|
* - in all upper case if this differs from transmitted
|
||||||
* - using lp_usernamelevel() for permutations.
|
* - using lp_usernamelevel() for permutations.
|
||||||
*/
|
****************************************************************************/
|
||||||
|
|
||||||
struct passwd *Get_Pwnam_internals(const char *user, char *user2)
|
struct passwd *Get_Pwnam_internals(const char *user, char *user2)
|
||||||
{
|
{
|
||||||
struct passwd *ret = NULL;
|
struct passwd *ret = NULL;
|
||||||
@ -275,24 +276,24 @@ struct passwd *Get_Pwnam(const char *user)
|
|||||||
static BOOL user_in_netgroup_list(const char *user, const char *ngname)
|
static BOOL user_in_netgroup_list(const char *user, const char *ngname)
|
||||||
{
|
{
|
||||||
#ifdef HAVE_NETGROUP
|
#ifdef HAVE_NETGROUP
|
||||||
static char *mydomain = NULL;
|
static char *mydomain = NULL;
|
||||||
if (mydomain == NULL)
|
if (mydomain == NULL)
|
||||||
yp_get_default_domain(&mydomain);
|
yp_get_default_domain(&mydomain);
|
||||||
|
|
||||||
if(mydomain == NULL) {
|
if(mydomain == NULL) {
|
||||||
DEBUG(5,("Unable to get default yp domain\n"));
|
DEBUG(5,("Unable to get default yp domain\n"));
|
||||||
} else {
|
return False;
|
||||||
DEBUG(5,("looking for user %s of domain %s in netgroup %s\n",
|
}
|
||||||
user, mydomain, ngname));
|
|
||||||
DEBUG(5,("innetgr is %s\n",
|
|
||||||
innetgr(ngname, NULL, user, mydomain)
|
|
||||||
? "TRUE" : "FALSE"));
|
|
||||||
|
|
||||||
if (innetgr(ngname, NULL, user, mydomain))
|
DEBUG(5,("looking for user %s of domain %s in netgroup %s\n",
|
||||||
return (True);
|
user, mydomain, ngname));
|
||||||
}
|
DEBUG(5,("innetgr is %s\n", innetgr(ngname, NULL, user, mydomain)
|
||||||
|
? "TRUE" : "FALSE"));
|
||||||
|
|
||||||
|
if (innetgr(ngname, NULL, user, mydomain))
|
||||||
|
return (True);
|
||||||
#endif /* HAVE_NETGROUP */
|
#endif /* HAVE_NETGROUP */
|
||||||
return False;
|
return False;
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
@ -489,7 +490,7 @@ BOOL user_in_list(const char *user,char **list)
|
|||||||
if(user_in_netgroup_list(user, *list +1))
|
if(user_in_netgroup_list(user, *list +1))
|
||||||
return True;
|
return True;
|
||||||
}
|
}
|
||||||
} else if (strchr(*list,*lp_winbind_separator()) != NULL) {
|
} else if (!name_is_local(*list)) {
|
||||||
/*
|
/*
|
||||||
* If user name did not match and token is not
|
* If user name did not match and token is not
|
||||||
* a unix group and the token has a winbind separator in the
|
* a unix group and the token has a winbind separator in the
|
||||||
@ -528,28 +529,28 @@ BOOL user_in_list(const char *user,char **list)
|
|||||||
|
|
||||||
static struct passwd *uname_string_combinations2(char *s,int offset,struct passwd *(*fn)(const char *),int N)
|
static struct passwd *uname_string_combinations2(char *s,int offset,struct passwd *(*fn)(const char *),int N)
|
||||||
{
|
{
|
||||||
ssize_t len = (ssize_t)strlen(s);
|
ssize_t len = (ssize_t)strlen(s);
|
||||||
int i;
|
int i;
|
||||||
struct passwd *ret;
|
struct passwd *ret;
|
||||||
|
|
||||||
#ifdef PASSWORD_LENGTH
|
#ifdef PASSWORD_LENGTH
|
||||||
len = MIN(len,PASSWORD_LENGTH);
|
len = MIN(len,PASSWORD_LENGTH);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (N <= 0 || offset >= len)
|
if (N <= 0 || offset >= len)
|
||||||
return(fn(s));
|
return(fn(s));
|
||||||
|
|
||||||
for (i=offset;i<(len-(N-1));i++) {
|
for (i=offset;i<(len-(N-1));i++) {
|
||||||
char c = s[i];
|
char c = s[i];
|
||||||
if (!islower(c))
|
if (!islower(c))
|
||||||
continue;
|
continue;
|
||||||
s[i] = toupper(c);
|
s[i] = toupper(c);
|
||||||
ret = uname_string_combinations2(s,i+1,fn,N-1);
|
ret = uname_string_combinations2(s,i+1,fn,N-1);
|
||||||
if(ret)
|
if(ret)
|
||||||
return(ret);
|
return(ret);
|
||||||
s[i] = c;
|
s[i] = c;
|
||||||
}
|
}
|
||||||
return(NULL);
|
return(NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
@ -562,22 +563,22 @@ static struct passwd *uname_string_combinations2(char *s,int offset,struct passw
|
|||||||
|
|
||||||
static struct passwd * uname_string_combinations(char *s,struct passwd * (*fn)(const char *),int N)
|
static struct passwd * uname_string_combinations(char *s,struct passwd * (*fn)(const char *),int N)
|
||||||
{
|
{
|
||||||
int n;
|
int n;
|
||||||
struct passwd *ret;
|
struct passwd *ret;
|
||||||
|
|
||||||
for (n=1;n<=N;n++) {
|
for (n=1;n<=N;n++) {
|
||||||
ret = uname_string_combinations2(s,0,fn,n);
|
ret = uname_string_combinations2(s,0,fn,n);
|
||||||
if(ret)
|
if(ret)
|
||||||
return(ret);
|
return(ret);
|
||||||
}
|
}
|
||||||
return(NULL);
|
return(NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
these wrappers allow appliance mode to work. In appliance mode the username
|
These wrappers allow appliance mode to work. In appliance mode the username
|
||||||
takes the form DOMAIN/user
|
takes the form DOMAIN/user.
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
struct passwd *smb_getpwnam(char *user, BOOL allow_change)
|
struct passwd *smb_getpwnam(char *user, BOOL allow_change)
|
||||||
{
|
{
|
||||||
struct passwd *pw;
|
struct passwd *pw;
|
||||||
@ -585,26 +586,27 @@ struct passwd *smb_getpwnam(char *user, BOOL allow_change)
|
|||||||
char *sep;
|
char *sep;
|
||||||
extern pstring global_myname;
|
extern pstring global_myname;
|
||||||
|
|
||||||
if (allow_change) {
|
if (allow_change)
|
||||||
pw = Get_Pwnam_Modify(user);
|
pw = Get_Pwnam_Modify(user);
|
||||||
} else {
|
else
|
||||||
pw = Get_Pwnam(user);
|
pw = Get_Pwnam(user);
|
||||||
}
|
|
||||||
if (pw) return pw;
|
|
||||||
|
|
||||||
/* if it is a domain qualified name and it isn't in our password
|
if (pw)
|
||||||
database but the domain portion matches our local machine name then
|
return pw;
|
||||||
lookup just the username portion locally */
|
|
||||||
|
/*
|
||||||
|
* If it is a domain qualified name and it isn't in our password
|
||||||
|
* database but the domain portion matches our local machine name then
|
||||||
|
* lookup just the username portion locally.
|
||||||
|
*/
|
||||||
|
|
||||||
sep = lp_winbind_separator();
|
sep = lp_winbind_separator();
|
||||||
if (!sep || !*sep) sep = "\\";
|
|
||||||
p = strchr_m(user,*sep);
|
p = strchr_m(user,*sep);
|
||||||
if (p &&
|
if (p && strncasecmp(global_myname, user, strlen(global_myname))==0) {
|
||||||
strncasecmp(global_myname, user, strlen(global_myname))==0) {
|
if (allow_change)
|
||||||
if (allow_change) {
|
|
||||||
pw = Get_Pwnam_Modify(p+1);
|
pw = Get_Pwnam_Modify(p+1);
|
||||||
} else {
|
else
|
||||||
pw = Get_Pwnam(p+1);
|
pw = Get_Pwnam(p+1);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
@ -436,6 +436,16 @@ void add_supplementary_nt_login_groups(int *n_groups, gid_t **pp_groups, NT_USER
|
|||||||
*pptok = new_tok;
|
*pptok = new_tok;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*****************************************************************
|
||||||
|
Check if a user or group name is local (this is a *local* name for
|
||||||
|
*local* people, there's nothing for you here...).
|
||||||
|
*****************************************************************/
|
||||||
|
|
||||||
|
BOOL name_is_local(const char *name)
|
||||||
|
{
|
||||||
|
return !strchr_m(name, *lp_winbind_separator());
|
||||||
|
}
|
||||||
|
|
||||||
/*****************************************************************
|
/*****************************************************************
|
||||||
*THE CANONICAL* convert name to SID function.
|
*THE CANONICAL* convert name to SID function.
|
||||||
Tries winbind first - then uses local lookup.
|
Tries winbind first - then uses local lookup.
|
||||||
|
Reference in New Issue
Block a user