c8b0e6a4427473cc23dad9906817ad6c3a364dab
[sfrench/samba-autobuild/.git] / source / libsmb / pwd_cache.c
1 /* 
2    Unix SMB/Netbios implementation.
3    Version 1.9.
4    Password cacheing.  obfuscation is planned
5    Copyright (C) Luke Kenneth Casson Leighton 1996-1998
6    
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2 of the License, or
10    (at your option) any later version.
11    
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16    
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software
19    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22 #include "includes.h"
23
24 extern int DEBUGLEVEL;
25
26
27 /****************************************************************************
28 initialises a password structure
29 ****************************************************************************/
30 void pwd_init(struct pwd_info *pwd)
31 {
32         bzero(pwd->password  , sizeof(pwd->password  ));
33         bzero(pwd->smb_lm_pwd, sizeof(pwd->smb_lm_pwd));
34         bzero(pwd->smb_nt_pwd, sizeof(pwd->smb_nt_pwd));
35         bzero(pwd->smb_lm_owf, sizeof(pwd->smb_lm_owf));
36         bzero(pwd->smb_nt_owf, sizeof(pwd->smb_nt_owf));
37         pwd->nt_owf_len = 0;
38
39         pwd->null_pwd  = True; /* safest option... */
40         pwd->cleartext = False;
41         pwd->crypted   = False;
42 }
43
44 /****************************************************************************
45 de-obfuscates a password
46 ****************************************************************************/
47 static void pwd_deobfuscate(struct pwd_info *pwd)
48 {
49 }
50
51 /****************************************************************************
52 obfuscates a password
53 ****************************************************************************/
54 static void pwd_obfuscate(struct pwd_info *pwd)
55 {
56 }
57
58 /****************************************************************************
59 sets the obfuscation key info
60 ****************************************************************************/
61 void pwd_obfuscate_key(struct pwd_info *pwd, uint32 int_key, char *str_key)
62 {
63 }
64
65 /****************************************************************************
66 reads a password
67 ****************************************************************************/
68 void pwd_read(struct pwd_info *pwd, char *passwd_report, BOOL do_encrypt)
69 {
70         /* grab a password */
71         char *user_pass;
72
73         pwd_init(pwd);
74
75         user_pass = (char*)getpass(passwd_report);
76
77         if (user_pass == NULL || user_pass[0] == 0)
78         {
79                 pwd_set_nullpwd(pwd);
80         }
81         else if (do_encrypt)
82         {
83                 pwd_make_lm_nt_16(pwd, user_pass);
84         }
85         else
86         {
87                 pwd_set_cleartext(pwd, user_pass);
88         }
89 }
90
91 /****************************************************************************
92  stores a cleartext password
93  ****************************************************************************/
94 void pwd_set_nullpwd(struct pwd_info *pwd)
95 {
96         pwd_init(pwd);
97
98         pwd->cleartext = False;
99         pwd->null_pwd  = True;
100         pwd->crypted   = False;
101 }
102
103 /****************************************************************************
104  stores a cleartext password
105  ****************************************************************************/
106 void pwd_set_cleartext(struct pwd_info *pwd, char *clr)
107 {
108         pwd_init(pwd);
109         fstrcpy(pwd->password, clr);
110         pwd->cleartext = True;
111         pwd->null_pwd  = False;
112         pwd->crypted   = False;
113
114         pwd_obfuscate(pwd);
115 }
116
117 /****************************************************************************
118  gets a cleartext password
119  ****************************************************************************/
120 void pwd_get_cleartext(struct pwd_info *pwd, char *clr)
121 {
122         pwd_deobfuscate(pwd);
123         if (pwd->cleartext)
124         {
125                 fstrcpy(clr, pwd->password);
126         }
127         else
128         {
129                 clr[0] = 0;
130         }
131         pwd_obfuscate(pwd);
132 }
133
134 /****************************************************************************
135  stores lm and nt hashed passwords
136  ****************************************************************************/
137 void pwd_set_lm_nt_16(struct pwd_info *pwd, uchar lm_pwd[16], uchar nt_pwd[16])
138 {
139         pwd_init(pwd);
140
141         if (lm_pwd)
142         {
143                 memcpy(pwd->smb_lm_pwd, lm_pwd, 16);
144         }
145         else
146         {
147                 bzero(pwd->smb_lm_pwd, 16);
148         }
149
150         if (nt_pwd)
151         {
152                 memcpy(pwd->smb_nt_pwd, nt_pwd, 16);
153         }
154         else
155         {
156                 bzero(pwd->smb_nt_pwd, 16);
157         }
158
159         pwd->null_pwd  = False;
160         pwd->cleartext = False;
161         pwd->crypted   = False;
162
163         pwd_obfuscate(pwd);
164 }
165
166 /****************************************************************************
167  gets lm and nt hashed passwords
168  ****************************************************************************/
169 void pwd_get_lm_nt_16(struct pwd_info *pwd, uchar lm_pwd[16], uchar nt_pwd[16])
170 {
171         pwd_deobfuscate(pwd);
172         if (lm_pwd != NULL)
173         {
174                 memcpy(lm_pwd, pwd->smb_lm_pwd, 16);
175         }
176         if (nt_pwd != NULL)
177         {
178                 memcpy(nt_pwd, pwd->smb_nt_pwd, 16);
179         }
180         pwd_obfuscate(pwd);
181 }
182
183 /****************************************************************************
184  makes lm and nt hashed passwords
185  ****************************************************************************/
186 void pwd_make_lm_nt_16(struct pwd_info *pwd, char *clr)
187 {
188         pwd_init(pwd);
189
190         nt_lm_owf_gen(clr, pwd->smb_nt_pwd, pwd->smb_lm_pwd);
191         pwd->null_pwd  = False;
192         pwd->cleartext = False;
193         pwd->crypted = False;
194
195         pwd_obfuscate(pwd);
196 }
197
198 /****************************************************************************
199  makes lm and nt OWF crypts
200  ****************************************************************************/
201 void pwd_make_lm_nt_owf2(struct pwd_info *pwd, const uchar srv_key[8],
202                 const char *user, const char *server, const char *domain)
203 {
204         uchar kr[16];
205
206         DEBUG(10,("pwd_make_lm_nt_owf2: user %s, srv %s, dom %s\n",
207                 user, server, domain));
208
209         pwd_deobfuscate(pwd);
210
211         SMBgenclientchals(pwd->lm_cli_chal,
212                           pwd->nt_cli_chal,
213                           &pwd->nt_cli_chal_len,
214                           server, domain);
215         
216         ntv2_owf_gen(pwd->smb_nt_pwd, user, domain, kr);
217
218         /* lm # */
219         SMBOWFencrypt_ntv2(kr,
220                            srv_key, 8,
221                            pwd->lm_cli_chal, 8,
222                            pwd->smb_lm_owf);
223         memcpy(&pwd->smb_lm_owf[16], pwd->lm_cli_chal, 8);
224
225         /* nt # */
226         SMBOWFencrypt_ntv2(kr,
227                        srv_key, 8,
228                        pwd->nt_cli_chal, pwd->nt_cli_chal_len,
229                        pwd->smb_nt_owf);
230         memcpy(&pwd->smb_nt_owf[16], pwd->nt_cli_chal, pwd->nt_cli_chal_len);
231         pwd->nt_owf_len = pwd->nt_cli_chal_len + 16;
232
233 #ifdef DEBUG_PASSWORD
234         DEBUG(100,("server cryptkey: "));
235         dump_data(100, srv_key, 8);
236
237         DEBUG(100,("client lmv2 cryptkey: "));
238         dump_data(100, pwd->lm_cli_chal, 8);
239
240         DEBUG(100,("client ntv2 cryptkey: "));
241         dump_data(100, pwd->nt_cli_chal, pwd->nt_cli_chal_len);
242
243         DEBUG(100,("ntv2_owf_passwd: "));
244         dump_data(100, pwd->smb_nt_owf, pwd->nt_owf_len);
245         DEBUG(100,("nt_sess_pwd: "));
246         dump_data(100, pwd->smb_nt_pwd, sizeof(pwd->smb_nt_pwd));
247
248         DEBUG(100,("lmv2_owf_passwd: "));
249         dump_data(100, pwd->smb_lm_owf, sizeof(pwd->smb_lm_owf));
250         DEBUG(100,("lm_sess_pwd: "));
251         dump_data(100, pwd->smb_lm_pwd, sizeof(pwd->smb_lm_pwd));
252 #endif
253         pwd->crypted = True;
254
255         pwd_obfuscate(pwd);
256 }
257
258 /****************************************************************************
259  makes lm and nt OWF crypts
260  ****************************************************************************/
261 void pwd_make_lm_nt_owf(struct pwd_info *pwd, uchar cryptkey[8])
262 {
263         if (pwd->null_pwd)
264         {
265 #ifdef DEBUG_PASSWORD
266                 DEBUG(100,("pwd_make_lm_nt_owf: NULL password\n"));
267 #endif
268                 pwd->nt_owf_len = 0;
269                 return;
270         }
271         pwd_deobfuscate(pwd);
272
273         SMBOWFencrypt(pwd->smb_lm_pwd, cryptkey, pwd->smb_lm_owf);
274         SMBOWFencrypt(pwd->smb_nt_pwd, cryptkey, pwd->smb_nt_owf);
275         pwd->nt_owf_len = 24;
276
277 #ifdef DEBUG_PASSWORD
278         DEBUG(100,("client cryptkey: "));
279         dump_data(100, cryptkey, 8);
280
281         DEBUG(100,("nt_owf_passwd: "));
282         dump_data(100, pwd->smb_nt_owf, pwd->nt_owf_len);
283         DEBUG(100,("nt_sess_pwd: "));
284         dump_data(100, pwd->smb_nt_pwd, sizeof(pwd->smb_nt_pwd));
285
286         DEBUG(100,("lm_owf_passwd: "));
287         dump_data(100, pwd->smb_lm_owf, sizeof(pwd->smb_lm_owf));
288         DEBUG(100,("lm_sess_pwd: "));
289         dump_data(100, pwd->smb_lm_pwd, sizeof(pwd->smb_lm_pwd));
290 #endif
291
292         pwd->crypted = True;
293
294         pwd_obfuscate(pwd);
295 }
296
297 /****************************************************************************
298  gets lm and nt crypts
299  ****************************************************************************/
300 void pwd_get_lm_nt_owf(struct pwd_info *pwd, uchar lm_owf[24],
301                                 uchar *nt_owf, size_t *nt_owf_len)
302 {
303         if (pwd->null_pwd)
304         {
305 #ifdef DEBUG_PASSWORD
306                 DEBUG(100,("pwd_get_lm_nt_owf: NULL password\n"));
307 #endif
308                 if (nt_owf_len != NULL)
309                 {
310                         *nt_owf_len = 0;
311                 }
312                 return;
313         }
314                 
315         pwd_deobfuscate(pwd);
316         if (lm_owf != NULL)
317         {
318                 memcpy(lm_owf, pwd->smb_lm_owf, 24);
319         }
320         if (nt_owf != NULL)
321         {
322                 memcpy(nt_owf, pwd->smb_nt_owf, pwd->nt_owf_len);
323         }
324         if (nt_owf_len != NULL)
325         {
326                 *nt_owf_len = pwd->nt_owf_len;
327         }
328         pwd_obfuscate(pwd);
329 }
330