Add some comments on writing new pdb modules. (from ctrlsoft)
[kai/samba.git] / source3 / passdb / pdb_get_set.c
1 /* 
2    Unix SMB/CIFS implementation.
3    SAM_ACCOUNT access routines
4    Copyright (C) Jeremy Allison                 1996-2001
5    Copyright (C) Luke Kenneth Casson Leighton   1996-1998
6    Copyright (C) Gerald (Jerry) Carter          2000-2001
7    Copyright (C) Andrew Bartlett                2001-2002
8    Copyright (C) Stefan (metze) Metzmacher      2002
9       
10    This program is free software; you can redistribute it and/or modify
11    it under the terms of the GNU General Public License as published by
12    the Free Software Foundation; either version 2 of the License, or
13    (at your option) any later version.
14    
15    This program is distributed in the hope that it will be useful,
16    but WITHOUT ANY WARRANTY; without even the implied warranty of
17    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18    GNU General Public License for more details.
19    
20    You should have received a copy of the GNU General Public License
21    along with this program; if not, write to the Free Software
22    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 */
24
25 #include "includes.h"
26
27 #undef DBGC_CLASS
28 #define DBGC_CLASS DBGC_PASSDB
29
30 /**
31  * @todo Redefine this to NULL, but this changes the API becouse
32  *       much of samba assumes that the pdb_get...() funtions 
33  *       return pstrings.  (ie not null-pointers).
34  *       See also pdb_fill_default_sam().
35  */
36
37 #define PDB_NOT_QUITE_NULL ""
38
39 /*********************************************************************
40  Collection of get...() functions for SAM_ACCOUNT_INFO.
41  ********************************************************************/
42
43 uint16 pdb_get_acct_ctrl (const SAM_ACCOUNT *sampass)
44 {
45         if (sampass)
46                 return (sampass->private.acct_ctrl);
47         else
48                 return (ACB_DISABLED);
49 }
50
51 time_t pdb_get_logon_time (const SAM_ACCOUNT *sampass)
52 {
53         if (sampass)
54                 return (sampass->private.logon_time);
55         else
56                 return (0);
57 }
58
59 time_t pdb_get_logoff_time (const SAM_ACCOUNT *sampass)
60 {
61         if (sampass)
62                 return (sampass->private.logoff_time);
63         else
64                 return (-1);
65 }
66
67 time_t pdb_get_kickoff_time (const SAM_ACCOUNT *sampass)
68 {
69         if (sampass)
70                 return (sampass->private.kickoff_time);
71         else
72                 return (-1);
73 }
74
75 time_t pdb_get_pass_last_set_time (const SAM_ACCOUNT *sampass)
76 {
77         if (sampass)
78                 return (sampass->private.pass_last_set_time);
79         else
80                 return (-1);
81 }
82
83 time_t pdb_get_pass_can_change_time (const SAM_ACCOUNT *sampass)
84 {
85         if (sampass)
86                 return (sampass->private.pass_can_change_time);
87         else
88                 return (-1);
89 }
90
91 time_t pdb_get_pass_must_change_time (const SAM_ACCOUNT *sampass)
92 {
93         if (sampass)
94                 return (sampass->private.pass_must_change_time);
95         else
96                 return (-1);
97 }
98
99 uint16 pdb_get_logon_divs (const SAM_ACCOUNT *sampass)
100 {
101         if (sampass)
102                 return (sampass->private.logon_divs);
103         else
104                 return (-1);
105 }
106
107 uint32 pdb_get_hours_len (const SAM_ACCOUNT *sampass)
108 {
109         if (sampass)
110                 return (sampass->private.hours_len);
111         else
112                 return (-1);
113 }
114
115 const uint8* pdb_get_hours (const SAM_ACCOUNT *sampass)
116 {
117         if (sampass)
118                 return (sampass->private.hours);
119         else
120                 return (NULL);
121 }
122
123 const uint8* pdb_get_nt_passwd (const SAM_ACCOUNT *sampass)
124 {
125         if (sampass) {
126                 SMB_ASSERT((!sampass->private.nt_pw.data) 
127                            || sampass->private.nt_pw.length == NT_HASH_LEN);
128                 return ((uint8*)sampass->private.nt_pw.data);
129         }
130         else
131                 return (NULL);
132 }
133
134 const uint8* pdb_get_lanman_passwd (const SAM_ACCOUNT *sampass)
135 {
136         if (sampass) {
137                 SMB_ASSERT((!sampass->private.lm_pw.data) 
138                            || sampass->private.lm_pw.length == LM_HASH_LEN);
139                 return ((uint8*)sampass->private.lm_pw.data);
140         }
141         else
142                 return (NULL);
143 }
144
145 /* Return the plaintext password if known.  Most of the time
146    it isn't, so don't assume anything magic about this function.
147    
148    Used to pass the plaintext to passdb backends that might 
149    want to store more than just the NTLM hashes.
150 */
151 const char* pdb_get_plaintext_passwd (const SAM_ACCOUNT *sampass)
152 {
153         if (sampass) {
154                 return ((char*)sampass->private.plaintext_pw.data);
155         }
156         else
157                 return (NULL);
158 }
159 const DOM_SID *pdb_get_user_sid(const SAM_ACCOUNT *sampass)
160 {
161         if (sampass) 
162                 return &sampass->private.user_sid;
163         else
164                 return (NULL);
165 }
166
167 const DOM_SID *pdb_get_group_sid(const SAM_ACCOUNT *sampass)
168 {
169         if (sampass)
170                 return &sampass->private.group_sid;
171         else    
172                 return (NULL);
173 }       
174
175 uint32 pdb_get_user_rid (const SAM_ACCOUNT *sampass)
176 {
177         uint32 u_rid;
178
179         if (sampass)
180                 if (sid_peek_check_rid(get_global_sam_sid(), pdb_get_user_sid(sampass),&u_rid))
181                         return u_rid;
182         
183         return (-1);
184 }
185
186 uint32 pdb_get_group_rid (const SAM_ACCOUNT *sampass)
187 {
188         uint32 g_rid;
189
190         if (sampass)
191                 if (sid_peek_check_rid(get_global_sam_sid(), pdb_get_group_sid(sampass),&g_rid))
192                         return g_rid;
193         return (-1);
194 }
195
196 /**
197  * Get flags showing what is initalised in the SAM_ACCOUNT
198  * @param sampass the SAM_ACCOUNT in question
199  * @return the flags indicating the members initialised in the struct.
200  **/
201  
202 uint32 pdb_get_init_flag (const SAM_ACCOUNT *sampass)
203 {
204         if (sampass)
205                 return sampass->private.init_flag;
206         else 
207                 return FLAG_SAM_UNINIT;
208 }
209
210 uid_t pdb_get_uid (const SAM_ACCOUNT *sampass)
211 {
212         if (sampass)
213                 return (sampass->private.uid);
214         else
215                 return (-1);
216 }
217
218 gid_t pdb_get_gid (const SAM_ACCOUNT *sampass)
219 {
220         if (sampass)
221                 return (sampass->private.gid);
222         else
223                 return (-1);
224 }
225
226 const char* pdb_get_username (const SAM_ACCOUNT *sampass)
227 {
228         if (sampass)
229                 return (sampass->private.username);
230         else
231                 return (NULL);
232 }
233
234 const char* pdb_get_domain (const SAM_ACCOUNT *sampass)
235 {
236         if (sampass)
237                 return (sampass->private.domain);
238         else
239                 return (NULL);
240 }
241
242 const char* pdb_get_nt_username (const SAM_ACCOUNT *sampass)
243 {
244         if (sampass)
245                 return (sampass->private.nt_username);
246         else
247                 return (NULL);
248 }
249
250 const char* pdb_get_fullname (const SAM_ACCOUNT *sampass)
251 {
252         if (sampass)
253                 return (sampass->private.full_name);
254         else
255                 return (NULL);
256 }
257
258 const char* pdb_get_homedir (const SAM_ACCOUNT *sampass)
259 {
260         if (sampass)
261                 return (sampass->private.home_dir);
262         else
263                 return (NULL);
264 }
265
266 const char* pdb_get_unix_homedir (const SAM_ACCOUNT *sampass)
267 {
268         if (sampass)
269                 return (sampass->private.unix_home_dir);
270         else
271                 return (NULL);
272 }
273
274 const char* pdb_get_dirdrive (const SAM_ACCOUNT *sampass)
275 {
276         if (sampass)
277                 return (sampass->private.dir_drive);
278         else
279                 return (NULL);
280 }
281
282 const char* pdb_get_logon_script (const SAM_ACCOUNT *sampass)
283 {
284         if (sampass)
285                 return (sampass->private.logon_script);
286         else
287                 return (NULL);
288 }
289
290 const char* pdb_get_profile_path (const SAM_ACCOUNT *sampass)
291 {
292         if (sampass)
293                 return (sampass->private.profile_path);
294         else
295                 return (NULL);
296 }
297
298 const char* pdb_get_acct_desc (const SAM_ACCOUNT *sampass)
299 {
300         if (sampass)
301                 return (sampass->private.acct_desc);
302         else
303                 return (NULL);
304 }
305
306 const char* pdb_get_workstations (const SAM_ACCOUNT *sampass)
307 {
308         if (sampass)
309                 return (sampass->private.workstations);
310         else
311                 return (NULL);
312 }
313
314 const char* pdb_get_unknown_str (const SAM_ACCOUNT *sampass)
315 {
316         if (sampass)
317                 return (sampass->private.unknown_str);
318         else
319                 return (NULL);
320 }
321
322 const char* pdb_get_munged_dial (const SAM_ACCOUNT *sampass)
323 {
324         if (sampass)
325                 return (sampass->private.munged_dial);
326         else
327                 return (NULL);
328 }
329
330 uint32 pdb_get_unknown3 (const SAM_ACCOUNT *sampass)
331 {
332         if (sampass)
333                 return (sampass->private.unknown_3);
334         else
335                 return (-1);
336 }
337
338 uint32 pdb_get_unknown5 (const SAM_ACCOUNT *sampass)
339 {
340         if (sampass)
341                 return (sampass->private.unknown_5);
342         else
343                 return (-1);
344 }
345
346 uint32 pdb_get_unknown6 (const SAM_ACCOUNT *sampass)
347 {
348         if (sampass)
349                 return (sampass->private.unknown_6);
350         else
351                 return (-1);
352 }
353
354 /*********************************************************************
355  Collection of set...() functions for SAM_ACCOUNT_INFO.
356  ********************************************************************/
357
358 BOOL pdb_set_acct_ctrl (SAM_ACCOUNT *sampass, uint16 flags)
359 {
360         if (!sampass)
361                 return False;
362                 
363         if (sampass) {
364                 sampass->private.acct_ctrl = flags;
365                 return True;
366         }
367         
368         return False;
369 }
370
371 BOOL pdb_set_logon_time (SAM_ACCOUNT *sampass, time_t mytime, BOOL store)
372 {
373         if (!sampass)
374                 return False;
375
376         sampass->private.logon_time = mytime;
377
378         if (store)
379                 pdb_set_init_flag(sampass, FLAG_SAM_LOGONTIME); 
380
381         return True;
382 }
383
384 BOOL pdb_set_logoff_time (SAM_ACCOUNT *sampass, time_t mytime, BOOL store)
385 {
386         if (!sampass)
387                 return False;
388
389         sampass->private.logoff_time = mytime;
390
391         if (store)
392                 pdb_set_init_flag(sampass, FLAG_SAM_LOGOFFTIME); 
393
394         return True;
395 }
396
397 BOOL pdb_set_kickoff_time (SAM_ACCOUNT *sampass, time_t mytime, BOOL store)
398 {
399         if (!sampass)
400                 return False;
401
402         sampass->private.kickoff_time = mytime;
403
404         if (store)
405                 pdb_set_init_flag(sampass, FLAG_SAM_KICKOFFTIME); 
406
407         return True;
408 }
409
410 BOOL pdb_set_pass_can_change_time (SAM_ACCOUNT *sampass, time_t mytime, BOOL store)
411 {
412         if (!sampass)
413                 return False;
414
415         sampass->private.pass_can_change_time = mytime;
416
417         if (store)
418                 pdb_set_init_flag(sampass, FLAG_SAM_CANCHANGETIME); 
419
420         return True;
421 }
422
423 BOOL pdb_set_pass_must_change_time (SAM_ACCOUNT *sampass, time_t mytime, BOOL store)
424 {
425         if (!sampass)
426                 return False;
427
428         sampass->private.pass_must_change_time = mytime;
429
430         if (store)
431                 pdb_set_init_flag(sampass, FLAG_SAM_MUSTCHANGETIME); 
432
433         return True;
434 }
435
436 BOOL pdb_set_pass_last_set_time (SAM_ACCOUNT *sampass, time_t mytime)
437 {
438         if (!sampass)
439                 return False;
440
441         sampass->private.pass_last_set_time = mytime;
442
443         return True;
444 }
445
446 BOOL pdb_set_hours_len (SAM_ACCOUNT *sampass, uint32 len)
447 {
448         if (!sampass)
449                 return False;
450
451         sampass->private.hours_len = len;
452         return True;
453 }
454
455 BOOL pdb_set_logon_divs (SAM_ACCOUNT *sampass, uint16 hours)
456 {
457         if (!sampass)
458                 return False;
459
460         sampass->private.logon_divs = hours;
461         return True;
462 }
463
464 /**
465  * Set flags showing what is initalised in the SAM_ACCOUNT
466  * @param sampass the SAM_ACCOUNT in question
467  * @param flag The *new* flag to be set.  Old flags preserved
468  *             this flag is only added.  
469  **/
470  
471 BOOL pdb_set_init_flag (SAM_ACCOUNT *sampass, uint32 flag)
472 {
473         if (!sampass)
474                 return False;
475
476         sampass->private.init_flag |= flag;
477
478         return True;
479 }
480
481 BOOL pdb_set_uid (SAM_ACCOUNT *sampass, const uid_t uid)
482 {
483         if (!sampass)
484                 return False;
485         
486         DEBUG(10, ("pdb_set_uid: setting uid %d, was %d\n", 
487                    (int)uid, (int)sampass->private.uid));
488  
489         sampass->private.uid = uid;
490         pdb_set_init_flag(sampass, FLAG_SAM_UID); 
491
492         return True;
493
494 }
495
496 BOOL pdb_set_gid (SAM_ACCOUNT *sampass, const gid_t gid)
497 {
498         if (!sampass)
499                 return False;
500                 
501         DEBUG(10, ("pdb_set_gid: setting gid %d, was %d\n", 
502                    (int)gid, (int)sampass->private.gid));
503  
504         sampass->private.gid = gid; 
505         pdb_set_init_flag(sampass, FLAG_SAM_GID); 
506
507         return True;
508
509 }
510
511 BOOL pdb_set_user_sid (SAM_ACCOUNT *sampass, DOM_SID *u_sid)
512 {
513         if (!sampass || !u_sid)
514                 return False;
515         
516         sid_copy(&sampass->private.user_sid, u_sid);
517
518         DEBUG(10, ("pdb_set_user_sid: setting user sid %s\n", 
519                     sid_string_static(&sampass->private.user_sid)));
520         
521         return True;
522 }
523
524 BOOL pdb_set_group_sid(SAM_ACCOUNT *sampass, DOM_SID *g_sid)
525 {
526         if (!sampass || !g_sid)
527                 return False;
528
529         sid_copy(&sampass->private.group_sid, g_sid);
530
531         DEBUG(10, ("pdb_set_group_sid: setting group sid %s\n", 
532                     sid_string_static(&sampass->private.group_sid)));
533
534         return True;
535 }
536
537 BOOL pdb_set_user_sid_from_rid (SAM_ACCOUNT *sampass, uint32 rid)
538 {
539         DOM_SID u_sid;
540         const DOM_SID *global_sam_sid;
541         
542         if (!sampass)
543                 return False;
544
545         if (!(global_sam_sid = get_global_sam_sid())) {
546                 DEBUG(1, ("pdb_set_user_sid_from_rid: Could not read global sam sid!\n"));
547                 return False;
548         }
549
550         sid_copy(&u_sid, global_sam_sid);
551
552         if (!sid_append_rid(&u_sid, rid))
553                 return False;
554
555         if (!pdb_set_user_sid(sampass, &u_sid))
556                 return False;
557
558         DEBUG(10, ("pdb_set_user_sid_from_rid:\n\tsetting user sid %s from rid %d\n", 
559                     sid_string_static(&u_sid),rid));
560
561         return True;
562 }
563
564 BOOL pdb_set_group_sid_from_rid (SAM_ACCOUNT *sampass, uint32 grid)
565 {
566         DOM_SID g_sid;
567         const DOM_SID *global_sam_sid;
568
569         if (!sampass)
570                 return False;
571         
572         if (!(global_sam_sid = get_global_sam_sid())) {
573                 DEBUG(1, ("pdb_set_user_sid_from_rid: Could not read global sam sid!\n"));
574                 return False;
575         }
576
577         sid_copy(&g_sid, global_sam_sid);
578         
579         if (!sid_append_rid(&g_sid, grid))
580                 return False;
581
582         if (!pdb_set_group_sid(sampass, &g_sid))
583                 return False;
584
585         DEBUG(10, ("pdb_set_group_sid_from_rid:\n\tsetting group sid %s from rid %d\n", 
586                     sid_string_static(&g_sid), grid));
587
588         return True;
589 }
590
591 /*********************************************************************
592  Set the user's UNIX name.
593  ********************************************************************/
594
595 BOOL pdb_set_username(SAM_ACCOUNT *sampass, const char *username)
596 {       
597         if (!sampass)
598                 return False;
599  
600         if (username) { 
601                 DEBUG(10, ("pdb_set_username: setting username %s, was %s\n", username,
602                         (sampass->private.username)?(sampass->private.username):"NULL"));
603
604                 sampass->private.username = talloc_strdup(sampass->mem_ctx, username);
605
606                 if (!sampass->private.username) {
607                         DEBUG(0, ("pdb_set_username: talloc_strdup() failed!\n"));
608                         return False;
609                 }
610
611         } else {
612                 sampass->private.username = PDB_NOT_QUITE_NULL;
613         }
614
615         return True;
616 }
617
618 /*********************************************************************
619  Set the domain name.
620  ********************************************************************/
621
622 BOOL pdb_set_domain(SAM_ACCOUNT *sampass, const char *domain)
623 {       
624         if (!sampass)
625                 return False;
626
627         if (domain) { 
628                 DEBUG(10, ("pdb_set_domain: setting domain %s, was %s\n", domain,
629                         (sampass->private.domain)?(sampass->private.domain):"NULL"));
630
631                 sampass->private.domain = talloc_strdup(sampass->mem_ctx, domain);
632
633                 if (!sampass->private.domain) {
634                         DEBUG(0, ("pdb_set_domain: talloc_strdup() failed!\n"));
635                         return False;
636                 }
637
638         } else {
639                 sampass->private.domain = PDB_NOT_QUITE_NULL;
640         }
641
642         return True;
643 }
644
645 /*********************************************************************
646  Set the user's NT name.
647  ********************************************************************/
648
649 BOOL pdb_set_nt_username(SAM_ACCOUNT *sampass, const char *nt_username)
650 {
651         if (!sampass)
652                 return False;
653
654         if (nt_username) { 
655                 DEBUG(10, ("pdb_set_nt_username: setting nt username %s, was %s\n", nt_username,
656                         (sampass->private.nt_username)?(sampass->private.nt_username):"NULL"));
657  
658                 sampass->private.nt_username = talloc_strdup(sampass->mem_ctx, nt_username);
659                 
660                 if (!sampass->private.nt_username) {
661                         DEBUG(0, ("pdb_set_nt_username: talloc_strdup() failed!\n"));
662                         return False;
663                 }
664
665         } else {
666                 sampass->private.nt_username = PDB_NOT_QUITE_NULL;
667         }
668
669         return True;
670 }
671
672 /*********************************************************************
673  Set the user's full name.
674  ********************************************************************/
675
676 BOOL pdb_set_fullname(SAM_ACCOUNT *sampass, const char *full_name)
677 {
678         if (!sampass)
679                 return False;
680
681         if (full_name) { 
682                 DEBUG(10, ("pdb_set_full_name: setting full name %s, was %s\n", full_name,
683                         (sampass->private.full_name)?(sampass->private.full_name):"NULL"));
684         
685                 sampass->private.full_name = talloc_strdup(sampass->mem_ctx, full_name);
686
687                 if (!sampass->private.full_name) {
688                         DEBUG(0, ("pdb_set_fullname: talloc_strdup() failed!\n"));
689                         return False;
690                 }
691
692         } else {
693                 sampass->private.full_name = PDB_NOT_QUITE_NULL;
694         }
695
696         return True;
697 }
698
699 /*********************************************************************
700  Set the user's logon script.
701  ********************************************************************/
702
703 BOOL pdb_set_logon_script(SAM_ACCOUNT *sampass, const char *logon_script, BOOL store)
704 {
705         if (!sampass)
706                 return False;
707
708         if (logon_script) { 
709                 DEBUG(10, ("pdb_set_logon_script: setting logon script %s, was %s\n", logon_script,
710                         (sampass->private.logon_script)?(sampass->private.logon_script):"NULL"));
711  
712                 sampass->private.logon_script = talloc_strdup(sampass->mem_ctx, logon_script);
713
714                 if (!sampass->private.logon_script) {
715                         DEBUG(0, ("pdb_set_logon_script: talloc_strdup() failed!\n"));
716                         return False;
717                 }
718
719         } else {
720                 sampass->private.logon_script = PDB_NOT_QUITE_NULL;
721         }
722         
723         if (store) {
724                 DEBUG(10, ("pdb_set_logon_script: setting logon script sam flag!\n"));
725                 pdb_set_init_flag(sampass, FLAG_SAM_LOGONSCRIPT);
726         }
727
728         return True;
729 }
730
731 /*********************************************************************
732  Set the user's profile path.
733  ********************************************************************/
734
735 BOOL pdb_set_profile_path (SAM_ACCOUNT *sampass, const char *profile_path, BOOL store)
736 {
737         if (!sampass)
738                 return False;
739
740         if (profile_path) { 
741                 DEBUG(10, ("pdb_set_profile_path: setting profile path %s, was %s\n", profile_path,
742                         (sampass->private.profile_path)?(sampass->private.profile_path):"NULL"));
743  
744                 sampass->private.profile_path = talloc_strdup(sampass->mem_ctx, profile_path);
745                 
746                 if (!sampass->private.profile_path) {
747                         DEBUG(0, ("pdb_set_profile_path: talloc_strdup() failed!\n"));
748                         return False;
749                 }
750
751         } else {
752                 sampass->private.profile_path = PDB_NOT_QUITE_NULL;
753         }
754
755         if (store) {
756                 DEBUG(10, ("pdb_set_profile_path: setting profile path sam flag!\n"));
757                 pdb_set_init_flag(sampass, FLAG_SAM_PROFILE);
758         }
759
760         return True;
761 }
762
763 /*********************************************************************
764  Set the user's directory drive.
765  ********************************************************************/
766
767 BOOL pdb_set_dir_drive (SAM_ACCOUNT *sampass, const char *dir_drive, BOOL store)
768 {
769         if (!sampass)
770                 return False;
771
772         if (dir_drive) { 
773                 DEBUG(10, ("pdb_set_dir_drive: setting dir drive %s, was %s\n", dir_drive,
774                         (sampass->private.dir_drive)?(sampass->private.dir_drive):"NULL"));
775  
776                 sampass->private.dir_drive = talloc_strdup(sampass->mem_ctx, dir_drive);
777                 
778                 if (!sampass->private.dir_drive) {
779                         DEBUG(0, ("pdb_set_dir_drive: talloc_strdup() failed!\n"));
780                         return False;
781                 }
782
783         } else {
784                 sampass->private.dir_drive = PDB_NOT_QUITE_NULL;
785         }
786         
787         if (store) {
788                 DEBUG(10, ("pdb_set_dir_drive: setting dir drive sam flag!\n"));
789                 pdb_set_init_flag(sampass, FLAG_SAM_DRIVE);
790         }
791
792         return True;
793 }
794
795 /*********************************************************************
796  Set the user's home directory.
797  ********************************************************************/
798
799 BOOL pdb_set_homedir (SAM_ACCOUNT *sampass, const char *home_dir, BOOL store)
800 {
801         if (!sampass)
802                 return False;
803
804         if (home_dir) { 
805                 DEBUG(10, ("pdb_set_homedir: setting home dir %s, was %s\n", home_dir,
806                         (sampass->private.home_dir)?(sampass->private.home_dir):"NULL"));
807  
808                 sampass->private.home_dir = talloc_strdup(sampass->mem_ctx, home_dir);
809                 
810                 if (!sampass->private.home_dir) {
811                         DEBUG(0, ("pdb_set_home_dir: talloc_strdup() failed!\n"));
812                         return False;
813                 }
814
815         } else {
816                 sampass->private.home_dir = PDB_NOT_QUITE_NULL;
817         }
818
819         if (store) {
820                 DEBUG(10, ("pdb_set_homedir: setting home dir sam flag!"));
821                 pdb_set_init_flag(sampass, FLAG_SAM_SMBHOME);
822         }
823
824         return True;
825 }
826
827 /*********************************************************************
828  Set the user's unix home directory.
829  ********************************************************************/
830
831 BOOL pdb_set_unix_homedir (SAM_ACCOUNT *sampass, const char *unix_home_dir)
832 {
833         if (!sampass)
834                 return False;
835
836         if (unix_home_dir) { 
837                 DEBUG(10, ("pdb_set_homedir: setting home dir %s, was %s\n", unix_home_dir,
838                         (sampass->private.unix_home_dir)?(sampass->private.unix_home_dir):"NULL"));
839  
840                 sampass->private.unix_home_dir = talloc_strdup(sampass->mem_ctx, 
841                                                           unix_home_dir);
842                 
843                 if (!sampass->private.unix_home_dir) {
844                         DEBUG(0, ("pdb_set_unix_home_dir: talloc_strdup() failed!\n"));
845                         return False;
846                 }
847
848         } else {
849                 sampass->private.unix_home_dir = PDB_NOT_QUITE_NULL;
850         }
851
852         return True;
853 }
854
855 /*********************************************************************
856  Set the user's account description.
857  ********************************************************************/
858
859 BOOL pdb_set_acct_desc (SAM_ACCOUNT *sampass, const char *acct_desc)
860 {
861         if (!sampass)
862                 return False;
863
864         if (acct_desc) { 
865                 sampass->private.acct_desc = talloc_strdup(sampass->mem_ctx, acct_desc);
866
867                 if (!sampass->private.acct_desc) {
868                         DEBUG(0, ("pdb_set_acct_desc: talloc_strdup() failed!\n"));
869                         return False;
870                 }
871
872         } else {
873                 sampass->private.acct_desc = PDB_NOT_QUITE_NULL;
874         }
875
876         return True;
877 }
878
879 /*********************************************************************
880  Set the user's workstation allowed list.
881  ********************************************************************/
882
883 BOOL pdb_set_workstations (SAM_ACCOUNT *sampass, const char *workstations)
884 {
885         if (!sampass)
886                 return False;
887
888         if (workstations) { 
889                 DEBUG(10, ("pdb_set_workstations: setting workstations %s, was %s\n", workstations,
890                         (sampass->private.workstations)?(sampass->private.workstations):"NULL"));
891  
892                 sampass->private.workstations = talloc_strdup(sampass->mem_ctx, workstations);
893
894                 if (!sampass->private.workstations) {
895                         DEBUG(0, ("pdb_set_workstations: talloc_strdup() failed!\n"));
896                         return False;
897                 }
898
899         } else {
900                 sampass->private.workstations = PDB_NOT_QUITE_NULL;
901         }
902
903         return True;
904 }
905
906 /*********************************************************************
907  Set the user's 'unknown_str', whatever the heck this actually is...
908  ********************************************************************/
909
910 BOOL pdb_set_unknown_str (SAM_ACCOUNT *sampass, const char *unknown_str)
911 {
912         if (!sampass)
913                 return False;
914
915         if (unknown_str) { 
916                 sampass->private.unknown_str = talloc_strdup(sampass->mem_ctx, unknown_str);
917                 
918                 if (!sampass->private.unknown_str) {
919                         DEBUG(0, ("pdb_set_unknown_str: talloc_strdup() failed!\n"));
920                         return False;
921                 }
922
923         } else {
924                 sampass->private.unknown_str = PDB_NOT_QUITE_NULL;
925         }
926
927         return True;
928 }
929
930 /*********************************************************************
931  Set the user's dial string.
932  ********************************************************************/
933
934 BOOL pdb_set_munged_dial (SAM_ACCOUNT *sampass, const char *munged_dial)
935 {
936         if (!sampass)
937                 return False;
938
939         if (munged_dial) { 
940                 sampass->private.munged_dial = talloc_strdup(sampass->mem_ctx, munged_dial);
941                 
942                 if (!sampass->private.munged_dial) {
943                         DEBUG(0, ("pdb_set_munged_dial: talloc_strdup() failed!\n"));
944                         return False;
945                 }
946
947         } else {
948                 sampass->private.munged_dial = PDB_NOT_QUITE_NULL;
949         }
950
951         return True;
952 }
953
954 /*********************************************************************
955  Set the user's NT hash.
956  ********************************************************************/
957
958 BOOL pdb_set_nt_passwd (SAM_ACCOUNT *sampass, const uint8 *pwd)
959 {
960         if (!sampass)
961                 return False;
962
963         data_blob_clear_free(&sampass->private.nt_pw);
964         
965         sampass->private.nt_pw = data_blob(pwd, NT_HASH_LEN);
966
967         return True;
968 }
969
970 /*********************************************************************
971  Set the user's LM hash.
972  ********************************************************************/
973
974 BOOL pdb_set_lanman_passwd (SAM_ACCOUNT *sampass, const uint8 pwd[16])
975 {
976         if (!sampass)
977                 return False;
978
979         data_blob_clear_free(&sampass->private.lm_pw);
980         
981         sampass->private.lm_pw = data_blob(pwd, LM_HASH_LEN);
982
983         return True;
984 }
985
986 /*********************************************************************
987  Set the user's plaintext password only (base procedure, see helper
988  below)
989  ********************************************************************/
990
991 BOOL pdb_set_plaintext_pw_only (SAM_ACCOUNT *sampass, const uint8 *password, size_t len)
992 {
993         if (!sampass)
994                 return False;
995
996         data_blob_clear_free(&sampass->private.plaintext_pw);
997         
998         sampass->private.plaintext_pw = data_blob(password, len);
999
1000         return True;
1001 }
1002
1003 BOOL pdb_set_unknown_3 (SAM_ACCOUNT *sampass, uint32 unkn)
1004 {
1005         if (!sampass)
1006                 return False;
1007
1008         sampass->private.unknown_3 = unkn;
1009         return True;
1010 }
1011
1012 BOOL pdb_set_unknown_5 (SAM_ACCOUNT *sampass, uint32 unkn)
1013 {
1014         if (!sampass)
1015                 return False;
1016
1017         sampass->private.unknown_5 = unkn;
1018         return True;
1019 }
1020
1021 BOOL pdb_set_unknown_6 (SAM_ACCOUNT *sampass, uint32 unkn)
1022 {
1023         if (!sampass)
1024                 return False;
1025
1026         sampass->private.unknown_6 = unkn;
1027         return True;
1028 }
1029
1030 BOOL pdb_set_hours (SAM_ACCOUNT *sampass, const uint8 *hours)
1031 {
1032         if (!sampass)
1033                 return False;
1034
1035         if (!hours) {
1036                 memset ((char *)sampass->private.hours, 0, MAX_HOURS_LEN);
1037                 return True;
1038         }
1039         
1040         memcpy (sampass->private.hours, hours, MAX_HOURS_LEN);
1041
1042         return True;
1043 }
1044
1045
1046 /* Helpful interfaces to the above */
1047
1048 /*********************************************************************
1049  Sets the last changed times and must change times for a normal
1050  password change.
1051  ********************************************************************/
1052
1053 BOOL pdb_set_pass_changed_now (SAM_ACCOUNT *sampass)
1054 {
1055         uint32 expire;
1056
1057         if (!sampass)
1058                 return False;
1059         
1060         if (!pdb_set_pass_last_set_time (sampass, time(NULL)))
1061                 return False;
1062
1063         account_policy_get(AP_MAX_PASSWORD_AGE, &expire);
1064
1065         if (expire==(uint32)-1) {
1066                 if (!pdb_set_pass_must_change_time (sampass, get_time_t_max(), False))
1067                         return False;
1068         } else {
1069                 if (!pdb_set_pass_must_change_time (sampass, 
1070                                             pdb_get_pass_last_set_time(sampass)
1071                                             + expire, True))
1072                         return False;
1073         }
1074         
1075         return True;
1076 }
1077
1078 /*********************************************************************
1079  Set the user's PLAINTEXT password.  Used as an interface to the above.
1080  Also sets the last change time to NOW.
1081  ********************************************************************/
1082
1083 BOOL pdb_set_plaintext_passwd (SAM_ACCOUNT *sampass, const char *plaintext)
1084 {
1085         uchar new_lanman_p16[16];
1086         uchar new_nt_p16[16];
1087
1088         if (!sampass || !plaintext)
1089                 return False;
1090         
1091         nt_lm_owf_gen (plaintext, new_nt_p16, new_lanman_p16);
1092
1093         if (!pdb_set_nt_passwd (sampass, new_nt_p16)) 
1094                 return False;
1095
1096         if (!pdb_set_lanman_passwd (sampass, new_lanman_p16)) 
1097                 return False;
1098         
1099         if (!pdb_set_pass_changed_now (sampass))
1100                 return False;
1101
1102         return True;
1103 }
1104