r25598: Add missing become_root/unbecome_root around calls of add_aliases.
[samba.git] / source / python / py_spoolss.c
index ead54febda2dbb08778b0d9addb669eda2b21778..2543324b318262d4815dc31286f872f88f9b7e2f 100644 (file)
@@ -5,7 +5,7 @@
    
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
-   the Free Software Foundation; either version 2 of the License, or
+   the Free Software Foundation; either version 3 of the License, or
    (at your option) any later version.
    
    This program is distributed in the hope that it will be useful,
@@ -14,8 +14,7 @@
    GNU General Public License for more details.
    
    You should have received a copy of the GNU General Public License
-   along with this program; if not, write to the Free Software
-   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
 
 #include "python/py_spoolss.h"
 
 PyObject *spoolss_error, *spoolss_werror;
 
-/*
- * Routines to convert from python hashes to Samba structures
- */
-
-struct cli_state *open_pipe_creds(char *system_name, PyObject *creds, 
-                                 cli_pipe_fn *connect_fn,
-                                 struct cli_state *cli)
-{
-       struct ntuser_creds nt_creds;
-
-       if (!cli) {
-               cli = (struct cli_state *)malloc(sizeof(struct cli_state));
-               if (!cli)
-                       return NULL;
-       }
-
-       ZERO_STRUCTP(cli);
-
-       /* Extract credentials from the python dictionary and initialise
-          the ntuser_creds struct from them. */
-
-       ZERO_STRUCT(nt_creds);
-       nt_creds.pwd.null_pwd = True;
-
-       if (creds && PyDict_Size(creds) > 0) {
-               char *username, *password, *domain;
-               PyObject *username_obj, *password_obj, *domain_obj;
-
-               /* Check credentials passed are valid.  This means the
-                  username, domain and password keys must exist and be
-                  string objects. */
-
-               username_obj = PyDict_GetItemString(creds, "username");
-               domain_obj = PyDict_GetItemString(creds, "domain");
-               password_obj = PyDict_GetItemString(creds, "password");
-
-               if (!username_obj || !domain_obj || !password_obj) {
-               error:
-                       PyErr_SetString(spoolss_error, "invalid credentials");
-                       return NULL;
-               }
-
-               if (!PyString_Check(username_obj) || 
-                   !PyString_Check(domain_obj) || 
-                   !PyString_Check(password_obj))
-                       goto error;
-
-               username = PyString_AsString(username_obj);
-               domain = PyString_AsString(domain_obj);
-               password = PyString_AsString(password_obj);
-
-               if (!username || !domain || !password)
-                       goto error;
-
-               /* Initialise nt_creds structure with passed creds */
-
-               fstrcpy(nt_creds.user_name, username);
-               fstrcpy(nt_creds.domain, domain);
-
-               if (lp_encrypted_passwords())
-                       pwd_make_lm_nt_16(&nt_creds.pwd, password);
-               else
-                       pwd_set_cleartext(&nt_creds.pwd, password);
-
-               nt_creds.pwd.null_pwd = False;
-       }
-
-       /* Now try to connect */
-
-       connect_fn(cli, system_name, &nt_creds);
-
-       return cli;
-}
-
-PyObject *new_policy_hnd_object(struct cli_state *cli, TALLOC_CTX *mem_ctx, 
-                               POLICY_HND *pol)
-{
-       spoolss_policy_hnd_object *o;
-
-       o = PyObject_New(spoolss_policy_hnd_object, &spoolss_policy_hnd_type);
-
-       o->cli = cli;
-       o->mem_ctx = mem_ctx;
-       memcpy(&o->pol, pol, sizeof(POLICY_HND));
-
-       return (PyObject*)o;
-}
-     
 /* 
  * Method dispatch table
  */
