attempting to fix "domain user map" up, but it's a bit complicated.
authorLuke Leighton <lkcl@samba.org>
Mon, 30 Nov 1998 22:42:13 +0000 (22:42 +0000)
committerLuke Leighton <lkcl@samba.org>
Mon, 30 Nov 1998 22:42:13 +0000 (22:42 +0000)
i may simply go for a response in the NetSamLogon returning the
unix username, forcing the NT user to appear to be a unix user,
however even that is fraught with implications.

might just have to go the whole hog and do this tuple thing,
"unix_name + nt_name" always associated together...

issue with api_net_sam_logon, getsam21pwent() being called twice,
the second time overwriting static buffer data (argh) so had to
make a copy.

noticed a nested "become_root()"/"unbecome_root()" which will have
to be tracked down...

source/lib/domain_namemap.c
source/lib/sids.c
source/lib/util_pwdb.c
source/passdb/sampassdb.c
source/rpc_server/srv_netlog.c
source/smbd/reply.c

index cc96a014c461116ca19cb47e54f66d30ab989e01..09908be5fee82140b89b9bcdf92e00a9e5115fd1 100644 (file)
@@ -273,6 +273,9 @@ static void delete_map_list(ubi_slList *map_list)
 ***************************************************************************/
 static BOOL make_mydomain_sid(DOM_NAME_MAP *grp, DOM_MAP_TYPE type)
 {
+       int ret = False;
+       fstring sid_str;
+
        if (!map_domain_name_to_sid(&grp->sid, &(grp->nt_domain)))
        {
                DEBUG(0,("make_mydomain_sid: unknown domain %s\n",
@@ -294,7 +297,7 @@ static BOOL make_mydomain_sid(DOM_NAME_MAP *grp, DOM_MAP_TYPE type)
                                  grp->unix_name, grp->nt_name));
                        return False;
                }
-               return True;
+               ret = True;
        }
        else if (lookup_wk_user_name(grp->nt_name, grp->nt_domain, &grp->sid, &grp->type) == 0x0)
        {
@@ -304,7 +307,7 @@ static BOOL make_mydomain_sid(DOM_NAME_MAP *grp, DOM_MAP_TYPE type)
                                  grp->nt_domain, grp->nt_name));
                        return False;
                }
-               return True;
+               ret = True;
        }
        else if (lookup_wk_group_name(grp->nt_name, grp->nt_domain, &grp->sid, &grp->type) == 0x0)
        {
@@ -314,12 +317,10 @@ static BOOL make_mydomain_sid(DOM_NAME_MAP *grp, DOM_MAP_TYPE type)
                                  grp->nt_domain, grp->nt_name));
                        return False;
                }
-               return True;
+               ret = True;
        }
        else
        {
-               BOOL ret;
-               fstring sid_str;
                switch (type)
                {
                        case DOM_MAP_USER:
@@ -340,45 +341,57 @@ static BOOL make_mydomain_sid(DOM_NAME_MAP *grp, DOM_MAP_TYPE type)
                }
 
                ret = pwdb_unixid_to_sam_sid(grp->unix_id, grp->type, &grp->sid);
-               sid_to_string(sid_str, &grp->sid);
-               DEBUG(10,("nt name %s gid %d mapped to %s\n",
-                          grp->nt_name, grp->unix_id, sid_str));
-               return ret;
        }
 
-       return False;
+       sid_to_string(sid_str, &grp->sid);
+       DEBUG(10,("nt name %s\\%s gid %d mapped to %s\n",
+                  grp->nt_domain, grp->nt_name, grp->unix_id, sid_str));
+       return ret;
 }
 
 /**************************************************************************
  makes a group sid out of an nt domain, nt group name or a unix group name.
 ***************************************************************************/
