Question

I have found a piece of code on the Internet that seemed to be a good example - http://www.freebsd.org/doc/en/articles/pam/article.html#pam-sample-appl

Unfortunatelly it does not properly deal with accounts which require change of a password on the first login. When I su - user (from non-root account,) I am properly asked for a password, and then for a change of a password. When I run my program, I am asked for the password, but alas, I have no password change requested, and inside of the code I have no indication that there would be even such need. Where is the problem?

PAM debug shows me only this:

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

Output from the program shown below is like that:

-bash-3.2$ ./pam tg
Password:
pam_authenticate = 7
pam_acct_mgmt = 0
Sorry - pam_err = 17

Here is part of a little bit modified code:

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;

Program above uses conversation function copied from here: http://www.freebsd.org/doc/en/articles/pam/article.html#pam-sample-conv

I have also used misc_conv declared in security/pam_misc.h, and available in -lpam_misc, but I got the same result - no request to change password or no indication that such would be needed.

Any idea how could I tackle it? If I remove conversation function I get the same errors, except no prompt to enter password.

Was it helpful?

Solution

I had a long day reading tens of pages, and doing tons of experiments. I hope this investigation will help someone else than me, too.

The problem I had was that I was running PAM application as non-superuser, and my program had usual permission attributes.

There were two changes I had to have done in order to go through the password change. Both changes were okay:

  • I had to become a root OR...
  • I had to login as root, and then run chmod +s pam

From this moment I was able to request expired password change:

-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:

One additional thing that I had to change in case I was calling my program as root is replacing "su" to "system-auth", as root can su without password.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top