@@ -120,141 +31,265 @@ static PyMethodDef spoolss_methods[] = {
 
        /* Open/close printer handles */
        
-       { "openprinter", spoolss_openprinter, METH_VARARGS | METH_KEYWORDS, 
-         "openprinter(printername, [creds, access]) -> <spoolss hnd object>
+       { "openprinter", (PyCFunction)spoolss_openprinter, METH_VARARGS | METH_KEYWORDS, 
+         "Open a printer by name in UNC format.\n"
+"\n"
+"Optionally a dictionary of (domain, username, password) may be given in\n"
+"which case they are used when opening the RPC pipe.  An access mask may\n"
+"also be given which defaults to MAXIMUM_ALLOWED_ACCESS.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> hnd = spoolss.openprinter(\"\\\\\\\\NPSD-PDC2\\\\meanie\")"},
+       
+       { "closeprinter", spoolss_closeprinter, METH_VARARGS, 
+         "Close a printer handle opened with openprinter or addprinter.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> spoolss.closeprinter(hnd)"},
 
-Open a printer given by printername in UNC format.  Optionally a 
-dictionary of (username, password) may be given in which case they are
-used when opening the RPC pipe.  An access mask may also be given which
-defaults to MAXIMUM_ALLOWED_ACCESS.
+       { "addprinterex", (PyCFunction)spoolss_addprinterex, METH_VARARGS, 
+         "addprinterex()"},
 
-Example:
+       /* Server enumeratation functions */
 
->>> hnd = spoolss.openprinter(\"\\\\\\\\NPSD-PDC2\\\\meanie\")
-"},
-       
-       { "closeprinter", spoolss_closeprinter, METH_VARARGS, 
-         "closeprinter()
+       { "enumprinters", (PyCFunction)spoolss_enumprinters, 
+         METH_VARARGS | METH_KEYWORDS,
+         "Enumerate printers on a print server.\n"
+"\n"
+"Return a list of printers on a print server.  The credentials, info level\n"
+"and flags may be specified as keyword arguments.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> print spoolss.enumprinters(\"\\\\\\\\npsd-pdc2\")\n"
+"[{'comment': 'i am a comment', 'printer_name': 'meanie', 'flags': 8388608, \n"
+"  'description': 'meanie,Generic / Text Only,i am a location'}, \n"
+" {'comment': '', 'printer_name': 'fileprint', 'flags': 8388608, \n"
+"  'description': 'fileprint,Generic / Text Only,'}]"},
+
+       { "enumports", (PyCFunction)spoolss_enumports, 
+         METH_VARARGS | METH_KEYWORDS,
+         "Enumerate ports on a print server.\n"
+"\n"
+"Return a list of ports on a print server.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> print spoolss.enumports(\"\\\\\\\\npsd-pdc2\")\n"
+"[{'name': 'LPT1:'}, {'name': 'LPT2:'}, {'name': 'COM1:'}, \n"
+"{'name': 'COM2:'}, {'name': 'FILE:'}, {'name': '\\\\nautilus1\\zpekt3r'}]"},
+
+       { "enumprinterdrivers", (PyCFunction)spoolss_enumprinterdrivers, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Enumerate printer drivers on a print server.\n"
+"\n"
+"Return a list of printer drivers."},
+
+       /* Miscellaneous other commands */
 
-Close a printer handle opened with openprinter or addprinter.
+       { "getprinterdriverdir", (PyCFunction)spoolss_getprinterdriverdir, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Return printer driver directory.\n"
+"\n"
+"Return the printer driver directory for a given architecture.  The\n"
+"architecture defaults to \"Windows NT x86\"."},
 
-Example:
+       /* Other stuff - this should really go into a samba config module
+          but for the moment let's leave it here. */
 
->>> spoolss.closeprinter(hnd)
-"},
+       { "setup_logging", (PyCFunction)py_setup_logging, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Set up debug logging.\n"
+"\n"
+"Initialises Samba's debug logging system.  One argument is expected which\n"
+"is a boolean specifying whether debugging is interactive and sent to stdout\n"
+"or logged to a file.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> spoolss.setup_logging(interactive = 1)" },
+
+       { "get_debuglevel", (PyCFunction)get_debuglevel, 
+         METH_VARARGS, 
+         "Set the current debug level.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> spoolss.get_debuglevel()\n"
+"0" },
+
+       { "set_debuglevel", (PyCFunction)set_debuglevel, 
+         METH_VARARGS, 
+         "Get the current debug level.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> spoolss.set_debuglevel(10)" },
+
+       /* Printer driver routines */
+       
+       { "addprinterdriver", (PyCFunction)spoolss_addprinterdriver, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Add a printer driver." },
 
-       /* Server enumeratation functions */
+       { "addprinterdriverex", (PyCFunction)spoolss_addprinterdriverex, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Add a printer driver." },
 
-       { "enumprinters", spoolss_enumprinters, METH_VARARGS | METH_KEYWORDS,
-         "enumprinters(server, [creds, level, flags]) -> list
+       { "deleteprinterdriver", (PyCFunction)spoolss_deleteprinterdriver, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Delete a printer driver." },
 
-Return a list of printers on a print server.  The credentials, info level
-and flags may be specified as keyword arguments.
+       { "deleteprinterdriverex", (PyCFunction)spoolss_deleteprinterdriverex, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Delete a printer driver." },
 
-Example:
+       { NULL }
+};
 
->>> print spoolss.enumprinters(\"\\\\\\\\npsd-pdc2\")
-[{'comment': 'i am a comment', 'printer_name': 'meanie', 'flags': 8388608, 
-  'description': 'meanie,Generic / Text Only,i am a location'}, 
- {'comment': '', 'printer_name': 'fileprint', 'flags': 8388608, 
-  'description': 'fileprint,Generic / Text Only,'}]
-"},
+/* Methods attached to a spoolss handle object */
 
-       { "enumports", spoolss_enumports, METH_VARARGS | METH_KEYWORDS,
-         "enumports(server, [creds, level]) -> list
+static PyMethodDef spoolss_hnd_methods[] = {
 
-Return a list of ports on a print server.
+       /* Printer info */
 
-Example:
+       { "getprinter", (PyCFunction)spoolss_hnd_getprinter, 
+           METH_VARARGS | METH_KEYWORDS,
+         "Get printer information.\n"
+"\n"
+"Return a dictionary of print information.  The info level defaults to 1.\n"
+"\n"
+"Example:\n"
+"\n"
+">>> hnd.getprinter()\n"
+"{'comment': 'i am a comment', 'printer_name': '\\\\NPSD-PDC2\\meanie',\n"
+" 'description': '\\\\NPSD-PDC2\\meanie,Generic / Text Only,i am a location',\n"
+" 'flags': 8388608}"},
+
+       { "setprinter", (PyCFunction)spoolss_hnd_setprinter, 
+          METH_VARARGS | METH_KEYWORDS,
+         "Set printer information."},
 
->>> print spoolss.enumports(\"\\\\\\\\npsd-pdc2\")
-[{'name': 'LPT1:'}, {'name': 'LPT2:'}, {'name': 'COM1:'}, {'name': 'COM2:'}, 
- {'name': 'FILE:'}, {'name': '\\\\nautilus1\\zpekt3r'}]
-"},
+       /* Printer drivers */
 
-       { "enumprinterdrivers", spoolss_enumprinterdrivers, METH_VARARGS |
-         METH_KEYWORDS, 
-"enumprinterdrivers(server, [level, arch, creds]) -> list
+       { "getprinterdriver", (PyCFunction)spoolss_hnd_getprinterdriver, 
+         METH_VARARGS | METH_KEYWORDS, 
+         "Return printer driver information.\n"
+"\n"
+"Return a dictionary of printer driver information for the printer driver\n"
+"bound to this printer."},
 
-Return a list of printer drivers.
-"},
-       /* Miscellaneous other commands */
+       /* Forms */
 
-       { "getprinterdriverdir", spoolss_getprinterdriverdir, METH_VARARGS |
-         METH_KEYWORDS, "getprinterdriverdir(server, [creds]) -> string
+       { "enumforms", (PyCFunction)spoolss_hnd_enumforms, 
+          METH_VARARGS | METH_KEYWORDS,
+         "Enumerate supported forms.\n"
+"\n"
+"Return a list of forms supported by this printer or print server."},
 
-Return the printer driver directory for a given architecture.  The 
-architecture defaults to \"Windows NT x86\".
-"},
+       { "setform", (PyCFunction)spoolss_hnd_setform, 
+          METH_VARARGS | METH_KEYWORDS,
+         "Set form data.\n"
+"\n"
+"Set the form given by the dictionary argument."},
 
-       /* Other stuff - this should really go into a samba config module
-          but for the moment let's leave it here. */
+       { "addform", (PyCFunction)spoolss_hnd_addform, 
+          METH_VARARGS | METH_KEYWORDS,
+         "Add a new form." },
 
-       { "setup_logging", py_setup_logging, METH_VARARGS | METH_KEYWORDS, 
-         "" },
+       { "getform", (PyCFunction)spoolss_hnd_getform, 
+          METH_VARARGS | METH_KEYWORDS,
+         "Get form properties." },
 
-       { "get_debuglevel", get_debuglevel, METH_VARARGS, "" },
-       { "set_debuglevel", set_debuglevel, METH_VARARGS, "" },
+       { "deleteform", (PyCFunction)spoolss_hnd_deleteform, 
+          METH_VARARGS | METH_KEYWORDS,
+         "Delete a form." },
 
-       { NULL }
-};
+        /* Job related methods */
 
-/* Methods attached to a spoolss handle object */
+        { "enumjobs", (PyCFunction)spoolss_hnd_enumjobs, 
+          METH_VARARGS | METH_KEYWORDS,
+          "Enumerate jobs." },
 
-static PyMethodDef spoolss_hnd_methods[] = {
+        { "setjob", (PyCFunction)spoolss_hnd_setjob, 
+          METH_VARARGS | METH_KEYWORDS,
+          "Set job information." },
 
-       /* Printer info */
+        { "getjob", (PyCFunction)spoolss_hnd_getjob, 
+          METH_VARARGS | METH_KEYWORDS,
+          "Get job information." },
 
-       { "getprinter", spoolss_getprinter, METH_VARARGS | METH_KEYWORDS,
-         "getprinter([level]) -> dict
+        { "startpageprinter", (PyCFunction)spoolss_hnd_startpageprinter, 
+           METH_VARARGS | METH_KEYWORDS,
+          "Notify spooler that a page is about to be printed." },
 
-Return a dictionary of print information.  The info level defaults to 1.
+        { "endpageprinter", (PyCFunction)spoolss_hnd_endpageprinter, 
+           METH_VARARGS | METH_KEYWORDS,
+          "Notify spooler that a page is about to be printed." },
 
-Example:
+        { "startdocprinter", (PyCFunction)spoolss_hnd_startdocprinter, 
+           METH_VARARGS | METH_KEYWORDS,
+          "Notify spooler that a document is about to be printed." },
 
->>> hnd.getprinter()
-{'comment': 'i am a comment', 'printer_name': '\\\\NPSD-PDC2\\meanie', 
- 'description': '\\\\NPSD-PDC2\\meanie,Generic / Text Only,i am a location',
- 'flags': 8388608}
-"},
+        { "enddocprinter", (PyCFunction)spoolss_hnd_enddocprinter, 
+           METH_VARARGS | METH_KEYWORDS,
+          "Notify spooler that a document is about to be printed." },
 
-       { "setprinter", spoolss_setprinter, METH_VARARGS | METH_KEYWORDS,
-         "setprinter(dict) -> None
+        { "writeprinter", (PyCFunction)spoolss_hnd_writeprinter,
+          METH_VARARGS | METH_KEYWORDS,
+          "Write job data to a printer." },
 
-Set printer information.
-"},
+        { "addjob", (PyCFunction)spoolss_hnd_addjob,
+          METH_VARARGS | METH_KEYWORDS,
+          "Add a job to the list of print jobs." },
 
-       /* Printer drivers */
+        /* Printer data */
 
-       { "getprinterdriver", spoolss_getprinterdriver, 
-         METH_VARARGS | METH_KEYWORDS, 
-         "getprinterdriver([level = 1, arch = \"Windows NT x86\"] -> dict
+        { "getprinterdata", (PyCFunction)spoolss_hnd_getprinterdata,
+           METH_VARARGS | METH_KEYWORDS,
+          "Get printer data." },
 
-Return a dictionary of printer driver information.
-"},
+        { "setprinterdata", (PyCFunction)spoolss_hnd_setprinterdata,
+           METH_VARARGS | METH_KEYWORDS,
+          "Set printer data." },
 
-       /* Forms */
+        { "enumprinterdata", (PyCFunction)spoolss_hnd_enumprinterdata,
+           METH_VARARGS | METH_KEYWORDS,
+          "Enumerate printer data." },
+
+        { "deleteprinterdata", (PyCFunction)spoolss_hnd_deleteprinterdata,
+           METH_VARARGS | METH_KEYWORDS,
+          "Delete printer data." },
 
-       { "enumforms", spoolss_enumforms, METH_VARARGS | METH_KEYWORDS,
-         "enumforms([level = 1]) -> list
+        { "getprinterdataex", (PyCFunction)spoolss_hnd_getprinterdataex,
+           METH_VARARGS | METH_KEYWORDS,
+          "Get printer data." },
 
-Return a list of forms supported by a printer.
-"},
+        { "setprinterdataex", (PyCFunction)spoolss_hnd_setprinterdataex,
+           METH_VARARGS | METH_KEYWORDS,
+          "Set printer data." },
 
-       { "setform", spoolss_setform, METH_VARARGS | METH_KEYWORDS,
-         "setform(dict) -> None
+        { "enumprinterdataex", (PyCFunction)spoolss_hnd_enumprinterdataex,
+           METH_VARARGS | METH_KEYWORDS,
+          "Enumerate printer data." },
 
-Set the form given by the dictionary argument.
-"},
+        { "deleteprinterdataex", (PyCFunction)spoolss_hnd_deleteprinterdataex,
+           METH_VARARGS | METH_KEYWORDS,
+          "Delete printer data." },
 
-       { "addform", spoolss_addform, METH_VARARGS | METH_KEYWORDS,
-         "Insert a form" },
+        { "enumprinterkey", (PyCFunction)spoolss_hnd_enumprinterkey,
+           METH_VARARGS | METH_KEYWORDS,
+          "Enumerate printer key." },
 
-       { "getform", spoolss_getform, METH_VARARGS | METH_KEYWORDS,
-         "Fetch form properties" },
+#if 0
+        /* Not implemented */
 
-       { "deleteform", spoolss_deleteform, METH_VARARGS | METH_KEYWORDS,
-         "Delete a form" },
+        { "deleteprinterkey", (PyCFunction)spoolss_hnd_deleteprinterkey,
+           METH_VARARGS | METH_KEYWORDS,
+          "Delete printer key." },
+#endif
 
        { NULL }
 
@@ -262,6 +297,15 @@ Set the form given by the dictionary argument.
 
 static void py_policy_hnd_dealloc(PyObject* self)
 {
+        spoolss_policy_hnd_object *hnd;
+
+        /* Close down policy handle and free talloc context */
+
+        hnd = (spoolss_policy_hnd_object*)self;
+
+        cli_shutdown(hnd->cli);
+        talloc_destroy(hnd->mem_ctx);
+
        PyObject_Del(self);
 }
 
@@ -300,10 +344,10 @@ PyTypeObject spoolss_policy_hnd_type = {
 
 /* Initialise constants */
 
-struct spoolss_const {
+static struct const_vals {
        char *name;
        uint32 value;
-} spoolss_const_vals[] = {
+} module_const_vals[] = {
        
        /* Access permissions */
 
@@ -381,15 +425,23 @@ struct spoolss_const {
        { "WERR_PRINTER_DRIVER_IN_USE", 3001 },
        { "WERR_STATUS_MORE_ENTRIES  ", 0x0105 },
 
+       /* Job control constants */
+
+       { "JOB_CONTROL_PAUSE", JOB_CONTROL_PAUSE },
+       { "JOB_CONTROL_RESUME", JOB_CONTROL_RESUME },
+       { "JOB_CONTROL_CANCEL", JOB_CONTROL_CANCEL },
+       { "JOB_CONTROL_RESTART", JOB_CONTROL_RESTART },
+       { "JOB_CONTROL_DELETE", JOB_CONTROL_DELETE },
+
        { NULL },
 };
 
 static void const_init(PyObject *dict)
 {
-       struct spoolss_const *tmp;
+       struct const_vals *tmp;
        PyObject *obj;
 
-       for (tmp = spoolss_const_vals; tmp->name; tmp++) {
+       for (tmp = module_const_vals; tmp->name; tmp++) {
                obj = PyInt_FromLong(tmp->value);
                PyDict_SetItemString(dict, tmp->name, obj);
                Py_DECREF(obj);
@@ -407,8 +459,7 @@ void initspoolss(void)
        module = Py_InitModule("spoolss", spoolss_methods);
        dict = PyModule_GetDict(module);
 
-       /* Make spools_error global an exception we can raise when an error
-          occurs. */
+       /* Exceptions we can raise */
 
        spoolss_error = PyErr_NewException("spoolss.error", NULL, NULL);
        PyDict_SetItemString(dict, "error", spoolss_error);