我在互联网上找到了一段似乎很好的例子 - http://www.freebsd.org/doc/en/articles/pam/article.html#pam-sample-appl
不幸的是,它无法正确处理首次登录时需要更改密码的帐户。
当我su - user
(来自非root帐户)时,我被正确地要求输入密码,然后更改密码。
当我运行我的程序时,我被要求输入密码,但是,我没有要求更改密码,并且在代码内部我没有迹象表明甚至会有这样的需求。
问题在哪里?
PAM调试只显示了这一点:
Mar 25 11:27:33 S-78 pam: pam_unix(su:auth): authentication failure; logname=greg uid=502 euid=502 tty=/dev/pts/4 ruser=greg rhost=SIR-78 user=tg
以下所示程序的输出如下:
-bash-3.2$ ./pam tg
Password:
pam_authenticate = 7
pam_acct_mgmt = 0
Sorry - pam_err = 17
以下是一些修改过的代码的一部分:
pam_start("su", user, &pamc, &pamh);
/* set some items */
gethostname(hostname, sizeof(hostname));
if ((pam_err = pam_set_item(pamh, PAM_RHOST, hostname)) != PAM_SUCCESS)
goto pamerr;
user = getlogin();
if ((pam_err = pam_set_item(pamh, PAM_RUSER, user)) != PAM_SUCCESS)
goto pamerr;
tty = ttyname(STDERR_FILENO);
if ((pam_err = pam_set_item(pamh, PAM_TTY, tty)) != PAM_SUCCESS)
goto pamerr;
/* authenticate the applicant */
if ((pam_err = pam_authenticate(pamh, 0)) != PAM_SUCCESS)
{
printf( "pam_authenticate = %d\n", ( int )pam_err ) ; /* returns error 7 - PAM_AUTH_ERR */
pam_err = pam_acct_mgmt(pamh, 0) ;
printf( "pam_acct_mgmt = %d\n", ( int )pam_err ) ; /* returns no error! */
}
/* establish the requested credentials */
if ((pam_err = pam_setcred(pamh, PAM_ESTABLISH_CRED)) != PAM_SUCCESS) /* returns error 17 - PAM_CRED_ERR */
goto pamerr;
上面的程序使用从此处复制的对话功能:http://www.freebsd.org/doc/en/articles/pam/article.html#pam-sample-conv
我还使用misc_conv
中声明的security/pam_misc.h
,并在-lpam_misc
中可用,但我得到了相同的结果 - 没有更改密码的请求或没有迹象表明需要这样做。
任何想法我怎么能解决它? 如果我删除会话功能,我会得到相同的错误,除了没有提示输入密码。
答案 0 :(得分:1)
我有一整天阅读了数十页,并进行了大量的实验。我希望这项调查能帮助别人而不是我。
我遇到的问题是我以非超级用户身份运行PAM应用程序,而我的程序具有通常的权限属性。
为了完成密码更改,我必须完成两项更改。两个变化都没问题:
从此刻起,我就可以请求过期的密码更改:
-bash-3.2$ chage -d 0 tg
-bash-3.2$ ./pam tg
Password:
Authenticated ok
You are required to change your password immediately (root enforced)
PAM_NEW_AUTHTOK_REQD
Changing password for tg
(current) UNIX password:
New UNIX password:
Retype new UNIX password:
如果我以root身份调用我的程序,我必须更改的另一件事是将“su”替换为“system-auth”,因为root可以没有密码。