电脑技术学习

在FreeBSD中添加用户(2)

dn001

Dru;Lavigne
01/10/2001


在第一部分里,我们已经考查了用adduser工具建立用户账号。在这个部分,我们将集中于建立用户账号时所修改的文件。

当超级用户建立一个用户账号时,会在口令数据库里添加对应于该用户的项目。实际上,你的FreeBSD系统需要更新四个口令数据库文件。让我们在仔细查看它们的格式之前先介绍一下这些文件。第一个文件称为/etc/passwd,它是个任何人都能读的ASCII文本文件:

file;/etc/passwd
/etc/passwd:;ASCII;text

ls;-l;/etc/passwd
-rw-r--r--;;1;root;;wheel;;1054;Dec;30;13:00;/etc/passwd
该文件的权限必须保持这种形式,否则很多FreeBSD工具就不能工作了。但是,在一个任何人都能读取的文件中保存口令会有安全风险的;为此,通常对应于口令的那一部分都用*来存储表示。

第二个文件是影子口令文件/etc/master.passwd。该文件包含用户口令的加密散列。我们会在将来的文章中详细讨论加密和散列;而现在,把散列想象为FreeBSD用于检测用户口令是否合法的值。

让我们来看一下该文件的类型及属性:

file;/etc/master.passwd
/etc/master.passwd:;ASCII;text

ls;-l;/etc/master.passwd
-rw-------;;1;root;;wheel;;1226;Dec;30;13:00;/etc/master.passwd
影子口令文件仍然是ASCII明文文本,不过只有root可以读取了。

第三个和第四个口令文件是/etc/pwd.db和/etc/spwd.db。来看一下它们的文件类型:

