xref: /titanic_50/usr/src/lib/krb5/kadm5/chpass_util.c (revision 159d09a20817016f09b3ea28d1bdada4a336bb91)
17c478bd9Sstevel@tonic-gate /*
2*159d09a2SMark Phalan  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
37c478bd9Sstevel@tonic-gate  * Use is subject to license terms.
47c478bd9Sstevel@tonic-gate  */
57c478bd9Sstevel@tonic-gate 
67c478bd9Sstevel@tonic-gate 
77c478bd9Sstevel@tonic-gate /*
87c478bd9Sstevel@tonic-gate  * WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
97c478bd9Sstevel@tonic-gate  *
107c478bd9Sstevel@tonic-gate  *	Openvision retains the copyright to derivative works of
117c478bd9Sstevel@tonic-gate  *	this source code.  Do *NOT* create a derivative of this
127c478bd9Sstevel@tonic-gate  *	source code before consulting with your legal department.
137c478bd9Sstevel@tonic-gate  *	Do *NOT* integrate *ANY* of this source code into another
147c478bd9Sstevel@tonic-gate  *	product before consulting with your legal department.
157c478bd9Sstevel@tonic-gate  *
167c478bd9Sstevel@tonic-gate  *	For further information, read the top-level Openvision
177c478bd9Sstevel@tonic-gate  *	copyright which is contained in the top-level MIT Kerberos
187c478bd9Sstevel@tonic-gate  *	copyright.
197c478bd9Sstevel@tonic-gate  *
207c478bd9Sstevel@tonic-gate  * WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
217c478bd9Sstevel@tonic-gate  *
227c478bd9Sstevel@tonic-gate  */
237c478bd9Sstevel@tonic-gate 
247c478bd9Sstevel@tonic-gate 
257c478bd9Sstevel@tonic-gate /*
267c478bd9Sstevel@tonic-gate  * Copyright 1993 OpenVision Technologies, Inc., All Rights Reserved.
277c478bd9Sstevel@tonic-gate  */
287c478bd9Sstevel@tonic-gate 
297c478bd9Sstevel@tonic-gate 
307c478bd9Sstevel@tonic-gate #include <stdio.h>
3156a424ccSmp153739 #ifdef HAVE_MEMORY_H
327c478bd9Sstevel@tonic-gate #include <memory.h>
3356a424ccSmp153739 #endif
347c478bd9Sstevel@tonic-gate #include <time.h>
357c478bd9Sstevel@tonic-gate #include <locale.h>
367c478bd9Sstevel@tonic-gate 
377c478bd9Sstevel@tonic-gate #include <kadm5/admin.h>
387c478bd9Sstevel@tonic-gate #include "admin_internal.h"
397c478bd9Sstevel@tonic-gate 
407c478bd9Sstevel@tonic-gate #include <krb5.h>
41*159d09a2SMark Phalan #include <strings.h>
427c478bd9Sstevel@tonic-gate 
437c478bd9Sstevel@tonic-gate #define string_text error_message
447c478bd9Sstevel@tonic-gate 
457c478bd9Sstevel@tonic-gate const char *chpw_error_message(kadm5_ret_t code);
467c478bd9Sstevel@tonic-gate 
477c478bd9Sstevel@tonic-gate /*
487c478bd9Sstevel@tonic-gate  * Function: kadm5_chpass_principal_util
497c478bd9Sstevel@tonic-gate  *
5056a424ccSmp153739  * Purpose: Wrapper around chpass_principal. We can read new pw, change pw and return useful messages
517c478bd9Sstevel@tonic-gate  *
527c478bd9Sstevel@tonic-gate  * Arguments:
537c478bd9Sstevel@tonic-gate  *
547c478bd9Sstevel@tonic-gate  *      princ          (input) a krb5b_principal structure for the
557c478bd9Sstevel@tonic-gate  *                     principal whose password we should change.
567c478bd9Sstevel@tonic-gate  *
577c478bd9Sstevel@tonic-gate  *      new_password   (input) NULL or a null terminated string with the
587c478bd9Sstevel@tonic-gate  *                     the principal's desired new password.  If new_password
597c478bd9Sstevel@tonic-gate  *                     is NULL then this routine will read a new password.
607c478bd9Sstevel@tonic-gate  *
617c478bd9Sstevel@tonic-gate  *	pw_ret		(output) if non-NULL, points to a static buffer
627c478bd9Sstevel@tonic-gate  *			containing the new password (if password is prompted
637c478bd9Sstevel@tonic-gate  *			internally), or to the new_password argument (if
647c478bd9Sstevel@tonic-gate  *			that is non-NULL).  If the former, then the buffer
657c478bd9Sstevel@tonic-gate  *			is only valid until the next call to the function,
667c478bd9Sstevel@tonic-gate  *			and the caller should be sure to zero it when
677c478bd9Sstevel@tonic-gate  *			it is no longer needed.
687c478bd9Sstevel@tonic-gate  *
697c478bd9Sstevel@tonic-gate  *      msg_ret         (output) a useful message is copied here.
707c478bd9Sstevel@tonic-gate  *
717c478bd9Sstevel@tonic-gate  *      <return value>  exit status of 0 for success, else the com err code
727c478bd9Sstevel@tonic-gate  *                      for the last significant routine called.
737c478bd9Sstevel@tonic-gate  *
747c478bd9Sstevel@tonic-gate  * Requires:
757c478bd9Sstevel@tonic-gate  *
767c478bd9Sstevel@tonic-gate  *      A msg_ret should point to a buffer large enough for the messasge.
777c478bd9Sstevel@tonic-gate  *
787c478bd9Sstevel@tonic-gate  * Effects:
797c478bd9Sstevel@tonic-gate  *
807c478bd9Sstevel@tonic-gate  * Modifies:
817c478bd9Sstevel@tonic-gate  *
827c478bd9Sstevel@tonic-gate  *
837c478bd9Sstevel@tonic-gate  */
847c478bd9Sstevel@tonic-gate 
_kadm5_chpass_principal_util(void * server_handle,void * lhandle,krb5_principal princ,char * new_pw,char ** ret_pw,char * msg_ret,unsigned int msg_len)857c478bd9Sstevel@tonic-gate kadm5_ret_t _kadm5_chpass_principal_util(void *server_handle,
867c478bd9Sstevel@tonic-gate 					 void *lhandle,
877c478bd9Sstevel@tonic-gate 					 krb5_principal princ,
887c478bd9Sstevel@tonic-gate 					 char *new_pw,
897c478bd9Sstevel@tonic-gate 					 char **ret_pw,
907c478bd9Sstevel@tonic-gate 					 char *msg_ret,
9156a424ccSmp153739 					 unsigned int msg_len)
927c478bd9Sstevel@tonic-gate {
937c478bd9Sstevel@tonic-gate   int code, code2;
947c478bd9Sstevel@tonic-gate   unsigned int pwsize;
957c478bd9Sstevel@tonic-gate   static char buffer[255];
967c478bd9Sstevel@tonic-gate   char *new_password;
977c478bd9Sstevel@tonic-gate   kadm5_principal_ent_rec princ_ent;
987c478bd9Sstevel@tonic-gate   kadm5_policy_ent_rec policy_ent;
997c478bd9Sstevel@tonic-gate   krb5_chgpwd_prot passwd_protocol;
1007c478bd9Sstevel@tonic-gate 
1017c478bd9Sstevel@tonic-gate   _KADM5_CHECK_HANDLE(server_handle);
1027c478bd9Sstevel@tonic-gate 
1037c478bd9Sstevel@tonic-gate   if (ret_pw)
1047c478bd9Sstevel@tonic-gate     *ret_pw = NULL;
1057c478bd9Sstevel@tonic-gate 
1067c478bd9Sstevel@tonic-gate   if (new_pw != NULL) {
1077c478bd9Sstevel@tonic-gate     new_password = new_pw;
1087c478bd9Sstevel@tonic-gate   } else { /* read the password */
1097c478bd9Sstevel@tonic-gate     krb5_context context;
1107c478bd9Sstevel@tonic-gate 
111*159d09a2SMark Phalan     if ((code = (int) kadm5_init_krb5_context(&context)) == 0) {
1127c478bd9Sstevel@tonic-gate       pwsize = sizeof(buffer);
11356a424ccSmp153739       code = krb5_read_password(context, KADM5_PW_FIRST_PROMPT,
1147c478bd9Sstevel@tonic-gate 				KADM5_PW_SECOND_PROMPT,
1157c478bd9Sstevel@tonic-gate 				buffer, &pwsize);
1167c478bd9Sstevel@tonic-gate       krb5_free_context(context);
1177c478bd9Sstevel@tonic-gate     }
1187c478bd9Sstevel@tonic-gate 
1197c478bd9Sstevel@tonic-gate     if (code == 0)
1207c478bd9Sstevel@tonic-gate       new_password = buffer;
1217c478bd9Sstevel@tonic-gate     else {
1227c478bd9Sstevel@tonic-gate #ifdef ZEROPASSWD
1237c478bd9Sstevel@tonic-gate       memset(buffer, 0, sizeof(buffer));
1247c478bd9Sstevel@tonic-gate #endif
1257c478bd9Sstevel@tonic-gate       if (code == KRB5_LIBOS_BADPWDMATCH) {
126*159d09a2SMark Phalan 	(void) strncpy(msg_ret, string_text(CHPASS_UTIL_NEW_PASSWORD_MISMATCH),
1277c478bd9Sstevel@tonic-gate 		msg_len - 1);
1287c478bd9Sstevel@tonic-gate 	msg_ret[msg_len - 1] = '\0';
1297c478bd9Sstevel@tonic-gate 	return(code);
1307c478bd9Sstevel@tonic-gate       } else {
131*159d09a2SMark Phalan         (void) strncpy(msg_ret, error_message(code), msg_len - 1);
132*159d09a2SMark Phalan         (void) strncat(msg_ret, " ", msg_len - 1);
133*159d09a2SMark Phalan         (void) strncat(msg_ret, string_text(CHPASS_UTIL_WHILE_READING_PASSWORD),
1347c478bd9Sstevel@tonic-gate 		msg_len - 1);
135*159d09a2SMark Phalan         (void) strncat(msg_ret, string_text(CHPASS_UTIL_PASSWORD_NOT_CHANGED),
1367c478bd9Sstevel@tonic-gate 		msg_len - 1);
1377c478bd9Sstevel@tonic-gate 	msg_ret[msg_len - 1] = '\0';
1387c478bd9Sstevel@tonic-gate 	return(code);
1397c478bd9Sstevel@tonic-gate       }
1407c478bd9Sstevel@tonic-gate     }
1417c478bd9Sstevel@tonic-gate     if (pwsize == 0) {
1427c478bd9Sstevel@tonic-gate #ifdef ZEROPASSWD
1437c478bd9Sstevel@tonic-gate       memset(buffer, 0, sizeof(buffer));
1447c478bd9Sstevel@tonic-gate #endif
1457c478bd9Sstevel@tonic-gate       strncpy(msg_ret, string_text(CHPASS_UTIL_NO_PASSWORD_READ), msg_len - 1);
1467c478bd9Sstevel@tonic-gate       msg_ret[msg_len - 1] = '\0';
1477c478bd9Sstevel@tonic-gate       return(KRB5_LIBOS_CANTREADPWD); /* could do better */
1487c478bd9Sstevel@tonic-gate     }
1497c478bd9Sstevel@tonic-gate   }
1507c478bd9Sstevel@tonic-gate 
1517c478bd9Sstevel@tonic-gate   if (ret_pw)
1527c478bd9Sstevel@tonic-gate     *ret_pw = new_password;
1537c478bd9Sstevel@tonic-gate 
1547c478bd9Sstevel@tonic-gate 	passwd_protocol = _kadm5_get_kpasswd_protocol(server_handle);
1557c478bd9Sstevel@tonic-gate 	if (passwd_protocol == KRB5_CHGPWD_CHANGEPW_V2) {
1567c478bd9Sstevel@tonic-gate 		kadm5_ret_t srvr_rsp_code;
1577c478bd9Sstevel@tonic-gate 		krb5_data   srvr_msg;
1587c478bd9Sstevel@tonic-gate 
1597c478bd9Sstevel@tonic-gate 		srvr_msg.length = 0;
1607c478bd9Sstevel@tonic-gate 		srvr_msg.data = NULL;
1617c478bd9Sstevel@tonic-gate 
1627c478bd9Sstevel@tonic-gate 		code = kadm5_chpass_principal_v2(server_handle, princ,
1637c478bd9Sstevel@tonic-gate 						new_password,
1647c478bd9Sstevel@tonic-gate 						&srvr_rsp_code,
1657c478bd9Sstevel@tonic-gate 						&srvr_msg);
1667c478bd9Sstevel@tonic-gate 		if (srvr_rsp_code) {
1677c478bd9Sstevel@tonic-gate 			sprintf(msg_ret, "%s%s%.*s\n",
1687c478bd9Sstevel@tonic-gate 				chpw_error_message(srvr_rsp_code),
1697c478bd9Sstevel@tonic-gate 				srvr_msg.length? ": " : "",
1707c478bd9Sstevel@tonic-gate 				srvr_msg.length,
1717c478bd9Sstevel@tonic-gate 				srvr_msg.data ? srvr_msg.data : "");
1727c478bd9Sstevel@tonic-gate 
1737c478bd9Sstevel@tonic-gate 			return (srvr_rsp_code);
1747c478bd9Sstevel@tonic-gate 		}
1757c478bd9Sstevel@tonic-gate 		return (code);
1767c478bd9Sstevel@tonic-gate 
1777c478bd9Sstevel@tonic-gate 	} else if (passwd_protocol == KRB5_CHGPWD_RPCSEC) {
1787c478bd9Sstevel@tonic-gate 		code = kadm5_chpass_principal(server_handle, princ,
1797c478bd9Sstevel@tonic-gate 					    new_password);
1807c478bd9Sstevel@tonic-gate 
1817c478bd9Sstevel@tonic-gate #ifdef ZEROPASSWD
1827c478bd9Sstevel@tonic-gate   if (!ret_pw)
18356a424ccSmp153739     memset(buffer, 0, sizeof(buffer)); /* in case we read a new password */
1847c478bd9Sstevel@tonic-gate #endif
1857c478bd9Sstevel@tonic-gate 
1867c478bd9Sstevel@tonic-gate   if (code == KADM5_OK) {
1877c478bd9Sstevel@tonic-gate     strncpy(msg_ret, string_text(CHPASS_UTIL_PASSWORD_CHANGED), msg_len - 1);
1887c478bd9Sstevel@tonic-gate     msg_ret[msg_len - 1] = '\0';
1897c478bd9Sstevel@tonic-gate     return(0);
1907c478bd9Sstevel@tonic-gate   }
1917c478bd9Sstevel@tonic-gate 
1927c478bd9Sstevel@tonic-gate   if ((code != KADM5_PASS_Q_TOOSHORT) &&
19356a424ccSmp153739       (code != KADM5_PASS_REUSE) &&(code != KADM5_PASS_Q_CLASS) &&
19456a424ccSmp153739       (code != KADM5_PASS_Q_DICT) && (code != KADM5_PASS_TOOSOON)) {
1957c478bd9Sstevel@tonic-gate     /* Can't get more info for other errors */
1967c478bd9Sstevel@tonic-gate     sprintf(buffer, "%s %s", error_message(code),
1977c478bd9Sstevel@tonic-gate 	    string_text(CHPASS_UTIL_WHILE_TRYING_TO_CHANGE));
19856a424ccSmp153739     sprintf(msg_ret, "%s\n%s\n", string_text(CHPASS_UTIL_PASSWORD_NOT_CHANGED),
1997c478bd9Sstevel@tonic-gate 	    buffer);
2007c478bd9Sstevel@tonic-gate     return(code);
2017c478bd9Sstevel@tonic-gate   }
2027c478bd9Sstevel@tonic-gate 
2037c478bd9Sstevel@tonic-gate   /* Ok, we have a password quality error. Return a good message */
2047c478bd9Sstevel@tonic-gate 
2057c478bd9Sstevel@tonic-gate   if (code == KADM5_PASS_REUSE) {
2067c478bd9Sstevel@tonic-gate     strncpy(msg_ret, string_text(CHPASS_UTIL_PASSWORD_REUSE), msg_len - 1);
2077c478bd9Sstevel@tonic-gate     msg_ret[msg_len - 1] = '\0';
2087c478bd9Sstevel@tonic-gate     return(code);
2097c478bd9Sstevel@tonic-gate   }
2107c478bd9Sstevel@tonic-gate 
2117c478bd9Sstevel@tonic-gate   if (code == KADM5_PASS_Q_DICT) {
2127c478bd9Sstevel@tonic-gate     strncpy(msg_ret, string_text(CHPASS_UTIL_PASSWORD_IN_DICTIONARY),
2137c478bd9Sstevel@tonic-gate 	    msg_len - 1);
2147c478bd9Sstevel@tonic-gate     msg_ret[msg_len - 1] = '\0';
2157c478bd9Sstevel@tonic-gate     return(code);
2167c478bd9Sstevel@tonic-gate   }
2177c478bd9Sstevel@tonic-gate 
2187c478bd9Sstevel@tonic-gate   /* Look up policy for the remaining messages */
2197c478bd9Sstevel@tonic-gate 
2207c478bd9Sstevel@tonic-gate   code2 = kadm5_get_principal (lhandle, princ, &princ_ent,
2217c478bd9Sstevel@tonic-gate 			       KADM5_PRINCIPAL_NORMAL_MASK);
2227c478bd9Sstevel@tonic-gate   if (code2 != 0) {
2237c478bd9Sstevel@tonic-gate     strncpy(msg_ret, error_message(code2), msg_len - 1);
2247c478bd9Sstevel@tonic-gate     strncat(msg_ret, " ", msg_len - 1 - strlen(msg_ret));
2257c478bd9Sstevel@tonic-gate     strncat(msg_ret, string_text(CHPASS_UTIL_GET_PRINC_INFO), msg_len - 1 - strlen(msg_ret));
2267c478bd9Sstevel@tonic-gate     strncat(msg_ret, "\n", msg_len - 1 - strlen(msg_ret));
2277c478bd9Sstevel@tonic-gate     strncat(msg_ret, error_message(code), msg_len - 1 - strlen(msg_ret));
2287c478bd9Sstevel@tonic-gate     strncat(msg_ret, " ", msg_len - 1 - strlen(msg_ret));
2297c478bd9Sstevel@tonic-gate     strncat(msg_ret, string_text(CHPASS_UTIL_WHILE_TRYING_TO_CHANGE),
2307c478bd9Sstevel@tonic-gate 	    msg_len - 1 - strlen(msg_ret));
2317c478bd9Sstevel@tonic-gate     strncat(msg_ret, "\n\n", msg_len - 1 - strlen(msg_ret));
2327c478bd9Sstevel@tonic-gate     strncat(msg_ret, string_text(CHPASS_UTIL_PASSWORD_NOT_CHANGED),
2337c478bd9Sstevel@tonic-gate 	    msg_len - 1 - strlen(msg_ret));
2347c478bd9Sstevel@tonic-gate     strncat(msg_ret, "\n", msg_len - 1 - strlen(msg_ret));
2357c478bd9Sstevel@tonic-gate     msg_ret[msg_len - 1] = '\0';
2367c478bd9Sstevel@tonic-gate     return(code);
2377c478bd9Sstevel@tonic-gate   }
2387c478bd9Sstevel@tonic-gate 
2397c478bd9Sstevel@tonic-gate   if ((princ_ent.aux_attributes & KADM5_POLICY) == 0) {
2407c478bd9Sstevel@tonic-gate     strncpy(msg_ret, error_message(code), msg_len - 1 - strlen(msg_ret));
2417c478bd9Sstevel@tonic-gate     strncat(msg_ret, " ", msg_len - 1 - strlen(msg_ret));
2427c478bd9Sstevel@tonic-gate     strncpy(msg_ret, string_text(CHPASS_UTIL_NO_POLICY_YET_Q_ERROR),
2437c478bd9Sstevel@tonic-gate 	    msg_len - 1 - strlen(msg_ret));
2447c478bd9Sstevel@tonic-gate     strncat(msg_ret, "\n\n", msg_len - 1 - strlen(msg_ret));
2457c478bd9Sstevel@tonic-gate     strncpy(msg_ret, string_text(CHPASS_UTIL_PASSWORD_NOT_CHANGED),
2467c478bd9Sstevel@tonic-gate 	    msg_len - 1 - strlen(msg_ret));
2477c478bd9Sstevel@tonic-gate     msg_ret[msg_len - 1] = '\0';
2487c478bd9Sstevel@tonic-gate 
2497c478bd9Sstevel@tonic-gate     (void) kadm5_free_principal_ent(lhandle, &princ_ent);
2507c478bd9Sstevel@tonic-gate     return(code);
2517c478bd9Sstevel@tonic-gate   }
2527c478bd9Sstevel@tonic-gate 
2537c478bd9Sstevel@tonic-gate   code2 = kadm5_get_policy(lhandle, princ_ent.policy,
2547c478bd9Sstevel@tonic-gate 			   &policy_ent);
2557c478bd9Sstevel@tonic-gate   if (code2 != 0) {
25656a424ccSmp153739     sprintf(msg_ret, "%s %s\n%s %s\n\n%s\n ", error_message(code2),
2577c478bd9Sstevel@tonic-gate 	    string_text(CHPASS_UTIL_GET_POLICY_INFO),
2587c478bd9Sstevel@tonic-gate 	    error_message(code),
2597c478bd9Sstevel@tonic-gate 	    string_text(CHPASS_UTIL_WHILE_TRYING_TO_CHANGE),
2607c478bd9Sstevel@tonic-gate 	    string_text(CHPASS_UTIL_PASSWORD_NOT_CHANGED));
2617c478bd9Sstevel@tonic-gate     (void) kadm5_free_principal_ent(lhandle, &princ_ent);
2627c478bd9Sstevel@tonic-gate     return(code);
2637c478bd9Sstevel@tonic-gate   }
2647c478bd9Sstevel@tonic-gate 
2657c478bd9Sstevel@tonic-gate   if (code == KADM5_PASS_Q_TOOSHORT) {
26656a424ccSmp153739     sprintf(msg_ret, string_text(CHPASS_UTIL_PASSWORD_TOO_SHORT),
2677c478bd9Sstevel@tonic-gate 	    policy_ent.pw_min_length);
2687c478bd9Sstevel@tonic-gate     (void) kadm5_free_principal_ent(lhandle, &princ_ent);
2697c478bd9Sstevel@tonic-gate     (void) kadm5_free_policy_ent(lhandle, &policy_ent);
2707c478bd9Sstevel@tonic-gate     return(code);
2717c478bd9Sstevel@tonic-gate   }
2727c478bd9Sstevel@tonic-gate 
27356a424ccSmp153739 
2747c478bd9Sstevel@tonic-gate   if (code == KADM5_PASS_Q_CLASS) {
27556a424ccSmp153739     sprintf(msg_ret, string_text(CHPASS_UTIL_TOO_FEW_CLASSES),
2767c478bd9Sstevel@tonic-gate 	    policy_ent.pw_min_classes);
2777c478bd9Sstevel@tonic-gate     (void) kadm5_free_principal_ent(lhandle, &princ_ent);
2787c478bd9Sstevel@tonic-gate     (void) kadm5_free_policy_ent(lhandle, &policy_ent);
2797c478bd9Sstevel@tonic-gate     return(code);
2807c478bd9Sstevel@tonic-gate   }
2817c478bd9Sstevel@tonic-gate 
2827c478bd9Sstevel@tonic-gate   if (code == KADM5_PASS_TOOSOON) {
2837c478bd9Sstevel@tonic-gate     time_t until;
2847c478bd9Sstevel@tonic-gate     char *time_string, *ptr;
2857c478bd9Sstevel@tonic-gate 
28656a424ccSmp153739     until = princ_ent.last_pwd_change + policy_ent.pw_min_life;
2877c478bd9Sstevel@tonic-gate 
2887c478bd9Sstevel@tonic-gate     time_string = ctime(&until);
28956a424ccSmp153739     if (*(ptr = &time_string[strlen(time_string)-1]) == '\n')
2907c478bd9Sstevel@tonic-gate       *ptr = '\0';
2917c478bd9Sstevel@tonic-gate 
29256a424ccSmp153739     sprintf(msg_ret, string_text(CHPASS_UTIL_PASSWORD_TOO_SOON),
2937c478bd9Sstevel@tonic-gate 	    time_string);
2947c478bd9Sstevel@tonic-gate     (void) kadm5_free_principal_ent(lhandle, &princ_ent);
2957c478bd9Sstevel@tonic-gate     (void) kadm5_free_policy_ent(lhandle, &policy_ent);
2967c478bd9Sstevel@tonic-gate     return(code);
2977c478bd9Sstevel@tonic-gate   } else {
29856a424ccSmp153739 
2997c478bd9Sstevel@tonic-gate   /* We should never get here, but just in case ... */
3007c478bd9Sstevel@tonic-gate   sprintf(buffer, "%s %s", error_message(code),
3017c478bd9Sstevel@tonic-gate 	  string_text(CHPASS_UTIL_WHILE_TRYING_TO_CHANGE));
30256a424ccSmp153739   sprintf(msg_ret, "%s\n%s\n", string_text(CHPASS_UTIL_PASSWORD_NOT_CHANGED),
3037c478bd9Sstevel@tonic-gate 	  buffer);
3047c478bd9Sstevel@tonic-gate   (void) kadm5_free_principal_ent(lhandle, &princ_ent);
3057c478bd9Sstevel@tonic-gate   (void) kadm5_free_policy_ent(lhandle, &policy_ent);
3067c478bd9Sstevel@tonic-gate   return(code);
3077c478bd9Sstevel@tonic-gate 		}
3087c478bd9Sstevel@tonic-gate 	} else {
3097c478bd9Sstevel@tonic-gate 		sprintf(msg_ret, "%s\n%s\n",
3107c478bd9Sstevel@tonic-gate 			string_text(CHPASS_UTIL_PASSWORD_NOT_CHANGED),
3117c478bd9Sstevel@tonic-gate 			"Password protocol in krb5.conf is not supported\n");
3127c478bd9Sstevel@tonic-gate 		return (-1);
3137c478bd9Sstevel@tonic-gate 	}
3147c478bd9Sstevel@tonic-gate }
3157c478bd9Sstevel@tonic-gate 
3167c478bd9Sstevel@tonic-gate /*
3177c478bd9Sstevel@tonic-gate  * krb5_chpw_result_code_string
3187c478bd9Sstevel@tonic-gate  *
3197c478bd9Sstevel@tonic-gate  * convert the return code received from the password server
3207c478bd9Sstevel@tonic-gate  * to a human-readable string.
3217c478bd9Sstevel@tonic-gate  */
3227c478bd9Sstevel@tonic-gate const char *
chpw_error_message(kadm5_ret_t result_code)3237c478bd9Sstevel@tonic-gate chpw_error_message(kadm5_ret_t result_code)
3247c478bd9Sstevel@tonic-gate {
3257c478bd9Sstevel@tonic-gate 	switch (result_code) {
3267c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_MALFORMED:
3277c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN, "Malformed request error"));
3287c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_HARDERROR:
3297c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN, "Server error"));
3307c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_AUTHERROR:
3317c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN, "Authentication error"));
3327c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_SOFTERROR:
3337c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN, "Password change rejected"));
3347c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_ACCESSDENIED:
3357c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN,
3367c478bd9Sstevel@tonic-gate 				"Not authorized to change password"));
3377c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_BAD_VERSION:
3387c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN, "Protocol version unsupported"));
3397c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_INITIAL_FLAG_NEEDED:
3407c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN,
3417c478bd9Sstevel@tonic-gate 				"initial flag required in changepw request"));
3427c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_POLICY_REJECT:
3437c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN, "new password fails policy"));
3447c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_BAD_PRINCIPAL:
3457c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN,
3467c478bd9Sstevel@tonic-gate 		    "target principal does not exist for "
3477c478bd9Sstevel@tonic-gate 		    "changepw request"));
3487c478bd9Sstevel@tonic-gate 	case KRB5_KPASSWD_ETYPE_NOSUPP:
3497c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN,
3507c478bd9Sstevel@tonic-gate 		    "changepw request key sequence has an "
3517c478bd9Sstevel@tonic-gate 		    "unsupported Etype"));
3527c478bd9Sstevel@tonic-gate 	default:
3537c478bd9Sstevel@tonic-gate 		return (dgettext(TEXT_DOMAIN, "Password change failed"));
3547c478bd9Sstevel@tonic-gate 	}
3557c478bd9Sstevel@tonic-gate }
356