4 * Copyright 1987, 1988 by the Massachusetts Institute of Technology.
6 * For copying and distribution information, please see the file
10 #include "mit-copyright.h"
19 * This file contains two routines: passwd_to_key() converts
20 * a password into a DES key (prompting for the password if
21 * not supplied), and krb_get_pw_in_tkt() gets an initial ticket for
26 * passwd_to_key(): given a password, return a DES key.
27 * There are extra arguments here which (used to be?)
28 * used by srvtab_to_key().
30 * If the "passwd" argument is not null, generate a DES
31 * key from it, using string_to_key().
33 * If the "passwd" argument is null, then on a Unix system we call
34 * des_read_password() to prompt for a password and then convert it
35 * into a DES key. But "prompting" the user is harder in a Windows or
36 * Macintosh environment, so we rely on our caller to explicitly do
39 * In either case, the resulting key is put in the "key" argument,
44 passwd_to_key(user,instance,realm,passwd,key)
45 char *user, *instance, *realm, *passwd;
48 #if defined(_WINDOWS) || defined(macintosh)
49 string_to_key(passwd, key);
53 placebo_read_password(key, "Password: ", 0);
54 #else /* Do encyryption */
56 string_to_key(passwd, key);
58 des_read_password(key, "Password: ", 0);
60 #endif /* NOENCRYPTION */
66 * krb_get_pw_in_tkt() takes the name of the server for which the initial
67 * ticket is to be obtained, the name of the principal the ticket is
68 * for, the desired lifetime of the ticket, and the user's password.
69 * It passes its arguments on to krb_get_in_tkt(), which contacts
70 * Kerberos to get the ticket, decrypts it using the password provided,
71 * and stores it away for future use.
73 * On a Unix system, krb_get_pw_in_tkt() is able to prompt the user
74 * for a password, if the supplied password is null. On a a non Unix
75 * system, it now requires the caller to supply a non-null password.
76 * This is because of the complexities of prompting the user in a
77 * non-terminal-oriented environment like the Macintosh (running in a
78 * driver) or MS-Windows (in a DLL).
80 * krb_get_pw_in_tkt() passes two additional arguments to krb_get_in_tkt():
81 * the name of a routine (passwd_to_key()) to be used to get the
82 * password in case the "password" argument is null and NULL for the
83 * decryption procedure indicating that krb_get_in_tkt should use the
84 * default method of decrypting the response from the KDC.
86 * The result of the call to krb_get_in_tkt() is returned.
90 krb_get_pw_in_tkt(user,instance,realm,service,sinstance,life,password)
91 char *user, *instance, *realm, *service, *sinstance;
95 #if defined(_WINDOWS) || defined(macintosh)
96 /* In spite of the comments above, we don't allow that path here,
97 to simplify coding the non-UNIX clients. The only code that now
98 depends on this behavior is the preauth support, which has a
99 seperate function without this trap. Strictly speaking, this
106 return(krb_get_in_tkt(user,instance,realm,service,sinstance,life,
108 (decrypt_tkt_type)NULL, password));
112 * krb_get_pw_in_tkt_preauth() gets handed the password or key explicitly,
113 * since the whole point of "pre" authentication is to prove that we've
114 * already got the key, and the only way to do that is to ask the user
115 * for it. Clearly we shouldn't ask twice.
118 static C_Block old_key;
120 static int stub_key(user,instance,realm,passwd,key)
121 char *user, *instance, *realm, *passwd;
124 (void) memcpy((char *) key, (char *) old_key, sizeof(old_key));
129 krb_get_pw_in_tkt_preauth(user,instance,realm,service,sinstance,life,password)
130 char *user, *instance, *realm, *service, *sinstance;
138 #if defined(_WINDOWS) || defined(macintosh)
139 /* On non-Unix systems, we can't handle a null password, because
140 passwd_to_key can't handle prompting for the password. */
145 krb_mk_preauth(&preauth_p,&preauth_len, passwd_to_key,
146 user,instance,realm,password,old_key);
147 ret_st = krb_get_in_tkt_preauth(user,instance,realm,service,sinstance,life,
148 (key_proc_type) stub_key,
149 (decrypt_tkt_type) NULL, password,
150 preauth_p, preauth_len);
152 krb_free_preauth(preauth_p, preauth_len);
156 /* FIXME! This routine belongs in the krb library and should simply
157 be shared between the encrypted and NOENCRYPTION versions! */
161 * This routine prints the supplied string to standard
162 * output as a prompt, and reads a password string without
169 #include <sys/ioctl.h>
185 static void sig_restore();
186 static push_signals(), pop_signals();
187 int placebo_read_pw_string();
190 /*** Routines ****************************************************** */
192 placebo_read_password(k,prompt,verify)
198 char key_string[BUFSIZ];
207 ok = placebo_read_pw_string(key_string, BUFSIZ, prompt, verify);
209 memset(k, 0, sizeof(C_Block));
212 memset(key_string, 0, sizeof (key_string));
217 * This version just returns the string, doesn't map to key.
219 * Returns 0 on success, non-zero on failure.
223 placebo_read_pw_string(s,max,prompt,verify)
234 struct sgttyb tty_state;
236 char key_string[BUFSIZ];
243 memcpy(env, old_env, sizeof(env));
247 /* save terminal state */
248 if (ioctl(0,TIOCGETP,&tty_state) == -1)
253 tty_state.sg_flags &= ~ECHO;
254 if (ioctl(0,TIOCSETP,&tty_state) == -1)
261 h19line(s,sizeof(s),0);
265 if (!fgets(s, max, stdin)) {
269 if ((ptr = strchr(s, '\n')))
273 printf("\nVerifying, please re-enter %s",prompt);
276 h19line(key_string,sizeof(key_string),0);
277 if (!strlen(key_string))
280 if (!fgets(key_string, sizeof(key_string), stdin)) {
284 if ((ptr = strchr(key_string, '\n')))
287 if (strcmp(s,key_string)) {
288 printf("\n\07\07Mismatch - try again\n");
301 /* turn echo back on */
302 tty_state.sg_flags |= ECHO;
303 if (ioctl(0,TIOCSETP,&tty_state))
306 memcpy(old_env, env, sizeof(env));
309 memset(key_string, 0, sizeof (key_string));
310 s[max-1] = 0; /* force termination */
311 return !ok; /* return nonzero if not okay */
316 * this can be static since we should never have more than
319 static sigtype (*old_sigfunc[NSIG])();
321 static push_signals()
324 for (i = 0; i < NSIG; i++)
325 old_sigfunc[i] = signal(i,sig_restore);
331 for (i = 0; i < NSIG; i++)
332 signal(i,old_sigfunc[i]);
335 static void sig_restore(sig,code,scp)
337 struct sigcontext *scp;
342 #endif /* NOENCRYPTION */