file;/etc/*pwd.db/etc/pwd.db:;Berkeley;DB;Hash;file;(Version;2,;Little;
Endian,;Bucket;Size;4096,;Bucket;Shift;12,;Directory;Size;256,;Segment;Size;256,;
Segment;Shift;8,;Overflow;Point;3,;Last;Freed;2,;Max;Bucket;7,;High;Mask;0xf,;
Low;Mask;0x7,;Fill;Factor;32,;Number;of;Keys;56)/etc/spwd.db:;Berkeley;DB;
Hash;file;(Version;2,;Little;Endian,;Bucket;Size;4096,;Bucket;Shift;12,;
Directory;Size;256,;Segment;Size;256,;Segment;Shift;8,;Overflow;Point;3,;Last;
Freed;2,;Max;Bucket;7,;High;Mask;0xf,;Low;Mask;0x7,;Fill;Factor;32,;Number;of;
Keys;56)
哦,它们干脆就不是ASCII文本文件了,所以就不要试图用cat、more或文本编辑器来打开它们了。这两个文件包含了与上面ASCII文本文件相同的信息,而用数据库的形式就提高了性能。这里的/etc/pwd.db是与/etc/passwd等价的数据库,它不包含任何散列。/etc/spwd.db的s表示shadow,所以它就是与etc/master.passwd等价的数据库,也不包含散列。

现在我们已经熟悉了这四文件的名称,来看一下它们包含的信息类型。以超级用户身份把/etc/master.passwd发送到屏幕上,结果看起来应该象这样:

su:
Password

more;/etc/master.passwd

#;$FreeBSD:;src/etc/master.passwd,v;1.25;1999/09/13;17:09:07;peter;Exp;$
#
root:$1$hnH/w50a$tPdv5HZRsDP46FtsW8eXH/:0:0::0:0:Charlie;&:/root:/bin/csh
toor:*:0:0::0:0:Bourne-again;Superuser:/root:
daemon:*:1:1::0:0:Owner;of;many;system;processes:/root:/sbin/nologin
operator:*:2:5::0:0:System;&:/:/sbin/nologin
bin:*:3:7::0:0:Binaries;Commands;and;Source,,,:/:/sbin/nologin
tty:*:4:65533::0:0:Tty;Sandbox:/:/sbin/nologin
kmem:*:5:65533::0:0:KMem;Sandbox:/:/sbin/nologin
games:*:7:13::0:0:Games;pseudo-user:/usr/games:/sbin/nologin
news:*:8:8::0:0:News;Subsystem:/:/sbin/nologin
man:*:9:9::0:0:Mister;Man;Pages:/usr/share/man:/sbin/nologin
bind:*:53:53::0:0:Bind;Sandbox:/:/sbin/nologin
uucp:*:66:66::0:0:UUCP;pseudo-user:/var/spool/uucppublic:/usr/libexec/uucp/uucico
xten:*:67:67::0:0:X-10;daemon:/usr/local/xten:/sbin/nologin
pop:*:68:6::0:0:Post;Office;Owner:/nonexistent:/sbin/nologin
nobody:*:65534:65534::0:0:Unprivileged;user:/nonexistent:/sbin/nologin
genisis:$1$.3tvchjG$C6wtsUV9FcXF4wzBboisJ/:1001:0::0:0:User;&:/home/genisis:/bin/csh
dlavigne:pZV8Ju.2sEqsY:1000:1000::0:0:Dru;Lavigne:/home/dlavigne:/bin/tcsh
test::1002:1002::0:0:test:/home/test:/bin/tcsh
看起来是不是不太顺?当我们理解了它的格式以后就会容易多了。文件中每一行包含一个用户的记录,而每条记录由十个用冒号分隔的字段组成。这些字段是以下面的顺序排列的:

name:hash:uid:gid:class:change:expire:gecos:home_dir:shell
你会注意到我的FreeBSD系统有15个系统建立的系统账号;最后三个账号(genisis、dlavigne和test)是由超级用户建立的。

现在单独来看一下“dlavigne”这条记录:

dlavigne:pZV8Ju.2sEqsY:1000:1000::0:0:Dru;Lavigne:/home/dlavigne:/bin/tcsh
第一个字段(dlavigne)是该用户用于登录到系统时所用的用户名。

第二个字段(pZV8Ju.2sEqsY)是加密散列;dlavigne很幸运,这并不是她在登录时键入的口令,也无法知道从该文件中读出的她的实际口令是什么。但是,注意“test”用户的第二个字段。因为那里个空白,就说明该用户没有使用口令,只要读一个该文件就知道了。再注意很多系统账号的第二个字段都是一个星号(*),这说明普通用户无法用账号进行登录。

第三个字段(1000)是用户的UID(user;ID);这是FreeBSD用来区别不同用户的,所以它必须是唯一的。当我们用adduser工具,它提议从1000开始建立UID,所以我建立的所有用户都有大于1000的UID。注意用户“root”和“toor”的UID为0,这说明他们都是系统的超级用户。

第四个字段(1000)是用户的初始GID(group;ID)。缺省情况下,当你在FreeBSD中建立一个用户时,会建立一个同名的组。

第五个字段(空白)是用户的类别。类别用于决定环境设定、会话记账和资源限制。我们会在将来讨论使用类别。这个字段缺省是空的。

第六个字段(0)表示口令的期限。这个字段缺省是零,表示用户无须更新他的口令。

第七个字段(0)表示用户账号的期限。如果用户账号过期,该用户将无法再登录了。这个字段缺省是零,表示账号永不过期。

第八个字段(Dru;Lavigne)包含用户的“gecos”综合信息。这里可以包含用户的全名、办公地点、工作电话和家庭电话,中间只要用逗号分隔。术语“gecos”的来源很有趣。当Unix最初在Bell实验室开发时,主计算机运行的是General;Electric;Computer;Operating;System(gecos),使用该计算机的用户的地址信息都被存在口令文件的“gecos”字段中。

第九个字段(/home/dlavigne)是用户的主目录。它就是用户登录时所处的目录。

第十个字段(/bin/tcsh)是用户命令解释器shell的路径。

让我们快速地比较一下/etc/passwd和/etc/master.passwd文件。我不再需要超级用户身份来读这些文件了,所以我先退出超级用户账号:

exit
more;/etc/passwd

#;$FreeBSD:;src/etc/master.passwd,v;1.25;1999/09/13;17:09:07;peter;Exp;$
#
root:*:0:0:Charlie;&:/root:/bin/csh
toor:*:0:0:Bourne-again;Superuser:/root:
daemon:*:1:1:Owner;of;many;system;processes:/root:/sbin/nologin
operator:*:2:5:System;&:/:/sbin/nologin
bin:*:3:7:Binaries;Commands;and;Source,,,:/:/sbin/nologin
tty:*:4:65533:Tty;Sandbox:/:/sbin/nologin
kmem:*:5:65533:KMem;Sandbox:/:/sbin/nologin
games:*:7:13:Games;pseudo-user:/usr/games:/sbin/nologin
news:*:8:8:News;Subsystem:/:/sbin/nologin
man:*:9:9:Mister;Man;Pages:/usr/share/man:/sbin/nologin
bind:*:53:53:Bind;Sandbox:/:/sbin/nologin
uucp:*:66:66:UUCP;pseudo-user:/var/spool/uucppublic:/usr/libexec/uucp/uucico
xten:*:67:67:X-10;daemon:/usr/local/xten:/sbin/nologin
pop:*:68:6:Post;Office;Owner:/nonexistent:/sbin/nologin
nobody:*:65534:65534:Unprivileged;user:/nonexistent:/sbin/nologin
genisis:*:1001:0:User;&:/home/genisis:/bin/csh
dlavigne:*:1000:1000:Dru;Lavigne:/home/dlavigne:/bin/tcsh
test:*:1002:1002:test:/home/test:/bin/tcsh
注意到它与影子口令文件很相似,只是所有的口令字段都用星号替换了用户的散列。同时,空白的和值为0的字段在此文件中都被省略了。

你还可能注意到当我们用ls;-l命令以长格式列出这些口令文件时,只有root拥有这些文件的写权限。要注意有一点很重要,就是root不要用文本编辑器去直接打开这些文件进行编辑。当更改一个口令文件时,不能把对此文件的更改直接用在其它口令文件中。这应该是系统工具pwd_mkdb的工作。如果root需要更改一个口噙文件,他需要使用一个工具来把更改发送给pwd_mkdb。

用于此目的的工具之一就是vipw。命令vipw用环境变量EDITOR所定义的编辑器来打开整个口令文件,通常这个编辑器是vi,因此它会被称作“vipw”。如果出于某些原因而使你的编辑器不是vi,那你或许应该避免使用vipw工具或者把EDITOR改回vi。其它的编辑器会折行,这会摧毁象口令文件这样的系统文件,当然这是非常不好的。要使用这个工具,你应该熟练使用vi编辑器并了解十个字段所代表的含义和每个字段可接受的值。所以,只有超级用户才可以使用这个工具。

其它用于编辑口令文件的工具有chpass,它也称为chfn或chsh。任何用户都可以使用这些工具来更改口令文件中属于他们自己的值。我以用户“dlavigne”登录或运行chpass工具:

login:;dlavigne
Password:

chpass

#Changing;user;database;information;for;dlavigne.
Shell:;/bin/tcsh
Full;Name:;Dru;Lavigne
Office;Location:
Office;Phone:
Home;Phone:
Other;information:
~
/etc/pw.m32496:;unmodified:;line;1
注意到一个普通用户只限于更改他们自己的缺省shell和gecos综合信息字段。我加入了一个办公电话以查看发生什么情况。因为我在vi编辑器环境里,所以我用箭头键移到文件中适当的位置,按ESC键后再按一下a进入添加模式,然后键入电话号码123-4567。接着再按ESC,键入:wq保存更改并退出vi编辑器。然后屏幕上会显示如下信息:

chpass:;updating;the;database...
chpass:;done
接着如果我变成超级用户并寻找/etc/passwd文件中的相应项,会看到刚才的更改:

su:
Password:

more;/etc/passwd

dlavigne:*:1000:1000:Dru;Lavigne,,123-4567:/home/dlavigne:/bin/tcsh
注意在gecos综合字段中添加的两个逗号指出你正在读的值。它们总是这样的次序排列:

full_name,office_location,work_phone,home_phone
所以我知道123-4567是用户Dru;Lavigne的工作电话。

现在,我以超级用户身份运行chpass。如果我给该命令一个用户名作为参数的话,我可以编辑属于该用户的项。来看一下超级可以为用户“dlavigne”作些什么:

chpass;dlavigne

#Changing;user;database;information;for;dlavigne.
Login:;dlavigne
Password:;pZV8Ju.2sEqsY
Uid;[#]:;1000
Gid;[#;or;name]:;1000
Change;[month;day;year]:
Expire;[month;day;year]:
Class:
Home;directory:;/home/dlavigne
Shell:;/bin/tcsh
Full;Name:;Dru;Lavigne
Office;Location:
Office;Phone:;123-4567
Home;Phone:
Other;information:
~
/etc/pw.B32584:;unmodified:;line;1

你应该能看懂该用户的所有十个字段了吧。超级用户账号可以用chpass带上用户名作参数来更改任何用户的记录。如果超级用户只键入:

chpass
他就可以更改root账号的记录了。chpass工具带有一些开关可使超级用户用于更改一个用户记录的特定字段;请看man;1;chpass的细节。

在所有口令数据库文件中安全更改用户口令的工具是passwd。我以“test”用户登录然后为该用户建一个口令:

login:;test
注意到没有提示我输入口令,因为“test”当前只有一个空口令。我用passwd工具来更改一下:

passwd;
Changing;local;password;for;test.
New;password:
Retype;new;password:
passwd:;updating;the;database...
passwd:;done
通常,当用户更改他们的口令,系统会提示他们输入旧口令;这就避免了其他用户来更改口令了。让我们再次以“test”运行passwd工具:

passwd
Changing;local;password;for;test.
Old;password:
New;password:
Retype;new;password:
passwd:;updating;the;database...
passwd:;done
如果用户忘了他们的口令会如何?还没有彻底完蛋,因为超级用户可以为他们更改口令;当超级用户更改其它用户的口令时,系统就不会提示他输入该用户的旧口令了:

su:
Password:

passwd;test
Changing;local;password;for;test.
New;password:
Retype;new;password:
passwd:;updating;the;database...
passwd:;done
注意,超级用户要使用用户名作为passwd工具的一个参数;如果不带用户名,那更改的就是root账号的口令了。

我要介绍的最后一个更改口令文件的工具是rmuser。该工具用于删除用户账号和任何与该用户相关的东西;所以它只能由超级用户运行。让我们来删除“test”账号:

rmuser
Enter;login;name;for;user;to;remove:;test
Matching;password;entry:

test:$1$P6kMmPWG$rZiu/HfaIPVwJC6hdOImc/:1002:1002::0:0:test:/home/test:/bin/tcsh

Is;this;the;entry;you;wish;to;remove?;y
Remove;user's;home;directory;(/home/test)?;y
Killed;process(es);belonging;to;test.
Updating;password;file,;updating;databases,;done.
Updating;group;file:;(removing;group;test;--;personal;group;is;empty);done.
Removing;user's;home;directory;(/home/test):;done.
Removing;user's;incoming;mail;file;/var/mail/test:;done.
Removing;files;belonging;to;test;from;/tmp:;done.
Removing;files;belonging;to;test;from;/var/tmp:;done.
Removing;files;belonging;to;test;from;/var/tmp/vi.recover:;done.
看,这是个很有效的工具;它不仅从口令文件中删除用户信息,还从删除用户的主目录、邮件文件和临时目录中属于该用户的任何文件。你还应该注意到,在我删除test用户前,他的口令字段已经不是空的了,看来passwd工具已经成功更新了口令数据库。

标签: