s3-passdb: Return assigned number of hours and not MAX_HOURS_LEN
[rusty/samba.git] / source3 / passdb / py_passdb.c
1 /*
2    Python interface to passdb
3
4    Copyright (C) Amitay Isaacs 2011
5
6    This program is free software; you can redistribute it and/or modify
7    it under the terms of the GNU General Public License as published by
8    the Free Software Foundation; either version 3 of the License, or
9    (at your option) any later version.
10
11    This program is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15
16    You should have received a copy of the GNU General Public License
17    along with this program.  If not, see <http://www.gnu.org/licenses/>.
18 */
19
20 #include <Python.h>
21 #include <pytalloc.h>
22 #include "includes.h"
23 #include "lib/util/talloc_stack.h"
24 #include "libcli/security/security.h"
25 #include "passdb.h"
26 #include "secrets.h"
27
28 /* There's no Py_ssize_t in 2.4, apparently */
29 #if PY_MAJOR_VERSION == 2 && PY_MINOR_VERSION < 5
30 typedef int Py_ssize_t;
31 typedef inquiry lenfunc;
32 typedef intargfunc ssizeargfunc;
33 #endif
34
35 #ifndef Py_RETURN_NONE
36 #define Py_RETURN_NONE  return Py_INCREF(Py_None), Py_None
37 #endif
38
39 #ifndef Py_TYPE /* Py_TYPE is only available on Python > 2.6 */
40 #define Py_TYPE(ob)             (((PyObject*)(ob))->ob_type)
41 #endif
42
43 #ifndef PY_CHECK_TYPE
44 #define PY_CHECK_TYPE(type, var, fail) \
45         if (!PyObject_TypeCheck(var, type)) {\
46                 PyErr_Format(PyExc_TypeError, __location__ ": Expected type '%s' for '%s' of type '%s'", (type)->tp_name, #var, Py_TYPE(var)->tp_name); \
47                 fail; \
48         }
49 #endif
50
51
52 static PyTypeObject *dom_sid_Type = NULL;
53 static PyTypeObject *security_Type = NULL;
54 static PyTypeObject *guid_Type = NULL;
55
56 staticforward PyTypeObject PySamu;
57 staticforward PyTypeObject PyGroupmap;
58 staticforward PyTypeObject PyPDB;
59
60 static PyObject *py_pdb_error;
61
62 void initpassdb(void);
63
64
65 /************************** PIDL Autogeneratd ******************************/
66
67 static PyObject *py_samu_get_logon_time(PyObject *obj, void *closure)
68 {
69         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
70         PyObject *py_logon_time;
71
72         py_logon_time = PyInt_FromLong(pdb_get_logon_time(sam_acct));
73         return py_logon_time;
74 }
75
76 static int py_samu_set_logon_time(PyObject *obj, PyObject *value, void *closure)
77 {
78         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
79
80         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
81         if (!pdb_set_logon_time(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
82                 return -1;
83         }
84         return 0;
85 }
86
87 static PyObject *py_samu_get_logoff_time(PyObject *obj, void *closure)
88 {
89         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
90         PyObject *py_logoff_time;
91
92         py_logoff_time = PyInt_FromLong(pdb_get_logoff_time(sam_acct));
93         return py_logoff_time;
94 }
95
96 static int py_samu_set_logoff_time(PyObject *obj, PyObject *value, void *closure)
97 {
98         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
99
100         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
101         if (!pdb_set_logoff_time(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
102                 return -1;
103         }
104         return 0;
105 }
106
107 static PyObject *py_samu_get_kickoff_time(PyObject *obj, void *closure)
108 {
109         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
110         PyObject *py_kickoff_time;
111
112         py_kickoff_time = PyInt_FromLong(pdb_get_kickoff_time(sam_acct));
113         return py_kickoff_time;
114 }
115
116 static int py_samu_set_kickoff_time(PyObject *obj, PyObject *value, void *closure)
117 {
118         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
119
120         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
121         if (!pdb_set_kickoff_time(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
122                 return -1;
123         }
124         return 0;
125 }
126
127 static PyObject *py_samu_get_bad_password_time(PyObject *obj, void *closure)
128 {
129         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
130         PyObject *py_bad_password_time;
131
132         py_bad_password_time = PyInt_FromLong(pdb_get_bad_password_time(sam_acct));
133         return py_bad_password_time;
134 }
135
136 static int py_samu_set_bad_password_time(PyObject *obj, PyObject *value, void *closure)
137 {
138         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
139
140         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
141         if (!pdb_set_bad_password_time(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
142                 return -1;
143         }
144         return 0;
145 }
146
147 static PyObject *py_samu_get_pass_last_set_time(PyObject *obj, void *closure)
148 {
149         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
150         PyObject *py_pass_last_set_time;
151
152         py_pass_last_set_time = PyInt_FromLong(pdb_get_pass_last_set_time(sam_acct));
153         return py_pass_last_set_time;
154 }
155
156 static int py_samu_set_pass_last_set_time(PyObject *obj, PyObject *value, void *closure)
157 {
158         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
159
160         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
161         if (!pdb_set_pass_last_set_time(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
162                 return -1;
163         }
164         return 0;
165 }
166
167 static PyObject *py_samu_get_pass_can_change_time(PyObject *obj, void *closure)
168 {
169         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
170         PyObject *py_pass_can_change_time;
171
172         py_pass_can_change_time = PyInt_FromLong(pdb_get_pass_can_change_time(sam_acct));
173         return py_pass_can_change_time;
174 }
175
176 static int py_samu_set_pass_can_change_time(PyObject *obj, PyObject *value, void *closure)
177 {
178         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
179
180         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
181         if (!pdb_set_pass_can_change_time(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
182                 return -1;
183         }
184         return 0;
185 }
186
187 static PyObject *py_samu_get_pass_must_change_time(PyObject *obj, void *closure)
188 {
189         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
190         PyObject *py_pass_must_change_time;
191
192         py_pass_must_change_time = PyInt_FromLong(pdb_get_pass_must_change_time(sam_acct));
193         return py_pass_must_change_time;
194 }
195
196 static int py_samu_set_pass_must_change_time(PyObject *obj, PyObject *value, void *closure)
197 {
198         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
199
200         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
201         if (!pdb_set_pass_must_change_time(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
202                 return -1;
203         }
204         return 0;
205 }
206
207 static PyObject *py_samu_get_username(PyObject *obj, void *closure)
208 {
209         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
210         PyObject *py_username;
211         const char *username;
212
213         username = pdb_get_username(sam_acct);
214         if (username == NULL) {
215                 Py_RETURN_NONE;
216         }
217
218         py_username = PyString_FromString(username);
219         return py_username;
220 }
221
222 static int py_samu_set_username(PyObject *obj, PyObject *value, void *closure)
223 {
224         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
225
226         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
227         if (!pdb_set_username(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
228                 return -1;
229         }
230         return 0;
231 }
232
233 static PyObject *py_samu_get_domain(PyObject *obj, void *closure)
234 {
235         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
236         PyObject *py_domain;
237         const char *domain;
238
239         domain = pdb_get_domain(sam_acct);
240         if (domain == NULL) {
241                 Py_RETURN_NONE;
242         }
243
244         py_domain = PyString_FromString(domain);
245         return py_domain;
246 }
247
248 static int py_samu_set_domain(PyObject *obj, PyObject *value, void *closure)
249 {
250         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
251
252         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
253         if (!pdb_set_domain(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
254                 return -1;
255         }
256         return 0;
257 }
258
259 static PyObject *py_samu_get_nt_username(PyObject *obj, void *closure)
260 {
261         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
262         PyObject *py_nt_username;
263         const char *nt_username;
264
265         nt_username = pdb_get_nt_username(sam_acct);
266         if (nt_username == NULL) {
267                 Py_RETURN_NONE;
268         }
269
270         py_nt_username = PyString_FromString(nt_username);
271         return py_nt_username;
272 }
273
274 static int py_samu_set_nt_username(PyObject *obj, PyObject *value, void *closure)
275 {
276         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
277
278         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
279         if (!pdb_set_nt_username(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
280                 return -1;
281         }
282         return 0;
283 }
284
285 static PyObject *py_samu_get_full_name(PyObject *obj, void *closure)
286 {
287         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
288         PyObject *py_full_name;
289         const char *full_name;
290
291         full_name = pdb_get_fullname(sam_acct);
292         if (full_name == NULL) {
293                 Py_RETURN_NONE;
294         }
295
296         py_full_name = PyString_FromString(full_name);
297         return py_full_name;
298 }
299
300 static int py_samu_set_full_name(PyObject *obj, PyObject *value, void *closure)
301 {
302         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
303
304         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
305         if (!pdb_set_fullname(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
306                 return -1;
307         }
308         return 0;
309 }
310
311 static PyObject *py_samu_get_home_dir(PyObject *obj, void *closure)
312 {
313         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
314         PyObject *py_home_dir;
315         const char *home_dir;
316
317         home_dir = pdb_get_homedir(sam_acct);
318         if (home_dir == NULL) {
319                 Py_RETURN_NONE;
320         }
321
322         py_home_dir = PyString_FromString(home_dir);
323         return py_home_dir;
324 }
325
326 static int py_samu_set_home_dir(PyObject *obj, PyObject *value, void *closure)
327 {
328         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
329
330         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
331         if (!pdb_set_homedir(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
332                 return -1;
333         }
334         return 0;
335 }
336
337 static PyObject *py_samu_get_dir_drive(PyObject *obj, void *closure)
338 {
339         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
340         PyObject *py_dir_drive;
341         const char *dir_drive;
342
343         dir_drive = pdb_get_dir_drive(sam_acct);
344         if (dir_drive == NULL) {
345                 Py_RETURN_NONE;
346         }
347
348         py_dir_drive = PyString_FromString(dir_drive);
349         return py_dir_drive;
350 }
351
352 static int py_samu_set_dir_drive(PyObject *obj, PyObject *value, void *closure)
353 {
354         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
355
356         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
357         if (!pdb_set_dir_drive(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
358                 return -1;
359         }
360         return 0;
361 }
362
363 static PyObject *py_samu_get_logon_script(PyObject *obj, void *closure)
364 {
365         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
366         PyObject *py_logon_script;
367         const char *logon_script;
368
369         logon_script = pdb_get_logon_script(sam_acct);
370         if (logon_script == NULL) {
371                 Py_RETURN_NONE;
372         }
373
374         py_logon_script = PyString_FromString(logon_script);
375         return py_logon_script;
376 }
377
378 static int py_samu_set_logon_script(PyObject *obj, PyObject *value, void *closure)
379 {
380         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
381
382         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
383         if (!pdb_set_logon_script(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
384                 return -1;
385         }
386         return 0;
387 }
388
389 static PyObject *py_samu_get_profile_path(PyObject *obj, void *closure)
390 {
391         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
392         PyObject *py_profile_path;
393         const char *profile_path;
394
395         profile_path = pdb_get_profile_path(sam_acct);
396         if (profile_path == NULL) {
397                 Py_RETURN_NONE;
398         }
399
400         py_profile_path = PyString_FromString(profile_path);
401         return py_profile_path;
402 }
403
404 static int py_samu_set_profile_path(PyObject *obj, PyObject *value, void *closure)
405 {
406         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
407
408         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
409         if (!pdb_set_profile_path(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
410                 return -1;
411         }
412         return 0;
413 }
414
415 static PyObject *py_samu_get_acct_desc(PyObject *obj, void *closure)
416 {
417         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
418         PyObject *py_acct_desc;
419         const char *acct_desc;
420
421         acct_desc = pdb_get_acct_desc(sam_acct);
422         if (acct_desc == NULL) {
423                 Py_RETURN_NONE;
424         }
425
426         py_acct_desc = PyString_FromString(acct_desc);
427         return py_acct_desc;
428 }
429
430 static int py_samu_set_acct_desc(PyObject *obj, PyObject *value, void *closure)
431 {
432         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
433
434         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
435         if (!pdb_set_acct_desc(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
436                 return -1;
437         }
438         return 0;
439 }
440
441 static PyObject *py_samu_get_workstations(PyObject *obj, void *closure)
442 {
443         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
444         PyObject *py_workstations;
445         const char *workstations;
446
447         workstations = pdb_get_workstations(sam_acct);
448         if (workstations == NULL) {
449                 Py_RETURN_NONE;
450         }
451
452         py_workstations = PyString_FromString(workstations);
453         return py_workstations;
454 }
455
456 static int py_samu_set_workstations(PyObject *obj, PyObject *value, void *closure)
457 {
458         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
459
460         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
461         if (!pdb_set_workstations(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
462                 return -1;
463         }
464         return 0;
465 }
466
467 static PyObject *py_samu_get_comment(PyObject *obj, void *closure)
468 {
469         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
470         PyObject *py_comment;
471         const char *comment;
472
473         comment = pdb_get_comment(sam_acct);
474         if (comment == NULL) {
475                 Py_RETURN_NONE;
476         }
477
478         py_comment = PyString_FromString(comment);
479         return py_comment;
480 }
481
482 static int py_samu_set_comment(PyObject *obj, PyObject *value, void *closure)
483 {
484         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
485
486         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
487         if (!pdb_set_comment(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
488                 return -1;
489         }
490         return 0;
491 }
492
493 static PyObject *py_samu_get_munged_dial(PyObject *obj, void *closure)
494 {
495         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
496         PyObject *py_munged_dial;
497         const char *munged_dial;
498
499         munged_dial = pdb_get_munged_dial(sam_acct);
500         if (munged_dial == NULL) {
501                 Py_RETURN_NONE;
502         }
503
504         py_munged_dial = PyString_FromString(munged_dial);
505         return py_munged_dial;
506 }
507
508 static int py_samu_set_munged_dial(PyObject *obj, PyObject *value, void *closure)
509 {
510         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
511
512         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
513         if (!pdb_set_munged_dial(sam_acct, PyString_AsString(value), PDB_CHANGED)) {
514                 return -1;
515         }
516         return 0;
517 }
518
519 static PyObject *py_samu_get_user_sid(PyObject *obj, void *closure)
520 {
521         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
522         PyObject *py_user_sid;
523         const struct dom_sid *user_sid;
524         struct dom_sid *copy_user_sid;
525         TALLOC_CTX *mem_ctx;
526
527         user_sid = pdb_get_user_sid(sam_acct);
528         if(user_sid == NULL) {
529                 Py_RETURN_NONE;
530         }
531
532         mem_ctx = talloc_new(NULL);
533         if (mem_ctx == NULL) {
534                 PyErr_NoMemory();
535                 return NULL;
536         }
537         copy_user_sid = dom_sid_dup(mem_ctx, user_sid);
538         if (copy_user_sid == NULL) {
539                 PyErr_NoMemory();
540                 talloc_free(mem_ctx);
541                 return NULL;
542         }
543
544         py_user_sid = pytalloc_steal(dom_sid_Type, copy_user_sid);
545
546         talloc_free(mem_ctx);
547
548         return py_user_sid;
549 }
550
551 static int py_samu_set_user_sid(PyObject *obj, PyObject *value, void *closure)
552 {
553         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
554
555         PY_CHECK_TYPE(dom_sid_Type, value, return -1;);
556         if (!pdb_set_user_sid(sam_acct, (struct dom_sid *)pytalloc_get_ptr(value), PDB_CHANGED)) {
557                 return -1;
558         }
559         return 0;
560 }
561
562 static PyObject *py_samu_get_group_sid(PyObject *obj, void *closure)
563 {
564         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
565         PyObject *py_group_sid;
566         const struct dom_sid *group_sid;
567         struct dom_sid *copy_group_sid;
568         TALLOC_CTX *mem_ctx;
569
570         group_sid = pdb_get_group_sid(sam_acct);
571         if (group_sid == NULL) {
572                 Py_RETURN_NONE;
573         }
574
575         mem_ctx = talloc_new(NULL);
576         if (mem_ctx == NULL) {
577                 PyErr_NoMemory();
578                 return NULL;
579         }
580         copy_group_sid = dom_sid_dup(mem_ctx, group_sid);
581         if (copy_group_sid == NULL) {
582                 PyErr_NoMemory();
583                 talloc_free(mem_ctx);
584                 return NULL;
585         }
586
587         py_group_sid = pytalloc_steal(dom_sid_Type, copy_group_sid);
588
589         talloc_free(mem_ctx);
590
591         return py_group_sid;
592 }
593
594 static int py_samu_set_group_sid(PyObject *obj, PyObject *value, void *closure)
595 {
596         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
597
598         PY_CHECK_TYPE(dom_sid_Type, value, return -1;);
599         if (!pdb_set_group_sid(sam_acct, (struct dom_sid *)pytalloc_get_ptr(value), PDB_CHANGED)) {
600                 return -1;
601         }
602         return 0;
603 }
604
605 static PyObject *py_samu_get_lanman_passwd(PyObject *obj, void *closure)
606 {
607         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
608         PyObject *py_lm_pw;
609         const char *lm_pw;
610
611         lm_pw = (const char *)pdb_get_lanman_passwd(sam_acct);
612         if (lm_pw == NULL) {
613                 Py_RETURN_NONE;
614         }
615
616         py_lm_pw = PyString_FromStringAndSize(lm_pw, LM_HASH_LEN);
617         return py_lm_pw;
618 }
619
620 static int py_samu_set_lanman_passwd(PyObject *obj, PyObject *value, void *closure)
621 {
622         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
623
624         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
625         if (!pdb_set_lanman_passwd(sam_acct, (uint8_t *)PyString_AsString(value), PDB_CHANGED)) {
626                 return -1;
627         }
628         return 0;
629 }
630
631 static PyObject *py_samu_get_nt_passwd(PyObject *obj, void *closure)
632 {
633         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
634         PyObject *py_nt_pw;
635         const char *nt_pw;
636
637         nt_pw = (const char *)pdb_get_nt_passwd(sam_acct);
638         if (nt_pw == NULL) {
639                 Py_RETURN_NONE;
640         }
641
642         py_nt_pw = PyString_FromStringAndSize(nt_pw, NT_HASH_LEN);
643         return py_nt_pw;
644 }
645
646 static int py_samu_set_nt_passwd(PyObject *obj, PyObject *value, void *closure)
647 {
648         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
649
650         if (!pdb_set_nt_passwd(sam_acct, (uint8_t *)PyString_AsString(value), PDB_CHANGED)) {
651                 return -1;
652         }
653         return 0;
654 }
655
656 static PyObject *py_samu_get_pw_history(PyObject *obj, void *closure)
657 {
658         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
659         PyObject *py_nt_pw_his;
660         const char *nt_pw_his;
661         uint32_t hist_len;
662
663         nt_pw_his = (const char *)pdb_get_pw_history(sam_acct, &hist_len);
664         if (nt_pw_his == NULL) {
665                 Py_RETURN_NONE;
666         }
667
668         py_nt_pw_his = PyString_FromStringAndSize(nt_pw_his, hist_len*PW_HISTORY_ENTRY_LEN);
669         return py_nt_pw_his;
670 }
671
672 static int py_samu_set_pw_history(PyObject *obj, PyObject *value, void *closure)
673 {
674         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
675         char *nt_pw_his;
676         Py_ssize_t len;
677         uint32_t hist_len;
678
679         PyString_AsStringAndSize(value, &nt_pw_his, &len);
680         hist_len = len / PW_HISTORY_ENTRY_LEN;
681         if (!pdb_set_pw_history(sam_acct, (uint8_t *)nt_pw_his, hist_len, PDB_CHANGED)) {
682                 return -1;
683         }
684         return 0;
685 }
686
687 static PyObject *py_samu_get_plaintext_passwd(PyObject *obj, void *closure)
688 {
689         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
690         PyObject *py_plaintext_pw;
691         const char *plaintext_pw;
692
693         plaintext_pw = pdb_get_plaintext_passwd(sam_acct);
694         if (plaintext_pw == NULL) {
695                 Py_RETURN_NONE;
696         }
697
698         py_plaintext_pw = PyString_FromString(plaintext_pw);
699         return py_plaintext_pw;
700 }
701
702 static int py_samu_set_plaintext_passwd(PyObject *obj, PyObject *value, void *closure)
703 {
704         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
705
706         if (!pdb_set_plaintext_passwd(sam_acct, PyString_AsString(value))) {
707                 return -1;
708         }
709         return 0;
710 }
711
712 static PyObject *py_samu_get_acct_ctrl(PyObject *obj, void *closure)
713 {
714         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
715         PyObject *py_acct_ctrl;
716
717         py_acct_ctrl = PyInt_FromLong(pdb_get_acct_ctrl(sam_acct));
718         return py_acct_ctrl;
719 }
720
721 static int py_samu_set_acct_ctrl(PyObject *obj, PyObject *value, void *closure)
722 {
723         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
724
725         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
726         if (!pdb_set_acct_ctrl(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
727                 return -1;
728         }
729         return 0;
730 }
731
732 static PyObject *py_samu_get_logon_divs(PyObject *obj, void *closure)
733 {
734         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
735         PyObject *py_logon_divs;
736
737         py_logon_divs = PyInt_FromLong(pdb_get_logon_divs(sam_acct));
738         return py_logon_divs;
739 }
740
741 static int py_samu_set_logon_divs(PyObject *obj, PyObject *value, void *closure)
742 {
743         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
744
745         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
746         if (!pdb_set_logon_divs(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
747                 return -1;
748         }
749         return 0;
750 }
751
752 static PyObject *py_samu_get_hours_len(PyObject *obj, void *closure)
753 {
754         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
755         PyObject *py_hours_len;
756
757         py_hours_len = PyInt_FromLong(pdb_get_hours_len(sam_acct));
758         return py_hours_len;
759 }
760
761 static int py_samu_set_hours_len(PyObject *obj, PyObject *value, void *closure)
762 {
763         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
764
765         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
766         if (!pdb_set_hours_len(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
767                 return -1;
768         }
769         return 0;
770 }
771
772 static PyObject *py_samu_get_hours(PyObject *obj, void *closure)
773 {
774         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
775         PyObject *py_hours;
776         const char *hours;
777         int hours_len, i;
778
779         hours = (const char *)pdb_get_hours(sam_acct);
780         if(! hours) {
781                 Py_RETURN_NONE;
782         }
783
784         hours_len = pdb_get_hours_len(sam_acct);
785         if ((py_hours = PyList_New(hours_len)) == NULL) {
786                 PyErr_NoMemory();
787                 return NULL;
788         }
789
790         for (i=0; i<hours_len; i++) {
791                 PyList_SetItem(py_hours, i, PyInt_FromLong(hours[i]));
792         }
793         return py_hours;
794 }
795
796 static int py_samu_set_hours(PyObject *obj, PyObject *value, void *closure)
797 {
798         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
799         int i;
800         uint8_t *hours;
801         int hours_len;
802         bool status;
803
804         PY_CHECK_TYPE(&PyList_Type, value, return -1;);
805
806         hours_len = PyList_GET_SIZE(value);
807
808         hours = talloc_array(pytalloc_get_mem_ctx(obj), uint8_t, hours_len);
809         if (!hours) {
810                 PyErr_NoMemory();
811                 return -1;
812         }
813
814         for (i=0; i < hours_len; i++) {
815                 PY_CHECK_TYPE(&PyInt_Type, PyList_GET_ITEM(value,i), return -1;);
816                 hours[i] = PyInt_AsLong(PyList_GET_ITEM(value, i));
817         }
818
819         status = pdb_set_hours(sam_acct, hours, hours_len, PDB_CHANGED);
820         talloc_free(hours);
821
822         if(! status) {
823                 return -1;
824         }
825         return 0;
826 }
827
828 static PyObject *py_samu_get_bad_password_count(PyObject *obj, void *closure)
829 {
830         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
831         PyObject *py_bad_password_count;
832
833         py_bad_password_count = PyInt_FromLong(pdb_get_bad_password_count(sam_acct));
834         return py_bad_password_count;
835 }
836
837 static int py_samu_set_bad_password_count(PyObject *obj, PyObject *value, void *closure)
838 {
839         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
840
841         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
842         if (!pdb_set_bad_password_count(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
843                 return -1;
844         }
845         return 0;
846 }
847
848 static PyObject *py_samu_get_logon_count(PyObject *obj, void *closure)
849 {
850         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
851         PyObject *py_logon_count;
852
853         py_logon_count = PyInt_FromLong(pdb_get_logon_count(sam_acct));
854         return py_logon_count;
855 }
856
857 static int py_samu_set_logon_count(PyObject *obj, PyObject *value, void *closure)
858 {
859         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
860
861         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
862         if (!pdb_set_logon_count(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
863                 return -1;
864         }
865         return 0;
866 }
867
868 static PyObject *py_samu_get_country_code(PyObject *obj, void *closure)
869 {
870         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
871         PyObject *py_country_code;
872
873         py_country_code = PyInt_FromLong(pdb_get_country_code(sam_acct));
874         return py_country_code;
875 }
876
877 static int py_samu_set_country_code(PyObject *obj, PyObject *value, void *closure)
878 {
879         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
880
881         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
882         if (!pdb_set_country_code(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
883                 return -1;
884         }
885         return 0;
886 }
887
888 static PyObject *py_samu_get_code_page(PyObject *obj, void *closure)
889 {
890         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
891         PyObject *py_code_page;
892
893         py_code_page = PyInt_FromLong(pdb_get_code_page(sam_acct));
894         return py_code_page;
895 }
896
897 static int py_samu_set_code_page(PyObject *obj, PyObject *value, void *closure)
898 {
899         struct samu *sam_acct = (struct samu *)pytalloc_get_ptr(obj);
900
901         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
902         if (!pdb_set_code_page(sam_acct, PyInt_AsLong(value), PDB_CHANGED)) {
903                 return -1;
904         }
905         return 0;
906 }
907
908 static PyGetSetDef py_samu_getsetters[] = {
909         { discard_const_p(char, "logon_time"), py_samu_get_logon_time, py_samu_set_logon_time },
910         { discard_const_p(char, "logoff_time"), py_samu_get_logoff_time, py_samu_set_logoff_time },
911         { discard_const_p(char, "kickoff_time"), py_samu_get_kickoff_time, py_samu_set_kickoff_time },
912         { discard_const_p(char, "bad_password_time"), py_samu_get_bad_password_time, py_samu_set_bad_password_time },
913         { discard_const_p(char, "pass_last_set_time"), py_samu_get_pass_last_set_time, py_samu_set_pass_last_set_time },
914         { discard_const_p(char, "pass_can_change_time"), py_samu_get_pass_can_change_time, py_samu_set_pass_can_change_time },
915         { discard_const_p(char, "pass_must_change_time"), py_samu_get_pass_must_change_time, py_samu_set_pass_must_change_time },
916         { discard_const_p(char, "username"), py_samu_get_username, py_samu_set_username },
917         { discard_const_p(char, "domain"), py_samu_get_domain, py_samu_set_domain },
918         { discard_const_p(char, "nt_username"), py_samu_get_nt_username, py_samu_set_nt_username },
919         { discard_const_p(char, "full_name"), py_samu_get_full_name, py_samu_set_full_name },
920         { discard_const_p(char, "home_dir"), py_samu_get_home_dir, py_samu_set_home_dir },
921         { discard_const_p(char, "dir_drive"), py_samu_get_dir_drive, py_samu_set_dir_drive },
922         { discard_const_p(char, "logon_script"), py_samu_get_logon_script, py_samu_set_logon_script },
923         { discard_const_p(char, "profile_path"), py_samu_get_profile_path, py_samu_set_profile_path },
924         { discard_const_p(char, "acct_desc"), py_samu_get_acct_desc, py_samu_set_acct_desc },
925         { discard_const_p(char, "workstations"), py_samu_get_workstations, py_samu_set_workstations },
926         { discard_const_p(char, "comment"), py_samu_get_comment, py_samu_set_comment },
927         { discard_const_p(char, "munged_dial"), py_samu_get_munged_dial, py_samu_set_munged_dial },
928         { discard_const_p(char, "user_sid"), py_samu_get_user_sid, py_samu_set_user_sid },
929         { discard_const_p(char, "group_sid"), py_samu_get_group_sid, py_samu_set_group_sid },
930         { discard_const_p(char, "lanman_passwd"), py_samu_get_lanman_passwd, py_samu_set_lanman_passwd },
931         { discard_const_p(char, "nt_passwd"), py_samu_get_nt_passwd, py_samu_set_nt_passwd },
932         { discard_const_p(char, "pw_history"), py_samu_get_pw_history, py_samu_set_pw_history },
933         { discard_const_p(char, "plaintext_passwd"), py_samu_get_plaintext_passwd, py_samu_set_plaintext_passwd },
934         { discard_const_p(char, "acct_ctrl"), py_samu_get_acct_ctrl, py_samu_set_acct_ctrl },
935         { discard_const_p(char, "logon_divs"), py_samu_get_logon_divs, py_samu_set_logon_divs },
936         { discard_const_p(char, "hours_len"), py_samu_get_hours_len, py_samu_set_hours_len },
937         { discard_const_p(char, "hours"), py_samu_get_hours, py_samu_set_hours },
938         { discard_const_p(char, "bad_password_count"), py_samu_get_bad_password_count, py_samu_set_bad_password_count },
939         { discard_const_p(char, "logon_count"), py_samu_get_logon_count, py_samu_set_logon_count },
940         { discard_const_p(char, "country_code"), py_samu_get_country_code, py_samu_set_country_code },
941         { discard_const_p(char, "code_page"), py_samu_get_code_page, py_samu_set_code_page },
942         { NULL }
943 };
944
945
946 /************************** PIDL Autogeneratd ******************************/
947
948 static PyObject *py_samu_new(PyTypeObject *type, PyObject *args, PyObject *kwargs)
949 {
950         struct samu *sam_acct;
951
952         sam_acct = samu_new(NULL);
953         if (!sam_acct) {
954                 PyErr_NoMemory();
955                 return NULL;
956         }
957
958         return pytalloc_steal(type, sam_acct);
959 }
960
961 static PyTypeObject PySamu = {
962         .tp_name = "passdb.Samu",
963         .tp_basicsize = sizeof(pytalloc_Object),
964         .tp_getset = py_samu_getsetters,
965         .tp_methods = NULL,
966         .tp_new = py_samu_new,
967         .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
968         .tp_doc = "Samu() -> samu object\n",
969 };
970
971
972 static PyObject *py_groupmap_get_gid(PyObject *obj, void *closure)
973 {
974         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
975         PyObject *py_gid;
976
977         py_gid = PyInt_FromLong(group_map->gid);
978         return py_gid;
979 }
980
981 static int py_groupmap_set_gid(PyObject *obj, PyObject *value, void *closure)
982 {
983         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
984
985         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
986         group_map->gid = PyInt_AsLong(value);
987         return 0;
988 }
989
990 static PyObject *py_groupmap_get_sid(PyObject *obj, void *closure)
991 {
992         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
993         PyObject *py_sid;
994         struct dom_sid *group_sid;
995         TALLOC_CTX *mem_ctx;
996
997         mem_ctx = talloc_new(NULL);
998         if (mem_ctx == NULL) {
999                 PyErr_NoMemory();
1000                 return NULL;
1001         }
1002
1003         group_sid = dom_sid_dup(mem_ctx, &group_map->sid);
1004         if (group_sid == NULL) {
1005                 PyErr_NoMemory();
1006                 talloc_free(mem_ctx);
1007                 return NULL;
1008         }
1009
1010         py_sid = pytalloc_steal(dom_sid_Type, group_sid);
1011
1012         talloc_free(mem_ctx);
1013
1014         return py_sid;
1015 }
1016
1017 static int py_groupmap_set_sid(PyObject *obj, PyObject *value, void *closure)
1018 {
1019         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
1020
1021         PY_CHECK_TYPE(dom_sid_Type, value, return -1;);
1022         group_map->sid = *pytalloc_get_type(value, struct dom_sid);
1023         return 0;
1024 }
1025
1026 static PyObject *py_groupmap_get_sid_name_use(PyObject *obj, void *closure)
1027 {
1028         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
1029         PyObject *py_sid_name_use;
1030
1031         py_sid_name_use = PyInt_FromLong(group_map->sid_name_use);
1032         return py_sid_name_use;
1033 }
1034
1035 static int py_groupmap_set_sid_name_use(PyObject *obj, PyObject *value, void *closure)
1036 {
1037         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
1038
1039         PY_CHECK_TYPE(&PyInt_Type, value, return -1;);
1040         group_map->sid_name_use = PyInt_AsLong(value);
1041         return 0;
1042 }
1043
1044 static PyObject *py_groupmap_get_nt_name(PyObject *obj, void *closure)
1045 {
1046         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
1047         PyObject *py_nt_name;
1048         if (group_map->nt_name == NULL) {
1049                 py_nt_name = Py_None;
1050                 Py_INCREF(py_nt_name);
1051         } else {
1052                 py_nt_name = PyString_FromString(group_map->nt_name);
1053         }
1054         return py_nt_name;
1055 }
1056
1057 static int py_groupmap_set_nt_name(PyObject *obj, PyObject *value, void *closure)
1058 {
1059         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
1060
1061         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
1062         if (value == Py_None) {
1063                 fstrcpy(group_map->nt_name, NULL);
1064         } else {
1065                 fstrcpy(group_map->nt_name, PyString_AsString(value));
1066         }
1067         return 0;
1068 }
1069
1070 static PyObject *py_groupmap_get_comment(PyObject *obj, void *closure)
1071 {
1072         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
1073         PyObject *py_comment;
1074         if (group_map->comment == NULL) {
1075                 py_comment = Py_None;
1076                 Py_INCREF(py_comment);
1077         } else {
1078                 py_comment = PyString_FromString(group_map->comment);
1079         }
1080         return py_comment;
1081 }
1082
1083 static int py_groupmap_set_comment(PyObject *obj, PyObject *value, void *closure)
1084 {
1085         GROUP_MAP *group_map = (GROUP_MAP *)pytalloc_get_ptr(obj);
1086
1087         PY_CHECK_TYPE(&PyString_Type, value, return -1;);
1088         if (value == Py_None) {
1089                 fstrcpy(group_map->comment, NULL);
1090         } else {
1091                 fstrcpy(group_map->comment, PyString_AsString(value));
1092         }
1093         return 0;
1094 }
1095
1096 static PyGetSetDef py_groupmap_getsetters[] = {
1097         { discard_const_p(char, "gid"), py_groupmap_get_gid, py_groupmap_set_gid },
1098         { discard_const_p(char, "sid"), py_groupmap_get_sid, py_groupmap_set_sid },
1099         { discard_const_p(char, "sid_name_use"), py_groupmap_get_sid_name_use, py_groupmap_set_sid_name_use },
1100         { discard_const_p(char, "nt_name"), py_groupmap_get_nt_name, py_groupmap_set_nt_name },
1101         { discard_const_p(char, "comment"), py_groupmap_get_comment, py_groupmap_set_comment },
1102         { NULL }
1103 };
1104
1105 static PyObject *py_groupmap_new(PyTypeObject *type, PyObject *args, PyObject *kwargs)
1106 {
1107         GROUP_MAP *group_map;
1108         TALLOC_CTX *mem_ctx;
1109         PyObject *py_group_map;
1110
1111         mem_ctx = talloc_new(NULL);
1112         if (mem_ctx == NULL) {
1113                 PyErr_NoMemory();
1114                 return NULL;
1115         }
1116
1117         group_map = talloc_zero(mem_ctx, GROUP_MAP);
1118         if (group_map == NULL) {
1119                 PyErr_NoMemory();
1120                 talloc_free(mem_ctx);
1121                 return NULL;
1122         }
1123
1124         py_group_map = pytalloc_steal(type, group_map);
1125         if (py_group_map == NULL) {
1126                 PyErr_NoMemory();
1127                 talloc_free(mem_ctx);
1128                 return NULL;
1129         }
1130
1131         talloc_free(mem_ctx);
1132
1133         return py_group_map;
1134 }
1135
1136
1137 static PyTypeObject PyGroupmap = {
1138         .tp_name = "passdb.Groupmap",
1139         .tp_basicsize = sizeof(pytalloc_Object),
1140         .tp_getset = py_groupmap_getsetters,
1141         .tp_methods = NULL,
1142         .tp_new = py_groupmap_new,
1143         .tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
1144         .tp_doc = "Groupmap() -> group map object\n",
1145 };
1146
1147
1148 static PyObject *py_pdb_domain_info(pytalloc_Object *self, PyObject *args)
1149 {
1150         struct pdb_methods *methods;
1151         struct pdb_domain_info *domain_info;
1152         PyObject *py_domain_info;
1153         TALLOC_CTX *tframe;
1154         struct dom_sid *sid;
1155         struct GUID *guid;
1156
1157         methods = pytalloc_get_ptr(self);
1158
1159         if ((tframe = talloc_stackframe()) == NULL) {
1160                 PyErr_NoMemory();
1161                 return NULL;
1162         }
1163
1164         domain_info = methods->get_domain_info(methods, tframe);
1165         if (! domain_info) {
1166                 Py_RETURN_NONE;
1167         }
1168
1169         sid = dom_sid_dup(tframe, &domain_info->sid);
1170         if (sid == NULL) {
1171                 PyErr_NoMemory();
1172                 talloc_free(tframe);
1173                 return NULL;
1174         }
1175
1176         guid = talloc(tframe, struct GUID);
1177         if (guid == NULL) {
1178                 PyErr_NoMemory();
1179                 talloc_free(tframe);
1180                 return NULL;
1181         }
1182         *guid = domain_info->guid;
1183
1184         if ((py_domain_info = PyDict_New()) == NULL) {
1185                 PyErr_NoMemory();
1186                 return NULL;
1187         }
1188
1189         PyDict_SetItemString(py_domain_info, "name", PyString_FromString(domain_info->name));
1190         PyDict_SetItemString(py_domain_info, "dns_domain", PyString_FromString(domain_info->name));
1191         PyDict_SetItemString(py_domain_info, "dns_forest", PyString_FromString(domain_info->name));
1192         PyDict_SetItemString(py_domain_info, "dom_sid", pytalloc_steal(dom_sid_Type, sid));
1193         PyDict_SetItemString(py_domain_info, "guid", pytalloc_steal(guid_Type, guid));
1194
1195         talloc_free(tframe);
1196
1197         return py_domain_info;
1198 }
1199
1200
1201 static PyObject *py_pdb_getsampwnam(pytalloc_Object *self, PyObject *args)
1202 {
1203         NTSTATUS status;
1204         const char *username;
1205         struct pdb_methods *methods;
1206         struct samu *sam_acct;
1207         PyObject *py_sam_acct;
1208         TALLOC_CTX *tframe;
1209
1210         if (!PyArg_ParseTuple(args, "s:getsampwnam", &username)) {
1211                 return NULL;
1212         }
1213
1214         methods = pytalloc_get_ptr(self);
1215
1216         if ((tframe = talloc_stackframe()) == NULL) {
1217                 PyErr_NoMemory();
1218                 return NULL;
1219         }
1220
1221         py_sam_acct = py_samu_new(&PySamu, NULL, NULL);
1222         if (py_sam_acct == NULL) {
1223                 PyErr_NoMemory();
1224                 talloc_free(tframe);
1225                 return NULL;
1226         }
1227         sam_acct = (struct samu *)pytalloc_get_ptr(py_sam_acct);
1228
1229         status = methods->getsampwnam(methods, sam_acct, username);
1230         if (!NT_STATUS_IS_OK(status)) {
1231                 PyErr_Format(py_pdb_error, "Unable to get user information for '%s', (%d,%s)",
1232                                 username,
1233                                 NT_STATUS_V(status),
1234                                 get_friendly_nt_error_msg(status));
1235                 Py_DECREF(py_sam_acct);
1236                 talloc_free(tframe);
1237                 return NULL;
1238         }
1239
1240         talloc_free(tframe);
1241         return py_sam_acct;
1242 }
1243
1244 static PyObject *py_pdb_getsampwsid(pytalloc_Object *self, PyObject *args)
1245 {
1246         NTSTATUS status;
1247         struct pdb_methods *methods;
1248         struct samu *sam_acct;
1249         PyObject *py_sam_acct;
1250         TALLOC_CTX *tframe;
1251         PyObject *py_user_sid;
1252
1253         if (!PyArg_ParseTuple(args, "O:getsampwsid", &py_user_sid)) {
1254                 return NULL;
1255         }
1256
1257         methods = pytalloc_get_ptr(self);
1258
1259         if ((tframe = talloc_stackframe()) == NULL) {
1260                 PyErr_NoMemory();
1261                 return NULL;
1262         }
1263
1264         py_sam_acct = py_samu_new(&PySamu, NULL, NULL);
1265         if (py_sam_acct == NULL) {
1266                 PyErr_NoMemory();
1267                 talloc_free(tframe);
1268                 return NULL;
1269         }
1270         sam_acct = (struct samu *)pytalloc_get_ptr(py_sam_acct);
1271
1272         status = methods->getsampwsid(methods, sam_acct, pytalloc_get_ptr(py_user_sid));
1273         if (!NT_STATUS_IS_OK(status)) {
1274                 PyErr_Format(py_pdb_error, "Unable to get user information from SID, (%d,%s)",
1275                                 NT_STATUS_V(status),
1276                                 get_friendly_nt_error_msg(status));
1277                 Py_DECREF(py_sam_acct);
1278                 talloc_free(tframe);
1279                 return NULL;
1280         }
1281
1282         talloc_free(tframe);
1283         return py_sam_acct;
1284 }
1285
1286 static PyObject *py_pdb_create_user(pytalloc_Object *self, PyObject *args)
1287 {
1288         NTSTATUS status;
1289         struct pdb_methods *methods;
1290         const char *username;
1291         unsigned int acct_flags;
1292         unsigned int rid;
1293         TALLOC_CTX *tframe;
1294
1295         if (!PyArg_ParseTuple(args, "sI:create_user", &username, &acct_flags)) {
1296                 return NULL;
1297         }
1298
1299         methods = pytalloc_get_ptr(self);
1300
1301         if ((tframe = talloc_stackframe()) == NULL) {
1302                 PyErr_NoMemory();
1303                 return NULL;
1304         }
1305
1306         status = methods->create_user(methods, tframe, username, acct_flags, &rid);
1307         if (!NT_STATUS_IS_OK(status)) {
1308                 PyErr_Format(py_pdb_error, "Unable to create user (%s), (%d,%s)",
1309                                 username,
1310                                 NT_STATUS_V(status),
1311                                 get_friendly_nt_error_msg(status));
1312                 talloc_free(tframe);
1313                 return NULL;
1314         }
1315
1316         talloc_free(tframe);
1317         return PyInt_FromLong(rid);
1318 }
1319
1320 static PyObject *py_pdb_delete_user(pytalloc_Object *self, PyObject *args)
1321 {
1322         NTSTATUS status;
1323         struct pdb_methods *methods;
1324         TALLOC_CTX *tframe;
1325         struct samu *sam_acct;
1326         PyObject *py_sam_acct;
1327
1328         if (!PyArg_ParseTuple(args, "O!:delete_user", &PySamu, &py_sam_acct)) {
1329                 return NULL;
1330         }
1331
1332         methods = pytalloc_get_ptr(self);
1333
1334         if ((tframe = talloc_stackframe()) == NULL) {
1335                 PyErr_NoMemory();
1336                 return NULL;
1337         }
1338
1339         sam_acct = pytalloc_get_ptr(py_sam_acct);
1340
1341         status = methods->delete_user(methods, tframe, sam_acct);
1342         if (!NT_STATUS_IS_OK(status)) {
1343                 PyErr_Format(py_pdb_error, "Unable to delete user, (%d,%s)",
1344                                 NT_STATUS_V(status),
1345                                 get_friendly_nt_error_msg(status));
1346                 talloc_free(tframe);
1347                 return NULL;
1348         }
1349
1350         talloc_free(tframe);
1351         Py_RETURN_NONE;
1352 }
1353
1354 static PyObject *py_pdb_add_sam_account(pytalloc_Object *self, PyObject *args)
1355 {
1356         NTSTATUS status;
1357         struct pdb_methods *methods;
1358         TALLOC_CTX *tframe;
1359         struct samu *sam_acct;
1360         PyObject *py_sam_acct;
1361
1362         if (!PyArg_ParseTuple(args, "O!:add_sam_account", &PySamu, &py_sam_acct)) {
1363                 return NULL;
1364         }
1365
1366         methods = pytalloc_get_ptr(self);
1367
1368         if ((tframe = talloc_stackframe()) == NULL) {
1369                 PyErr_NoMemory();
1370                 return NULL;
1371         }
1372
1373         sam_acct = pytalloc_get_ptr(py_sam_acct);
1374
1375         status = methods->add_sam_account(methods, sam_acct);
1376         if (!NT_STATUS_IS_OK(status)) {
1377                 PyErr_Format(py_pdb_error, "Unable to add sam account '%s', (%d,%s)",
1378                                 sam_acct->username,
1379                                 NT_STATUS_V(status),
1380                                 get_friendly_nt_error_msg(status));
1381                 talloc_free(tframe);
1382                 return NULL;
1383         }
1384
1385         talloc_free(tframe);
1386         Py_RETURN_NONE;
1387 }
1388
1389 static PyObject *py_pdb_update_sam_account(pytalloc_Object *self, PyObject *args)
1390 {
1391         NTSTATUS status;
1392         struct pdb_methods *methods;
1393         TALLOC_CTX *tframe;
1394         struct samu *sam_acct;
1395         PyObject *py_sam_acct;
1396
1397         if (!PyArg_ParseTuple(args, "O!:update_sam_account", &PySamu, &py_sam_acct)) {
1398                 return NULL;
1399         }
1400
1401         methods = pytalloc_get_ptr(self);
1402
1403         if ((tframe = talloc_stackframe()) == NULL) {
1404                 PyErr_NoMemory();
1405                 return NULL;
1406         }
1407
1408         sam_acct = pytalloc_get_ptr(py_sam_acct);
1409
1410         status = methods->update_sam_account(methods, sam_acct);
1411         if (!NT_STATUS_IS_OK(status)) {
1412                 PyErr_Format(py_pdb_error, "Unable to update sam account, (%d,%s)",
1413                                 NT_STATUS_V(status),
1414                                 get_friendly_nt_error_msg(status));
1415                 talloc_free(tframe);
1416                 return NULL;
1417         }
1418
1419         talloc_free(tframe);
1420         Py_RETURN_NONE;
1421 }
1422
1423 static PyObject *py_pdb_delete_sam_account(pytalloc_Object *self, PyObject *args)
1424 {
1425         NTSTATUS status;
1426         struct pdb_methods *methods;
1427         TALLOC_CTX *tframe;
1428         struct samu *sam_acct;
1429         PyObject *py_sam_acct;
1430
1431         if (!PyArg_ParseTuple(args, "O!:delete_sam_account", &PySamu, &py_sam_acct)) {
1432                 return NULL;
1433         }
1434
1435         methods = pytalloc_get_ptr(self);
1436
1437         if ((tframe = talloc_stackframe()) == NULL) {
1438                 PyErr_NoMemory();
1439                 return NULL;
1440         }
1441
1442         sam_acct = pytalloc_get_ptr(py_sam_acct);
1443
1444         status = methods->delete_sam_account(methods, sam_acct);
1445         if (!NT_STATUS_IS_OK(status)) {
1446                 PyErr_Format(py_pdb_error, "Unable to delete sam account, (%d,%s)",
1447                                 NT_STATUS_V(status),
1448                                 get_friendly_nt_error_msg(status));
1449                 talloc_free(tframe);
1450                 return NULL;
1451         }
1452
1453         talloc_free(tframe);
1454         Py_RETURN_NONE;
1455 }
1456
1457 static PyObject *py_pdb_rename_sam_account(pytalloc_Object *self, PyObject *args)
1458 {
1459         NTSTATUS status;
1460         struct pdb_methods *methods;
1461         TALLOC_CTX *tframe;
1462         struct samu *sam_acct;
1463         const char *new_username;
1464         PyObject *py_sam_acct;
1465
1466         if (!PyArg_ParseTuple(args, "O!s:rename_sam_account", &PySamu, &py_sam_acct,
1467                                         &new_username)) {
1468                 return NULL;
1469         }
1470
1471         methods = pytalloc_get_ptr(self);
1472
1473         if ((tframe = talloc_stackframe()) == NULL) {
1474                 PyErr_NoMemory();
1475                 return NULL;
1476         }
1477
1478         sam_acct = pytalloc_get_ptr(py_sam_acct);
1479
1480         status = methods->rename_sam_account(methods, sam_acct, new_username);
1481         if (!NT_STATUS_IS_OK(status)) {
1482                 PyErr_Format(py_pdb_error, "Unable to rename sam account, (%d,%s)",
1483                                 NT_STATUS_V(status),
1484                                 get_friendly_nt_error_msg(status));
1485                 talloc_free(tframe);
1486                 return NULL;
1487         }
1488
1489         talloc_free(tframe);
1490         Py_RETURN_NONE;
1491 }
1492
1493
1494 static PyObject *py_pdb_getgrsid(pytalloc_Object *self, PyObject *args)
1495 {
1496         NTSTATUS status;
1497         struct pdb_methods *methods;
1498         TALLOC_CTX *tframe;
1499         GROUP_MAP *group_map;
1500         struct dom_sid *domain_sid;
1501         PyObject *py_domain_sid, *py_group_map;
1502
1503         if (!PyArg_ParseTuple(args, "O!:getgrsid", dom_sid_Type, &py_domain_sid)) {
1504                 return NULL;
1505         }
1506
1507         methods = pytalloc_get_ptr(self);
1508
1509         if ((tframe = talloc_stackframe()) == NULL) {
1510                 PyErr_NoMemory();
1511                 return NULL;
1512         }
1513
1514         domain_sid = pytalloc_get_ptr(py_domain_sid);
1515
1516         py_group_map = py_groupmap_new(&PyGroupmap, NULL, NULL);
1517         if (py_group_map == NULL) {
1518                 PyErr_NoMemory();
1519                 talloc_free(tframe);
1520                 return NULL;
1521         }
1522
1523         group_map = pytalloc_get_ptr(py_group_map);
1524
1525         status = methods->getgrsid(methods, group_map, *domain_sid);
1526         if (!NT_STATUS_IS_OK(status)) {
1527                 PyErr_Format(py_pdb_error, "Unable to get group information by sid, (%d,%s)",
1528                                 NT_STATUS_V(status),
1529                                 get_friendly_nt_error_msg(status));
1530                 talloc_free(tframe);
1531                 return NULL;
1532         }
1533
1534         talloc_free(tframe);
1535         return py_group_map;
1536 }
1537
1538
1539 static PyObject *py_pdb_getgrgid(pytalloc_Object *self, PyObject *args)
1540 {
1541         NTSTATUS status;
1542         struct pdb_methods *methods;
1543         TALLOC_CTX *tframe;
1544         GROUP_MAP *group_map;
1545         PyObject *py_group_map;
1546         unsigned int gid_value;
1547
1548         if (!PyArg_ParseTuple(args, "I:getgrgid", &gid_value)) {
1549                 return NULL;
1550         }
1551
1552         methods = pytalloc_get_ptr(self);
1553
1554         if ((tframe = talloc_stackframe()) == NULL) {
1555                 PyErr_NoMemory();
1556                 return NULL;
1557         }
1558
1559         py_group_map = py_groupmap_new(&PyGroupmap, NULL, NULL);
1560         if (py_group_map == NULL) {
1561                 PyErr_NoMemory();
1562                 talloc_free(tframe);
1563                 return NULL;
1564         }
1565
1566         group_map = pytalloc_get_ptr(py_group_map);
1567
1568         status = methods->getgrgid(methods, group_map, gid_value);
1569         if (!NT_STATUS_IS_OK(status)) {
1570                 PyErr_Format(py_pdb_error, "Unable to get group information by gid, (%d,%s)",
1571                                 NT_STATUS_V(status),
1572                                 get_friendly_nt_error_msg(status));
1573                 talloc_free(tframe);
1574                 return NULL;
1575         }
1576
1577         talloc_free(tframe);
1578         return py_group_map;
1579 }
1580
1581
1582 static PyObject *py_pdb_getgrnam(pytalloc_Object *self, PyObject *args)
1583 {
1584         NTSTATUS status;
1585         struct pdb_methods *methods;
1586         TALLOC_CTX *tframe;
1587         GROUP_MAP *group_map;
1588         PyObject *py_group_map;
1589         const char *groupname;
1590
1591         if (!PyArg_ParseTuple(args, "s:getgrnam", &groupname)) {
1592                 return NULL;
1593         }
1594
1595         methods = pytalloc_get_ptr(self);
1596
1597         if ((tframe = talloc_stackframe()) == NULL) {
1598                 PyErr_NoMemory();
1599                 return NULL;
1600         }
1601
1602         py_group_map = py_groupmap_new(&PyGroupmap, NULL, NULL);
1603         if (py_group_map == NULL) {
1604                 PyErr_NoMemory();
1605                 talloc_free(tframe);
1606                 return NULL;
1607         }
1608
1609         group_map = pytalloc_get_ptr(py_group_map);
1610
1611         status = methods->getgrnam(methods, group_map, groupname);
1612         if (!NT_STATUS_IS_OK(status)) {
1613                 PyErr_Format(py_pdb_error, "Unable to get group information by name, (%d,%s)",
1614                                 NT_STATUS_V(status),
1615                                 get_friendly_nt_error_msg(status));
1616                 talloc_free(tframe);
1617                 return NULL;
1618         }
1619
1620         talloc_free(tframe);
1621         return py_group_map;
1622 }
1623
1624
1625 static PyObject *py_pdb_create_dom_group(pytalloc_Object *self, PyObject *args)
1626 {
1627         NTSTATUS status;
1628         struct pdb_methods *methods;
1629         TALLOC_CTX *tframe;
1630         const char *groupname;
1631         uint32_t group_rid;
1632
1633         if (!PyArg_ParseTuple(args, "s:create_dom_group", &groupname)) {
1634                 return NULL;
1635         }
1636
1637         methods = pytalloc_get_ptr(self);
1638
1639         if ((tframe = talloc_stackframe()) == NULL) {
1640                 PyErr_NoMemory();
1641                 return NULL;
1642         }
1643
1644         status = methods->create_dom_group(methods, tframe, groupname, &group_rid);
1645         if (!NT_STATUS_IS_OK(status)) {
1646                 PyErr_Format(py_pdb_error, "Unable to create domain group (%s), (%d,%s)",
1647                                 groupname,
1648                                 NT_STATUS_V(status),
1649                                 get_friendly_nt_error_msg(status));
1650                 talloc_free(tframe);
1651                 return NULL;
1652         }
1653
1654         talloc_free(tframe);
1655         return PyInt_FromLong(group_rid);
1656 }
1657
1658
1659 static PyObject *py_pdb_delete_dom_group(pytalloc_Object *self, PyObject *args)
1660 {
1661         NTSTATUS status;
1662         struct pdb_methods *methods;
1663         TALLOC_CTX *tframe;
1664         unsigned int group_rid;
1665
1666         if (!PyArg_ParseTuple(args, "I:delete_dom_group", &group_rid)) {
1667                 return NULL;
1668         }
1669
1670         methods = pytalloc_get_ptr(self);
1671
1672         if ((tframe = talloc_stackframe()) == NULL) {
1673                 PyErr_NoMemory();
1674                 return NULL;
1675         }
1676
1677         status = methods->delete_dom_group(methods, tframe, group_rid);
1678         if (!NT_STATUS_IS_OK(status)) {
1679                 PyErr_Format(py_pdb_error, "Unable to delete domain group (rid=%d), (%d,%s)",
1680                                 group_rid,
1681                                 NT_STATUS_V(status),
1682                                 get_friendly_nt_error_msg(status));
1683                 talloc_free(tframe);
1684                 return NULL;
1685         }
1686
1687         talloc_free(tframe);
1688         Py_RETURN_NONE;
1689 }
1690
1691
1692 static PyObject *py_pdb_add_group_mapping_entry(pytalloc_Object *self, PyObject *args)
1693 {
1694         NTSTATUS status;
1695         struct pdb_methods *methods;
1696         TALLOC_CTX *tframe;
1697         PyObject *py_group_map;
1698         GROUP_MAP *group_map;
1699
1700         if (!PyArg_ParseTuple(args, "O!:add_group_mapping_entry", &PyGroupmap, &py_group_map)) {
1701                 return NULL;
1702         }
1703
1704         methods = pytalloc_get_ptr(self);
1705
1706         if ((tframe = talloc_stackframe()) == NULL) {
1707                 PyErr_NoMemory();
1708                 return NULL;
1709         }
1710
1711         group_map = pytalloc_get_ptr(py_group_map);
1712
1713         status = methods->add_group_mapping_entry(methods, group_map);
1714         if (!NT_STATUS_IS_OK(status)) {
1715                 PyErr_Format(py_pdb_error, "Unable to add group mapping entry, (%d,%s)",
1716                                 NT_STATUS_V(status),
1717                                 get_friendly_nt_error_msg(status));
1718                 talloc_free(tframe);
1719                 return NULL;
1720         }
1721
1722         talloc_free(tframe);
1723         Py_RETURN_NONE;
1724 }
1725
1726
1727 static PyObject *py_pdb_update_group_mapping_entry(pytalloc_Object *self, PyObject *args)
1728 {
1729         NTSTATUS status;
1730         struct pdb_methods *methods;
1731         TALLOC_CTX *tframe;
1732         PyObject *py_group_map;
1733         GROUP_MAP *group_map;
1734
1735         if (!PyArg_ParseTuple(args, "O!:update_group_mapping_entry", &PyGroupmap, &py_group_map)) {
1736                 return NULL;
1737         }
1738
1739         methods = pytalloc_get_ptr(self);
1740
1741         if ((tframe = talloc_stackframe()) == NULL) {
1742                 PyErr_NoMemory();
1743                 return NULL;
1744         }
1745
1746         group_map = pytalloc_get_ptr(py_group_map);
1747
1748         status = methods->update_group_mapping_entry(methods, group_map);
1749         if (!NT_STATUS_IS_OK(status)) {
1750                 PyErr_Format(py_pdb_error, "Unable to update group mapping entry, (%d,%s)",
1751                                 NT_STATUS_V(status),
1752                                 get_friendly_nt_error_msg(status));
1753                 talloc_free(tframe);
1754                 return NULL;
1755         }
1756
1757         talloc_free(tframe);
1758         Py_RETURN_NONE;
1759 }
1760
1761
1762 static PyObject *py_pdb_delete_group_mapping_entry(pytalloc_Object *self, PyObject *args)
1763 {
1764         NTSTATUS status;
1765         struct pdb_methods *methods;
1766         TALLOC_CTX *tframe;
1767         PyObject *py_group_sid;
1768         struct dom_sid *group_sid;
1769
1770         if (!PyArg_ParseTuple(args, "O!:delete_group_mapping_entry", dom_sid_Type, &py_group_sid)) {
1771                 return NULL;
1772         }
1773
1774         methods = pytalloc_get_ptr(self);
1775
1776         if ((tframe = talloc_stackframe()) == NULL) {
1777                 PyErr_NoMemory();
1778                 return NULL;
1779         }
1780
1781         group_sid = pytalloc_get_ptr(py_group_sid);
1782
1783         status = methods->delete_group_mapping_entry(methods, *group_sid);
1784         if (!NT_STATUS_IS_OK(status)) {
1785                 PyErr_Format(py_pdb_error, "Unable to delete group mapping entry, (%d,%s)",
1786                                 NT_STATUS_V(status),
1787                                 get_friendly_nt_error_msg(status));
1788                 talloc_free(tframe);
1789                 return NULL;
1790         }
1791
1792         talloc_free(tframe);
1793         Py_RETURN_NONE;
1794 }
1795
1796
1797 static PyObject *py_pdb_enum_group_mapping(pytalloc_Object *self, PyObject *args)
1798 {
1799         NTSTATUS status;
1800         struct pdb_methods *methods;
1801         TALLOC_CTX *tframe;
1802         enum lsa_SidType sid_name_use;
1803         int lsa_sidtype_value = SID_NAME_UNKNOWN;
1804         int unix_only = 0;
1805         PyObject *py_domain_sid;
1806         struct dom_sid *domain_sid = NULL;
1807         GROUP_MAP *gmap, *group_map;
1808         size_t num_entries;
1809         PyObject *py_gmap_list, *py_group_map;
1810         int i;
1811
1812         py_domain_sid = Py_None;
1813         Py_INCREF(Py_None);
1814
1815         if (!PyArg_ParseTuple(args, "|O!ii:enum_group_mapping", dom_sid_Type, &py_domain_sid,
1816                                         &lsa_sidtype_value, &unix_only)) {
1817                 return NULL;
1818         }
1819
1820         methods = pytalloc_get_ptr(self);
1821
1822         if ((tframe = talloc_stackframe()) == NULL) {
1823                 PyErr_NoMemory();
1824                 return NULL;
1825         }
1826
1827         sid_name_use = lsa_sidtype_value;
1828
1829         if (py_domain_sid != Py_None) {
1830                 domain_sid = pytalloc_get_ptr(py_domain_sid);
1831         }
1832
1833         status = methods->enum_group_mapping(methods, domain_sid, sid_name_use,
1834                                                 &gmap, &num_entries, unix_only);
1835         if (!NT_STATUS_IS_OK(status)) {
1836                 PyErr_Format(py_pdb_error, "Unable to enumerate group mappings, (%d,%s)",
1837                                 NT_STATUS_V(status),
1838                                 get_friendly_nt_error_msg(status));
1839                 talloc_free(tframe);
1840                 return NULL;
1841         }
1842
1843         py_gmap_list = PyList_New(0);
1844         if (py_gmap_list == NULL) {
1845                 PyErr_NoMemory();
1846                 talloc_free(tframe);
1847                 return NULL;
1848         }
1849
1850         for(i=0; i<num_entries; i++) {
1851                 py_group_map = py_groupmap_new(&PyGroupmap, NULL, NULL);
1852                 if (py_group_map) {
1853                         group_map = pytalloc_get_ptr(py_group_map);
1854                         *group_map = gmap[i];
1855
1856                         PyList_Append(py_gmap_list, py_group_map);
1857                 }
1858         }
1859
1860         free(gmap);
1861         talloc_free(tframe);
1862
1863         return py_gmap_list;
1864 }
1865
1866
1867 static PyObject *py_pdb_enum_group_members(pytalloc_Object *self, PyObject *args)
1868 {
1869         NTSTATUS status;
1870         struct pdb_methods *methods;
1871         TALLOC_CTX *tframe;
1872         PyObject *py_group_sid;
1873         struct dom_sid *group_sid;
1874         uint32_t *member_rids;
1875         size_t num_members;
1876         PyObject *py_sid_list;
1877         struct dom_sid *domain_sid, *member_sid;
1878         int i;
1879
1880         if (!PyArg_ParseTuple(args, "O!:enum_group_members", dom_sid_Type, &py_group_sid)) {
1881                 return NULL;
1882         }
1883
1884         methods = pytalloc_get_ptr(self);
1885
1886         if ((tframe = talloc_stackframe()) == NULL) {
1887                 PyErr_NoMemory();
1888                 return NULL;
1889         }
1890
1891         group_sid = pytalloc_get_ptr(py_group_sid);
1892
1893         status = methods->enum_group_members(methods, tframe, group_sid,
1894                                                 &member_rids, &num_members);
1895         if (!NT_STATUS_IS_OK(status)) {
1896                 PyErr_Format(py_pdb_error, "Unable to enumerate group members, (%d,%s)",
1897                                 NT_STATUS_V(status),
1898                                 get_friendly_nt_error_msg(status));
1899                 talloc_free(tframe);
1900                 return NULL;
1901         }
1902
1903         py_sid_list = PyList_New(0);
1904         if (py_sid_list == NULL) {
1905                 PyErr_NoMemory();
1906                 talloc_free(tframe);
1907                 return NULL;
1908         }
1909
1910         domain_sid = get_global_sam_sid();
1911
1912         for(i=0; i<num_members; i++) {
1913                 member_sid = dom_sid_add_rid(tframe, domain_sid, member_rids[i]);
1914                 PyList_Append(py_sid_list, pytalloc_steal(dom_sid_Type, member_sid));
1915         }
1916
1917         talloc_free(tframe);
1918
1919         return py_sid_list;
1920 }
1921
1922
1923 static PyObject *py_pdb_add_groupmem(pytalloc_Object *self, PyObject *args)
1924 {
1925         NTSTATUS status;
1926         struct pdb_methods *methods;
1927         TALLOC_CTX *tframe;
1928         uint32_t group_rid, member_rid;
1929
1930         if (!PyArg_ParseTuple(args, "II:add_groupmem", &group_rid, &member_rid)) {
1931                 return NULL;
1932         }
1933
1934         methods = pytalloc_get_ptr(self);
1935
1936         if ((tframe = talloc_stackframe()) == NULL) {
1937                 PyErr_NoMemory();
1938                 return NULL;
1939         }
1940
1941         status = methods->add_groupmem(methods, tframe, group_rid, member_rid);
1942         if (!NT_STATUS_IS_OK(status)) {
1943                 PyErr_Format(py_pdb_error, "Unable to add group member, (%d,%s)",
1944                                 NT_STATUS_V(status),
1945                                 get_friendly_nt_error_msg(status));
1946                 talloc_free(tframe);
1947                 return NULL;
1948         }
1949
1950         talloc_free(tframe);
1951         Py_RETURN_NONE;
1952 }
1953
1954
1955 static PyObject *py_pdb_del_groupmem(pytalloc_Object *self, PyObject *args)
1956 {
1957         NTSTATUS status;
1958         struct pdb_methods *methods;
1959         TALLOC_CTX *tframe;
1960         uint32_t group_rid, member_rid;
1961
1962         if (!PyArg_ParseTuple(args, "II:del_groupmem", &group_rid, &member_rid)) {
1963                 return NULL;
1964         }
1965
1966         methods = pytalloc_get_ptr(self);
1967
1968         if ((tframe = talloc_stackframe()) == NULL) {
1969                 PyErr_NoMemory();
1970                 return NULL;
1971         }
1972
1973         status = methods->del_groupmem(methods, tframe, group_rid, member_rid);
1974         if (!NT_STATUS_IS_OK(status)) {
1975                 PyErr_Format(py_pdb_error, "Unable to rename sam account, (%d,%s)",
1976                                 NT_STATUS_V(status),
1977                                 get_friendly_nt_error_msg(status));
1978                 talloc_free(tframe);
1979                 return NULL;
1980         }
1981
1982         talloc_free(tframe);
1983         Py_RETURN_NONE;
1984 }
1985
1986
1987 static PyObject *py_pdb_create_alias(pytalloc_Object *self, PyObject *args)
1988 {
1989         NTSTATUS status;
1990         struct pdb_methods *methods;
1991         TALLOC_CTX *tframe;
1992         const char *alias_name;
1993         uint32_t rid;
1994
1995         if (!PyArg_ParseTuple(args, "s:create_alias", &alias_name)) {
1996                 return NULL;
1997         }
1998
1999         methods = pytalloc_get_ptr(self);
2000
2001         if ((tframe = talloc_stackframe()) == NULL) {
2002                 PyErr_NoMemory();
2003                 return NULL;
2004         }
2005
2006         status = methods->create_alias(methods, alias_name, &rid);
2007         if (!NT_STATUS_IS_OK(status)) {
2008                 PyErr_Format(py_pdb_error, "Unable to create alias (%s), (%d,%s)",
2009                                 alias_name,
2010                                 NT_STATUS_V(status),
2011                                 get_friendly_nt_error_msg(status));
2012                 talloc_free(tframe);
2013                 return NULL;
2014         }
2015
2016         talloc_free(tframe);
2017
2018         return PyInt_FromLong(rid);
2019 }
2020
2021
2022 static PyObject *py_pdb_delete_alias(pytalloc_Object *self, PyObject *args)
2023 {
2024         NTSTATUS status;
2025         struct pdb_methods *methods;
2026         TALLOC_CTX *tframe;
2027         PyObject *py_alias_sid;
2028         struct dom_sid *alias_sid;
2029
2030         if (!PyArg_ParseTuple(args, "O!:delete_alias", dom_sid_Type, &py_alias_sid)) {
2031                 return NULL;
2032         }
2033
2034         methods = pytalloc_get_ptr(self);
2035
2036         if ((tframe = talloc_stackframe()) == NULL) {
2037                 PyErr_NoMemory();
2038                 return NULL;
2039         }
2040
2041         alias_sid = pytalloc_get_ptr(py_alias_sid);
2042
2043         status = methods->delete_alias(methods, alias_sid);
2044         if (!NT_STATUS_IS_OK(status)) {
2045                 PyErr_Format(py_pdb_error, "Unable to delete alias, (%d,%s)",
2046                                 NT_STATUS_V(status),
2047                                 get_friendly_nt_error_msg(status));
2048                 talloc_free(tframe);
2049                 return NULL;
2050         }
2051
2052         talloc_free(tframe);
2053         Py_RETURN_NONE;
2054 }
2055
2056
2057 static PyObject *py_pdb_get_aliasinfo(pytalloc_Object *self, PyObject *args)
2058 {
2059         NTSTATUS status;
2060         struct pdb_methods *methods;
2061         TALLOC_CTX *tframe;
2062         PyObject *py_alias_sid;
2063         struct dom_sid *alias_sid;
2064         struct acct_info alias_info;
2065         PyObject *py_alias_info;
2066
2067         if (!PyArg_ParseTuple(args, "O!:get_aliasinfo", dom_sid_Type, &py_alias_sid)) {
2068                 return NULL;
2069         }
2070
2071         methods = pytalloc_get_ptr(self);
2072
2073         if ((tframe = talloc_stackframe()) == NULL) {
2074                 PyErr_NoMemory();
2075                 return NULL;
2076         }
2077
2078         alias_sid = pytalloc_get_ptr(py_alias_sid);
2079
2080         status = methods->get_aliasinfo(methods, alias_sid, &alias_info);
2081         if (!NT_STATUS_IS_OK(status)) {
2082                 PyErr_Format(py_pdb_error, "Unable to get alias information, (%d,%s)",
2083                                 NT_STATUS_V(status),
2084                                 get_friendly_nt_error_msg(status));
2085                 talloc_free(tframe);
2086                 return NULL;
2087         }
2088
2089         py_alias_info = PyDict_New();
2090         if (py_alias_info == NULL) {
2091                 PyErr_NoMemory();
2092                 talloc_free(tframe);
2093                 return NULL;
2094         }
2095
2096         PyDict_SetItemString(py_alias_info, "acct_name", PyString_FromString(alias_info.acct_name));
2097         PyDict_SetItemString(py_alias_info, "acct_desc", PyString_FromString(alias_info.acct_desc));
2098         PyDict_SetItemString(py_alias_info, "rid", PyInt_FromLong(alias_info.rid));
2099
2100         talloc_free(tframe);
2101
2102         return py_alias_info;
2103 }
2104
2105
2106 static PyObject *py_pdb_set_aliasinfo(pytalloc_Object *self, PyObject *args)
2107 {
2108         NTSTATUS status;
2109         struct pdb_methods *methods;
2110         TALLOC_CTX *tframe;
2111         PyObject *py_alias_sid, *py_alias_info;
2112         struct dom_sid *alias_sid;
2113         struct acct_info alias_info;
2114
2115         if (!PyArg_ParseTuple(args, "O!O:set_alias_info", dom_sid_Type, &py_alias_sid,
2116                                 &py_alias_info)) {
2117                 return NULL;
2118         }
2119
2120         methods = pytalloc_get_ptr(self);
2121
2122         if ((tframe = talloc_stackframe()) == NULL) {
2123                 PyErr_NoMemory();
2124                 return NULL;
2125         }
2126
2127         alias_sid = pytalloc_get_ptr(py_alias_sid);
2128
2129         fstrcpy(alias_info.acct_name, PyString_AsString(PyDict_GetItemString(py_alias_info, "acct_name")));
2130         fstrcpy(alias_info.acct_desc, PyString_AsString(PyDict_GetItemString(py_alias_info, "acct_desc")));
2131
2132         status = methods->set_aliasinfo(methods, alias_sid, &alias_info);
2133         if (!NT_STATUS_IS_OK(status)) {
2134                 PyErr_Format(py_pdb_error, "Unable to set alias information, (%d,%s)",
2135                                 NT_STATUS_V(status),
2136                                 get_friendly_nt_error_msg(status));
2137                 talloc_free(tframe);
2138                 return NULL;
2139         }
2140
2141         talloc_free(tframe);
2142         Py_RETURN_NONE;
2143 }
2144
2145
2146 static PyObject *py_pdb_add_aliasmem(pytalloc_Object *self, PyObject *args)
2147 {
2148         NTSTATUS status;
2149         struct pdb_methods *methods;
2150         TALLOC_CTX *tframe;
2151         PyObject *py_alias_sid, *py_member_sid;
2152         struct dom_sid *alias_sid, *member_sid;
2153
2154         if (!PyArg_ParseTuple(args, "O!O!:add_aliasmem", dom_sid_Type, &py_alias_sid,
2155                                         dom_sid_Type, &py_member_sid)) {
2156                 return NULL;
2157         }
2158
2159         methods = pytalloc_get_ptr(self);
2160
2161         if ((tframe = talloc_stackframe()) == NULL) {
2162                 PyErr_NoMemory();
2163                 return NULL;
2164         }
2165
2166         alias_sid = pytalloc_get_ptr(py_alias_sid);
2167         member_sid = pytalloc_get_ptr(py_member_sid);
2168
2169         status = methods->add_aliasmem(methods, alias_sid, member_sid);
2170         if (!NT_STATUS_IS_OK(status)) {
2171                 PyErr_Format(py_pdb_error, "Unable to add member to alias, (%d,%s)",
2172                                 NT_STATUS_V(status),
2173                                 get_friendly_nt_error_msg(status));
2174                 talloc_free(tframe);
2175                 return NULL;
2176         }
2177
2178         talloc_free(tframe);
2179         Py_RETURN_NONE;
2180 }
2181
2182
2183 static PyObject *py_pdb_del_aliasmem(pytalloc_Object *self, PyObject *args)
2184 {
2185         NTSTATUS status;
2186         struct pdb_methods *methods;
2187         TALLOC_CTX *tframe;
2188         PyObject *py_alias_sid, *py_member_sid;
2189         const struct dom_sid *alias_sid, *member_sid;
2190
2191         if (!PyArg_ParseTuple(args, "O!O!:del_aliasmem", dom_sid_Type, &py_alias_sid,
2192                                         dom_sid_Type, &py_member_sid)) {
2193                 return NULL;
2194         }
2195
2196         methods = pytalloc_get_ptr(self);
2197
2198         if ((tframe = talloc_stackframe()) == NULL) {
2199                 PyErr_NoMemory();
2200                 return NULL;
2201         }
2202
2203         alias_sid = pytalloc_get_ptr(py_alias_sid);
2204         member_sid = pytalloc_get_ptr(py_member_sid);
2205
2206         status = methods->del_aliasmem(methods, alias_sid, member_sid);
2207         if (!NT_STATUS_IS_OK(status)) {
2208                 PyErr_Format(py_pdb_error, "Unable to delete member from alias, (%d,%s)",
2209                                 NT_STATUS_V(status),
2210                                 get_friendly_nt_error_msg(status));
2211                 talloc_free(tframe);
2212                 return NULL;
2213         }
2214
2215         talloc_free(tframe);
2216         Py_RETURN_NONE;
2217 }
2218
2219
2220 static PyObject *py_pdb_enum_aliasmem(pytalloc_Object *self, PyObject *args)
2221 {
2222         NTSTATUS status;
2223         struct pdb_methods *methods;
2224         TALLOC_CTX *tframe;
2225         PyObject *py_alias_sid;
2226         struct dom_sid *alias_sid, *member_sid;
2227         PyObject *py_member_list, *py_member_sid;
2228         size_t num_members;
2229         int i;
2230
2231         if (!PyArg_ParseTuple(args, "O!:enum_aliasmem", dom_sid_Type, &py_alias_sid)) {
2232                 return NULL;
2233         }
2234
2235         methods = pytalloc_get_ptr(self);
2236
2237         if ((tframe = talloc_stackframe()) == NULL) {
2238                 PyErr_NoMemory();
2239                 return NULL;
2240         }
2241
2242         alias_sid = pytalloc_get_ptr(py_alias_sid);
2243
2244         status = methods->enum_aliasmem(methods, alias_sid, tframe, &member_sid, &num_members);
2245         if (!NT_STATUS_IS_OK(status)) {
2246                 PyErr_Format(py_pdb_error, "Unable to enumerate members for alias, (%d,%s)",
2247                                 NT_STATUS_V(status),
2248                                 get_friendly_nt_error_msg(status));
2249                 talloc_free(tframe);
2250                 return NULL;
2251         }
2252
2253         py_member_list = PyList_New(0);
2254         if (py_member_list == NULL) {
2255                 PyErr_NoMemory();
2256                 talloc_free(tframe);
2257                 return NULL;
2258         }
2259
2260         for(i=0; i<num_members; i++) {
2261                 py_member_sid = pytalloc_steal(dom_sid_Type, &member_sid[i]);
2262                 if (py_member_sid) {
2263                         PyList_Append(py_member_list, py_member_sid);
2264                 }
2265         }
2266
2267         talloc_free(tframe);
2268
2269         return py_member_list;
2270 }
2271
2272
2273 static PyObject *py_pdb_get_account_policy(pytalloc_Object *self)
2274 {
2275         NTSTATUS status;
2276         struct pdb_methods *methods;
2277         TALLOC_CTX *tframe;
2278         PyObject *py_acct_policy;
2279         uint32_t value;
2280         const char **names;
2281         int count, i;
2282         enum pdb_policy_type type;
2283
2284         methods = pytalloc_get_ptr(self);
2285
2286         if ((tframe = talloc_stackframe()) == NULL) {
2287                 PyErr_NoMemory();
2288                 return NULL;
2289         }
2290
2291         py_acct_policy = PyDict_New();
2292         if (py_acct_policy == NULL) {
2293                 PyErr_NoMemory();
2294                 return NULL;
2295         }
2296
2297         account_policy_names_list(tframe, &names, &count);
2298         for (i=0; i<count; i++) {
2299                 type = account_policy_name_to_typenum(names[i]);
2300                 status = methods->get_account_policy(methods, type, &value);
2301                 if (NT_STATUS_IS_OK(status)) {
2302                         PyDict_SetItemString(py_acct_policy, names[i], PyInt_FromLong(value));
2303                 }
2304         }
2305
2306         talloc_free(tframe);
2307
2308         return py_acct_policy;
2309 }
2310
2311
2312 static PyObject *py_pdb_set_account_policy(pytalloc_Object *self, PyObject *args)
2313 {
2314         NTSTATUS status;
2315         struct pdb_methods *methods;
2316         TALLOC_CTX *tframe;
2317         PyObject *py_acct_policy, *py_value;
2318         const char **names;
2319         int count, i;
2320         enum pdb_policy_type type;
2321
2322         if (!PyArg_ParseTuple(args, "O!:set_account_policy", PyDict_Type, &py_acct_policy)) {
2323                 return NULL;
2324         }
2325
2326         methods = pytalloc_get_ptr(self);
2327
2328         if ((tframe = talloc_stackframe()) == NULL) {
2329                 PyErr_NoMemory();
2330                 return NULL;
2331         }
2332
2333         account_policy_names_list(tframe, &names, &count);
2334         for (i=0; i<count; i++) {
2335                 if ((py_value = PyDict_GetItemString(py_acct_policy, names[i])) != NULL) {
2336                         type = account_policy_name_to_typenum(names[i]);
2337                         status = methods->set_account_policy(methods, type, PyInt_AsLong(py_value));
2338                         if (!NT_STATUS_IS_OK(status)) {
2339                                 PyErr_Format(py_pdb_error, "Error setting account policy (%s), (%d,%s)",
2340                                                 names[i],
2341                                                 NT_STATUS_V(status),
2342                                                 get_friendly_nt_error_msg(status));
2343                         }
2344                 }
2345         }
2346
2347
2348         talloc_free(tframe);
2349
2350         Py_RETURN_NONE;
2351 }
2352
2353 static PyObject *py_pdb_search_users(pytalloc_Object *self, PyObject *args)
2354 {
2355         NTSTATUS status;
2356         struct pdb_methods *methods;
2357         TALLOC_CTX *tframe;
2358         unsigned int acct_flags;
2359         struct pdb_search *search;
2360         struct samr_displayentry *entry;
2361         PyObject *py_userlist, *py_dict;
2362
2363         if (!PyArg_ParseTuple(args, "I:search_users", &acct_flags)) {
2364                 return NULL;
2365         }
2366
2367         methods = pytalloc_get_ptr(self);
2368
2369         if ((tframe = talloc_stackframe()) == NULL) {
2370                 PyErr_NoMemory();
2371                 return NULL;
2372         }
2373
2374         search = talloc_zero(tframe, struct pdb_search);
2375         if (search == NULL) {
2376                 PyErr_NoMemory();
2377                 talloc_free(tframe);
2378                 return NULL;
2379         }
2380
2381         if (!methods->search_users(methods, search, acct_flags)) {
2382                 PyErr_Format(py_pdb_error, "Unable to search users, (%d,%s)",
2383                                 NT_STATUS_V(status),
2384                                 get_friendly_nt_error_msg(status));
2385                 talloc_free(tframe);
2386                 return NULL;
2387         }
2388
2389         entry = talloc_zero(tframe, struct samr_displayentry);
2390         if (entry == NULL) {
2391                 PyErr_NoMemory();
2392                 talloc_free(tframe);
2393                 return NULL;
2394         }
2395
2396         py_userlist = PyList_New(0);
2397         if (py_userlist == NULL) {
2398                 PyErr_NoMemory();
2399                 talloc_free(tframe);
2400                 return NULL;
2401         }
2402
2403         while (search->next_entry(search, entry)) {
2404                 py_dict = PyDict_New();
2405                 if (py_dict == NULL) {
2406                         PyErr_NoMemory();
2407                 } else {
2408                         PyDict_SetItemString(py_dict, "idx", PyInt_FromLong(entry->idx));
2409                         PyDict_SetItemString(py_dict, "rid", PyInt_FromLong(entry->rid));
2410                         PyDict_SetItemString(py_dict, "acct_flags", PyInt_FromLong(entry->acct_flags));
2411                         PyDict_SetItemString(py_dict, "account_name", PyString_FromString(entry->account_name));
2412                         PyDict_SetItemString(py_dict, "fullname", PyString_FromString(entry->fullname));
2413                         PyDict_SetItemString(py_dict, "description", PyString_FromString(entry->description));
2414                         PyList_Append(py_userlist, py_dict);
2415                 }
2416         }
2417         search->search_end(search);
2418
2419         talloc_free(tframe);
2420
2421         return py_userlist;
2422 }
2423
2424
2425 static PyObject *py_pdb_search_groups(pytalloc_Object *self)
2426 {
2427         NTSTATUS status;
2428         struct pdb_methods *methods;
2429         TALLOC_CTX *tframe;
2430         struct pdb_search *search;
2431         struct samr_displayentry *entry;
2432         PyObject *py_grouplist, *py_dict;
2433
2434         methods = pytalloc_get_ptr(self);
2435
2436         if ((tframe = talloc_stackframe()) == NULL) {
2437                 PyErr_NoMemory();
2438                 return NULL;
2439         }
2440
2441         search = talloc_zero(tframe, struct pdb_search);
2442         if (search == NULL) {
2443                 PyErr_NoMemory();
2444                 talloc_free(tframe);
2445                 return NULL;
2446         }
2447
2448         if (!methods->search_groups(methods, search)) {
2449                 PyErr_Format(py_pdb_error, "Unable to search groups, (%d,%s)",
2450                                 NT_STATUS_V(status),
2451                                 get_friendly_nt_error_msg(status));
2452                 talloc_free(tframe);
2453                 return NULL;
2454         }
2455
2456         entry = talloc_zero(tframe, struct samr_displayentry);
2457         if (entry == NULL) {
2458                 PyErr_NoMemory();
2459                 talloc_free(tframe);
2460                 return NULL;
2461         }
2462
2463         py_grouplist = PyList_New(0);
2464         if (py_grouplist == NULL) {
2465                 PyErr_NoMemory();
2466                 talloc_free(tframe);
2467                 return NULL;
2468         }
2469
2470         while (search->next_entry(search, entry)) {
2471                 py_dict = PyDict_New();
2472                 if (py_dict == NULL) {
2473                         PyErr_NoMemory();
2474                 } else {
2475                         PyDict_SetItemString(py_dict, "idx", PyInt_FromLong(entry->idx));
2476                         PyDict_SetItemString(py_dict, "rid", PyInt_FromLong(entry->rid));
2477                         PyDict_SetItemString(py_dict, "acct_flags", PyInt_FromLong(entry->acct_flags));
2478                         PyDict_SetItemString(py_dict, "account_name", PyString_FromString(entry->account_name));
2479                         PyDict_SetItemString(py_dict, "fullname", PyString_FromString(entry->fullname));
2480                         PyDict_SetItemString(py_dict, "description", PyString_FromString(entry->description));
2481                         PyList_Append(py_grouplist, py_dict);
2482                 }
2483         }
2484         search->search_end(search);
2485
2486         talloc_free(tframe);
2487
2488         return py_grouplist;
2489 }
2490
2491
2492 static PyObject *py_pdb_search_aliases(pytalloc_Object *self, PyObject *args)
2493 {
2494         struct pdb_methods *methods;
2495         TALLOC_CTX *tframe;
2496         struct pdb_search *search;
2497         struct samr_displayentry *entry;
2498         PyObject *py_aliaslist, *py_dict;
2499         PyObject *py_domain_sid;
2500         struct dom_sid *dom_sid;
2501
2502         if (!PyArg_ParseTuple(args, "O!:search_users", dom_sid_Type, &py_domain_sid)) {
2503                 return NULL;
2504         }
2505
2506         methods = pytalloc_get_ptr(self);
2507
2508         if ((tframe = talloc_stackframe()) == NULL) {
2509                 PyErr_NoMemory();
2510                 return NULL;
2511         }
2512
2513         dom_sid = pytalloc_get_ptr(py_domain_sid);
2514
2515         search = talloc_zero(tframe, struct pdb_search);
2516         if (search == NULL) {
2517                 PyErr_NoMemory();
2518                 talloc_free(tframe);
2519                 return NULL;
2520         }
2521
2522         if (!methods->search_aliases(methods, search, dom_sid)) {
2523                 PyErr_Format(py_pdb_error, "Unable to search aliases");
2524                 talloc_free(tframe);
2525                 return NULL;
2526         }
2527
2528         entry = talloc_zero(tframe, struct samr_displayentry);
2529         if (entry == NULL) {
2530                 PyErr_NoMemory();
2531                 talloc_free(tframe);
2532                 return NULL;
2533         }
2534
2535         py_aliaslist = PyList_New(0);
2536         if (py_aliaslist == NULL) {
2537                 PyErr_NoMemory();
2538                 talloc_free(tframe);
2539                 return NULL;
2540         }
2541
2542         while (search->next_entry(search, entry)) {
2543                 py_dict = PyDict_New();
2544                 if (py_dict == NULL) {
2545                         PyErr_NoMemory();
2546                 } else {
2547                         PyDict_SetItemString(py_dict, "idx", PyInt_FromLong(entry->idx));
2548                         PyDict_SetItemString(py_dict, "rid", PyInt_FromLong(entry->rid));
2549                         PyDict_SetItemString(py_dict, "acct_flags", PyInt_FromLong(entry->acct_flags));
2550                         PyDict_SetItemString(py_dict, "account_name", PyString_FromString(entry->account_name));
2551                         PyDict_SetItemString(py_dict, "fullname", PyString_FromString(entry->fullname));
2552                         PyDict_SetItemString(py_dict, "description", PyString_FromString(entry->description));
2553                         PyList_Append(py_aliaslist, py_dict);
2554                 }
2555         }
2556         search->search_end(search);
2557
2558         talloc_free(tframe);
2559
2560         return py_aliaslist;
2561 }
2562
2563
2564 static PyObject *py_pdb_uid_to_sid(pytalloc_Object *self, PyObject *args)
2565 {
2566         struct pdb_methods *methods;
2567         TALLOC_CTX *tframe;
2568         unsigned int uid;
2569         struct dom_sid user_sid, *copy_user_sid;
2570         PyObject *py_user_sid;
2571
2572         if (!PyArg_ParseTuple(args, "I:uid_to_sid", &uid)) {
2573                 return NULL;
2574         }
2575
2576         methods = pytalloc_get_ptr(self);
2577
2578         if ((tframe = talloc_stackframe()) == NULL) {
2579                 PyErr_NoMemory();
2580                 return NULL;
2581         }
2582
2583         if (!methods->uid_to_sid(methods, uid, &user_sid)) {
2584                 PyErr_Format(py_pdb_error, "Unable to get sid for uid=%d", uid);
2585                 talloc_free(tframe);
2586                 return NULL;
2587         }
2588
2589         copy_user_sid = dom_sid_dup(tframe, &user_sid);
2590         if (copy_user_sid == NULL) {
2591                 PyErr_NoMemory();
2592                 talloc_free(tframe);
2593                 return NULL;
2594         }
2595
2596         py_user_sid = pytalloc_steal(dom_sid_Type, copy_user_sid);
2597
2598         talloc_free(tframe);
2599
2600         return py_user_sid;
2601 }
2602
2603
2604 static PyObject *py_pdb_gid_to_sid(pytalloc_Object *self, PyObject *args)
2605 {
2606         struct pdb_methods *methods;
2607         TALLOC_CTX *tframe;
2608         unsigned int gid;
2609         struct dom_sid group_sid, *copy_group_sid;
2610         PyObject *py_group_sid;
2611
2612         if (!PyArg_ParseTuple(args, "I:gid_to_sid", &gid)) {
2613                 return NULL;
2614         }
2615
2616         methods = pytalloc_get_ptr(self);
2617
2618         if ((tframe = talloc_stackframe()) == NULL) {
2619                 PyErr_NoMemory();
2620                 return NULL;
2621         }
2622
2623         if (!methods->gid_to_sid(methods, gid, &group_sid)) {
2624                 PyErr_Format(py_pdb_error, "Unable to get sid for gid=%d", gid);
2625                 talloc_free(tframe);
2626                 return NULL;
2627         }
2628
2629         copy_group_sid = dom_sid_dup(tframe, &group_sid);
2630         if (copy_group_sid == NULL) {
2631                 PyErr_NoMemory();
2632                 talloc_free(tframe);
2633                 return NULL;
2634         }
2635
2636         py_group_sid = pytalloc_steal(dom_sid_Type, copy_group_sid);
2637
2638         talloc_free(tframe);
2639
2640         return py_group_sid;
2641 }
2642
2643
2644 static PyObject *py_pdb_sid_to_id(pytalloc_Object *self, PyObject *args)
2645 {
2646         struct pdb_methods *methods;
2647         TALLOC_CTX *tframe;
2648         PyObject *py_sid;
2649         struct dom_sid *sid;
2650         union unid_t id;
2651         enum lsa_SidType type;
2652
2653         if (!PyArg_ParseTuple(args, "O!:sid_to_id", dom_sid_Type, &py_sid)) {
2654                 return NULL;
2655         }
2656
2657         methods = pytalloc_get_ptr(self);
2658
2659         if ((tframe = talloc_stackframe()) == NULL) {
2660                 PyErr_NoMemory();
2661                 return NULL;
2662         }
2663
2664         sid = pytalloc_get_ptr(py_sid);
2665
2666         if (!methods->sid_to_id(methods, sid, &id, &type)) {
2667                 PyErr_Format(py_pdb_error, "Unable to get id for sid");
2668                 talloc_free(tframe);
2669                 return NULL;
2670         }
2671
2672         talloc_free(tframe);
2673
2674         return Py_BuildValue("(II)", id.uid, type);
2675 }
2676
2677
2678 static PyObject *py_pdb_new_rid(pytalloc_Object *self)
2679 {
2680         struct pdb_methods *methods;
2681         TALLOC_CTX *tframe;
2682         uint32_t rid;
2683
2684         methods = pytalloc_get_ptr(self);
2685
2686         if ((tframe = talloc_stackframe()) == NULL) {
2687                 PyErr_NoMemory();
2688                 return NULL;
2689         }
2690
2691         if (!methods->new_rid(methods, &rid)) {
2692                 PyErr_Format(py_pdb_error, "Unable to get new rid");
2693                 talloc_free(tframe);
2694                 return NULL;
2695         }
2696
2697         talloc_free(tframe);
2698
2699         return PyInt_FromLong(rid);
2700 }
2701
2702
2703 static PyObject *py_pdb_get_trusteddom_pw(pytalloc_Object *self, PyObject *args)
2704 {
2705         struct pdb_methods *methods;
2706         TALLOC_CTX *tframe;
2707         const char *domain;
2708         char *pwd;
2709         struct dom_sid sid, *copy_sid;
2710         PyObject *py_sid;
2711         time_t last_set_time;
2712         PyObject *py_value;
2713
2714         if (!PyArg_ParseTuple(args, "s:get_trusteddom_pw", &domain)) {
2715                 return NULL;
2716         }
2717
2718         methods = pytalloc_get_ptr(self);
2719
2720         if ((tframe = talloc_stackframe()) == NULL) {
2721                 PyErr_NoMemory();
2722                 return NULL;
2723         }
2724
2725         if (!methods->get_trusteddom_pw(methods, domain, &pwd, &sid, &last_set_time)) {
2726                 PyErr_Format(py_pdb_error, "Unable to get trusted domain password");
2727                 talloc_free(tframe);
2728                 return NULL;
2729         }
2730
2731         copy_sid = dom_sid_dup(tframe, &sid);
2732         if (copy_sid == NULL) {
2733                 PyErr_NoMemory();
2734                 talloc_free(tframe);
2735                 return NULL;
2736         }
2737
2738         py_sid = pytalloc_steal(dom_sid_Type, copy_sid);
2739         if (py_sid == NULL) {
2740                 PyErr_NoMemory();
2741                 talloc_free(tframe);
2742                 return NULL;
2743         }
2744
2745         talloc_free(tframe);
2746
2747         py_value = PyDict_New();
2748         if (py_value == NULL) {
2749                 PyErr_NoMemory();
2750                 return NULL;
2751         }
2752
2753         PyDict_SetItemString(py_value, "pwd", PyString_FromString(pwd));
2754         PyDict_SetItemString(py_value, "sid", py_sid);
2755         PyDict_SetItemString(py_value, "last_set_tim", PyInt_FromLong(last_set_time));
2756
2757         return py_value;
2758 }
2759
2760
2761 static PyObject *py_pdb_set_trusteddom_pw(pytalloc_Object *self, PyObject *args)
2762 {
2763         struct pdb_methods *methods;
2764         TALLOC_CTX *tframe;
2765         const char *domain;
2766         const char *pwd;
2767         const struct dom_sid *domain_sid;
2768         PyObject *py_domain_sid;
2769
2770         if (!PyArg_ParseTuple(args, "ssO!:set_trusteddom_pw", &domain, &pwd,
2771                                         dom_sid_Type, &py_domain_sid)) {
2772                 return NULL;
2773         }
2774
2775         methods = pytalloc_get_ptr(self);
2776
2777         if ((tframe = talloc_stackframe()) == NULL) {
2778                 PyErr_NoMemory();
2779                 return NULL;
2780         }
2781
2782         domain_sid = pytalloc_get_ptr(py_domain_sid);
2783
2784         if (!methods->set_trusteddom_pw(methods, domain, pwd, domain_sid)) {
2785                 PyErr_Format(py_pdb_error, "Unable to set trusted domain password");
2786                 talloc_free(tframe);
2787                 return NULL;
2788         }
2789
2790         Py_RETURN_NONE;
2791 }
2792
2793
2794 static PyObject *py_pdb_del_trusteddom_pw(pytalloc_Object *self, PyObject *args)
2795 {
2796         struct pdb_methods *methods;
2797         TALLOC_CTX *tframe;
2798         const char *domain;
2799
2800         if (!PyArg_ParseTuple(args, "s:del_trusteddom_pw", &domain)) {
2801                 return NULL;
2802         }
2803
2804         methods = pytalloc_get_ptr(self);
2805
2806         if ((tframe = talloc_stackframe()) == NULL) {
2807                 PyErr_NoMemory();
2808                 return NULL;
2809         }
2810
2811         if (!methods->del_trusteddom_pw(methods, domain)) {
2812                 PyErr_Format(py_pdb_error, "Unable to delete trusted domain password");
2813                 talloc_free(tframe);
2814                 return NULL;
2815         }
2816
2817         Py_RETURN_NONE;
2818 }
2819
2820
2821 static PyObject *py_pdb_enum_trusteddoms(pytalloc_Object *self)
2822 {
2823         NTSTATUS status;
2824         struct pdb_methods *methods;
2825         TALLOC_CTX *tframe;
2826         uint32_t num_domains;
2827         struct trustdom_info **domains;
2828         PyObject *py_domain_list, *py_dict;
2829         int i;
2830
2831         methods = pytalloc_get_ptr(self);
2832
2833         if ((tframe = talloc_stackframe()) == NULL) {
2834                 PyErr_NoMemory();
2835                 return NULL;
2836         }
2837
2838         status = methods->enum_trusteddoms(methods, tframe, &num_domains, &domains);
2839         if (!NT_STATUS_IS_OK(status)) {
2840                 PyErr_Format(py_pdb_error, "Unable to enumerate trusted domains, (%d,%s)",
2841                                 NT_STATUS_V(status),
2842                                 get_friendly_nt_error_msg(status));
2843                 talloc_free(tframe);
2844                 return NULL;
2845         }
2846
2847         py_domain_list = PyList_New(0);
2848         if (py_domain_list == NULL) {
2849                 PyErr_NoMemory();
2850                 talloc_free(tframe);
2851                 return NULL;
2852         }
2853
2854         for(i=0; i<num_domains; i++) {
2855                 py_dict = PyDict_New();
2856                 if (py_dict) {
2857                         PyDict_SetItemString(py_dict, "name",
2858                                         PyString_FromString(domains[i]->name));
2859                         PyDict_SetItemString(py_dict, "sid",
2860                                         pytalloc_steal(dom_sid_Type, &domains[i]->sid));
2861                 }
2862
2863                 PyList_Append(py_domain_list, py_dict);
2864         }
2865
2866         talloc_free(tframe);
2867
2868         return py_domain_list;
2869 }
2870
2871
2872 static PyObject *py_pdb_get_trusted_domain(pytalloc_Object *self, PyObject *args)
2873 {
2874         NTSTATUS status;
2875         struct pdb_methods *methods;
2876         TALLOC_CTX *tframe;
2877         const char *domain;
2878         struct pdb_trusted_domain *td;
2879         PyObject *py_domain_info;
2880
2881         if (!PyArg_ParseTuple(args, "s:get_trusted_domain", &domain)) {
2882                 return NULL;
2883         }
2884
2885         methods = pytalloc_get_ptr(self);
2886
2887         if ((tframe = talloc_stackframe()) == NULL) {
2888                 PyErr_NoMemory();
2889                 return NULL;
2890         }
2891
2892         status = methods->get_trusted_domain(methods, tframe, domain, &td);
2893         if (!NT_STATUS_IS_OK(status)) {
2894                 PyErr_Format(py_pdb_error, "Unable to get trusted domain information, (%d,%s)",
2895                                 NT_STATUS_V(status),
2896                                 get_friendly_nt_error_msg(status));
2897                 talloc_free(tframe);
2898                 return NULL;
2899         }
2900
2901         py_domain_info = PyDict_New();
2902         if (py_domain_info == NULL) {
2903                 PyErr_NoMemory();
2904                 talloc_free(tframe);
2905                 return NULL;
2906         }
2907
2908         PyDict_SetItemString(py_domain_info, "domain_name",
2909                         PyString_FromString(td->domain_name));
2910         PyDict_SetItemString(py_domain_info, "netbios_name",
2911                         PyString_FromString(td->netbios_name));
2912         PyDict_SetItemString(py_domain_info, "security_identifier",
2913                         pytalloc_steal(dom_sid_Type, &td->security_identifier));
2914         PyDict_SetItemString(py_domain_info, "trust_auth_incoming",
2915                         PyString_FromStringAndSize((char *)td->trust_auth_incoming.data,
2916                                                 td->trust_auth_incoming.length));
2917         PyDict_SetItemString(py_domain_info, "trust_auth_outgoing",
2918                         PyString_FromStringAndSize((char *)td->trust_auth_outgoing.data,
2919                                                 td->trust_auth_outgoing.length));
2920         PyDict_SetItemString(py_domain_info, "trust_direction",
2921                         PyInt_FromLong(td->trust_direction));
2922         PyDict_SetItemString(py_domain_info, "trust_type",
2923                         PyInt_FromLong(td->trust_type));
2924         PyDict_SetItemString(py_domain_info, "trust_attributes",
2925                         PyInt_FromLong(td->trust_attributes));
2926         PyDict_SetItemString(py_domain_info, "trust_forest_trust_info",
2927                         PyString_FromStringAndSize((char *)td->trust_forest_trust_info.data,
2928                                                 td->trust_forest_trust_info.length));
2929
2930         talloc_free(tframe);
2931
2932         return py_domain_info;
2933 }
2934
2935
2936 static PyObject *py_pdb_get_trusted_domain_by_sid(pytalloc_Object *self, PyObject *args)
2937 {
2938         NTSTATUS status;
2939         struct pdb_methods *methods;
2940         TALLOC_CTX *tframe;
2941         PyObject *py_domain_sid;
2942         struct dom_sid *domain_sid;
2943         struct pdb_trusted_domain *td;
2944         PyObject *py_domain_info;
2945
2946         if (!PyArg_ParseTuple(args, "O!:get_trusted_domain_by_sid", dom_sid_Type, &py_domain_sid)) {
2947                 return NULL;
2948         }
2949
2950         methods = pytalloc_get_ptr(self);
2951
2952         if ((tframe = talloc_stackframe()) == NULL) {
2953                 PyErr_NoMemory();
2954                 return NULL;
2955         }
2956
2957         domain_sid = pytalloc_get_ptr(py_domain_sid);
2958
2959         status = methods->get_trusted_domain_by_sid(methods, tframe, domain_sid, &td);
2960         if (!NT_STATUS_IS_OK(status)) {
2961                 PyErr_Format(py_pdb_error, "Unable to get trusted domain information, (%d,%s)",
2962                                 NT_STATUS_V(status),
2963                                 get_friendly_nt_error_msg(status));
2964                 talloc_free(tframe);
2965                 return NULL;
2966         }
2967
2968         py_domain_info = PyDict_New();
2969         if (py_domain_info == NULL) {
2970                 PyErr_NoMemory();
2971                 talloc_free(tframe);
2972                 return NULL;
2973         }
2974
2975         PyDict_SetItemString(py_domain_info, "domain_name",
2976                         PyString_FromString(td->domain_name));
2977         PyDict_SetItemString(py_domain_info, "netbios_name",
2978                         PyString_FromString(td->netbios_name));
2979         PyDict_SetItemString(py_domain_info, "security_identifier",
2980                         pytalloc_steal(dom_sid_Type, &td->security_identifier));
2981         PyDict_SetItemString(py_domain_info, "trust_auth_incoming",
2982                         PyString_FromStringAndSize((char *)td->trust_auth_incoming.data,
2983                                                 td->trust_auth_incoming.length));
2984         PyDict_SetItemString(py_domain_info, "trust_auth_outgoing",
2985                         PyString_FromStringAndSize((char *)td->trust_auth_outgoing.data,
2986                                                 td->trust_auth_outgoing.length));
2987         PyDict_SetItemString(py_domain_info, "trust_direction",
2988                         PyInt_FromLong(td->trust_direction));
2989         PyDict_SetItemString(py_domain_info, "trust_type",
2990                         PyInt_FromLong(td->trust_type));
2991         PyDict_SetItemString(py_domain_info, "trust_attributes",
2992                         PyInt_FromLong(td->trust_attributes));
2993         PyDict_SetItemString(py_domain_info, "trust_forest_trust_info",
2994                         PyString_FromStringAndSize((char *)td->trust_forest_trust_info.data,
2995                                                 td->trust_forest_trust_info.length));
2996
2997         talloc_free(tframe);
2998
2999         return py_domain_info;
3000 }
3001
3002
3003 static PyObject *py_pdb_set_trusted_domain(pytalloc_Object *self, PyObject *args)
3004 {
3005         NTSTATUS status;
3006         struct pdb_methods *methods;
3007         TALLOC_CTX *tframe;
3008         const char *domain;
3009         PyObject *py_td_info;
3010         struct pdb_trusted_domain td_info;
3011         PyObject *py_tmp;
3012         Py_ssize_t len;
3013
3014         if (!PyArg_ParseTuple(args, "sO!:set_trusted_domain", &domain, &PyDict_Type, &py_td_info)) {
3015                 return NULL;
3016         }
3017
3018         py_tmp = PyDict_GetItemString(py_td_info, "domain_name");
3019         td_info.domain_name = PyString_AsString(py_tmp);
3020
3021         py_tmp = PyDict_GetItemString(py_td_info, "netbios_name");
3022         td_info.netbios_name = PyString_AsString(py_tmp);
3023
3024         py_tmp = PyDict_GetItemString(py_td_info, "security_identifier");
3025         td_info.security_identifier = *pytalloc_get_type(py_tmp, struct dom_sid);
3026
3027         py_tmp = PyDict_GetItemString(py_td_info, "trust_auth_incoming");
3028         PyString_AsStringAndSize(py_tmp, (char **)&td_info.trust_auth_incoming.data, &len);
3029         td_info.trust_auth_incoming.length = len;
3030
3031         py_tmp = PyDict_GetItemString(py_td_info, "trust_auth_outgoing");
3032         PyString_AsStringAndSize(py_tmp, (char **)&td_info.trust_auth_outgoing.data, &len);
3033         td_info.trust_auth_outgoing.length = len;
3034
3035         py_tmp = PyDict_GetItemString(py_td_info, "trust_direction");
3036         td_info.trust_direction = PyInt_AsLong(py_tmp);
3037
3038         py_tmp = PyDict_GetItemString(py_td_info, "trust_type");
3039         td_info.trust_type = PyInt_AsLong(py_tmp);
3040
3041         py_tmp = PyDict_GetItemString(py_td_info, "trust_attributes");
3042         td_info.trust_attributes = PyInt_AsLong(py_tmp);
3043
3044         py_tmp = PyDict_GetItemString(py_td_info, "trust_forest_trust_info");
3045         PyString_AsStringAndSize(py_tmp, (char **)&td_info.trust_forest_trust_info.data, &len);
3046         td_info.trust_forest_trust_info.length = len;
3047
3048         methods = pytalloc_get_ptr(self);
3049
3050         if ((tframe = talloc_stackframe()) == NULL) {
3051                 PyErr_NoMemory();
3052                 return NULL;
3053         }
3054
3055         status = methods->set_trusted_domain(methods, domain, &td_info);
3056         if (!NT_STATUS_IS_OK(status)) {
3057                 PyErr_Format(py_pdb_error, "Unable to set trusted domain information, (%d,%s)",
3058                                 NT_STATUS_V(status),
3059                                 get_friendly_nt_error_msg(status));
3060                 talloc_free(tframe);
3061                 return NULL;
3062         }
3063
3064         talloc_free(tframe);
3065
3066         Py_RETURN_NONE;
3067 }
3068
3069
3070 static PyObject *py_pdb_del_trusted_domain(pytalloc_Object *self, PyObject *args)
3071 {
3072         NTSTATUS status;
3073         struct pdb_methods *methods;
3074         TALLOC_CTX *tframe;
3075         const char *domain;
3076
3077         if (!PyArg_ParseTuple(args, "s:del_trusted_domain", &domain)) {
3078                 return NULL;
3079         }
3080
3081         methods = pytalloc_get_ptr(self);
3082
3083         if ((tframe = talloc_stackframe()) == NULL) {
3084                 PyErr_NoMemory();
3085                 return NULL;
3086         }
3087
3088         status = methods->del_trusted_domain(methods, domain);
3089         if (!NT_STATUS_IS_OK(status)) {
3090                 PyErr_Format(py_pdb_error, "Unable to delete trusted domain, (%d,%s)",
3091                                 NT_STATUS_V(status),
3092                                 get_friendly_nt_error_msg(status));
3093                 talloc_free(tframe);
3094                 return NULL;
3095         }
3096
3097         talloc_free(tframe);
3098
3099         Py_RETURN_NONE;
3100 }
3101
3102
3103 static PyObject *py_pdb_enum_trusted_domains(pytalloc_Object *self)
3104 {
3105         NTSTATUS status;
3106         struct pdb_methods *methods;
3107         TALLOC_CTX *tframe;
3108         uint32_t num_domains;
3109         struct pdb_trusted_domain **td_info, *td;
3110         PyObject *py_td_info, *py_domain_info;
3111         int i;
3112
3113         methods = pytalloc_get_ptr(self);
3114
3115         if ((tframe = talloc_stackframe()) == NULL) {
3116                 PyErr_NoMemory();
3117                 return NULL;
3118         }
3119
3120         status = methods->enum_trusted_domains(methods, tframe, &num_domains, &td_info);
3121         if (!NT_STATUS_IS_OK(status)) {
3122                 PyErr_Format(py_pdb_error, "Unable to delete trusted domain, (%d,%s)",
3123                                 NT_STATUS_V(status),
3124                                 get_friendly_nt_error_msg(status));
3125                 talloc_free(tframe);
3126                 return NULL;
3127         }
3128
3129         py_td_info = PyList_New(0);
3130         if (py_td_info == NULL) {
3131                 PyErr_NoMemory();
3132                 talloc_free(tframe);
3133                 return NULL;
3134         }
3135
3136         for (i=0; i<num_domains; i++) {
3137
3138                 py_domain_info = PyDict_New();
3139                 if (py_domain_info == NULL) {
3140                         PyErr_NoMemory();
3141                         Py_DECREF(py_td_info);
3142                         talloc_free(tframe);
3143                         return NULL;
3144                 }
3145
3146                 td = td_info[i];
3147
3148                 PyDict_SetItemString(py_domain_info, "domain_name",
3149                                 PyString_FromString(td->domain_name));
3150                 PyDict_SetItemString(py_domain_info, "netbios_name",
3151                                 PyString_FromString(td->netbios_name));
3152                 PyDict_SetItemString(py_domain_info, "security_identifier",
3153                                 pytalloc_steal(dom_sid_Type, &td->security_identifier));
3154                 PyDict_SetItemString(py_domain_info, "trust_auth_incoming",
3155                                 PyString_FromStringAndSize((char *)td->trust_auth_incoming.data,
3156                                                         td->trust_auth_incoming.length));
3157                 PyDict_SetItemString(py_domain_info, "trust_auth_outgoing",
3158                                 PyString_FromStringAndSize((char *)td->trust_auth_outgoing.data,
3159                                                         td->trust_auth_outgoing.length));
3160                 PyDict_SetItemString(py_domain_info, "trust_direction",
3161                                 PyInt_FromLong(td->trust_direction));
3162                 PyDict_SetItemString(py_domain_info, "trust_type",
3163                                 PyInt_FromLong(td->trust_type));
3164                 PyDict_SetItemString(py_domain_info, "trust_attributes",
3165                                 PyInt_FromLong(td->trust_attributes));
3166                 PyDict_SetItemString(py_domain_info, "trust_forest_trust_info",
3167                                 PyString_FromStringAndSize((char *)td->trust_forest_trust_info.data,
3168                                                         td->trust_forest_trust_info.length));
3169                 PyList_Append(py_td_info, py_domain_info);
3170         }
3171
3172         talloc_free(tframe);
3173
3174         return py_td_info;
3175 }
3176
3177
3178 static PyObject *py_pdb_get_secret(pytalloc_Object *self, PyObject *args)
3179 {
3180         NTSTATUS status;
3181         struct pdb_methods *methods;
3182         TALLOC_CTX *tframe;
3183         const char *secret_name;
3184         DATA_BLOB secret_current, secret_old;
3185         NTTIME secret_current_lastchange, secret_old_lastchange;
3186         PyObject *py_sd;
3187         struct security_descriptor *sd;
3188         PyObject *py_secret;
3189
3190         if (!PyArg_ParseTuple(args, "s:get_secret_name", &secret_name)) {
3191                 return NULL;
3192         }
3193
3194         methods = pytalloc_get_ptr(self);
3195
3196         if ((tframe = talloc_stackframe()) == NULL) {
3197                 PyErr_NoMemory();
3198                 return NULL;
3199         }
3200
3201         py_sd = pytalloc_new(struct security_descriptor, security_Type);
3202         if (py_sd == NULL) {
3203                 PyErr_NoMemory();
3204                 talloc_free(tframe);
3205                 return NULL;
3206         }
3207         sd = pytalloc_get_ptr(py_sd);
3208
3209         status = methods->get_secret(methods, tframe, secret_name,
3210                                         &secret_current,
3211                                         &secret_current_lastchange,
3212                                         &secret_old,
3213                                         &secret_old_lastchange,
3214                                         &sd);
3215         if (!NT_STATUS_IS_OK(status)) {
3216                 PyErr_Format(py_pdb_error, "Unable to get information for secret (%s), (%d,%s)",
3217                                 secret_name,
3218                                 NT_STATUS_V(status),
3219                                 get_friendly_nt_error_msg(status));
3220                 talloc_free(tframe);
3221                 return NULL;
3222         }
3223
3224         py_secret = PyDict_New();
3225         if (py_secret == NULL) {
3226                 PyErr_NoMemory();
3227                 Py_DECREF(py_sd);
3228                 talloc_free(tframe);
3229                 return NULL;
3230         }
3231
3232         PyDict_SetItemString(py_secret, "secret_current",
3233                         PyString_FromStringAndSize((char *)secret_current.data, secret_current.length));
3234         PyDict_SetItemString(py_secret, "secret_current_lastchange",
3235                         PyLong_FromUnsignedLongLong(secret_current_lastchange));
3236         PyDict_SetItemString(py_secret, "secret_old",
3237                         PyString_FromStringAndSize((char *)secret_old.data, secret_old.length));
3238         PyDict_SetItemString(py_secret, "secret_old_lastchange",
3239                         PyLong_FromUnsignedLongLong(secret_old_lastchange));
3240         PyDict_SetItemString(py_secret, "sd", py_sd);
3241
3242         talloc_free(tframe);
3243
3244         return py_secret;
3245 }
3246
3247
3248 static PyObject *py_pdb_set_secret(pytalloc_Object *self, PyObject *args)
3249 {
3250         NTSTATUS status;
3251         struct pdb_methods *methods;
3252         TALLOC_CTX *tframe;
3253         const char *secret_name;
3254         PyObject *py_secret;
3255         PyObject *py_secret_cur, *py_secret_old, *py_sd;
3256         DATA_BLOB secret_current, secret_old;
3257         struct security_descriptor *sd;
3258         Py_ssize_t len;
3259
3260         if (!PyArg_ParseTuple(args, "sO!:set_secret_name", &secret_name, PyDict_Type, &py_secret)) {
3261                 return NULL;
3262         }
3263
3264         py_secret_cur = PyDict_GetItemString(py_secret, "secret_current");
3265         py_secret_old = PyDict_GetItemString(py_secret, "secret_old");
3266         py_sd = PyDict_GetItemString(py_secret, "sd");
3267
3268         PY_CHECK_TYPE(&PyString_Type, py_secret_cur, return NULL;);
3269         PY_CHECK_TYPE(&PyString_Type, py_secret_old, return NULL;);
3270         PY_CHECK_TYPE(security_Type, py_sd, return NULL;);
3271
3272         methods = pytalloc_get_ptr(self);
3273
3274         if ((tframe = talloc_stackframe()) == NULL) {
3275                 PyErr_NoMemory();
3276                 return NULL;
3277         }
3278
3279         PyString_AsStringAndSize(py_secret_cur, (char **)&secret_current.data, &len);
3280         secret_current.length = len;
3281         PyString_AsStringAndSize(py_secret_old, (char **)&secret_old.data, &len);
3282         secret_current.length = len;
3283         sd = pytalloc_get_ptr(py_sd);
3284
3285         status = methods->set_secret(methods, secret_name, &secret_current, &secret_old, sd);
3286         if (!NT_STATUS_IS_OK(status)) {
3287                 PyErr_Format(py_pdb_error, "Unable to set information for secret (%s), (%d,%s)",
3288                                 secret_name,
3289                                 NT_STATUS_V(status),
3290                                 get_friendly_nt_error_msg(status));
3291                 talloc_free(tframe);
3292                 return NULL;
3293         }
3294
3295         talloc_free(tframe);
3296
3297         Py_RETURN_NONE;
3298 }
3299
3300
3301 static PyObject *py_pdb_delete_secret(pytalloc_Object *self, PyObject *args)
3302 {
3303         NTSTATUS status;
3304         struct pdb_methods *methods;
3305         TALLOC_CTX *tframe;
3306         const char *secret_name;
3307
3308         if (!PyArg_ParseTuple(args, "s:delete_secret", &secret_name)) {
3309                 return NULL;
3310         }
3311
3312         methods = pytalloc_get_ptr(self);
3313
3314         if ((tframe = talloc_stackframe()) == NULL) {
3315                 PyErr_NoMemory();
3316                 return NULL;
3317         }
3318
3319         status = methods->delete_secret(methods, secret_name);
3320         if (!NT_STATUS_IS_OK(status)) {
3321                 PyErr_Format(py_pdb_error, "Unable to delete secret (%s), (%d,%s)",
3322                                 secret_name,
3323                                 NT_STATUS_V(status),
3324                                 get_friendly_nt_error_msg(status));
3325                 talloc_free(tframe);
3326                 return NULL;
3327         }
3328
3329         talloc_free(tframe);
3330
3331         Py_RETURN_NONE;
3332 }
3333
3334 static PyMethodDef py_pdb_methods[] = {
3335         { "domain_info", (PyCFunction)py_pdb_domain_info, METH_NOARGS,
3336                 "domain_info() -> str\n\n \
3337                 Get domain information for the database." },
3338         { "getsampwnam", (PyCFunction)py_pdb_getsampwnam, METH_VARARGS,
3339                 "getsampwnam(username) -> samu object\n\n \
3340                 Get user information by name." },
3341         { "getsampwsid", (PyCFunction)py_pdb_getsampwsid, METH_VARARGS,
3342                 "getsampwsid(user_sid) -> samu object\n\n \
3343                 Get user information by sid (dcerpc.security.dom_sid object)." },
3344         { "create_user", (PyCFunction)py_pdb_create_user, METH_VARARGS,
3345                 "create_user(username, acct_flags) -> rid\n\n \
3346                 Create user. acct_flags are samr account control flags." },
3347         { "delete_user", (PyCFunction)py_pdb_delete_user, METH_VARARGS,
3348                 "delete_user(samu object) -> None\n\n \
3349                 Delete user." },
3350         { "add_sam_account", (PyCFunction)py_pdb_add_sam_account, METH_VARARGS,
3351                 "add_sam_account(samu object) -> None\n\n \
3352                 Add SAM account." },
3353         { "update_sam_account", (PyCFunction)py_pdb_update_sam_account, METH_VARARGS,
3354                 "update_sam_account(samu object) -> None\n\n \
3355                 Update SAM account." },
3356         { "delete_sam_account", (PyCFunction)py_pdb_delete_sam_account, METH_VARARGS,
3357                 "delete_sam_account(samu object) -> None\n\n \
3358                 Delete SAM account." },
3359         { "rename_sam_account", (PyCFunction)py_pdb_rename_sam_account, METH_VARARGS,
3360                 "rename_sam_account(samu object1, new_username) -> None\n\n \
3361                 Rename SAM account." },
3362         /* update_login_attempts */
3363         { "getgrsid", (PyCFunction)py_pdb_getgrsid, METH_VARARGS,
3364                 "getgrsid(group_sid) -> groupmap object\n\n \
3365                 Get group information by sid (dcerpc.security.dom_sid object)." },
3366         { "getgrgid", (PyCFunction)py_pdb_getgrgid, METH_VARARGS,
3367                 "getgrsid(gid) -> groupmap object\n\n \
3368                 Get group information by gid." },
3369         { "getgrnam", (PyCFunction)py_pdb_getgrnam, METH_VARARGS,
3370                 "getgrsid(groupname) -> groupmap object\n\n \
3371                 Get group information by name." },
3372         { "create_dom_group", (PyCFunction)py_pdb_create_dom_group, METH_VARARGS,
3373                 "create_dom_group(groupname) -> group_rid\n\n \
3374                 Create new domain group by name." },
3375         { "delete_dom_group", (PyCFunction)py_pdb_delete_dom_group, METH_VARARGS,
3376                 "delete_dom_group(group_rid) -> None\n\n \
3377                 Delete domain group identified by rid" },
3378         { "add_group_mapping_entry", (PyCFunction)py_pdb_add_group_mapping_entry, METH_VARARGS,
3379                 "add_group_mapping_entry(groupmap) -> None\n \
3380                 Add group mapping entry for groupmap object." },
3381         { "update_group_mapping_entry", (PyCFunction)py_pdb_update_group_mapping_entry, METH_VARARGS,
3382                 "update_group_mapping_entry(groupmap) -> None\n\n \
3383                 Update group mapping entry for groupmap object." },
3384         { "delete_group_mapping_entry", (PyCFunction)py_pdb_delete_group_mapping_entry, METH_VARARGS,
3385                 "delete_group_mapping_entry(groupmap) -> None\n\n \
3386                 Delete group mapping entry for groupmap object." },
3387         { "enum_group_mapping", (PyCFunction)py_pdb_enum_group_mapping, METH_VARARGS,
3388                 "enum_group_mapping([domain_sid, [type, [unix_only]]]) -> List\n\n \
3389                 Return list of group mappings as groupmap objects. Optional arguments are domain_sid object, type of group, unix only flag." },
3390         { "enum_group_members", (PyCFunction)py_pdb_enum_group_members, METH_VARARGS,
3391                 "enum_group_members(group_sid) -> List\n\n \
3392                 Return list of users (dom_sid object) in group." },
3393         /* enum_group_memberships */
3394         /* set_unix_primary_group */
3395         { "add_groupmem", (PyCFunction)py_pdb_add_groupmem, METH_VARARGS,
3396                 "add_groupmem(group_rid, member_rid) -> None\n\n \
3397                 Add user to group." },
3398         { "del_groupmem", (PyCFunction)py_pdb_del_groupmem, METH_VARARGS,
3399                 "del_groupmem(group_rid, member_rid) -> None\n\n \
3400                 Remove user from from group." },
3401         { "create_alias", (PyCFunction)py_pdb_create_alias, METH_VARARGS,
3402                 "create_alias(alias_name) -> alias_rid\n\n \
3403                 Create alias entry." },
3404         { "delete_alias", (PyCFunction)py_pdb_delete_alias, METH_VARARGS,
3405                 "delete_alias(alias_sid) -> None\n\n \
3406                 Delete alias entry." },
3407         { "get_aliasinfo", (PyCFunction)py_pdb_get_aliasinfo, METH_VARARGS,
3408                 "get_aliasinfo(alias_sid) -> Mapping\n\n \
3409                 Get alias information as a dictionary with keys - acct_name, acct_desc, rid." },
3410         { "set_aliasinfo", (PyCFunction)py_pdb_set_aliasinfo, METH_VARARGS,
3411                 "set_alias_info(alias_sid, Mapping) -> None\n\n \
3412                 Set alias information from a dictionary with keys - acct_name, acct_desc." },
3413         { "add_aliasmem", (PyCFunction)py_pdb_add_aliasmem, METH_VARARGS,
3414                 "add_aliasmem(alias_sid, member_sid) -> None\n\n \
3415                 Add user to alias entry." },
3416         { "del_aliasmem", (PyCFunction)py_pdb_del_aliasmem, METH_VARARGS,
3417                 "del_aliasmem(alias_sid, member_sid) -> None\n\n \
3418                 Remove a user from alias entry." },
3419         { "enum_aliasmem", (PyCFunction)py_pdb_enum_aliasmem, METH_VARARGS,
3420                 "enum_aliasmem(alias_sid) -> List\n\n \
3421                 Return a list of members (dom_sid object) for alias entry." },
3422         /* enum_alias_memberships */
3423         /* lookup_rids */
3424         /* lookup_names */
3425         { "get_account_policy", (PyCFunction)py_pdb_get_account_policy, METH_NOARGS,
3426                 "get_account_policy() -> Mapping\n\n \
3427                 Get account policy information as a dictionary." },
3428         { "set_account_policy", (PyCFunction)py_pdb_set_account_policy, METH_VARARGS,
3429                 "get_account_policy(Mapping) -> None\n\n \
3430                 Set account policy settings from a dicionary." },
3431         /* get_seq_num */
3432         { "search_users", (PyCFunction)py_pdb_search_users, METH_VARARGS,
3433                 "search_users(acct_flags) -> List\n\n \
3434                 Search users. acct_flags are samr account control flags.\n \
3435                 Each list entry is dictionary with keys - idx, rid, acct_flags, account_name, fullname, description." },
3436         { "search_groups", (PyCFunction)py_pdb_search_groups, METH_NOARGS,
3437                 "search_groups() -> List\n\n \
3438                 Search unix only groups. \n \
3439                 Each list entry is dictionary with keys - idx, rid, acct_flags, account_name, fullname, description." },
3440         { "search_aliases", (PyCFunction)py_pdb_search_aliases, METH_VARARGS,
3441                 "search_aliases(domain_sid) -> List\n\n \
3442                 Search aliases. domain_sid is dcerpc.security.dom_sid object.\n \
3443                 Each list entry is dictionary with keys - idx, rid, acct_flags, account_name, fullname, description." },
3444         { "uid_to_sid", (PyCFunction)py_pdb_uid_to_sid, METH_VARARGS,
3445                 "uid_to_sid(uid) -> sid\n\n \
3446                 Return sid for given user id." },
3447         { "gid_to_sid", (PyCFunction)py_pdb_gid_to_sid, METH_VARARGS,
3448                 "gid_to_sid(gid) -> sid\n\n \
3449                 Return sid for given group id." },
3450         { "sid_to_id", (PyCFunction)py_pdb_sid_to_id, METH_VARARGS,
3451                 "sid_to_id(sid) -> Tuple\n\n \
3452                 Return id and type for given sid." },
3453         /* capabilities */
3454         { "new_rid", (PyCFunction)py_pdb_new_rid, METH_NOARGS,
3455                 "new_rid() -> rid\n\n \
3456                 Get a new rid." },
3457         { "get_trusteddom_pw", (PyCFunction)py_pdb_get_trusteddom_pw, METH_VARARGS,
3458                 "get_trusteddom_pw(domain) -> Mapping\n\n \
3459                 Get trusted domain password, sid and last set time in a dictionary." },
3460         { "set_trusteddom_pw", (PyCFunction)py_pdb_set_trusteddom_pw, METH_VARARGS,
3461                 "set_trusteddom_pw(domain, pwd, sid) -> None\n\n \
3462                 Set trusted domain password." },
3463         { "del_trusteddom_pw", (PyCFunction)py_pdb_del_trusteddom_pw, METH_VARARGS,
3464                 "del_trusteddom_pw(domain) -> None\n\n \
3465                 Delete trusted domain password." },
3466         { "enum_trusteddoms", (PyCFunction)py_pdb_enum_trusteddoms, METH_NOARGS,
3467                 "enum_trusteddoms() -> List\n\n \
3468                 Get list of trusted domains. Each item is a dictionary with name and sid keys" },
3469         { "get_trusted_domain", (PyCFunction)py_pdb_get_trusted_domain, METH_VARARGS,
3470                 "get_trusted_domain(domain) -> Mapping\n\n \
3471                 Get trusted domain information by name. Information is a dictionary with keys - domain_name, netbios_name, security_identifier, trust_auth_incoming, trust_auth_outgoing, trust_direction, trust_type, trust_attributes, trust_forest_trust_info." },
3472         { "get_trusted_domain_by_sid", (PyCFunction)py_pdb_get_trusted_domain_by_sid, METH_VARARGS,
3473                 "get_trusted_domain_by_sid(domain_sid) -> Mapping\n\n \
3474                 Get trusted domain information by sid. Information is a dictionary with keys - domain_name, netbios_name, security_identifier, trust_auth_incoming, trust_auth_outgoing, trust_direction, trust_type, trust_attributes, trust_forest_trust_info" },
3475         { "set_trusted_domain", (PyCFunction)py_pdb_set_trusted_domain, METH_VARARGS,
3476                 "set_trusted_domain(domain, Mapping) -> None\n\n \
3477                 Set trusted domain information for domain. Mapping is a dictionary with keys - domain_name, netbios_name, security_identifier, trust_auth_incoming, trust_auth_outgoing, trust_direction, trust_type, trust_attributes, trust_forest_trust_info." },
3478         { "del_trusted_domain", (PyCFunction)py_pdb_del_trusted_domain, METH_VARARGS,
3479                 "del_trusted_domain(domain) -> None\n\n \
3480                 Delete trusted domain." },
3481         { "enum_trusted_domains", (PyCFunction)py_pdb_enum_trusted_domains, METH_VARARGS,
3482                 "enum_trusted_domains() -> List\n\n \
3483                 Get list of trusted domains. Each entry is a dictionary with keys - domain_name, netbios_name, security_identifier, trust_auth_incoming, trust_auth_outgoing, trust_direction, trust_type, trust_attributes, trust_forest_trust_info." },
3484         { "get_secret", (PyCFunction)py_pdb_get_secret, METH_VARARGS,
3485                 "get_secret(secret_name) -> Mapping\n\n \
3486                 Get secret information for secret_name. Information is a dictionary with keys - secret_current, secret_current_lastchange, secret_old, secret_old_lastchange, sd." },
3487         { "set_secret", (PyCFunction)py_pdb_set_secret, METH_VARARGS,
3488                 "set_secret(secret_name, Mapping) -> None\n\n \
3489                 Set secret information for secret_name using dictionary with keys - secret_current, sd." },
3490         { "delete_secret", (PyCFunction)py_pdb_delete_secret, METH_VARARGS,
3491                 "delete_secret(secret_name) -> None\n\n \
3492                 Delete secret information for secret_name." },
3493         { NULL },
3494 };
3495
3496
3497 static PyObject *py_pdb_new(PyTypeObject *type, PyObject *args, PyObject *kwargs)
3498 {
3499         const char *url = NULL;
3500         PyObject *pypdb;
3501         NTSTATUS status;
3502         struct pdb_methods *methods;
3503
3504         if (!PyArg_ParseTuple(args, "s", &url)) {
3505                 return NULL;
3506         }
3507
3508         /* Initalize list of methods */
3509         status = make_pdb_method_name(&methods, url);
3510         if (!NT_STATUS_IS_OK(status)) {
3511                 PyErr_Format(py_pdb_error, "Cannot load backend methods for '%s' backend (%d,%s)",
3512                                 url,
3513                                 NT_STATUS_V(status),
3514                                 get_friendly_nt_error_msg(status));
3515                 return NULL;
3516         }
3517
3518         if ((pypdb = pytalloc_steal(type, methods)) == NULL) {
3519                 PyErr_NoMemory();
3520                 return NULL;
3521         }
3522
3523         return pypdb;
3524 }
3525
3526
3527 static PyTypeObject PyPDB = {
3528         .tp_name = "passdb.PDB",
3529         .tp_basicsize = sizeof(pytalloc_Object),
3530         .tp_new = py_pdb_new,
3531         .tp_flags = Py_TPFLAGS_DEFAULT,
3532         .tp_methods = py_pdb_methods,
3533         .tp_doc = "PDB(url[, read_write_flags]) -> Password DB object\n",
3534 };
3535
3536
3537 /*
3538  * Return a list of passdb backends
3539  */
3540 static PyObject *py_passdb_backends(PyObject *self)
3541 {
3542         PyObject *py_blist;
3543         const struct pdb_init_function_entry *entry;
3544         TALLOC_CTX *tframe;
3545
3546         if ((tframe = talloc_stackframe()) == NULL) {
3547                 PyErr_NoMemory();
3548                 return NULL;
3549         }
3550
3551         entry = pdb_get_backends();
3552         if(! entry) {
3553                 Py_RETURN_NONE;
3554         }
3555
3556         if((py_blist = PyList_New(0)) == NULL) {
3557                 PyErr_NoMemory();
3558                 return NULL;
3559         }
3560
3561         while(entry) {
3562                 PyList_Append(py_blist, PyString_FromString(entry->name));
3563                 entry = entry->next;
3564         }
3565
3566         talloc_free(tframe);
3567
3568         return py_blist;
3569 }
3570
3571
3572 static PyObject *py_set_smb_config(PyObject *self, PyObject *args)
3573 {
3574         const char *smb_config;
3575         TALLOC_CTX *tframe;
3576
3577         if (!PyArg_ParseTuple(args, "s", &smb_config)) {
3578                 return NULL;
3579         }
3580
3581         if ((tframe = talloc_stackframe()) == NULL) {
3582                 PyErr_NoMemory();
3583                 return NULL;
3584         }
3585
3586         /* Load smbconf parameters */
3587         if (!lp_load_global(smb_config)) {
3588                 PyErr_Format(py_pdb_error, "Cannot open '%s'", smb_config);
3589                 return NULL;
3590         }
3591
3592         talloc_free(tframe);
3593
3594         Py_RETURN_NONE;
3595 }
3596
3597
3598 static PyObject *py_set_secrets_dir(PyObject *self, PyObject *args)
3599 {
3600         const char *private_dir;
3601         TALLOC_CTX *tframe;
3602
3603         if (!PyArg_ParseTuple(args, "s", &private_dir)) {
3604                 return NULL;
3605         }
3606
3607         if ((tframe = talloc_stackframe()) == NULL) {
3608                 PyErr_NoMemory();
3609                 return NULL;
3610         }
3611
3612         /* Initialize secrets database */
3613         if (!secrets_init_path(private_dir)) {
3614                 PyErr_Format(py_pdb_error, "Cannot open secrets file database in '%s'",
3615                                 private_dir);
3616                 return NULL;
3617         }
3618
3619         talloc_free(tframe);
3620
3621         Py_RETURN_NONE;
3622 }
3623
3624 static PyObject *py_get_global_sam_sid(PyObject *self)
3625 {
3626         struct dom_sid *domain_sid, *domain_sid_copy;
3627         TALLOC_CTX *tframe;
3628         PyObject *py_dom_sid;
3629
3630         tframe = talloc_stackframe();
3631         if (tframe == NULL) {
3632                 PyErr_NoMemory();
3633                 return NULL;
3634         }
3635
3636         domain_sid = get_global_sam_sid();
3637
3638         domain_sid_copy = dom_sid_dup(tframe, domain_sid);
3639         if (domain_sid_copy == NULL) {
3640                 PyErr_NoMemory();
3641                 talloc_free(tframe);
3642                 return NULL;
3643         }
3644
3645         py_dom_sid = pytalloc_steal(dom_sid_Type, domain_sid_copy);
3646
3647         talloc_free(tframe);
3648
3649         return py_dom_sid;
3650 }
3651
3652
3653 static PyMethodDef py_passdb_methods[] = {
3654         { "get_backends", (PyCFunction)py_passdb_backends, METH_NOARGS,
3655                 "get_backends() -> list\n\n \
3656                 Get a list of password database backends supported." },
3657         { "set_smb_config", (PyCFunction)py_set_smb_config, METH_VARARGS,
3658                 "set_smb_config(path) -> None\n\n \
3659                 Set path to smb.conf file to load configuration parameters." },
3660         { "set_secrets_dir", (PyCFunction)py_set_secrets_dir, METH_VARARGS,
3661                 "set_secrets_dir(private_dir) -> None\n\n \
3662                 Set path to private directory to load secrets database from non-default location." },
3663         { "get_global_sam_sid", (PyCFunction)py_get_global_sam_sid, METH_NOARGS,
3664                 "get_global_sam_sid() -> dom_sid\n\n \
3665                 Return domain SID." },
3666         { NULL },
3667 };
3668
3669 void initpassdb(void)
3670 {
3671         PyObject *m, *mod;
3672         char exception_name[] = "passdb.error";
3673
3674         PyTypeObject *talloc_type = pytalloc_GetObjectType();
3675         if (talloc_type == NULL) {
3676                 return;
3677         }
3678
3679         PyPDB.tp_base = talloc_type;
3680         if (PyType_Ready(&PyPDB) < 0) {
3681                 return;
3682         }
3683
3684         PySamu.tp_base = talloc_type;
3685         if (PyType_Ready(&PySamu) < 0) {
3686                 return;
3687         }
3688
3689         PyGroupmap.tp_base = talloc_type;
3690         if (PyType_Ready(&PyGroupmap) < 0) {
3691                 return;
3692         }
3693
3694         m = Py_InitModule3("passdb", py_passdb_methods, "SAMBA Password Database");
3695         if (m == NULL) {
3696             return;
3697         }
3698
3699         /* Create new exception for passdb module */
3700         py_pdb_error = PyErr_NewException(exception_name, NULL, NULL);
3701         Py_INCREF(py_pdb_error);
3702         PyModule_AddObject(m, "error", py_pdb_error);
3703
3704         Py_INCREF(&PyPDB);
3705         PyModule_AddObject(m, "PDB", (PyObject *)&PyPDB);
3706
3707         Py_INCREF(&PySamu);
3708         PyModule_AddObject(m, "Samu", (PyObject *)&PySamu);
3709
3710         Py_INCREF(&PyGroupmap);
3711         PyModule_AddObject(m, "Groupmap", (PyObject *)&PyGroupmap);
3712
3713         /* Import dom_sid type from dcerpc.security */
3714         mod = PyImport_ImportModule("samba.dcerpc.security");
3715         if (mod == NULL) {
3716                 return;
3717         }
3718
3719         dom_sid_Type = (PyTypeObject *)PyObject_GetAttrString(mod, "dom_sid");
3720         if (dom_sid_Type == NULL) {
3721                 return;
3722         }
3723
3724         /* Import security_descriptor type from dcerpc.security */
3725         security_Type = (PyTypeObject *)PyObject_GetAttrString(mod, "descriptor");
3726         Py_DECREF(mod);
3727         if (security_Type == NULL) {
3728                 return;
3729         }
3730
3731         /* Import GUID type from dcerpc.misc */
3732         mod = PyImport_ImportModule("samba.dcerpc.misc");
3733         if (mod == NULL) {
3734                 return;
3735         }
3736
3737         guid_Type = (PyTypeObject *)PyObject_GetAttrString(mod, "GUID");
3738         Py_DECREF(mod);
3739         if (guid_Type == NULL) {
3740                 return;
3741         }
3742 }