-static BOOL unix_name_to_group_info(DOM_NAME_MAP *grp, DOM_MAP_TYPE type)
+static BOOL unix_name_to_nt_name_info(DOM_NAME_MAP *map, DOM_MAP_TYPE type)
 {
-       struct group *gptr = NULL;
-
        /*
         * Attempt to get the unix gid_t for this name.
         */
 
-       DEBUG(5,("unix_name_to_group_info: unix_name:%s\n", grp->unix_name));
+       DEBUG(5,("unix_name_to_nt_name_info: unix_name:%s\n", map->unix_name));
 
-       gptr = (struct group *)getgrnam(grp->unix_name);
-       if (gptr == NULL)
+       if (type == DOM_MAP_USER)
        {
-               DEBUG(0,("unix_name_to_group_info: getgrnam for group %s\
-failed. Error was %s.\n", grp->unix_name, strerror(errno) ));
-               return False;
+               struct passwd *pwptr = Get_Pwnam(map->unix_name, False);
+               if (pwptr == NULL)
+               {
+                       DEBUG(0,("unix_name_to_nt_name_info: Get_Pwnam for user %s\
+failed. Error was %s.\n", map->unix_name, strerror(errno) ));
+                       return False;
+               }
+
+               map->unix_id = (uint32)pwptr->pw_uid;
        }
+       else
+       {
+               struct group *gptr = getgrnam(map->unix_name);
+               if (gptr == NULL)
+               {
+                       DEBUG(0,("unix_name_to_nt_name_info: getgrnam for group %s\
+failed. Error was %s.\n", map->unix_name, strerror(errno) ));
+                       return False;
+               }
 
-       grp->unix_id = (uint32)gptr->gr_gid;
+               map->unix_id = (uint32)gptr->gr_gid;
+       }
 
-       DEBUG(5,("unix_name_to_group_info: unix gid:%d\n", grp->unix_id));
+       DEBUG(5,("unix_name_to_nt_name_info: unix gid:%d\n", map->unix_id));
 
        /*
         * Now map the name to an NT SID+RID.
         */
 
-       if (grp->nt_domain != NULL && !strequal(grp->nt_domain, global_sam_name))
+       if (map->nt_domain != NULL && !strequal(map->nt_domain, global_sam_name))
        {
                /* Must add client-call lookup code here, to 
                 * resolve remote domain's sid and the group's rid,
@@ -394,15 +407,15 @@ failed. Error was %s.\n", grp->unix_name, strerror(errno) ));
                 * RIDs in a foriegn domain.
                 */
 
-               if (!map_domain_name_to_sid(&grp->sid, &(grp->nt_domain)))
+               if (!map_domain_name_to_sid(&map->sid, &(map->nt_domain)))
                {
-                       DEBUG(0,("unix_name_to_group_info: no known sid for %s\n",
-                                 grp->nt_domain));
+                       DEBUG(0,("unix_name_to_nt_name_info: no known sid for %s\n",
+                                 map->nt_domain));
                        return False;
                }
        }
 
-       return make_mydomain_sid(grp, type);
+       return make_mydomain_sid(map, type);
 }
 
 static BOOL make_name_entry(name_map_entry **new_ep,
@@ -440,7 +453,7 @@ static BOOL make_name_entry(name_map_entry **new_ep,
         * look up the group names, make the Group-SID and unix gid
         */
  
-       if (!unix_name_to_group_info(&(*new_ep)->grp, type))
+       if (!unix_name_to_nt_name_info(&(*new_ep)->grp, type))
        {
                delete_name_entry((*new_ep));
                return False;
@@ -559,7 +572,7 @@ static ubi_slList *load_name_map(DOM_MAP_TYPE type)
                pstring unixname;
                pstring nt_name;
                fstring nt_domain;
-               fstring nt_group;
+               fstring ntname;
                char *p;
 
                DEBUG(10,("Read line |%s|\n", s));
@@ -589,21 +602,24 @@ static ubi_slList *load_name_map(DOM_MAP_TYPE type)
                if (p == NULL)
                {
                        memset(nt_domain, 0, sizeof(nt_domain));
-                       fstrcpy(nt_group, nt_name);
+                       fstrcpy(ntname, nt_name);
                }
                else
                {
                        *p = 0;
                        p++;
                        fstrcpy(nt_domain, nt_name);
-                       fstrcpy(nt_group , p);
+                       fstrcpy(ntname , p);
                }
 
-               if (make_name_entry(&new_ep, nt_domain, nt_group, unixname, type))
+               if (make_name_entry(&new_ep, nt_domain, ntname, unixname, type))
                {
                        ubi_slAddTail(map_list, (ubi_slNode *)new_ep);
                        DEBUG(5,("unixname = %s, ntname = %s\\%s type = %d\n",
-                                 unixname, nt_domain, nt_group, new_ep->grp.type));
+                                 new_ep->grp.unix_name,
+                                 new_ep->grp.nt_domain,
+                                 new_ep->grp.nt_name,
+                                 new_ep->grp.type));
                }
        }
 
