LCOV - code coverage report
Current view: top level - source4/param - pyparam.c (source / functions) Hit Total Coverage
Test: coverage report for master 2b515b7d Lines: 271 353 76.8 %
Date: 2024-02-28 12:06:22 Functions: 28 32 87.5 %

          Line data    Source code
       1             : /*
       2             :    Unix SMB/CIFS implementation.
       3             :    Samba utility functions
       4             :    Copyright (C) Jelmer Vernooij <jelmer@samba.org> 2007-2008
       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 "lib/replace/system/python.h"
      21             : #include "python/py3compat.h"
      22             : #include "includes.h"
      23             : #include "param/param.h"
      24             : #include "param/loadparm.h"
      25             : #include <pytalloc.h>
      26             : #include "dynconfig/dynconfig.h"
      27             : 
      28             : #define PyLoadparmContext_AsLoadparmContext(obj) pytalloc_get_type(obj, struct loadparm_context)
      29             : #define PyLoadparmService_AsLoadparmService(obj) pytalloc_get_type(obj, struct loadparm_service)
      30             : 
      31             : extern PyTypeObject PyLoadparmContext;
      32             : extern PyTypeObject PyLoadparmService;
      33             : 
      34           2 : static PyObject *PyLoadparmService_FromService(struct loadparm_service *service)
      35             : {
      36           2 :         return pytalloc_reference(&PyLoadparmService, service);
      37             : }
      38             : 
      39       74827 : static PyObject *py_lp_ctx_get_helper(struct loadparm_context *lp_ctx, const char *service_name, const char *param_name)
      40             : {
      41       74827 :         struct parm_struct *parm = NULL;
      42       74827 :         void *parm_ptr = NULL;
      43        2079 :         int i;
      44             : 
      45       79751 :         if (service_name != NULL && strwicmp(service_name, GLOBAL_NAME) &&
      46        9826 :                 strwicmp(service_name, GLOBAL_NAME2)) {
      47         249 :                 struct loadparm_service *service;
      48             :                 /* its a share parameter */
      49        4924 :                 service = lpcfg_service(lp_ctx, service_name);
      50        4924 :                 if (service == NULL) {
      51          20 :                         return NULL;
      52             :                 }
      53        4902 :                 if (strchr(param_name, ':')) {
      54             :                         /* its a parametric option on a share */
      55           0 :                         const char *type = talloc_strndup(lp_ctx, param_name,
      56             :                                                                                           strcspn(param_name, ":"));
      57           0 :                         const char *option = strchr(param_name, ':') + 1;
      58           0 :                         const char *value;
      59           0 :                         if (type == NULL || option == NULL) {
      60           0 :                         return NULL;
      61             :                         }
      62           0 :                         value = lpcfg_get_parametric(lp_ctx, service, type, option);
      63           0 :                         if (value == NULL) {
      64           0 :                         return NULL;
      65             :                         }
      66           0 :                         return PyUnicode_FromString(value);
      67             :                 }
      68             : 
      69        4902 :                 parm = lpcfg_parm_struct(lp_ctx, param_name);
      70        4902 :                 if (parm == NULL || parm->p_class == P_GLOBAL) {
      71           0 :                         return NULL;
      72             :                 }
      73        4902 :                 parm_ptr = lpcfg_parm_ptr(lp_ctx, service, parm);
      74       69903 :     } else if (strchr(param_name, ':')) {
      75             :                 /* its a global parametric option */
      76       39311 :                 const char *type = talloc_strndup(lp_ctx,
      77             :                                   param_name, strcspn(param_name, ":"));
      78       39311 :                 const char *option = strchr(param_name, ':') + 1;
      79        1402 :                 const char *value;
      80       39311 :                 if (type == NULL || option == NULL) {
      81           0 :                         return NULL;
      82             :                 }
      83       39311 :                 value = lpcfg_get_parametric(lp_ctx, NULL, type, option);
      84       39311 :                 if (value == NULL)
      85         820 :                         return NULL;
      86       38127 :                 return PyUnicode_FromString(value);
      87             :         } else {
      88             :                 /* its a global parameter */
      89       30592 :                 parm = lpcfg_parm_struct(lp_ctx, param_name);
      90       30592 :                 if (parm == NULL) {
      91           0 :                         return NULL;
      92             :                 }
      93       30592 :                 parm_ptr = lpcfg_parm_ptr(lp_ctx, NULL, parm);
      94             :         }
      95             : 
      96       35494 :         if (parm == NULL || parm_ptr == NULL) {
      97           0 :                 return NULL;
      98             :     }
      99             : 
     100             :     /* construct and return the right type of python object */
     101       35494 :     switch (parm->type) {
     102           0 :     case P_CHAR:
     103           0 :         return PyUnicode_FromFormat("%c", *(char *)parm_ptr);
     104       17688 :     case P_STRING:
     105             :     case P_USTRING:
     106       17688 :         return PyUnicode_FromString(*(char **)parm_ptr);
     107         160 :     case P_BOOL:
     108         160 :         return PyBool_FromLong(*(bool *)parm_ptr);
     109           0 :     case P_BOOLREV:
     110           0 :         return PyBool_FromLong(!(*(bool *)parm_ptr));
     111       10141 :     case P_INTEGER:
     112             :     case P_OCTAL:
     113             :     case P_BYTES:
     114       10141 :         return PyLong_FromLong(*(int *)parm_ptr);
     115        2965 :     case P_ENUM:
     116        8617 :         for (i=0; parm->enum_list[i].name; i++) {
     117        8617 :             if (*(int *)parm_ptr == parm->enum_list[i].value) {
     118        3026 :                 return PyUnicode_FromString(parm->enum_list[i].name);
     119             :             }
     120             :         }
     121           0 :         return NULL;
     122        4479 :     case P_CMDLIST:
     123             :     case P_LIST:
     124             :         {
     125         203 :             int j;
     126        4479 :             const char **strlist = *(const char ***)parm_ptr;
     127         203 :             PyObject *pylist;
     128             : 
     129        4479 :             if(strlist == NULL) {
     130        3932 :                     return PyList_New(0);
     131             :             }
     132             : 
     133         547 :             pylist = PyList_New(str_list_length(strlist));
     134        4252 :             for (j = 0; strlist[j]; j++)
     135        3698 :                 PyList_SetItem(pylist, j,
     136        3661 :                                PyUnicode_FromString(strlist[j]));
     137         540 :             return pylist;
     138             :         }
     139             :     }
     140           0 :     return NULL;
     141             : 
     142             : }
     143             : 
     144       26335 : static PyObject *py_lp_ctx_load(PyObject *self, PyObject *args)
     145             : {
     146         323 :         char *filename;
     147         323 :         bool ret;
     148       26335 :         if (!PyArg_ParseTuple(args, "s", &filename))
     149           0 :                 return NULL;
     150             : 
     151       26335 :         ret = lpcfg_load(PyLoadparmContext_AsLoadparmContext(self), filename);
     152             : 
     153       26335 :         if (!ret) {
     154           0 :                 PyErr_Format(PyExc_RuntimeError, "Unable to load file %s", filename);
     155           0 :                 return NULL;
     156             :         }
     157       26335 :         Py_RETURN_NONE;
     158             : }
     159             : 
     160          87 : static PyObject *py_lp_ctx_load_default(PyObject *self, PyObject *unused)
     161             : {
     162           4 :         bool ret;
     163          87 :         ret = lpcfg_load_default(PyLoadparmContext_AsLoadparmContext(self));
     164             : 
     165          87 :         if (!ret) {
     166           0 :                 PyErr_SetString(PyExc_RuntimeError, "Unable to load default file");
     167           0 :                 return NULL;
     168             :         }
     169          87 :         Py_RETURN_NONE;
     170             : }
     171             : 
     172       74827 : static PyObject *py_lp_ctx_get(PyObject *self, PyObject *args)
     173             : {
     174        2079 :         char *param_name;
     175       74827 :         char *section_name = NULL;
     176        2079 :         PyObject *ret;
     177       74827 :         if (!PyArg_ParseTuple(args, "s|z", &param_name, &section_name))
     178           0 :                 return NULL;
     179             : 
     180       74827 :         ret = py_lp_ctx_get_helper(PyLoadparmContext_AsLoadparmContext(self), section_name, param_name);
     181       74827 :         if (ret == NULL)
     182        1206 :                 Py_RETURN_NONE;
     183       71908 :         return ret;
     184             : }
     185             : 
     186           2 : static PyObject *py_lp_ctx_is_myname(PyObject *self, PyObject *args)
     187             : {
     188           2 :         char *name;
     189           2 :         if (!PyArg_ParseTuple(args, "s", &name))
     190           0 :                 return NULL;
     191             : 
     192           2 :         return PyBool_FromLong(lpcfg_is_myname(PyLoadparmContext_AsLoadparmContext(self), name));
     193             : }
     194             : 
     195           2 : static PyObject *py_lp_ctx_is_mydomain(PyObject *self, PyObject *args)
     196             : {
     197           2 :         char *name;
     198           2 :         if (!PyArg_ParseTuple(args, "s", &name))
     199           0 :                 return NULL;
     200             : 
     201           2 :         return PyBool_FromLong(lpcfg_is_mydomain(PyLoadparmContext_AsLoadparmContext(self), name));
     202             : }
     203             : 
     204        4329 : static PyObject *py_lp_ctx_set(PyObject *self, PyObject *args)
     205             : {
     206         278 :         char *name, *value;
     207         278 :         bool ret;
     208        4329 :         if (!PyArg_ParseTuple(args, "ss", &name, &value))
     209           0 :                 return NULL;
     210             : 
     211        4329 :         ret = lpcfg_set_cmdline(PyLoadparmContext_AsLoadparmContext(self), name, value);
     212        4329 :         if (!ret) {
     213           2 :                 PyErr_SetString(PyExc_RuntimeError, "Unable to set parameter");
     214           2 :                 return NULL;
     215             :         }
     216             : 
     217        4327 :         Py_RETURN_NONE;
     218             : }
     219             : 
     220       32681 : static PyObject *py_lp_ctx_private_path(PyObject *self, PyObject *args)
     221             : {
     222         166 :         char *name, *path;
     223         166 :         PyObject *ret;
     224       32681 :         if (!PyArg_ParseTuple(args, "s", &name))
     225           0 :                 return NULL;
     226             : 
     227       32681 :         path = lpcfg_private_path(NULL, PyLoadparmContext_AsLoadparmContext(self), name);
     228       32681 :         ret = PyUnicode_FromString(path);
     229       32681 :         talloc_free(path);
     230             : 
     231       32681 :         return ret;
     232             : }
     233             : 
     234         272 : static PyObject *py_lp_ctx_services(PyObject *self, PyObject *unused)
     235             : {
     236         272 :         struct loadparm_context *lp_ctx = PyLoadparmContext_AsLoadparmContext(self);
     237          20 :         PyObject *ret;
     238          20 :         int i;
     239         272 :         ret = PyList_New(lpcfg_numservices(lp_ctx));
     240        4224 :         for (i = 0; i < lpcfg_numservices(lp_ctx); i++) {
     241        3932 :                 struct loadparm_service *service = lpcfg_servicebynum(lp_ctx, i);
     242        3932 :                 if (service != NULL) {
     243        3932 :                         PyList_SetItem(ret, i, PyUnicode_FromString(lpcfg_servicename(service)));
     244             :                 }
     245             :         }
     246         272 :         return ret;
     247             : }
     248             : 
     249         227 : static PyObject *py_lp_ctx_server_role(PyObject *self, PyObject *unused)
     250             : {
     251         227 :         struct loadparm_context *lp_ctx = PyLoadparmContext_AsLoadparmContext(self);
     252           5 :         uint32_t role;
     253           5 :         const char *role_str;
     254             : 
     255         227 :         role = lpcfg_server_role(lp_ctx);
     256         227 :         role_str = server_role_str(role);
     257             : 
     258         227 :         return PyUnicode_FromString(role_str);
     259             : }
     260             : 
     261         769 : static PyObject *py_lp_dump(PyObject *self, PyObject *args)
     262             : {
     263         769 :         bool show_defaults = false;
     264         769 :         const char *file_name = "";
     265         769 :         const char *mode = "w";
     266          25 :         FILE *f;
     267         769 :         struct loadparm_context *lp_ctx = PyLoadparmContext_AsLoadparmContext(self);
     268             : 
     269         769 :         if (!PyArg_ParseTuple(args, "|bss", &show_defaults, &file_name, &mode))
     270           0 :                 return NULL;
     271             : 
     272         769 :         if (file_name[0] == '\0') {
     273         537 :                 f = stdout;
     274             :         } else {
     275         232 :                 f = fopen(file_name, mode);
     276             :         }
     277             : 
     278         769 :         if (f == NULL) {
     279           0 :                 PyErr_SetFromErrno(PyExc_IOError);
     280           0 :                 return NULL;
     281             :         }
     282             : 
     283         769 :         lpcfg_dump(lp_ctx, f, show_defaults, lpcfg_numservices(lp_ctx));
     284             : 
     285         769 :         if (f != stdout) {
     286         232 :                 fclose(f);
     287             :         }
     288             : 
     289         769 :         Py_RETURN_NONE;
     290             : }
     291             : 
     292           2 : static PyObject *py_lp_dump_globals(PyObject *self, PyObject *args)
     293             : {
     294           2 :         bool show_defaults = false;
     295           2 :         const char *file_name = "";
     296           2 :         const char *mode = "w";
     297           2 :         FILE *f;
     298           2 :         struct loadparm_context *lp_ctx = PyLoadparmContext_AsLoadparmContext(self);
     299             : 
     300           2 :         if (!PyArg_ParseTuple(args, "|bss", &show_defaults, &file_name, &mode))
     301           0 :                 return NULL;
     302             : 
     303           2 :         if (file_name[0] == '\0') {
     304           2 :                 f = stdout;
     305             :         } else {
     306           0 :                 f = fopen(file_name, mode);
     307             :         }
     308             : 
     309           2 :         if (f == NULL) {
     310           0 :                 PyErr_SetFromErrno(PyExc_IOError);
     311           0 :                 return NULL;
     312             :         }
     313             : 
     314           2 :         lpcfg_dump_globals(lp_ctx, f, show_defaults);
     315             : 
     316           2 :         if (f != stdout) {
     317           0 :                 fclose(f);
     318             :         }
     319             : 
     320           2 :         Py_RETURN_NONE;
     321             : }
     322             : 
     323        1495 : static PyObject *py_lp_dump_a_parameter(PyObject *self, PyObject *args)
     324             : {
     325           6 :         char *param_name;
     326        1495 :         const char *section_name = NULL;
     327        1495 :         const char *file_name = "";
     328        1495 :         const char *mode = "w";
     329           6 :         FILE *f;
     330        1495 :         struct loadparm_context *lp_ctx = PyLoadparmContext_AsLoadparmContext(self);
     331           6 :         struct loadparm_service *service;
     332           6 :         bool ret;
     333             : 
     334        1495 :         if (!PyArg_ParseTuple(args, "s|zss", &param_name, &section_name, &file_name, &mode))
     335           0 :                 return NULL;
     336             : 
     337        1495 :         if (file_name[0] == '\0') {
     338        1494 :                 f = stdout;
     339             :         } else {
     340           1 :                 f = fopen(file_name, mode);
     341             :         }
     342             : 
     343        1495 :         if (f == NULL) {
     344           0 :                 return NULL;
     345             :         }
     346             : 
     347        1900 :         if (section_name != NULL && strwicmp(section_name, GLOBAL_NAME) &&
     348         405 :                 strwicmp(section_name, GLOBAL_NAME2)) {
     349             :                 /* it's a share parameter */
     350         405 :                 service = lpcfg_service(lp_ctx, section_name);
     351         405 :                 if (service == NULL) {
     352           1 :                         PyErr_Format(PyExc_RuntimeError, "Unknown section %s", section_name);
     353           1 :                         return NULL;
     354             :                 }
     355             :         } else {
     356             :                 /* it's global */
     357        1090 :                 service = NULL;
     358        1090 :                 section_name = "global";
     359             :         }
     360             : 
     361        1494 :         ret = lpcfg_dump_a_parameter(lp_ctx, service, param_name, f);
     362             : 
     363        1494 :         if (!ret) {
     364           1 :                 PyErr_Format(PyExc_RuntimeError, "Parameter %s unknown for section %s", param_name, section_name);
     365           1 :                 if (f != stdout) {
     366           0 :                         fclose(f);
     367             :                 }
     368           1 :                 return NULL;
     369             :         }
     370             : 
     371        1493 :         if (f != stdout) {
     372           1 :                 fclose(f);
     373             :         }
     374             : 
     375        1493 :         Py_RETURN_NONE;
     376             : 
     377             : }
     378             : 
     379        1370 : static PyObject *py_lp_log_level(PyObject *self, PyObject *unused)
     380             : {
     381        1370 :         int ret = debuglevel_get();
     382        1370 :         return PyLong_FromLong(ret);
     383             : }
     384             : 
     385             : 
     386        6360 : static PyObject *py_samdb_url(PyObject *self, PyObject *unused)
     387             : {
     388        6360 :         struct loadparm_context *lp_ctx = PyLoadparmContext_AsLoadparmContext(self);
     389        6360 :         return PyUnicode_FromFormat("tdb://%s/sam.ldb", lpcfg_private_dir(lp_ctx));
     390             : }
     391             : 
     392        4800 : static PyObject *py_cache_path(PyObject *self, PyObject *args)
     393             : {
     394        4800 :         struct loadparm_context *lp_ctx = PyLoadparmContext_AsLoadparmContext(self);
     395        4800 :         char *name = NULL;
     396        4800 :         char *path = NULL;
     397        4800 :         PyObject *ret = NULL;
     398             : 
     399        4800 :         if (!PyArg_ParseTuple(args, "s", &name)) {
     400           0 :                 return NULL;
     401             :         }
     402             : 
     403        4800 :         path = lpcfg_cache_path(NULL, lp_ctx, name);
     404        4800 :         if (!path) {
     405           0 :                 PyErr_Format(PyExc_RuntimeError,
     406             :                              "Unable to access cache %s", name);
     407           0 :                 return NULL;
     408             :         }
     409        4800 :         ret = PyUnicode_FromString(path);
     410        4800 :         talloc_free(path);
     411             : 
     412        4800 :         return ret;
     413             : }
     414             : 
     415         158 : static PyObject *py_state_path(PyObject *self, PyObject *args)
     416             : {
     417           0 :         struct loadparm_context *lp_ctx =
     418         158 :                 PyLoadparmContext_AsLoadparmContext(self);
     419         158 :         char *name = NULL;
     420         158 :         char *path = NULL;
     421         158 :         PyObject *ret = NULL;
     422             : 
     423         158 :         if (!PyArg_ParseTuple(args, "s", &name)) {
     424           0 :                 return NULL;
     425             :         }
     426             : 
     427         158 :         path = lpcfg_state_path(NULL, lp_ctx, name);
     428         158 :         if (!path) {
     429           0 :                 PyErr_Format(PyExc_RuntimeError,
     430             :                              "Unable to access cache %s", name);
     431           0 :                 return NULL;
     432             :         }
     433         158 :         ret = PyUnicode_FromString(path);
     434         158 :         talloc_free(path);
     435             : 
     436         158 :         return ret;
     437             : }
     438             : 
     439             : static PyMethodDef py_lp_ctx_methods[] = {
     440             :         { "load", py_lp_ctx_load, METH_VARARGS,
     441             :                 "S.load(filename) -> None\n"
     442             :                 "Load specified file." },
     443             :         { "load_default", py_lp_ctx_load_default, METH_NOARGS,
     444             :                 "S.load_default() -> None\n"
     445             :                 "Load default smb.conf file." },
     446             :         { "is_myname", py_lp_ctx_is_myname, METH_VARARGS,
     447             :                 "S.is_myname(name) -> bool\n"
     448             :                 "Check whether the specified name matches one of our netbios names." },
     449             :         { "is_mydomain", py_lp_ctx_is_mydomain, METH_VARARGS,
     450             :                 "S.is_mydomain(name) -> bool\n"
     451             :                 "Check whether the specified name matches our domain name." },
     452             :         { "get", py_lp_ctx_get, METH_VARARGS,
     453             :                 "S.get(name, service_name) -> value\n"
     454             :                 "Find specified parameter." },
     455             :         { "set", py_lp_ctx_set, METH_VARARGS,
     456             :                 "S.set(name, value) -> bool\n"
     457             :                 "Change a parameter." },
     458             :         { "private_path", py_lp_ctx_private_path, METH_VARARGS,
     459             :                 "S.private_path(name) -> path\n" },
     460             :         { "services", py_lp_ctx_services, METH_NOARGS,
     461             :                 "S.services() -> list" },
     462             :         { "server_role", py_lp_ctx_server_role, METH_NOARGS,
     463             :                 "S.server_role() -> value\n"
     464             :                 "Get the server role." },
     465             :         { "dump", py_lp_dump, METH_VARARGS,
     466             :                 "S.dump(show_defaults=False, file_name='', mode='w')" },
     467             :         { "dump_globals", py_lp_dump_globals, METH_VARARGS,
     468             :                 "S.dump_globals(show_defaults=False, file_name='', mode='w')" },
     469             :         { "dump_a_parameter", py_lp_dump_a_parameter, METH_VARARGS,
     470             :                 "S.dump_a_parameter(name, service_name, file_name='', mode='w')" },
     471             :         { "log_level", py_lp_log_level, METH_NOARGS,
     472             :                 "S.log_level() -> int\n Get the active log level" },
     473             :         { "samdb_url", py_samdb_url, METH_NOARGS,
     474             :                 "S.samdb_url() -> string\n"
     475             :                 "Returns the current URL for sam.ldb." },
     476             :         { "cache_path", py_cache_path, METH_VARARGS,
     477             :                 "S.cache_path(name) -> string\n"
     478             :                 "Returns a path in the Samba cache directory." },
     479             :         { "state_path", py_state_path, METH_VARARGS,
     480             :                 "S.state_path(name) -> string\n"
     481             :                 "Returns a path in the Samba state directory." },
     482             :         {0}
     483             : };
     484             : 
     485           1 : static PyObject *py_lp_ctx_default_service(PyObject *self, void *closure)
     486             : {
     487           1 :         return PyLoadparmService_FromService(lpcfg_default_service(PyLoadparmContext_AsLoadparmContext(self)));
     488             : }
     489             : 
     490        4778 : static PyObject *py_lp_ctx_config_file(PyObject *self, void *closure)
     491             : {
     492        4778 :         const char *configfile = lpcfg_configfile(PyLoadparmContext_AsLoadparmContext(self));
     493        4778 :         if (configfile == NULL)
     494           0 :                 Py_RETURN_NONE;
     495             :         else
     496        4778 :                 return PyUnicode_FromString(configfile);
     497             : }
     498             : 
     499           0 : static PyObject *py_lp_ctx_weak_crypto(PyObject *self, void *closure)
     500             : {
     501           0 :         enum samba_weak_crypto weak_crypto =
     502           0 :                 lpcfg_weak_crypto(PyLoadparmContext_AsLoadparmContext(self));
     503             : 
     504           0 :         switch(weak_crypto) {
     505           0 :         case SAMBA_WEAK_CRYPTO_UNKNOWN:
     506           0 :                 Py_RETURN_NONE;
     507           0 :         case SAMBA_WEAK_CRYPTO_ALLOWED:
     508           0 :                 return PyUnicode_FromString("allowed");
     509           0 :         case SAMBA_WEAK_CRYPTO_DISALLOWED:
     510           0 :                 return PyUnicode_FromString("disallowed");
     511             :         }
     512             : 
     513           0 :         Py_RETURN_NONE;
     514             : }
     515             : 
     516             : static PyGetSetDef py_lp_ctx_getset[] = {
     517             :         {
     518             :                 .name = discard_const_p(char, "default_service"),
     519             :                 .get  = (getter)py_lp_ctx_default_service,
     520             :         },
     521             :         {
     522             :                 .name = discard_const_p(char, "configfile"),
     523             :                 .get  = (getter)py_lp_ctx_config_file,
     524             :                 .doc  = discard_const_p(char, "Name of last config file that was loaded.")
     525             :         },
     526             :         {
     527             :                 .name = discard_const_p(char, "weak_crypto"),
     528             :                 .get  = (getter)py_lp_ctx_weak_crypto,
     529             :                 .doc  = discard_const_p(char, "If weak crypto is allowed.")
     530             :         },
     531             :         { .name = NULL }
     532             : };
     533             : 
     534       25008 : static PyObject *py_lp_ctx_new(PyTypeObject *type, PyObject *args, PyObject *kwargs)
     535             : {
     536       25008 :         const char *kwnames[] = {"filename_for_non_global_lp", NULL};
     537         283 :         PyObject *lp_ctx;
     538       25008 :         const char *non_global_conf = NULL;
     539         283 :         struct loadparm_context *ctx;
     540             : 
     541       25008 :         if (!PyArg_ParseTupleAndKeywords(args,
     542             :                                          kwargs,
     543             :                                          "|s",
     544             :                                          discard_const_p(char *,
     545             :                                                          kwnames),
     546             :                                          &non_global_conf)) {
     547           0 :                 return NULL;
     548             :         }
     549             : 
     550             :         /*
     551             :          * by default, any LoadParm python objects map to a single global
     552             :          * underlying object. The filename_for_non_global_lp arg overrides this
     553             :          * default behaviour and creates a separate underlying LoadParm object.
     554             :          */
     555       25008 :         if (non_global_conf != NULL) {
     556          10 :                 bool ok;
     557         108 :                 ctx = loadparm_init(NULL);
     558         108 :                 if (ctx == NULL) {
     559           0 :                         PyErr_NoMemory();
     560           0 :                         return NULL;
     561             :                 }
     562             : 
     563         108 :                 lp_ctx = pytalloc_reference(type, ctx);
     564         108 :                 if (lp_ctx == NULL) {
     565           0 :                         PyErr_NoMemory();
     566           0 :                         return NULL;
     567             :                 }
     568             : 
     569         108 :                 ok = lpcfg_load_no_global(
     570         108 :                         PyLoadparmContext_AsLoadparmContext(lp_ctx),
     571             :                         non_global_conf);
     572         108 :                 if (!ok) {
     573           2 :                         PyErr_Format(PyExc_ValueError,
     574             :                                      "Could not load non-global conf %s",
     575             :                                      non_global_conf);
     576           2 :                         return NULL;
     577             :                 }
     578          98 :                 return lp_ctx;
     579             :         } else{
     580       24900 :                 return pytalloc_reference(type, loadparm_init_global(false));
     581             :         }
     582             : }
     583             : 
     584           7 : static Py_ssize_t py_lp_ctx_len(PyObject *self)
     585             : {
     586           7 :         return lpcfg_numservices(PyLoadparmContext_AsLoadparmContext(self));
     587             : }
     588             : 
     589           5 : static PyObject *py_lp_ctx_getitem(PyObject *self, PyObject *name)
     590             : {
     591           5 :         struct loadparm_service *service;
     592           5 :         if (!PyUnicode_Check(name)) {
     593           0 :                 PyErr_SetString(PyExc_TypeError, "Only string subscripts are supported");
     594           0 :                 return NULL;
     595             :         }
     596           5 :         service = lpcfg_service(PyLoadparmContext_AsLoadparmContext(self), PyUnicode_AsUTF8(name));
     597           5 :         if (service == NULL) {
     598           4 :                 PyErr_SetString(PyExc_KeyError, "No such section");
     599           4 :                 return NULL;
     600             :         }
     601           1 :         return PyLoadparmService_FromService(service);
     602             : }
     603             : 
     604             : static PyMappingMethods py_lp_ctx_mapping = {
     605             :         .mp_length = (lenfunc)py_lp_ctx_len,
     606             :         .mp_subscript = (binaryfunc)py_lp_ctx_getitem,
     607             : };
     608             : 
     609             : PyTypeObject PyLoadparmContext = {
     610             :         .tp_name = "param.LoadParm",
     611             :         .tp_getset = py_lp_ctx_getset,
     612             :         .tp_methods = py_lp_ctx_methods,
     613             :         .tp_new = py_lp_ctx_new,
     614             :         .tp_as_mapping = &py_lp_ctx_mapping,
     615             :         .tp_flags = Py_TPFLAGS_DEFAULT,
     616             : };
     617             : 
     618           1 : static PyObject *py_lp_service_dump(PyObject *self, PyObject *args)
     619             : {
     620           1 :         bool show_defaults = false;
     621           1 :         FILE *f;
     622           1 :         const char *file_name = "";
     623           1 :         const char *mode = "w";
     624           1 :         struct loadparm_service *service = PyLoadparmService_AsLoadparmService(self);
     625           1 :         struct loadparm_service *default_service;
     626           1 :         PyObject *py_default_service;
     627             : 
     628           1 :         if (!PyArg_ParseTuple(args, "O|bss", &py_default_service, &show_defaults, &file_name, &mode))
     629           0 :                 return NULL;
     630             : 
     631           1 :         if (file_name[0] == '\0') {
     632           1 :                 f = stdout;
     633             :         } else {
     634           0 :                 f = fopen(file_name, mode);
     635             :         }
     636             : 
     637           1 :         if (f == NULL) {
     638           0 :                 return NULL;
     639             :         }
     640             : 
     641           1 :         if (!PyObject_TypeCheck(py_default_service, &PyLoadparmService)) {
     642           0 :                 PyErr_SetNone(PyExc_TypeError);
     643           0 :                 if (f != stdout) {
     644           0 :                         fclose(f);
     645             :                 }
     646           0 :                 return NULL;
     647             :         }
     648             : 
     649           1 :         default_service = PyLoadparmService_AsLoadparmService(py_default_service);
     650             : 
     651           1 :         lpcfg_dump_one(f, show_defaults, service, default_service);
     652             : 
     653           1 :         if (f != stdout) {
     654           0 :                 fclose(f);
     655             :         }
     656             : 
     657           1 :         Py_RETURN_NONE;
     658             : }
     659             : 
     660             : static PyMethodDef py_lp_service_methods[] = {
     661             :         { "dump", (PyCFunction)py_lp_service_dump, METH_VARARGS,
     662             :                 "S.dump(default_service, show_defaults=False, file_name='', mode='w')" },
     663             :         {0}
     664             : };
     665             : 
     666             : PyTypeObject PyLoadparmService = {
     667             :         .tp_name = "param.LoadparmService",
     668             :         .tp_methods = py_lp_service_methods,
     669             :         .tp_flags = Py_TPFLAGS_DEFAULT,
     670             : };
     671             : 
     672         296 : static PyObject *py_data_dir(PyObject *self, PyObject *Py_UNUSED(ignored))
     673             : {
     674         296 :         return PyUnicode_FromString(dyn_DATADIR);
     675             : }
     676             : 
     677           0 : static PyObject *py_default_path(PyObject *self, PyObject *Py_UNUSED(ignored))
     678             : {
     679           0 :         return PyUnicode_FromString(lp_default_path());
     680             : }
     681             : 
     682        8328 : static PyObject *py_setup_dir(PyObject *self, PyObject *Py_UNUSED(ignored))
     683             : {
     684        8328 :         return PyUnicode_FromString(dyn_SETUPDIR);
     685             : }
     686             : 
     687       35032 : static PyObject *py_modules_dir(PyObject *self, PyObject *Py_UNUSED(ignored))
     688             : {
     689       35032 :         return PyUnicode_FromString(dyn_MODULESDIR);
     690             : }
     691             : 
     692         503 : static PyObject *py_bin_dir(PyObject *self, PyObject *Py_UNUSED(ignored))
     693             : {
     694         503 :         return PyUnicode_FromString(dyn_BINDIR);
     695             : }
     696             : 
     697           0 : static PyObject *py_sbin_dir(PyObject *self, PyObject *Py_UNUSED(ignored))
     698             : {
     699           0 :         return PyUnicode_FromString(dyn_SBINDIR);
     700             : }
     701             : 
     702             : static PyMethodDef pyparam_methods[] = {
     703             :         { "data_dir", (PyCFunction)py_data_dir, METH_NOARGS,
     704             :                 "Returns the compiled in location of data directory." },
     705             :         { "default_path", (PyCFunction)py_default_path, METH_NOARGS,
     706             :                 "Returns the default smb.conf path." },
     707             :         { "setup_dir", (PyCFunction)py_setup_dir, METH_NOARGS,
     708             :                 "Returns the compiled in location of provision templates." },
     709             :         { "modules_dir", (PyCFunction)py_modules_dir, METH_NOARGS,
     710             :                 "Returns the compiled in location of modules." },
     711             :         { "bin_dir", (PyCFunction)py_bin_dir, METH_NOARGS,
     712             :                 "Returns the compiled in BINDIR." },
     713             :         { "sbin_dir", (PyCFunction)py_sbin_dir, METH_NOARGS,
     714             :                 "Returns the compiled in SBINDIR." },
     715             :         {0}
     716             : };
     717             : 
     718             : static struct PyModuleDef moduledef = {
     719             :         PyModuleDef_HEAD_INIT,
     720             :         .m_name = "param",
     721             :         .m_doc = "Parsing and writing Samba configuration files.",
     722             :         .m_size = -1,
     723             :         .m_methods = pyparam_methods,
     724             : };
     725             : 
     726       13165 : MODULE_INIT_FUNC(param)
     727             : {
     728         537 :         PyObject *m;
     729       13165 :         PyTypeObject *talloc_type = pytalloc_GetObjectType();
     730       13165 :         if (talloc_type == NULL)
     731           0 :                 return NULL;
     732             : 
     733       13165 :         if (pytalloc_BaseObject_PyType_Ready(&PyLoadparmContext) < 0)
     734           0 :                 return NULL;
     735             : 
     736       13165 :         if (pytalloc_BaseObject_PyType_Ready(&PyLoadparmService) < 0)
     737           0 :                 return NULL;
     738             : 
     739       13165 :         m = PyModule_Create(&moduledef);
     740       13165 :         if (m == NULL)
     741           0 :                 return NULL;
     742             : 
     743       11035 :         Py_INCREF(&PyLoadparmContext);
     744       13165 :         PyModule_AddObject(m, "LoadParm", (PyObject *)&PyLoadparmContext);
     745       13165 :         return m;
     746             : }

Generated by: LCOV version 1.14