auth pycredentials: incorrect PyArg_ParseTupleAndKeywords call
[metze/samba/wip.git] / auth / credentials / pycredentials.c
1 /* 
2    Unix SMB/CIFS implementation.
3    Copyright (C) Jelmer Vernooij <jelmer@samba.org> 2007
4    
5    This program is free software; you can redistribute it and/or modify
6    it under the terms of the GNU General Public License as published by
7    the Free Software Foundation; either version 3 of the License, or
8    (at your option) any later version.
9    
10    This program is distributed in the hope that it will be useful,
11    but WITHOUT ANY WARRANTY; without even the implied warranty of
12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13    GNU General Public License for more details.
14    
15    You should have received a copy of the GNU General Public License
16    along with this program.  If not, see <http://www.gnu.org/licenses/>.
17 */
18
19 #include <Python.h>
20 #include "python/py3compat.h"
21 #include "includes.h"
22 #include "pycredentials.h"
23 #include "param/param.h"
24 #include "lib/cmdline/credentials.h"
25 #include "librpc/gen_ndr/samr.h" /* for struct samr_Password */
26 #include "libcli/util/pyerrors.h"
27 #include "param/pyparam.h"
28 #include <tevent.h>
29
30 void initcredentials(void);
31
32 static PyObject *PyString_FromStringOrNULL(const char *str)
33 {
34         if (str == NULL)
35                 Py_RETURN_NONE;
36         return PyStr_FromString(str);
37 }
38
39 static PyObject *py_creds_new(PyTypeObject *type, PyObject *args, PyObject *kwargs)
40 {
41         return pytalloc_steal(type, cli_credentials_init(NULL));
42 }
43
44 static PyObject *py_creds_get_username(PyObject *self, PyObject *unused)
45 {
46         return PyString_FromStringOrNULL(cli_credentials_get_username(PyCredentials_AsCliCredentials(self)));
47 }
48
49 static PyObject *py_creds_set_username(PyObject *self, PyObject *args)
50 {
51         char *newval;
52         enum credentials_obtained obt = CRED_SPECIFIED;
53         int _obt = obt;
54
55         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
56                 return NULL;
57         }
58         obt = _obt;
59
60         return PyBool_FromLong(cli_credentials_set_username(PyCredentials_AsCliCredentials(self), newval, obt));
61 }
62
63 static PyObject *py_creds_get_ntlm_username_domain(PyObject *self, PyObject *unused)
64 {
65         TALLOC_CTX *frame = talloc_stackframe();
66         const char *user = NULL;
67         const char *domain = NULL;
68         PyObject *ret = NULL;
69         cli_credentials_get_ntlm_username_domain(PyCredentials_AsCliCredentials(self),
70                                                  frame, &user, &domain);
71         ret = Py_BuildValue("(OO)",
72                             PyString_FromStringOrNULL(user),
73                             PyString_FromStringOrNULL(domain));
74         TALLOC_FREE(frame);
75         return ret;
76 }
77
78 static PyObject *py_creds_get_ntlm_response(PyObject *self, PyObject *args, PyObject *kwargs)
79 {
80         TALLOC_CTX *frame = talloc_stackframe();
81         PyObject *ret = NULL;
82         int flags;
83         struct timeval tv_now;
84         NTTIME server_timestamp;
85         DATA_BLOB challenge = data_blob_null;
86         DATA_BLOB target_info = data_blob_null;
87         NTSTATUS status;
88         DATA_BLOB lm_response = data_blob_null;
89         DATA_BLOB nt_response = data_blob_null;
90         DATA_BLOB lm_session_key = data_blob_null;
91         DATA_BLOB nt_session_key = data_blob_null;
92         const char *kwnames[] = { "flags", "challenge",
93                                   "target_info",
94                                   NULL };
95
96         tv_now = timeval_current();
97         server_timestamp = timeval_to_nttime(&tv_now);
98
99         if (!PyArg_ParseTupleAndKeywords(args, kwargs, "is#|s#",
100                                          discard_const_p(char *, kwnames),
101                                          &flags,
102                                          &challenge.data,
103                                          &challenge.length,
104                                          &target_info.data,
105                                          &target_info.length)) {
106                 return NULL;
107         }
108
109         status = cli_credentials_get_ntlm_response(PyCredentials_AsCliCredentials(self),
110                                                    frame, &flags,
111                                                    challenge,
112                                                    &server_timestamp,
113                                                    target_info,
114                                                    &lm_response, &nt_response,
115                                                    &lm_session_key, &nt_session_key);
116
117         if (!NT_STATUS_IS_OK(status)) {
118                 PyErr_SetNTSTATUS(status);
119                 TALLOC_FREE(frame);
120                 return NULL;
121         }
122
123         ret = Py_BuildValue("{sis" PYARG_BYTES_LEN "s" PYARG_BYTES_LEN
124                                     "s" PYARG_BYTES_LEN "s" PYARG_BYTES_LEN "}",
125                             "flags", flags,
126                             "lm_reponse",
127                             (const char *)lm_response.data, lm_response.length,
128                             "nt_response",
129                             (const char *)nt_response.data, nt_response.length,
130                             "lm_session_key",
131                             (const char *)lm_session_key.data, lm_session_key.length,
132                             "nt_session_key",
133                             (const char *)nt_session_key.data, nt_session_key.length);
134         TALLOC_FREE(frame);
135         return ret;
136 }
137
138 static PyObject *py_creds_get_principal(PyObject *self, PyObject *unused)
139 {
140         TALLOC_CTX *frame = talloc_stackframe();
141         PyObject *ret = PyString_FromStringOrNULL(cli_credentials_get_principal(PyCredentials_AsCliCredentials(self), frame));
142         TALLOC_FREE(frame);
143         return ret;
144 }
145
146 static PyObject *py_creds_set_principal(PyObject *self, PyObject *args)
147 {
148         char *newval;
149         enum credentials_obtained obt = CRED_SPECIFIED;
150         int _obt = obt;
151
152         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
153                 return NULL;
154         }
155         obt = _obt;
156
157         return PyBool_FromLong(cli_credentials_set_principal(PyCredentials_AsCliCredentials(self), newval, obt));
158 }
159
160 static PyObject *py_creds_get_password(PyObject *self, PyObject *unused)
161 {
162         return PyString_FromStringOrNULL(cli_credentials_get_password(PyCredentials_AsCliCredentials(self)));
163 }
164
165 static PyObject *py_creds_set_password(PyObject *self, PyObject *args)
166 {
167         char *newval;
168         enum credentials_obtained obt = CRED_SPECIFIED;
169         int _obt = obt;
170
171         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
172                 return NULL;
173         }
174         obt = _obt;
175
176         return PyBool_FromLong(cli_credentials_set_password(PyCredentials_AsCliCredentials(self), newval, obt));
177 }
178
179 static PyObject *py_creds_set_utf16_password(PyObject *self, PyObject *args)
180 {
181         enum credentials_obtained obt = CRED_SPECIFIED;
182         int _obt = obt;
183         PyObject *newval = NULL;
184         DATA_BLOB blob = data_blob_null;
185         Py_ssize_t size =  0;
186         int result;
187         bool ok;
188
189         if (!PyArg_ParseTuple(args, "O|i", &newval, &_obt)) {
190                 return NULL;
191         }
192         obt = _obt;
193
194         result = PyBytes_AsStringAndSize(newval, (char **)&blob.data, &size);
195         if (result != 0) {
196                 PyErr_SetString(PyExc_RuntimeError, "Failed to convert passed value to Bytes");
197                 return NULL;
198         }
199         blob.length = size;
200
201         ok = cli_credentials_set_utf16_password(PyCredentials_AsCliCredentials(self),
202                                                 &blob, obt);
203
204         return PyBool_FromLong(ok);
205 }
206
207 static PyObject *py_creds_get_old_password(PyObject *self, PyObject *unused)
208 {
209         return PyString_FromStringOrNULL(cli_credentials_get_old_password(PyCredentials_AsCliCredentials(self)));
210 }
211
212 static PyObject *py_creds_set_old_password(PyObject *self, PyObject *args)
213 {
214         char *oldval;
215         enum credentials_obtained obt = CRED_SPECIFIED;
216         int _obt = obt;
217
218         if (!PyArg_ParseTuple(args, "s|i", &oldval, &_obt)) {
219                 return NULL;
220         }
221         obt = _obt;
222
223         return PyBool_FromLong(cli_credentials_set_old_password(PyCredentials_AsCliCredentials(self), oldval, obt));
224 }
225
226 static PyObject *py_creds_set_old_utf16_password(PyObject *self, PyObject *args)
227 {
228         PyObject *oldval = NULL;
229         DATA_BLOB blob = data_blob_null;
230         Py_ssize_t size =  0;
231         int result;
232         bool ok;
233
234         if (!PyArg_ParseTuple(args, "O", &oldval)) {
235                 return NULL;
236         }
237
238         result = PyBytes_AsStringAndSize(oldval, (char **)&blob.data, &size);
239         if (result != 0) {
240                 PyErr_SetString(PyExc_RuntimeError, "Failed to convert passed value to Bytes");
241                 return NULL;
242         }
243         blob.length = size;
244
245         ok = cli_credentials_set_old_utf16_password(PyCredentials_AsCliCredentials(self),
246                                                     &blob);
247
248         return PyBool_FromLong(ok);
249 }
250
251 static PyObject *py_creds_get_domain(PyObject *self, PyObject *unused)
252 {
253         return PyString_FromStringOrNULL(cli_credentials_get_domain(PyCredentials_AsCliCredentials(self)));
254 }
255
256 static PyObject *py_creds_set_domain(PyObject *self, PyObject *args)
257 {
258         char *newval;
259         enum credentials_obtained obt = CRED_SPECIFIED;
260         int _obt = obt;
261
262         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
263                 return NULL;
264         }
265         obt = _obt;
266
267         return PyBool_FromLong(cli_credentials_set_domain(PyCredentials_AsCliCredentials(self), newval, obt));
268 }
269
270 static PyObject *py_creds_get_realm(PyObject *self, PyObject *unused)
271 {
272         return PyString_FromStringOrNULL(cli_credentials_get_realm(PyCredentials_AsCliCredentials(self)));
273 }
274
275 static PyObject *py_creds_set_realm(PyObject *self, PyObject *args)
276 {
277         char *newval;
278         enum credentials_obtained obt = CRED_SPECIFIED;
279         int _obt = obt;
280
281         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
282                 return NULL;
283         }
284         obt = _obt;
285
286         return PyBool_FromLong(cli_credentials_set_realm(PyCredentials_AsCliCredentials(self), newval, obt));
287 }
288
289 static PyObject *py_creds_get_bind_dn(PyObject *self, PyObject *unused)
290 {
291         return PyString_FromStringOrNULL(cli_credentials_get_bind_dn(PyCredentials_AsCliCredentials(self)));
292 }
293
294 static PyObject *py_creds_set_bind_dn(PyObject *self, PyObject *args)
295 {
296         char *newval;
297         if (!PyArg_ParseTuple(args, "s", &newval))
298                 return NULL;
299
300         return PyBool_FromLong(cli_credentials_set_bind_dn(PyCredentials_AsCliCredentials(self), newval));
301 }
302
303 static PyObject *py_creds_get_workstation(PyObject *self, PyObject *unused)
304 {
305         return PyString_FromStringOrNULL(cli_credentials_get_workstation(PyCredentials_AsCliCredentials(self)));
306 }
307
308 static PyObject *py_creds_set_workstation(PyObject *self, PyObject *args)
309 {
310         char *newval;
311         enum credentials_obtained obt = CRED_SPECIFIED;
312         int _obt = obt;
313
314         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
315                 return NULL;
316         }
317         obt = _obt;
318
319         return PyBool_FromLong(cli_credentials_set_workstation(PyCredentials_AsCliCredentials(self), newval, obt));
320 }
321
322 static PyObject *py_creds_is_anonymous(PyObject *self, PyObject *unused)
323 {
324         return PyBool_FromLong(cli_credentials_is_anonymous(PyCredentials_AsCliCredentials(self)));
325 }
326
327 static PyObject *py_creds_set_anonymous(PyObject *self, PyObject *unused)
328 {
329         cli_credentials_set_anonymous(PyCredentials_AsCliCredentials(self));
330         Py_RETURN_NONE;
331 }
332
333 static PyObject *py_creds_authentication_requested(PyObject *self, PyObject *unused)
334 {
335         return PyBool_FromLong(cli_credentials_authentication_requested(PyCredentials_AsCliCredentials(self)));
336 }
337
338 static PyObject *py_creds_wrong_password(PyObject *self, PyObject *unused)
339 {
340         return PyBool_FromLong(cli_credentials_wrong_password(PyCredentials_AsCliCredentials(self)));
341 }
342
343 static PyObject *py_creds_set_cmdline_callbacks(PyObject *self, PyObject *unused)
344 {
345         return PyBool_FromLong(cli_credentials_set_cmdline_callbacks(PyCredentials_AsCliCredentials(self)));
346 }
347
348 static PyObject *py_creds_parse_string(PyObject *self, PyObject *args)
349 {
350         char *newval;
351         enum credentials_obtained obt = CRED_SPECIFIED;
352         int _obt = obt;
353
354         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
355                 return NULL;
356         }
357         obt = _obt;
358
359         cli_credentials_parse_string(PyCredentials_AsCliCredentials(self), newval, obt);
360         Py_RETURN_NONE;
361 }
362
363 static PyObject *py_creds_parse_file(PyObject *self, PyObject *args)
364 {
365         char *newval;
366         enum credentials_obtained obt = CRED_SPECIFIED;
367         int _obt = obt;
368
369         if (!PyArg_ParseTuple(args, "s|i", &newval, &_obt)) {
370                 return NULL;
371         }
372         obt = _obt;
373
374         cli_credentials_parse_file(PyCredentials_AsCliCredentials(self), newval, obt);
375         Py_RETURN_NONE;
376 }
377
378 static PyObject *py_cli_credentials_set_password_will_be_nt_hash(PyObject *self, PyObject *args)
379 {
380         struct cli_credentials *creds = PyCredentials_AsCliCredentials(self);
381         PyObject *py_val = NULL;
382         bool val = false;
383
384         if (!PyArg_ParseTuple(args, "O!", &PyBool_Type, &py_val)) {
385                 return NULL;
386         }
387         val = PyObject_IsTrue(py_val);
388
389         cli_credentials_set_password_will_be_nt_hash(creds, val);
390         Py_RETURN_NONE;
391 }
392
393 static PyObject *py_creds_get_nt_hash(PyObject *self, PyObject *unused)
394 {
395         PyObject *ret;
396         struct cli_credentials *creds = PyCredentials_AsCliCredentials(self);
397         struct samr_Password *ntpw = cli_credentials_get_nt_hash(creds, creds);
398
399         ret = PyBytes_FromStringAndSize(discard_const_p(char, ntpw->hash), 16);
400         TALLOC_FREE(ntpw);
401         return ret;
402 }
403
404 static PyObject *py_creds_get_kerberos_state(PyObject *self, PyObject *unused)
405 {
406         int state = cli_credentials_get_kerberos_state(PyCredentials_AsCliCredentials(self));
407         return PyInt_FromLong(state);
408 }
409
410 static PyObject *py_creds_set_kerberos_state(PyObject *self, PyObject *args)
411 {
412         int state;
413         if (!PyArg_ParseTuple(args, "i", &state))
414                 return NULL;
415
416         cli_credentials_set_kerberos_state(PyCredentials_AsCliCredentials(self), state);
417         Py_RETURN_NONE;
418 }
419
420 static PyObject *py_creds_set_krb_forwardable(PyObject *self, PyObject *args)
421 {
422         int state;
423         if (!PyArg_ParseTuple(args, "i", &state))
424                 return NULL;
425
426         cli_credentials_set_krb_forwardable(PyCredentials_AsCliCredentials(self), state);
427         Py_RETURN_NONE;
428 }
429
430
431 static PyObject *py_creds_get_forced_sasl_mech(PyObject *self, PyObject *unused)
432 {
433         return PyString_FromStringOrNULL(cli_credentials_get_forced_sasl_mech(PyCredentials_AsCliCredentials(self)));
434 }
435
436 static PyObject *py_creds_set_forced_sasl_mech(PyObject *self, PyObject *args)
437 {
438         char *newval;
439         enum credentials_obtained obt = CRED_SPECIFIED;
440         int _obt = obt;
441
442         if (!PyArg_ParseTuple(args, "s", &newval)) {
443                 return NULL;
444         }
445         obt = _obt;
446
447         cli_credentials_set_forced_sasl_mech(PyCredentials_AsCliCredentials(self), newval);
448         Py_RETURN_NONE;
449 }
450
451 static PyObject *py_creds_guess(PyObject *self, PyObject *args)
452 {
453         PyObject *py_lp_ctx = Py_None;
454         struct loadparm_context *lp_ctx;
455         TALLOC_CTX *mem_ctx;
456         struct cli_credentials *creds;
457
458         creds = PyCredentials_AsCliCredentials(self);
459
460         if (!PyArg_ParseTuple(args, "|O", &py_lp_ctx))
461                 return NULL;
462
463         mem_ctx = talloc_new(NULL);
464         if (mem_ctx == NULL) {
465                 PyErr_NoMemory();
466                 return NULL;
467         }
468
469         lp_ctx = lpcfg_from_py_object(mem_ctx, py_lp_ctx);
470         if (lp_ctx == NULL) {
471                 talloc_free(mem_ctx);
472                 return NULL;
473         }
474
475         cli_credentials_guess(creds, lp_ctx);
476
477         talloc_free(mem_ctx);
478
479         Py_RETURN_NONE;
480 }
481
482 static PyObject *py_creds_set_machine_account(PyObject *self, PyObject *args)
483 {
484         PyObject *py_lp_ctx = Py_None;
485         struct loadparm_context *lp_ctx;
486         NTSTATUS status;
487         struct cli_credentials *creds;
488         TALLOC_CTX *mem_ctx;
489
490         creds = PyCredentials_AsCliCredentials(self);
491
492         if (!PyArg_ParseTuple(args, "|O", &py_lp_ctx))
493                 return NULL;
494
495         mem_ctx = talloc_new(NULL);
496         if (mem_ctx == NULL) {
497                 PyErr_NoMemory();
498                 return NULL;
499         }
500
501         lp_ctx = lpcfg_from_py_object(mem_ctx, py_lp_ctx);
502         if (lp_ctx == NULL) {
503                 talloc_free(mem_ctx);
504                 return NULL;
505         }
506
507         status = cli_credentials_set_machine_account(creds, lp_ctx);
508         talloc_free(mem_ctx);
509
510         PyErr_NTSTATUS_IS_ERR_RAISE(status);
511
512         Py_RETURN_NONE;
513 }
514
515 static PyObject *PyCredentialCacheContainer_from_ccache_container(struct ccache_container *ccc)
516 {
517         return pytalloc_reference(&PyCredentialCacheContainer, ccc);
518 }
519
520
521 static PyObject *py_creds_get_named_ccache(PyObject *self, PyObject *args)
522 {
523         PyObject *py_lp_ctx = Py_None;
524         char *ccache_name;
525         struct loadparm_context *lp_ctx;
526         struct ccache_container *ccc;
527         struct tevent_context *event_ctx;
528         int ret;
529         const char *error_string;
530         struct cli_credentials *creds;
531         TALLOC_CTX *mem_ctx;
532
533         creds = PyCredentials_AsCliCredentials(self);
534
535         if (!PyArg_ParseTuple(args, "|Os", &py_lp_ctx, &ccache_name))
536                 return NULL;
537
538         mem_ctx = talloc_new(NULL);
539         if (mem_ctx == NULL) {
540                 PyErr_NoMemory();
541                 return NULL;
542         }
543
544         lp_ctx = lpcfg_from_py_object(mem_ctx, py_lp_ctx);
545         if (lp_ctx == NULL) {
546                 talloc_free(mem_ctx);
547                 return NULL;
548         }
549
550         event_ctx = samba_tevent_context_init(mem_ctx);
551
552         ret = cli_credentials_get_named_ccache(creds, event_ctx, lp_ctx,
553                                                ccache_name, &ccc, &error_string);
554         talloc_unlink(mem_ctx, lp_ctx);
555         if (ret == 0) {
556                 talloc_steal(ccc, event_ctx);
557                 talloc_free(mem_ctx);
558                 return PyCredentialCacheContainer_from_ccache_container(ccc);
559         }
560
561         PyErr_SetString(PyExc_RuntimeError, error_string?error_string:"NULL");
562
563         talloc_free(mem_ctx);
564         return NULL;
565 }
566
567 static PyObject *py_creds_set_gensec_features(PyObject *self, PyObject *args)
568 {
569         unsigned int gensec_features;
570
571         if (!PyArg_ParseTuple(args, "I", &gensec_features))
572                 return NULL;
573
574         cli_credentials_set_gensec_features(PyCredentials_AsCliCredentials(self), gensec_features);
575
576         Py_RETURN_NONE;
577 }
578
579 static PyObject *py_creds_get_gensec_features(PyObject *self, PyObject *args)
580 {
581         unsigned int gensec_features;
582
583         gensec_features = cli_credentials_get_gensec_features(PyCredentials_AsCliCredentials(self));
584         return PyInt_FromLong(gensec_features);
585 }
586
587 static PyObject *py_creds_set_secure_channel_type(PyObject *self, PyObject *args)
588 {
589         unsigned int channel_type;
590
591         if (!PyArg_ParseTuple(args, "I", &channel_type))
592                 return NULL;
593
594         cli_credentials_set_secure_channel_type(
595                 PyCredentials_AsCliCredentials(self),
596                 channel_type);
597
598         Py_RETURN_NONE;
599 }
600
601
602 static PyMethodDef py_creds_methods[] = {
603         { "get_username", py_creds_get_username, METH_NOARGS,
604                 "S.get_username() -> username\nObtain username." },
605         { "set_username", py_creds_set_username, METH_VARARGS,
606                 "S.set_username(name[, credentials.SPECIFIED]) -> None\n"
607                 "Change username." },
608         { "get_principal", py_creds_get_principal, METH_NOARGS,
609                 "S.get_principal() -> user@realm\nObtain user principal." },
610         { "set_principal", py_creds_set_principal, METH_VARARGS,
611                 "S.set_principal(name[, credentials.SPECIFIED]) -> None\n"
612                 "Change principal." },
613         { "get_password", py_creds_get_password, METH_NOARGS,
614                 "S.get_password() -> password\n"
615                 "Obtain password." },
616         { "get_ntlm_username_domain", py_creds_get_ntlm_username_domain, METH_NOARGS,
617                 "S.get_ntlm_username_domain() -> (domain, username)\n"
618                 "Obtain NTLM username and domain, split up either as (DOMAIN, user) or (\"\", \"user@realm\")." },
619         { "get_ntlm_response", (PyCFunction)py_creds_get_ntlm_response, METH_VARARGS | METH_KEYWORDS,
620                 "S.get_ntlm_response"
621                 "(flags, challenge[, target_info]) -> "
622                 "(flags, lm_response, nt_response, lm_session_key, nt_session_key)\n"
623                 "Obtain LM or NTLM response." },
624         { "set_password", py_creds_set_password, METH_VARARGS,
625                 "S.set_password(password[, credentials.SPECIFIED]) -> None\n"
626                 "Change password." },
627         { "set_utf16_password", py_creds_set_utf16_password, METH_VARARGS,
628                 "S.set_utf16_password(password[, credentials.SPECIFIED]) -> None\n"
629                 "Change password." },
630         { "get_old_password", py_creds_get_old_password, METH_NOARGS,
631                 "S.get_old_password() -> password\n"
632                 "Obtain old password." },
633         { "set_old_password", py_creds_set_old_password, METH_VARARGS,
634                 "S.set_old_password(password[, credentials.SPECIFIED]) -> None\n"
635                 "Change old password." },
636         { "set_old_utf16_password", py_creds_set_old_utf16_password, METH_VARARGS,
637                 "S.set_old_utf16_password(password[, credentials.SPECIFIED]) -> None\n"
638                 "Change old password." },
639         { "get_domain", py_creds_get_domain, METH_NOARGS,
640                 "S.get_domain() -> domain\n"
641                 "Obtain domain name." },
642         { "set_domain", py_creds_set_domain, METH_VARARGS,
643                 "S.set_domain(domain[, credentials.SPECIFIED]) -> None\n"
644                 "Change domain name." },
645         { "get_realm", py_creds_get_realm, METH_NOARGS,
646                 "S.get_realm() -> realm\n"
647                 "Obtain realm name." },
648         { "set_realm", py_creds_set_realm, METH_VARARGS,
649                 "S.set_realm(realm[, credentials.SPECIFIED]) -> None\n"
650                 "Change realm name." },
651         { "get_bind_dn", py_creds_get_bind_dn, METH_NOARGS,
652                 "S.get_bind_dn() -> bind dn\n"
653                 "Obtain bind DN." },
654         { "set_bind_dn", py_creds_set_bind_dn, METH_VARARGS,
655                 "S.set_bind_dn(bind_dn) -> None\n"
656                 "Change bind DN." },
657         { "is_anonymous", py_creds_is_anonymous, METH_NOARGS,
658                 NULL },
659         { "set_anonymous", py_creds_set_anonymous, METH_NOARGS,
660                 "S.set_anonymous() -> None\n"
661                 "Use anonymous credentials." },
662         { "get_workstation", py_creds_get_workstation, METH_NOARGS,
663                 NULL },
664         { "set_workstation", py_creds_set_workstation, METH_VARARGS,
665                 NULL },
666         { "authentication_requested", py_creds_authentication_requested, METH_NOARGS,
667                 NULL },
668         { "wrong_password", py_creds_wrong_password, METH_NOARGS,
669                 "S.wrong_password() -> bool\n"
670                 "Indicate the returned password was incorrect." },
671         { "set_cmdline_callbacks", py_creds_set_cmdline_callbacks, METH_NOARGS,
672                 "S.set_cmdline_callbacks() -> bool\n"
673                 "Use command-line to obtain credentials not explicitly set." },
674         { "parse_string", py_creds_parse_string, METH_VARARGS,
675                 "S.parse_string(text[, credentials.SPECIFIED]) -> None\n"
676                 "Parse credentials string." },
677         { "parse_file", py_creds_parse_file, METH_VARARGS,
678                 "S.parse_file(filename[, credentials.SPECIFIED]) -> None\n"
679                 "Parse credentials file." },
680         { "set_password_will_be_nt_hash",
681                 py_cli_credentials_set_password_will_be_nt_hash, METH_VARARGS,
682                 "S.set_password_will_be_nt_hash(bool) -> None\n"
683                 "Alters the behaviour of S.set_password() "
684                 "to expect the NTHASH as hexstring." },
685         { "get_nt_hash", py_creds_get_nt_hash, METH_NOARGS,
686                 NULL },
687         { "get_kerberos_state", py_creds_get_kerberos_state, METH_NOARGS,
688                 NULL },
689         { "set_kerberos_state", py_creds_set_kerberos_state, METH_VARARGS,
690                 NULL },
691         { "set_krb_forwardable", py_creds_set_krb_forwardable, METH_VARARGS,
692                 NULL },
693         { "guess", py_creds_guess, METH_VARARGS, NULL },
694         { "set_machine_account", py_creds_set_machine_account, METH_VARARGS, NULL },
695         { "get_named_ccache", py_creds_get_named_ccache, METH_VARARGS, NULL },
696         { "set_gensec_features", py_creds_set_gensec_features, METH_VARARGS, NULL },
697         { "get_gensec_features", py_creds_get_gensec_features, METH_NOARGS, NULL },
698         { "get_forced_sasl_mech", py_creds_get_forced_sasl_mech, METH_NOARGS,
699                 "S.get_forced_sasl_mech() -> SASL mechanism\nObtain forced SASL mechanism." },
700         { "set_forced_sasl_mech", py_creds_set_forced_sasl_mech, METH_VARARGS,
701                 "S.set_forced_sasl_mech(name) -> None\n"
702                 "Set forced SASL mechanism." },
703         { "set_secure_channel_type", py_creds_set_secure_channel_type,
704           METH_VARARGS, NULL },
705         { NULL }
706 };
707
708 static struct PyModuleDef moduledef = {
709     PyModuleDef_HEAD_INIT,
710     .m_name = "credentials",
711     .m_doc = "Credentials management.",
712     .m_size = -1,
713     .m_methods = py_creds_methods,
714 };
715
716 PyTypeObject PyCredentials = {
717         .tp_name = "credentials.Credentials",
718         .tp_new = py_creds_new,
719         .tp_flags = Py_TPFLAGS_DEFAULT,
720         .tp_methods = py_creds_methods,
721 };
722
723
724 PyTypeObject PyCredentialCacheContainer = {
725         .tp_name = "credentials.CredentialCacheContainer",
726         .tp_flags = Py_TPFLAGS_DEFAULT,
727 };
728
729 MODULE_INIT_FUNC(credentials)
730 {
731         PyObject *m;
732         if (pytalloc_BaseObject_PyType_Ready(&PyCredentials) < 0)
733                 return NULL;
734
735         if (pytalloc_BaseObject_PyType_Ready(&PyCredentialCacheContainer) < 0)
736                 return NULL;
737
738         m = PyModule_Create(&moduledef);
739         if (m == NULL)
740                 return NULL;
741
742         PyModule_AddObject(m, "UNINITIALISED", PyInt_FromLong(CRED_UNINITIALISED));
743         PyModule_AddObject(m, "CALLBACK", PyInt_FromLong(CRED_CALLBACK));
744         PyModule_AddObject(m, "GUESS_ENV", PyInt_FromLong(CRED_GUESS_ENV));
745         PyModule_AddObject(m, "GUESS_FILE", PyInt_FromLong(CRED_GUESS_FILE));
746         PyModule_AddObject(m, "CALLBACK_RESULT", PyInt_FromLong(CRED_CALLBACK_RESULT));
747         PyModule_AddObject(m, "SPECIFIED", PyInt_FromLong(CRED_SPECIFIED));
748
749         PyModule_AddObject(m, "AUTO_USE_KERBEROS", PyInt_FromLong(CRED_AUTO_USE_KERBEROS));
750         PyModule_AddObject(m, "DONT_USE_KERBEROS", PyInt_FromLong(CRED_DONT_USE_KERBEROS));
751         PyModule_AddObject(m, "MUST_USE_KERBEROS", PyInt_FromLong(CRED_MUST_USE_KERBEROS));
752
753         PyModule_AddObject(m, "AUTO_KRB_FORWARDABLE",  PyInt_FromLong(CRED_AUTO_KRB_FORWARDABLE));
754         PyModule_AddObject(m, "NO_KRB_FORWARDABLE",    PyInt_FromLong(CRED_NO_KRB_FORWARDABLE));
755         PyModule_AddObject(m, "FORCE_KRB_FORWARDABLE", PyInt_FromLong(CRED_FORCE_KRB_FORWARDABLE));
756         PyModule_AddObject(m, "CLI_CRED_NTLM2", PyInt_FromLong(CLI_CRED_NTLM2));
757         PyModule_AddObject(m, "CLI_CRED_NTLMv2_AUTH", PyInt_FromLong(CLI_CRED_NTLMv2_AUTH));
758         PyModule_AddObject(m, "CLI_CRED_LANMAN_AUTH", PyInt_FromLong(CLI_CRED_LANMAN_AUTH));
759         PyModule_AddObject(m, "CLI_CRED_NTLM_AUTH", PyInt_FromLong(CLI_CRED_NTLM_AUTH));
760         PyModule_AddObject(m, "CLI_CRED_CLEAR_AUTH", PyInt_FromLong(CLI_CRED_CLEAR_AUTH));
761
762         Py_INCREF(&PyCredentials);
763         PyModule_AddObject(m, "Credentials", (PyObject *)&PyCredentials);
764         Py_INCREF(&PyCredentialCacheContainer);
765         PyModule_AddObject(m, "CredentialCacheContainer", (PyObject *)&PyCredentialCacheContainer);
766         return m;
767 }