@@ -647,7 +663,7 @@ static BOOL map_unixname(DOM_MAP_TYPE type,
                if (strequal(gmep->grp.unix_name, unixname))
                {
                        copy_grp_map_entry(grp_info, &gmep->grp);
-                       DEBUG(7,("map_unixname: Mapping unix group %s to nt group %s.\n",
+                       DEBUG(7,("map_unixname: Mapping unix name %s to nt group %s.\n",
                               gmep->grp.unix_name, gmep->grp.nt_name ));
                        return True;
                }
@@ -680,7 +696,7 @@ static BOOL map_ntname(DOM_MAP_TYPE type, char *ntname, char *ntdomain,
                    strequal(gmep->grp.nt_domain, ntdomain))
                {
                        copy_grp_map_entry(grp_info, &gmep->grp);
-                       DEBUG(7,("map_ntname: Mapping unix group %s to nt group %s.\n",
+                       DEBUG(7,("map_ntname: Mapping unix name %s to nt name %s.\n",
                               gmep->grp.unix_name, gmep->grp.nt_name ));
                        return True;
                }
@@ -711,7 +727,7 @@ static BOOL map_sid(DOM_MAP_TYPE type,
                if (sid_equal(&gmep->grp.sid, psid))
                {
                        copy_grp_map_entry(grp_info, &gmep->grp);
-                       DEBUG(7,("map_sid: Mapping unix group %s to nt group %s.\n",
+                       DEBUG(7,("map_sid: Mapping unix name %s to nt name %s.\n",
                               gmep->grp.unix_name, gmep->grp.nt_name ));
                        return True;
                }
@@ -744,7 +760,7 @@ static BOOL map_unixid(DOM_MAP_TYPE type, uint32 unix_id, DOM_NAME_MAP *grp_info
                if (gmep->grp.unix_id == unix_id)
                {
                        copy_grp_map_entry(grp_info, &gmep->grp);
-                       DEBUG(7,("map_unixid: Mapping unix group %s to nt group %s type %d\n",
+                       DEBUG(7,("map_unixid: Mapping unix name %s to nt name %s type %d\n",
                               gmep->grp.unix_name, gmep->grp.nt_name, gmep->grp.type));
                        return True;
                }
index 854e9d578674c14a0bc6f6b59eae3287b37bafce..f5fed0f656adc82f36f65f64422a775d84dc0a19 100644 (file)
@@ -283,6 +283,13 @@ BOOL generate_sam_sid(char *domain_name)
        uchar raw_sid_data[12];
 
        pstrcpy(sid_file, lp_smb_passwd_file());
+
+       if (sid_file[0] == 0)
+       {
+               DEBUG(0,("cannot find smb passwd file\n"));
+               return False;
+       }
+
        p = strrchr(sid_file, '/');
        if (p != NULL)
        {
@@ -456,10 +463,10 @@ BOOL map_domain_name_to_sid(DOM_SID *sid, char **nt_domain)
 
        if ((*nt_domain)[0] == 0)
        {
-               DEBUG(5,("map_domain_name_to_sid: overriding blank name to %s\n",
-                         global_sam_name));
                free(*nt_domain);
                (*nt_domain) = strdup(global_sam_name);
+               DEBUG(5,("map_domain_name_to_sid: overriding blank name to %s\n",
+                         (*nt_domain)));
                sid_copy(sid, &global_sam_sid);
                return True;
        }
index 74d5ff6794c17b12cd810c85c92d196d8a44ea6b..588070f7b8701b29c2dae52f1248566543e654c9 100644 (file)
@@ -141,7 +141,6 @@ uint32 lookup_wk_user_name(const char *user_name, const char *domain,
 
        if (usr_name != NULL)
        {
-               sid_copy(sid, &global_sid_S_1_5_20);
                sid_append_rid(sid, domain_user_rids[i].rid);
                return 0;
        }
index 95055ed29837126b9d07204187ec960a79fcc51b..bcd2764abcf1961f7fe8a19a90656e8243a2cd91 100644 (file)
@@ -126,12 +126,15 @@ struct sam_passwd *getsam21pwent(void *vp)
  does not have search facilities.
 *************************************************************************/
 
-struct sam_passwd *iterate_getsam21pwntnam(const char *name)
+struct sam_passwd *iterate_getsam21pwntnam(const char *ntname)
 {
+       fstring nt_name;
        struct sam_passwd *pwd = NULL;
        void *fp = NULL;
 
-       DEBUG(10, ("search by name: %s\n", name));
+       DEBUG(10, ("search by name: %s\n", ntname));
+
+       fstrcpy(nt_name, ntname);
 
        /* Open the smb password database - not for update. */
        fp = startsmbpwent(False);
@@ -142,14 +145,14 @@ struct sam_passwd *iterate_getsam21pwntnam(const char *name)
                return NULL;
        }
 
-       while ((pwd = getsam21pwent(fp)) != NULL && !strequal(pwd->nt_name, name))
+       while ((pwd = getsam21pwent(fp)) != NULL && !strequal(pwd->nt_name, nt_name))
        {
                DEBUG(10, ("iterate: %s 0x%x\n", pwd->nt_name, pwd->user_rid));
        }
 
        if (pwd != NULL)
        {
-               DEBUG(10, ("found by name: %s\n", name));
+               DEBUG(10, ("found by name: %s\n", nt_name));
        }
 
        endsmbpwent(fp);
@@ -436,6 +439,9 @@ struct sam_passwd *pwdb_sam_map_names(struct sam_passwd *sam)
        if (sam->unix_uid  == (uid_t)-1 ) sam->unix_uid  = (uid_t)gmep.unix_id;
        if (sam->user_rid  == 0xffffffff) sid_split_rid(&gmep.sid, &sam->user_rid);
 
+       DEBUG(10,("pwdb_sam_map_name: found unix user %s nt %s uid %d rid 0x%x\n",
+                  sam->unix_name, sam->nt_name, sam->unix_uid, sam->user_rid));
+
        /*
         * group details
         */
@@ -511,5 +517,8 @@ you will get this warning only once (for all trust accounts)\n", unix_name));
        if (sam->unix_gid  == (gid_t)-1 ) sam->unix_gid  = (gid_t)gmep.unix_id;
        if (sam->group_rid == 0xffffffff) sid_split_rid(&gmep.sid, &sam->group_rid);
 
+       DEBUG(10,("pwdb_sam_map_name: found gid %d and group rid 0x%x for unix user %s\n",
+                  sam->unix_gid, sam->group_rid, sam->unix_name));
+
        return sam;
 }
index 4f49735ca020facc666980d1541424220bbb5ecf..bb8bc59bc5436c2175e264fc97f79d48ef2dd215 100644 (file)
@@ -599,8 +599,26 @@ static void api_net_sam_logon( uint16 vuid,
        DOM_CRED srv_cred;
        struct sam_passwd *sam_pass = NULL;
        UNISTR2 *uni_samlogon_user = NULL;
+       UNISTR2 *uni_domain = NULL;
        fstring nt_username;
 
+       NTTIME logon_time           ;
+       NTTIME logoff_time          ;
+       NTTIME kickoff_time         ;
+       NTTIME pass_last_set_time   ;
+       NTTIME pass_can_change_time ;
+       NTTIME pass_must_change_time;
+
+       fstring nt_name     ;
+       fstring full_name   ;
+       fstring logon_script;
+       fstring profile_path;
+       fstring home_dir    ;
+       fstring dir_drive   ;
+
+       uint32 user_rid ;
+       uint32 group_rid;
+
        user_struct *vuser = NULL;
 
        if ((vuser = get_valid_user_struct(vuid)) == NULL)
@@ -630,6 +648,7 @@ static void api_net_sam_logon( uint16 vuid,
                        case INTERACTIVE_LOGON_TYPE:
                        {
                                uni_samlogon_user = &(q_l.sam_id.ctr->auth.id1.uni_user_name);
+                               uni_domain        = &(q_l.sam_id.ctr->auth.id1.uni_domain_name);
 
                                DEBUG(3,("SAM Logon (Interactive). Domain:[%s].  ", global_sam_name));
                                break;
@@ -637,6 +656,7 @@ static void api_net_sam_logon( uint16 vuid,
                        case NET_LOGON_TYPE:
                        {
                                uni_samlogon_user = &(q_l.sam_id.ctr->auth.id2.uni_user_name);
+                               uni_domain        = &(q_l.sam_id.ctr->auth.id2.uni_domain_name);
 
                                DEBUG(3,("SAM Logon (Network). Domain:[%s].  ", global_sam_name));
                                break;
@@ -654,9 +674,12 @@ static void api_net_sam_logon( uint16 vuid,
 
        if (status == 0)
        {
-               pstrcpy(nt_username, unistrn2(uni_samlogon_user->buffer,
-                                               uni_samlogon_user->uni_str_len));
-
+               fstrcpy(nt_username, unistr2_to_str(uni_samlogon_user));
+#if 0
+               slprintf(nt_username, sizeof(nt_username), "%s\\%s",
+                        unistr2_to_str(uni_domain),
+                        unistr2_to_str(uni_samlogon_user));
+#endif
                DEBUG(3,("User:[%s]\n", nt_username));
 
                become_root(True);
@@ -674,6 +697,26 @@ static void api_net_sam_logon( uint16 vuid,
                }
        }
 
+       if (status == 0x0)
+       {
+               logon_time            = sam_pass->logon_time;
+               logoff_time           = sam_pass->logoff_time;
+               kickoff_time          = sam_pass->kickoff_time;
+               pass_last_set_time    = sam_pass->pass_last_set_time;
+               pass_can_change_time  = sam_pass->pass_can_change_time;
+               pass_must_change_time = sam_pass->pass_must_change_time;
+
+               fstrcpy(nt_name     , sam_pass->nt_name);
+               fstrcpy(full_name   , sam_pass->full_name);
+               fstrcpy(logon_script, sam_pass->logon_script);
+               fstrcpy(profile_path, sam_pass->profile_path);
+               fstrcpy(home_dir    , sam_pass->home_dir);
+               fstrcpy(dir_drive   , sam_pass->dir_drive);
+
+               user_rid  = sam_pass->user_rid;
+               group_rid = sam_pass->group_rid;
+       }
+
        /* validate password - if required */
 
        if (status == 0 && !(IS_BITS_SET_ALL(sam_pass->acct_ctrl, ACB_PWNOTREQ)))
@@ -705,7 +748,7 @@ static void api_net_sam_logon( uint16 vuid,
        if (status == 0)
        {
                int num_gids = 0;
-               DOMAIN_GRP *grp_mem;
+               DOMAIN_GRP *grp_mem = NULL;
 
                /* set up pointer indicating user/password failed to be found */
                usr_info.ptr_user_info = 0;
@@ -721,25 +764,25 @@ static void api_net_sam_logon( uint16 vuid,
                        num_gids = make_dom_gids(grp_mem, num_gids, &gids);
 
                        make_net_user_info3(&usr_info,
-                               &sam_pass->logon_time,
-                               &sam_pass->logoff_time,
-                               &sam_pass->kickoff_time,
-                               &sam_pass->pass_last_set_time,
-                               &sam_pass->pass_can_change_time,
-                               &sam_pass->pass_must_change_time,
-
-                               sam_pass->nt_name         , /* user_name */
-                               sam_pass->full_name       , /* full_name */
-                               sam_pass->logon_script    , /* logon_script */
-                               sam_pass->profile_path    , /* profile_path */
-                               sam_pass->home_dir        , /* home_dir */
-                               sam_pass->dir_drive       , /* dir_drive */
+                               &logon_time,
+                               &logoff_time,
+                               &kickoff_time,
+                               &pass_last_set_time,
+                               &pass_can_change_time,
+                               &pass_must_change_time,
+
+                               nt_name         , /* user_name */
+                               full_name       , /* full_name */
+                               logon_script    , /* logon_script */
+                               profile_path    , /* profile_path */
+                               home_dir        , /* home_dir */
+                               dir_drive       , /* dir_drive */
 
                                0, /* logon_count */
                                0, /* bad_pw_count */
 
-                               sam_pass->user_rid   , /* RID user_id */
-                               sam_pass->group_rid  , /* RID group_id */
+                               user_rid   , /* RID user_id */
+                               group_rid  , /* RID group_id */
                                num_gids,    /* uint32 num_groups */
                                gids    , /* DOM_GID *gids */
                                0x20    , /* uint32 user_flgs (?) */
index 1abb084124b030153bc06c08f5c378b1dd2b958d..505067c83e573c41ce7dd1f623eec136b1cc3d50 100644 (file)
@@ -60,6 +60,49 @@ static void overflow_attack(int len)
 }
 
 
+/****************************************************************************
+  does _both_ nt->unix and unix->unix username remappings.
+****************************************************************************/
+static BOOL map_nt_and_unix_username(const char *domain, char *user)
+{
+       DOM_NAME_MAP gmep;
+       fstring nt_username;
+
+       /*
+        * Pass the user through the NT -> unix user mapping
+        * function.
+        */
+   
+       memset(nt_username, 0, sizeof(nt_username));
+       if (domain != NULL)
+       {
+               slprintf(nt_username, sizeof(nt_username)-1, "%s\\%s",
+                        domain, user);
+       }
+       else
+       {
+               fstrcpy(nt_username, user);
+       }
+       if (!lookupsmbpwntnam(nt_username, &gmep))
+       {
+               return False;
+       }
+
+       fstrcpy(user, gmep.unix_name);
+
+       /*
+        * Pass the user through the unix -> unix user mapping
+        * function.
+        */
+
+       (void)map_username(user);
+
+       /*
+        * Do any UNIX username case mangling.
+        */
+       return Get_Pwnam( user, True) != NULL;
+}
+
 /****************************************************************************
   reply to an special message 
 ****************************************************************************/
@@ -220,17 +263,10 @@ int reply_tcon(connection_struct *conn,
 
        parse_connect(smb_buf(inbuf)+1,service,user,password,&pwlen,dev);
 
-       /*
-        * Pass the user through the NT -> unix user mapping
-        * function.
-        */
-   
-       (void)map_username(user);
-
-       /*
-        * Do any UNIX username case mangling.
-        */
-       (void)Get_Pwnam( user, True);
+       if (!map_nt_and_unix_username(global_myworkgroup, user))
+       {
+               return(connection_error(inbuf,outbuf,ERRbadpw));
+       }
 
        conn = make_connection(service,user,password,pwlen,dev,vuid,&ecode);
   
@@ -300,18 +336,11 @@ int reply_tcon_and_X(connection_struct *conn, char *inbuf,char *outbuf,int lengt
        StrnCpy(devicename,path + strlen(path) + 1,6);
        DEBUG(4,("Got device type %s\n",devicename));
 
-       /*
-        * Pass the user through the NT -> unix user mapping
-        * function.
-        */
-       
-       (void)map_username(user);
-       
-       /*
-        * Do any UNIX username case mangling.
-        */
-       (void)Get_Pwnam(user, True);
-       
+       if (!map_nt_and_unix_username(global_myworkgroup, user))
+       {
+               return(connection_error(inbuf,outbuf,ERRbadpw));
+       }
+
        conn = make_connection(service,user,password,passlen,devicename,vuid,&ecode);
        
        if (!conn)
@@ -642,17 +671,10 @@ int reply_sesssetup_and_X(connection_struct *conn, char *inbuf,char *outbuf,int
 
   pstrcpy( orig_user, user);
 
-  /*
-   * Pass the user through the NT -> unix user mapping
-   * function.
-   */
-   
-  (void)map_username(user);
-
-  /*
-   * Do any UNIX username case mangling.
-   */
-  (void)Get_Pwnam( user, True);
+       if (!map_nt_and_unix_username(domain, user))
+       {
+               return(ERROR(ERRSRV,ERRbadpw));
+       }
 
   add_session_user(user);