3 * Unix SMB/Netbios implementation.
5 * RPC Pipe client / server routines
6 * Copyright (C) Andrew Tridgell 1992-2000,
7 * Copyright (C) Jean François Micouleau 1998-2000.
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
26 extern int DEBUGLEVEL;
27 extern pstring global_myname;
28 extern DOM_SID global_sid_World;
30 static TDB_CONTEXT *tdb; /* used for driver files */
32 #define FORMS_PREFIX "FORMS/"
33 #define DRIVERS_PREFIX "DRIVERS/"
34 #define PRINTERS_PREFIX "PRINTERS/"
36 #define DATABASE_VERSION 1
38 /* we need to have a small set of default forms to support our
40 static nt_forms_struct default_forms[] = {
41 {"Letter", 0x2, 0x34b5b, 0x44367, 0x0, 0x0, 0x34b5b, 0x44367},
42 {"A4", 0x2, 0x3354f, 0x4884e, 0x0, 0x0, 0x3354f, 0x4884e}
46 /****************************************************************************
47 open the NT printing tdb
48 ****************************************************************************/
49 BOOL nt_printing_init(void)
51 static pid_t local_pid;
53 if (tdb && local_pid == sys_getpid()) return True;
54 tdb = tdb_open(lock_path("ntdrivers.tdb"), 0, 0, O_RDWR|O_CREAT, 0600);
56 DEBUG(0,("Failed to open nt drivers database\n"));
60 local_pid = sys_getpid();
62 /* handle a Samba upgrade */
64 if (tdb_fetch_int(tdb, "INFO/version") != DATABASE_VERSION) {
65 tdb_traverse(tdb, (tdb_traverse_func)tdb_delete, NULL);
66 tdb_store_int(tdb, "INFO/version", DATABASE_VERSION);
74 /****************************************************************************
75 get a form struct list
76 ****************************************************************************/
77 int get_ntforms(nt_forms_struct **list)
79 TDB_DATA kbuf, newkey, dbuf;
84 for (kbuf = tdb_firstkey(tdb);
86 newkey = tdb_nextkey(tdb, kbuf), safe_free(kbuf.dptr), kbuf=newkey) {
87 if (strncmp(kbuf.dptr, FORMS_PREFIX, strlen(FORMS_PREFIX)) != 0) continue;
89 dbuf = tdb_fetch(tdb, kbuf);
90 if (!dbuf.dptr) continue;
92 fstrcpy(form.name, kbuf.dptr+strlen(FORMS_PREFIX));
93 ret = tdb_unpack(dbuf.dptr, dbuf.dsize, "ddddddd",
94 &form.flag, &form.width, &form.length, &form.left,
95 &form.top, &form.right, &form.bottom);
97 if (ret != dbuf.dsize) continue;
99 *list = Realloc(*list, sizeof(nt_forms_struct)*(n+1));
104 /* we should never return a null forms list or NT gets unhappy */
106 *list = (nt_forms_struct *)memdup(&default_forms[0], sizeof(default_forms));
107 n = sizeof(default_forms) / sizeof(default_forms[0]);
114 /****************************************************************************
115 write a form struct list
116 ****************************************************************************/
117 int write_ntforms(nt_forms_struct **list, int number)
124 for (i=0;i<number;i++) {
125 len = tdb_pack(buf, sizeof(buf), "ddddddd",
126 (*list)[i].flag, (*list)[i].width, (*list)[i].length,
127 (*list)[i].left, (*list)[i].top, (*list)[i].right,
129 if (len > sizeof(buf)) break;
130 slprintf(key, sizeof(key), "%s%s", FORMS_PREFIX, (*list)[i].name);
131 kbuf.dsize = strlen(key)+1;
135 if (tdb_store(tdb, kbuf, dbuf, TDB_REPLACE) != 0) break;
141 /****************************************************************************
142 add a form struct at the end of the list
143 ****************************************************************************/
144 BOOL add_a_form(nt_forms_struct **list, const FORM *form, int *count)
151 * NT tries to add forms even when
152 * they are already in the base
153 * only update the values if already present
158 unistr2_to_ascii(form_name, &(form->name), sizeof(form_name)-1);
159 for (n=0; n<*count && update==False; n++)
161 if (!strncmp((*list)[n].name, form_name, strlen(form_name)))
163 DEBUG(103, ("NT workaround, [%s] already exists\n", form_name));
170 if((*list=Realloc(*list, (n+1)*sizeof(nt_forms_struct))) == NULL)
172 unistr2_to_ascii((*list)[n].name, &(form->name), sizeof((*list)[n].name)-1);
176 (*list)[n].flag=form->flags;
177 (*list)[n].width=form->size_x;
178 (*list)[n].length=form->size_y;
179 (*list)[n].left=form->left;
180 (*list)[n].top=form->top;
181 (*list)[n].right=form->right;
182 (*list)[n].bottom=form->bottom;
187 /****************************************************************************
189 ****************************************************************************/
190 void update_a_form(nt_forms_struct **list, const FORM *form, int count)
194 unistr2_to_ascii(form_name, &(form->name), sizeof(form_name)-1);
196 DEBUG(106, ("[%s]\n", form_name));
197 for (n=0; n<count; n++)
199 DEBUGADD(106, ("n [%d]:[%s]\n", n, (*list)[n].name));
200 if (!strncmp((*list)[n].name, form_name, strlen(form_name)))
204 if (n==count) return;
206 (*list)[n].flag=form->flags;
207 (*list)[n].width=form->size_x;
208 (*list)[n].length=form->size_y;
209 (*list)[n].left=form->left;
210 (*list)[n].top=form->top;
211 (*list)[n].right=form->right;
212 (*list)[n].bottom=form->bottom;
215 /****************************************************************************
216 get the nt drivers list
218 traverse the database and look-up the matching names
219 ****************************************************************************/
220 int get_ntdrivers(fstring **list, char *architecture, uint32 version)
225 TDB_DATA kbuf, newkey;
227 get_short_archi(short_archi, architecture);
228 slprintf(key, sizeof(key), "%s%s/%d/", DRIVERS_PREFIX, short_archi, version);
230 for (kbuf = tdb_firstkey(tdb);
232 newkey = tdb_nextkey(tdb, kbuf), safe_free(kbuf.dptr), kbuf=newkey) {
233 if (strncmp(kbuf.dptr, key, strlen(key)) != 0) continue;
235 if((*list = Realloc(*list, sizeof(fstring)*(total+1))) == NULL)
238 fstrcpy((*list)[total], kbuf.dptr+strlen(key));
245 /****************************************************************************
246 function to do the mapping between the long architecture name and
248 ****************************************************************************/
249 BOOL get_short_archi(char *short_archi, char *long_archi)
256 struct table archi_table[]=
258 {"Windows 4.0", "WIN40" },
259 {"Windows NT x86", "W32X86" },
260 {"Windows NT R4000", "W32MIPS" },
261 {"Windows NT Alpha_AXP", "W32ALPHA" },
262 {"Windows NT PowerPC", "W32PPC" },
268 DEBUG(107,("Getting architecture dependant directory\n"));
271 } while ( (archi_table[i].long_archi!=NULL ) &&
272 StrCaseCmp(long_archi, archi_table[i].long_archi) );
274 if (archi_table[i].long_archi==NULL) {
275 DEBUGADD(107,("Unknown architecture [%s] !\n", long_archi));
279 StrnCpy (short_archi, archi_table[i].short_archi, strlen(archi_table[i].short_archi));
281 DEBUGADD(108,("index: [%d]\n", i));
282 DEBUGADD(108,("long architecture: [%s]\n", long_archi));
283 DEBUGADD(108,("short architecture: [%s]\n", short_archi));
288 /****************************************************************************
289 ****************************************************************************/
290 static void clean_up_driver_struct_level_3(NT_PRINTER_DRIVER_INFO_LEVEL_3 *driver)
292 fstring architecture;
297 /* jfm:7/16/2000 the client always sends the cversion=0.
298 * The server should check which version the driver is by reading the PE header
299 * of driver->driverpath.
301 * For Windows 95/98 the version is 0 (so the value sent is correct)
302 * For Windows NT (the architecture doesn't matter)
304 * NT 3.5/3.51: cversion=1
309 get_short_archi(architecture, driver->environment);
311 /* if it's Windows 95/98, we keep the version at 0
312 * jfmxxx: I need to redo that more correctly for NT2K.
315 if (StrCaseCmp(driver->environment, "Windows 4.0")==0)
320 /* clean up the driver name.
321 * we can get .\driver.dll
322 * or worse c:\windows\system\driver.dll !
324 /* using an intermediate string to not have overlaping memcpy()'s */
325 if ((p = strrchr(driver->driverpath,'\\')) != NULL) {
326 fstrcpy(new_name, p+1);
327 fstrcpy(driver->driverpath, new_name);
330 if ((p = strrchr(driver->datafile,'\\')) != NULL) {
331 fstrcpy(new_name, p+1);
332 fstrcpy(driver->datafile, new_name);
335 if ((p = strrchr(driver->configfile,'\\')) != NULL) {
336 fstrcpy(new_name, p+1);
337 fstrcpy(driver->configfile, new_name);
340 if ((p = strrchr(driver->helpfile,'\\')) != NULL) {
341 fstrcpy(new_name, p+1);
342 fstrcpy(driver->helpfile, new_name);
345 if (driver->dependentfiles) {
346 for (i=0; *driver->dependentfiles[i]; i++) {
347 if ((p = strrchr(driver->dependentfiles[i],'\\')) != NULL) {
348 fstrcpy(new_name, p+1);
349 fstrcpy(driver->dependentfiles[i], new_name);
355 /****************************************************************************
356 ****************************************************************************/
357 static void clean_up_driver_struct_level_6(NT_PRINTER_DRIVER_INFO_LEVEL_6 *driver)
362 /****************************************************************************
363 ****************************************************************************/
364 void clean_up_driver_struct(NT_PRINTER_DRIVER_INFO_LEVEL driver_abstract, uint32 level)
369 NT_PRINTER_DRIVER_INFO_LEVEL_3 *driver;
370 driver=driver_abstract.info_3;
371 clean_up_driver_struct_level_3(driver);
376 NT_PRINTER_DRIVER_INFO_LEVEL_6 *driver;
377 driver=driver_abstract.info_6;
378 clean_up_driver_struct_level_6(driver);
384 /****************************************************************************
385 ****************************************************************************/
386 BOOL move_driver_to_download_area(NT_PRINTER_DRIVER_INFO_LEVEL driver_abstract, uint32 level, struct current_user *user, uint32 *perr)
388 NT_PRINTER_DRIVER_INFO_LEVEL_3 *driver;
389 fstring architecture;
395 connection_struct *conn;
398 struct smb_passwd *smb_pass;
404 memset(inbuf, '\0', sizeof(inbuf));
405 memset(outbuf, '\0', sizeof(outbuf));
408 driver=driver_abstract.info_3;
410 get_short_archi(architecture, driver->environment);
413 smb_pass = getsmbpwuid(user->uid);
414 if(smb_pass == NULL) {
415 DEBUG(0,("move_driver_to_download_area: Unable to get smbpasswd entry for uid %u\n",
416 (unsigned int)user->uid ));
422 /* connect to the print$ share under the same account as the user connected to the rpc pipe */
423 fstrcpy(user_name, smb_pass->smb_name );
424 DEBUG(10,("move_driver_to_download_area: uid %d -> user %s\n", (int)user->uid, user_name));
426 /* Null password is ok - we are already an authenticated user... */
428 conn = make_connection("print$", user_name, null_pw, 0, "A:", user->vuid, &ecode);
431 DEBUG(0,("move_driver_to_download_area: Unable to connect\n"));
432 *perr = (uint32)ecode;
437 * Save who we are - we are temporarily becoming the connection user.
442 if (!become_user(conn, conn->vuid)) {
443 DEBUG(0,("move_driver_to_download_area: Can't become user %s\n", user_name ));
449 * make the directories version and version\driver_name
450 * under the architecture directory.
452 DEBUG(5,("Creating first directory\n"));
453 slprintf(new_dir, sizeof(new_dir), "%s\\%d", architecture, driver->cversion);
454 mkdir_internal(conn, inbuf, outbuf, new_dir);
456 /* move all the files, one by one,
457 * from archi\filexxx.yyy to
458 * archi\version\filexxx.yyy
460 * Note: drivers may list the same file name in several places. This
461 * causes problems on a second attempt to move the file. JRR
463 * Note: use the replace flag on rename_internals() call, otherwise it
464 * is very difficult to change previously installed drivers... the Windows
465 * GUI offers the user the choice to replace or keep exisitng driver. JRR
468 DEBUG(5,("Moving file now !\n"));
469 slprintf(old_name, sizeof(old_name), "%s\\%s", architecture, driver->driverpath);
470 slprintf(new_name, sizeof(new_name), "%s\\%s", new_dir, driver->driverpath);
471 if ((outsize = rename_internals(conn, inbuf, outbuf, old_name, new_name, True)) != 0) {
472 DEBUG(0,("move_driver_to_download_area: Unable to rename %s to %s\n",
473 old_name, new_name ));
474 close_cnum(conn, user->vuid);
476 *perr = (uint32)SVAL(outbuf,smb_err);
480 if (!strequal(driver->datafile, driver->driverpath)) {
481 slprintf(old_name, sizeof(old_name), "%s\\%s", architecture, driver->datafile);
482 slprintf(new_name, sizeof(new_name), "%s\\%s", new_dir, driver->datafile);
483 if ((outsize = rename_internals(conn, inbuf, outbuf, old_name, new_name, True)) != 0) {
484 DEBUG(0,("move_driver_to_download_area: Unable to rename %s to %s\n",
485 old_name, new_name ));
486 close_cnum(conn, user->vuid);
488 *perr = (uint32)SVAL(outbuf,smb_err);
493 if (!strequal(driver->configfile, driver->driverpath) &&
494 !strequal(driver->configfile, driver->datafile)) {
495 slprintf(old_name, sizeof(old_name), "%s\\%s", architecture, driver->configfile);
496 slprintf(new_name, sizeof(new_name), "%s\\%s", new_dir, driver->configfile);
497 if ((outsize = rename_internals(conn, inbuf, outbuf, old_name, new_name, True)) != 0) {
498 DEBUG(0,("move_driver_to_download_area: Unable to rename %s to %s\n",
499 old_name, new_name ));
500 close_cnum(conn, user->vuid);
502 *perr = (uint32)SVAL(outbuf,smb_err);
507 if (!strequal(driver->helpfile, driver->driverpath) &&
508 !strequal(driver->helpfile, driver->datafile) &&
509 !strequal(driver->helpfile, driver->configfile)) {
510 slprintf(old_name, sizeof(old_name), "%s\\%s", architecture, driver->helpfile);
511 slprintf(new_name, sizeof(new_name), "%s\\%s", new_dir, driver->helpfile);
512 if ((outsize = rename_internals(conn, inbuf, outbuf, old_name, new_name, True)) != 0) {
513 DEBUG(0,("move_driver_to_download_area: Unable to rename %s to %s\n",
514 old_name, new_name ));
515 close_cnum(conn, user->vuid);
517 *perr = (uint32)SVAL(outbuf,smb_err);
522 if (driver->dependentfiles) {
523 for (i=0; *driver->dependentfiles[i]; i++) {
524 if (!strequal(driver->dependentfiles[i], driver->driverpath) &&
525 !strequal(driver->dependentfiles[i], driver->datafile) &&
526 !strequal(driver->dependentfiles[i], driver->configfile) &&
527 !strequal(driver->dependentfiles[i], driver->helpfile)) {
529 for (j=0; j < i; j++) {
530 if (strequal(driver->dependentfiles[i], driver->dependentfiles[j])) {
535 slprintf(old_name, sizeof(old_name), "%s\\%s", architecture, driver->dependentfiles[i]);
536 slprintf(new_name, sizeof(new_name), "%s\\%s", new_dir, driver->dependentfiles[i]);
537 if ((outsize = rename_internals(conn, inbuf, outbuf, old_name, new_name, True)) != 0) {
538 DEBUG(0,("move_driver_to_download_area: Unable to rename %s to %s\n",
539 old_name, new_name ));
540 close_cnum(conn, user->vuid);
542 *perr = (uint32)SVAL(outbuf,smb_err);
550 close_cnum(conn, user->vuid);
556 /****************************************************************************
557 ****************************************************************************/
558 static uint32 add_a_printer_driver_3(NT_PRINTER_DRIVER_INFO_LEVEL_3 *driver)
561 fstring architecture;
569 get_short_archi(architecture, driver->environment);
571 /* The names are relative. We store them in the form: \print$\arch\version\driver.xxx
572 * \\server is added in the rpc server layer.
573 * It does make sense to NOT store the server's name in the printer TDB.
576 slprintf(directory, sizeof(directory), "\\print$\\%s\\%d\\", architecture, driver->cversion);
579 fstrcpy(temp_name, driver->driverpath);
580 slprintf(driver->driverpath, sizeof(driver->driverpath), "%s%s", directory, temp_name);
582 fstrcpy(temp_name, driver->datafile);
583 slprintf(driver->datafile, sizeof(driver->datafile), "%s%s", directory, temp_name);
585 fstrcpy(temp_name, driver->configfile);
586 slprintf(driver->configfile, sizeof(driver->configfile), "%s%s", directory, temp_name);
588 fstrcpy(temp_name, driver->helpfile);
589 slprintf(driver->helpfile, sizeof(driver->helpfile), "%s%s", directory, temp_name);
591 if (driver->dependentfiles) {
592 for (i=0; *driver->dependentfiles[i]; i++) {
593 fstrcpy(temp_name, driver->dependentfiles[i]);
594 slprintf(driver->dependentfiles[i], sizeof(driver->dependentfiles[i]), "%s%s", directory, temp_name);
598 slprintf(key, sizeof(key), "%s%s/%d/%s", DRIVERS_PREFIX, architecture, driver->cversion, driver->name);
605 len += tdb_pack(buf+len, buflen-len, "dffffffff",
614 driver->defaultdatatype);
616 if (driver->dependentfiles) {
617 for (i=0; *driver->dependentfiles[i]; i++) {
618 len += tdb_pack(buf+len, buflen-len, "f",
619 driver->dependentfiles[i]);
624 buf = (char *)Realloc(buf, len);
631 kbuf.dsize = strlen(key)+1;
635 ret = tdb_store(tdb, kbuf, dbuf, TDB_REPLACE);
641 /****************************************************************************
642 ****************************************************************************/
643 static uint32 add_a_printer_driver_6(NT_PRINTER_DRIVER_INFO_LEVEL_6 *driver)
645 NT_PRINTER_DRIVER_INFO_LEVEL_3 info3;
648 info3.cversion = driver->version;
649 fstrcpy(info3.environment,driver->environment);
650 fstrcpy(info3.driverpath,driver->driverpath);
651 fstrcpy(info3.datafile,driver->datafile);
652 fstrcpy(info3.configfile,driver->configfile);
653 fstrcpy(info3.helpfile,driver->helpfile);
654 fstrcpy(info3.monitorname,driver->monitorname);
655 fstrcpy(info3.defaultdatatype,driver->defaultdatatype);
656 info3.dependentfiles = driver->dependentfiles;
658 return add_a_printer_driver_3(&info3);
662 /****************************************************************************
663 ****************************************************************************/
664 static uint32 get_a_printer_driver_3_default(NT_PRINTER_DRIVER_INFO_LEVEL_3 **info_ptr, fstring in_prt, fstring in_arch)
666 NT_PRINTER_DRIVER_INFO_LEVEL_3 info;
670 fstrcpy(info.name, in_prt);
671 fstrcpy(info.defaultdatatype, "RAW");
673 fstrcpy(info.driverpath, "");
674 fstrcpy(info.datafile, "");
675 fstrcpy(info.configfile, "");
676 fstrcpy(info.helpfile, "");
678 if ((info.dependentfiles=(fstring *)malloc(2*sizeof(fstring))) == NULL)
679 return ERROR_NOT_ENOUGH_MEMORY;
681 memset(info.dependentfiles, '\0', 2*sizeof(fstring));
682 fstrcpy(info.dependentfiles[0], "");
684 *info_ptr = memdup(&info, sizeof(info));
689 /****************************************************************************
690 ****************************************************************************/
691 static uint32 get_a_printer_driver_3(NT_PRINTER_DRIVER_INFO_LEVEL_3 **info_ptr, fstring in_prt, fstring in_arch, uint32 version)
693 NT_PRINTER_DRIVER_INFO_LEVEL_3 driver;
695 fstring architecture;
702 get_short_archi(architecture, in_arch);
704 DEBUG(8,("get_a_printer_driver_3: [%s%s/%d/%s]\n", DRIVERS_PREFIX, architecture, version, in_prt));
706 slprintf(key, sizeof(key), "%s%s/%d/%s", DRIVERS_PREFIX, architecture, version, in_prt);
709 kbuf.dsize = strlen(key)+1;
711 dbuf = tdb_fetch(tdb, kbuf);
713 if (!dbuf.dptr) return get_a_printer_driver_3_default(info_ptr, in_prt, in_arch);
715 if (!dbuf.dptr) return 5;
717 len += tdb_unpack(dbuf.dptr, dbuf.dsize, "dffffffff",
726 driver.defaultdatatype);
729 while (len < dbuf.dsize) {
730 driver.dependentfiles = (fstring *)Realloc(driver.dependentfiles,
731 sizeof(fstring)*(i+2));
732 if (driver.dependentfiles == NULL)
735 len += tdb_unpack(dbuf.dptr+len, dbuf.dsize-len, "f",
736 &driver.dependentfiles[i]);
739 if (driver.dependentfiles != NULL)
740 fstrcpy(driver.dependentfiles[i], "");
742 safe_free(dbuf.dptr);
744 if (len != dbuf.dsize) {
745 if (driver.dependentfiles != NULL)
746 safe_free(driver.dependentfiles);
748 return get_a_printer_driver_3_default(info_ptr, in_prt, in_arch);
751 *info_ptr = (NT_PRINTER_DRIVER_INFO_LEVEL_3 *)memdup(&driver, sizeof(driver));
756 /****************************************************************************
757 ****************************************************************************/
758 uint32 get_a_printer_driver_9x_compatible(pstring line, fstring model)
760 NT_PRINTER_DRIVER_INFO_LEVEL_3 *info3;
766 slprintf(key, sizeof(key), "%s%s/%d/%s", DRIVERS_PREFIX, "WIN40", 0, model);
767 DEBUG(10,("driver key: [%s]\n", key));
770 kbuf.dsize = strlen(key)+1;
771 if (!tdb_exists(tdb, kbuf)) return False;
774 get_a_printer_driver_3(&info3, model, "Windows 4.0", 0);
776 DEBUGADD(10,("info3->name [%s]\n", info3->name));
777 DEBUGADD(10,("info3->datafile [%s]\n", info3->datafile));
778 DEBUGADD(10,("info3->helpfile [%s]\n", info3->helpfile));
779 DEBUGADD(10,("info3->monitorname [%s]\n", info3->monitorname));
780 DEBUGADD(10,("info3->defaultdatatype [%s]\n", info3->defaultdatatype));
781 for (i=0; info3->dependentfiles && *info3->dependentfiles[i]; i++) {
782 DEBUGADD(10,("info3->dependentfiles [%s]\n", info3->dependentfiles[i]));
784 DEBUGADD(10,("info3->environment [%s]\n", info3->environment));
785 DEBUGADD(10,("info3->driverpath [%s]\n", info3->driverpath));
786 DEBUGADD(10,("info3->configfile [%s]\n", info3->configfile));
788 /*pstrcat(line, info3->name); pstrcat(line, ":");*/
789 trim_string(info3->configfile, "\\print$\\WIN40\\0\\", 0);
790 pstrcat(line, info3->configfile);
792 trim_string(info3->datafile, "\\print$\\WIN40\\0\\", 0);
793 pstrcat(line, info3->datafile);
795 trim_string(info3->helpfile, "\\print$\\WIN40\\0\\", 0);
796 pstrcat(line, info3->helpfile);
798 trim_string(info3->monitorname, "\\print$\\WIN40\\0\\", 0);
799 pstrcat(line, info3->monitorname);
801 pstrcat(line, "RAW"); /*info3->defaultdatatype);*/
804 for (i=0; info3->dependentfiles &&
805 *info3->dependentfiles[i]; i++) {
806 if (i) pstrcat(line, ","); /* don't end in a "," */
807 trim_string(info3->dependentfiles[i], "\\print$\\WIN40\\0\\", 0);
808 pstrcat(line, info3->dependentfiles[i]);
816 /****************************************************************************
817 debugging function, dump at level 6 the struct in the logs
818 ****************************************************************************/
819 static uint32 dump_a_printer_driver(NT_PRINTER_DRIVER_INFO_LEVEL driver, uint32 level)
822 NT_PRINTER_DRIVER_INFO_LEVEL_3 *info3;
825 DEBUG(106,("Dumping printer driver at level [%d]\n", level));
831 if (driver.info_3 == NULL)
836 DEBUGADD(106,("version:[%d]\n", info3->cversion));
837 DEBUGADD(106,("name:[%s]\n", info3->name));
838 DEBUGADD(106,("environment:[%s]\n", info3->environment));
839 DEBUGADD(106,("driverpath:[%s]\n", info3->driverpath));
840 DEBUGADD(106,("datafile:[%s]\n", info3->datafile));
841 DEBUGADD(106,("configfile:[%s]\n", info3->configfile));
842 DEBUGADD(106,("helpfile:[%s]\n", info3->helpfile));
843 DEBUGADD(106,("monitorname:[%s]\n", info3->monitorname));
844 DEBUGADD(106,("defaultdatatype:[%s]\n", info3->defaultdatatype));
846 for (i=0; info3->dependentfiles &&
847 *info3->dependentfiles[i]; i++) {
848 DEBUGADD(106,("dependentfile:[%s]\n",
849 info3->dependentfiles[i]));
856 DEBUGADD(1,("Level not implemented\n"));
864 /****************************************************************************
865 ****************************************************************************/
866 static int pack_devicemode(NT_DEVICEMODE *nt_devmode, char *buf, int buflen)
870 len += tdb_pack(buf+len, buflen-len, "p", nt_devmode);
872 if (!nt_devmode) return len;
874 len += tdb_pack(buf+len, buflen-len, "ffwwwwwwwwwwwwwwwwwwddddddddddddddp",
875 nt_devmode->devicename,
876 nt_devmode->formname,
878 nt_devmode->specversion,
879 nt_devmode->driverversion,
881 nt_devmode->driverextra,
882 nt_devmode->orientation,
883 nt_devmode->papersize,
884 nt_devmode->paperlength,
885 nt_devmode->paperwidth,
888 nt_devmode->defaultsource,
889 nt_devmode->printquality,
892 nt_devmode->yresolution,
893 nt_devmode->ttoption,
895 nt_devmode->logpixels,
898 nt_devmode->bitsperpel,
899 nt_devmode->pelswidth,
900 nt_devmode->pelsheight,
901 nt_devmode->displayflags,
902 nt_devmode->displayfrequency,
903 nt_devmode->icmmethod,
904 nt_devmode->icmintent,
905 nt_devmode->mediatype,
906 nt_devmode->dithertype,
907 nt_devmode->reserved1,
908 nt_devmode->reserved2,
909 nt_devmode->panningwidth,
910 nt_devmode->panningheight,
911 nt_devmode->private);
914 if (nt_devmode->private) {
915 len += tdb_pack(buf+len, buflen-len, "B",
916 nt_devmode->driverextra,
917 nt_devmode->private);
920 DEBUG(8,("Packed devicemode [%s]\n", nt_devmode->formname));
925 /****************************************************************************
926 ****************************************************************************/
927 static int pack_specifics(NT_PRINTER_PARAM *param, char *buf, int buflen)
931 while (param != NULL) {
932 len += tdb_pack(buf+len, buflen-len, "pfdB",
941 len += tdb_pack(buf+len, buflen-len, "p", param);
947 /****************************************************************************
948 delete a printer - this just deletes the printer info file, any open
949 handles are not affected
950 ****************************************************************************/
951 uint32 del_a_printer(char *sharename)
956 slprintf(key, sizeof(key), "%s%s",
957 PRINTERS_PREFIX, sharename);
960 kbuf.dsize=strlen(key)+1;
962 tdb_delete(tdb, kbuf);
966 /****************************************************************************
967 ****************************************************************************/
968 static uint32 add_a_printer_2(NT_PRINTER_INFO_LEVEL_2 *info)
972 int buflen, len, ret;
975 time_t time_unix = time(NULL);
978 * in addprinter: no servername and the printer is the name
979 * in setprinter: servername is \\server
980 * and printer is \\server\\printer
982 * Samba manages only local printers.
983 * we currently don't support things like path=\\other_server\printer
986 if (info->servername[0]!='\0') {
987 trim_string(info->printername, info->servername, NULL);
988 trim_string(info->printername, "\\", NULL);
989 info->servername[0]='\0';
993 * JFM: one day I'll forget.
994 * below that's info->portname because that's the SAMBA sharename
995 * and I made NT 'thinks' it's the portname
996 * the info->sharename is the thing you can name when you add a printer
997 * that's the short-name when you create shared printer for 95/98
998 * So I've made a limitation in SAMBA: you can only have 1 printer model
999 * behind a SAMBA share.
1002 unix_to_nt_time(&time_nt, time_unix);
1003 info->changeid=time_nt.low;
1004 info->c_setprinter++;
1011 len += tdb_pack(buf+len, buflen-len, "dddddddddddfffffPfffff",
1014 info->default_priority,
1031 info->printprocessor,
1035 len += pack_devicemode(info->devmode, buf+len, buflen-len);
1036 len += pack_specifics(info->specific, buf+len, buflen-len);
1038 if (buflen != len) {
1039 buf = (char *)Realloc(buf, len);
1045 slprintf(key, sizeof(key), "%s%s",
1046 PRINTERS_PREFIX, info->sharename);
1049 kbuf.dsize = strlen(key)+1;
1053 ret = tdb_store(tdb, kbuf, dbuf, TDB_REPLACE);
1056 DEBUG(8, ("error updating printer to tdb on disk\n"));
1060 DEBUG(8,("packed printer [%s] with driver [%s] portname=[%s] len=%d\n",
1061 info->sharename, info->drivername, info->portname, len));
1067 /****************************************************************************
1068 ****************************************************************************/
1069 BOOL add_a_specific_param(NT_PRINTER_INFO_LEVEL_2 *info_2, NT_PRINTER_PARAM *param)
1071 NT_PRINTER_PARAM *current;
1073 DEBUG(108,("add_a_specific_param\n"));
1077 if (info_2->specific == NULL)
1079 info_2->specific=param;
1083 current=info_2->specific;
1084 while (current->next != NULL) {
1085 current=current->next;
1087 current->next=param;
1092 /****************************************************************************
1093 ****************************************************************************/
1094 BOOL unlink_specific_param_if_exist(NT_PRINTER_INFO_LEVEL_2 *info_2, NT_PRINTER_PARAM *param)
1096 NT_PRINTER_PARAM *current;
1097 NT_PRINTER_PARAM *previous;
1099 current=info_2->specific;
1102 if (current==NULL) return (False);
1104 if ( !strcmp(current->value, param->value) &&
1105 (strlen(current->value)==strlen(param->value)) ) {
1106 DEBUG(109,("deleting first value\n"));
1107 info_2->specific=current->next;
1108 safe_free(current->data);
1110 DEBUG(109,("deleted first value\n"));
1114 current=previous->next;
1116 while ( current!=NULL ) {
1117 if (!strcmp(current->value, param->value) &&
1118 strlen(current->value)==strlen(param->value) ) {
1119 DEBUG(109,("deleting current value\n"));
1120 previous->next=current->next;
1121 safe_free(current->data);
1123 DEBUG(109,("deleted current value\n"));
1127 previous=previous->next;
1128 current=current->next;
1133 /****************************************************************************
1134 Clean up and deallocate a (maybe partially) allocated NT_PRINTER_PARAM.
1135 ****************************************************************************/
1136 static void free_nt_printer_param(NT_PRINTER_PARAM **param_ptr)
1138 NT_PRINTER_PARAM *param = *param_ptr;
1143 DEBUG(106,("free_nt_printer_param: deleting param [%s]\n", param->value));
1146 safe_free(param->data);
1152 /****************************************************************************
1153 Malloc and return an NT devicemode.
1154 ****************************************************************************/
1156 NT_DEVICEMODE *construct_nt_devicemode(const fstring default_devicename)
1159 * should I init this ones ???
1160 nt_devmode->devicename
1164 NT_DEVICEMODE *nt_devmode = (NT_DEVICEMODE *)malloc(sizeof(NT_DEVICEMODE));
1166 if (nt_devmode == NULL) {
1167 DEBUG(0,("construct_nt_devicemode: malloc fail.\n"));
1171 ZERO_STRUCTP(nt_devmode);
1173 snprintf(adevice, sizeof(adevice), "\\\\%s\\%s", global_myname, default_devicename);
1174 fstrcpy(nt_devmode->devicename, adevice);
1177 fstrcpy(nt_devmode->formname, "Letter");
1179 nt_devmode->specversion = 0x0401;
1180 nt_devmode->driverversion = 0x0400;
1181 nt_devmode->size = 0x00DC;
1182 nt_devmode->driverextra = 0x0000;
1183 nt_devmode->fields = FORMNAME | TTOPTION | PRINTQUALITY |
1184 DEFAULTSOURCE | COPIES | SCALE |
1185 PAPERSIZE | ORIENTATION;
1186 nt_devmode->orientation = 1;
1187 nt_devmode->papersize = PAPER_LETTER;
1188 nt_devmode->paperlength = 0;
1189 nt_devmode->paperwidth = 0;
1190 nt_devmode->scale = 0x64;
1191 nt_devmode->copies = 01;
1192 nt_devmode->defaultsource = BIN_FORMSOURCE;
1193 nt_devmode->printquality = 0x0258;
1194 nt_devmode->color = COLOR_MONOCHROME;
1195 nt_devmode->duplex = DUP_SIMPLEX;
1196 nt_devmode->yresolution = 0;
1197 nt_devmode->ttoption = TT_SUBDEV;
1198 nt_devmode->collate = COLLATE_FALSE;
1199 nt_devmode->icmmethod = 0;
1200 nt_devmode->icmintent = 0;
1201 nt_devmode->mediatype = 0;
1202 nt_devmode->dithertype = 0;
1204 /* non utilisés par un driver d'imprimante */
1205 nt_devmode->logpixels = 0;
1206 nt_devmode->bitsperpel = 0;
1207 nt_devmode->pelswidth = 0;
1208 nt_devmode->pelsheight = 0;
1209 nt_devmode->displayflags = 0;
1210 nt_devmode->displayfrequency = 0;
1211 nt_devmode->reserved1 = 0;
1212 nt_devmode->reserved2 = 0;
1213 nt_devmode->panningwidth = 0;
1214 nt_devmode->panningheight = 0;
1216 nt_devmode->private=NULL;
1221 /****************************************************************************
1222 Deepcopy an NT devicemode.
1223 ****************************************************************************/
1225 NT_DEVICEMODE *dup_nt_devicemode(NT_DEVICEMODE *nt_devicemode)
1227 NT_DEVICEMODE *new_nt_devicemode = NULL;
1229 if ((new_nt_devicemode = (NT_DEVICEMODE *)memdup(nt_devicemode, sizeof(NT_DEVICEMODE))) == NULL) {
1230 DEBUG(0,("dup_nt_devicemode: malloc fail.\n"));
1234 new_nt_devicemode->private = NULL;
1235 if (nt_devicemode->private != NULL) {
1236 if ((new_nt_devicemode->private = memdup(nt_devicemode->private, nt_devicemode->driverextra)) == NULL) {
1237 safe_free(new_nt_devicemode);
1238 DEBUG(0,("dup_nt_devicemode: malloc fail.\n"));
1243 return new_nt_devicemode;
1246 /****************************************************************************
1247 Clean up and deallocate a (maybe partially) allocated NT_DEVICEMODE.
1248 ****************************************************************************/
1250 void free_nt_devicemode(NT_DEVICEMODE **devmode_ptr)
1252 NT_DEVICEMODE *nt_devmode = *devmode_ptr;
1254 if(nt_devmode == NULL)
1257 DEBUG(106,("free_nt_devicemode: deleting DEVMODE\n"));
1259 if(nt_devmode->private)
1260 safe_free(nt_devmode->private);
1262 safe_free(nt_devmode);
1263 *devmode_ptr = NULL;
1266 /****************************************************************************
1267 Clean up and deallocate a (maybe partially) allocated NT_PRINTER_INFO_LEVEL_2.
1268 ****************************************************************************/
1269 static void free_nt_printer_info_level_2(NT_PRINTER_INFO_LEVEL_2 **info_ptr)
1271 NT_PRINTER_INFO_LEVEL_2 *info = *info_ptr;
1272 NT_PRINTER_PARAM *param_ptr;
1277 DEBUG(106,("free_nt_printer_info_level_2: deleting info\n"));
1279 free_nt_devicemode(&info->devmode);
1280 free_sec_desc_buf(&info->secdesc_buf);
1282 for(param_ptr = info->specific; param_ptr; ) {
1283 NT_PRINTER_PARAM *tofree = param_ptr;
1285 param_ptr = param_ptr->next;
1286 free_nt_printer_param(&tofree);
1289 safe_free(*info_ptr);
1294 /****************************************************************************
1295 ****************************************************************************/
1296 static int unpack_devicemode(NT_DEVICEMODE **nt_devmode, char *buf, int buflen)
1300 NT_DEVICEMODE devmode;
1302 ZERO_STRUCT(devmode);
1304 len += tdb_unpack(buf+len, buflen-len, "p", nt_devmode);
1306 if (!*nt_devmode) return len;
1308 len += tdb_unpack(buf+len, buflen-len, "ffwwwwwwwwwwwwwwwwwwddddddddddddddp",
1312 &devmode.specversion,
1313 &devmode.driverversion,
1315 &devmode.driverextra,
1316 &devmode.orientation,
1318 &devmode.paperlength,
1319 &devmode.paperwidth,
1322 &devmode.defaultsource,
1323 &devmode.printquality,
1326 &devmode.yresolution,
1332 &devmode.bitsperpel,
1334 &devmode.pelsheight,
1335 &devmode.displayflags,
1336 &devmode.displayfrequency,
1340 &devmode.dithertype,
1343 &devmode.panningwidth,
1344 &devmode.panningheight,
1347 if (devmode.private) {
1348 /* the len in tdb_unpack is an int value and
1349 * devmoce.driverextra is only a short
1351 len += tdb_unpack(buf+len, buflen-len, "B", &extra_len, &devmode.private);
1352 devmode.driverextra=(uint16)extra_len;
1355 *nt_devmode = (NT_DEVICEMODE *)memdup(&devmode, sizeof(devmode));
1357 DEBUG(8,("Unpacked devicemode [%s](%s)\n", devmode.devicename, devmode.formname));
1358 if (devmode.private)
1359 DEBUG(8,("with a private section of %d bytes\n", devmode.driverextra));
1364 /****************************************************************************
1365 ****************************************************************************/
1366 static int unpack_specifics(NT_PRINTER_PARAM **list, char *buf, int buflen)
1369 NT_PRINTER_PARAM param, *p;
1374 len += tdb_unpack(buf+len, buflen-len, "p", &p);
1377 len += tdb_unpack(buf+len, buflen-len, "fdB",
1383 *list = memdup(¶m, sizeof(param));
1385 DEBUG(8,("specific: [%s], len: %d\n", param.value, param.data_len));
1392 /****************************************************************************
1393 get a default printer info 2 struct
1394 ****************************************************************************/
1395 static uint32 get_a_printer_2_default(NT_PRINTER_INFO_LEVEL_2 **info_ptr, fstring sharename)
1397 extern pstring global_myname;
1399 NT_PRINTER_INFO_LEVEL_2 info;
1403 snum = lp_servicenumber(sharename);
1405 fstrcpy(info.servername, global_myname);
1406 fstrcpy(info.printername, sharename);
1407 fstrcpy(info.portname, SAMBA_PRINTER_PORT_NAME);
1408 fstrcpy(info.drivername, lp_printerdriver(snum));
1409 pstrcpy(info.comment, "");
1410 fstrcpy(info.printprocessor, "winprint");
1411 fstrcpy(info.datatype, "RAW");
1413 info.attributes = PRINTER_ATTRIBUTE_SHARED \
1414 | PRINTER_ATTRIBUTE_LOCAL \
1415 | PRINTER_ATTRIBUTE_RAW_ONLY ; /* attributes */
1417 info.starttime = 0; /* Minutes since 12:00am GMT */
1418 info.untiltime = 0; /* Minutes since 12:00am GMT */
1420 info.default_priority = 1;
1422 if ((info.devmode = construct_nt_devicemode(info.printername)) == NULL)
1425 if (!nt_printing_getsec(sharename, &info.secdesc_buf))
1428 *info_ptr = (NT_PRINTER_INFO_LEVEL_2 *)memdup(&info, sizeof(info));
1430 DEBUG(0,("get_a_printer_2_default: malloc fail.\n"));
1439 free_nt_devicemode(&info.devmode);
1440 if (info.secdesc_buf)
1441 free_sec_desc_buf(&info.secdesc_buf);
1445 /****************************************************************************
1446 ****************************************************************************/
1447 static uint32 get_a_printer_2(NT_PRINTER_INFO_LEVEL_2 **info_ptr, fstring sharename)
1450 NT_PRINTER_INFO_LEVEL_2 info;
1452 TDB_DATA kbuf, dbuf;
1456 slprintf(key, sizeof(key), "%s%s", PRINTERS_PREFIX, sharename);
1459 kbuf.dsize = strlen(key)+1;
1461 dbuf = tdb_fetch(tdb, kbuf);
1464 return get_a_printer_2_default(info_ptr, sharename);
1466 if (!dbuf.dptr) return 1;
1469 len += tdb_unpack(dbuf.dptr+len, dbuf.dsize-len, "dddddddddddfffffPfffff",
1472 &info.default_priority,
1489 info.printprocessor,
1493 /* Samba has to have shared raw drivers. */
1494 info.attributes |= (PRINTER_ATTRIBUTE_SHARED|PRINTER_ATTRIBUTE_RAW_ONLY);
1496 len += unpack_devicemode(&info.devmode,dbuf.dptr+len, dbuf.dsize-len);
1497 len += unpack_specifics(&info.specific,dbuf.dptr+len, dbuf.dsize-len);
1500 nt_printing_getsec(sharename, &info.secdesc_buf);
1501 #endif /* JRATEST */
1503 safe_free(dbuf.dptr);
1504 *info_ptr=memdup(&info, sizeof(info));
1506 DEBUG(9,("Unpacked printer [%s] running driver [%s]\n",
1507 sharename, info.drivername));
1513 /****************************************************************************
1514 debugging function, dump at level 6 the struct in the logs
1515 ****************************************************************************/
1516 static uint32 dump_a_printer(NT_PRINTER_INFO_LEVEL printer, uint32 level)
1519 NT_PRINTER_INFO_LEVEL_2 *info2;
1521 DEBUG(106,("Dumping printer at level [%d]\n", level));
1527 if (printer.info_2 == NULL)
1531 info2=printer.info_2;
1533 DEBUGADD(106,("attributes:[%d]\n", info2->attributes));
1534 DEBUGADD(106,("priority:[%d]\n", info2->priority));
1535 DEBUGADD(106,("default_priority:[%d]\n", info2->default_priority));
1536 DEBUGADD(106,("starttime:[%d]\n", info2->starttime));
1537 DEBUGADD(106,("untiltime:[%d]\n", info2->untiltime));
1538 DEBUGADD(106,("status:[%d]\n", info2->status));
1539 DEBUGADD(106,("cjobs:[%d]\n", info2->cjobs));
1540 DEBUGADD(106,("averageppm:[%d]\n", info2->averageppm));
1541 DEBUGADD(106,("changeid:[%d]\n", info2->changeid));
1542 DEBUGADD(106,("c_setprinter:[%d]\n", info2->c_setprinter));
1543 DEBUGADD(106,("setuptime:[%d]\n", info2->setuptime));
1545 DEBUGADD(106,("servername:[%s]\n", info2->servername));
1546 DEBUGADD(106,("printername:[%s]\n", info2->printername));
1547 DEBUGADD(106,("sharename:[%s]\n", info2->sharename));
1548 DEBUGADD(106,("portname:[%s]\n", info2->portname));
1549 DEBUGADD(106,("drivername:[%s]\n", info2->drivername));
1550 DEBUGADD(106,("comment:[%s]\n", info2->comment));
1551 DEBUGADD(106,("location:[%s]\n", info2->location));
1552 DEBUGADD(106,("sepfile:[%s]\n", info2->sepfile));
1553 DEBUGADD(106,("printprocessor:[%s]\n", info2->printprocessor));
1554 DEBUGADD(106,("datatype:[%s]\n", info2->datatype));
1555 DEBUGADD(106,("parameters:[%s]\n", info2->parameters));
1561 DEBUGADD(1,("Level not implemented\n"));
1569 /****************************************************************************
1570 Get the parameters we can substitute in an NT print job.
1571 ****************************************************************************/
1573 void get_printer_subst_params(int snum, fstring *printername, fstring *sharename, fstring *portname)
1575 NT_PRINTER_INFO_LEVEL *printer = NULL;
1577 **printername = **sharename = **portname = '\0';
1579 if (get_a_printer(&printer, 2, lp_servicename(snum))!=0)
1582 fstrcpy(*printername, printer->info_2->printername);
1583 fstrcpy(*sharename, printer->info_2->sharename);
1584 fstrcpy(*portname, printer->info_2->portname);
1586 free_a_printer(&printer, 2);
1590 * The function below are the high level ones.
1591 * only those ones must be called from the spoolss code.
1595 /****************************************************************************
1596 ****************************************************************************/
1597 uint32 add_a_printer(NT_PRINTER_INFO_LEVEL printer, uint32 level)
1601 dump_a_printer(printer, level);
1607 success=add_a_printer_2(printer.info_2);
1618 /****************************************************************************
1619 Get a NT_PRINTER_INFO_LEVEL struct. It returns malloced memory.
1620 ****************************************************************************/
1622 uint32 get_a_printer(NT_PRINTER_INFO_LEVEL **pp_printer, uint32 level, fstring sharename)
1625 NT_PRINTER_INFO_LEVEL *printer = NULL;
1629 DEBUG(10,("get_a_printer: [%s] level %u\n", sharename, (unsigned int)level));
1635 if ((printer = (NT_PRINTER_INFO_LEVEL *)malloc(sizeof(NT_PRINTER_INFO_LEVEL))) == NULL) {
1636 DEBUG(0,("get_a_printer: malloc fail.\n"));
1639 ZERO_STRUCTP(printer);
1640 success=get_a_printer_2(&printer->info_2, sharename);
1642 dump_a_printer(*printer, level);
1643 *pp_printer = printer;
1654 DEBUG(10,("get_a_printer: [%s] level %u returning %u\n", sharename, (unsigned int)level, (unsigned int)success));
1659 /****************************************************************************
1660 Deletes a NT_PRINTER_INFO_LEVEL struct.
1661 ****************************************************************************/
1663 uint32 free_a_printer(NT_PRINTER_INFO_LEVEL **pp_printer, uint32 level)
1666 NT_PRINTER_INFO_LEVEL *printer = *pp_printer;
1668 DEBUG(104,("freeing a printer at level [%d]\n", level));
1670 if (printer == NULL)
1677 if (printer->info_2 != NULL)
1679 free_nt_printer_info_level_2(&printer->info_2);
1698 /****************************************************************************
1699 ****************************************************************************/
1700 uint32 add_a_printer_driver(NT_PRINTER_DRIVER_INFO_LEVEL driver, uint32 level)
1703 DEBUG(104,("adding a printer at level [%d]\n", level));
1704 dump_a_printer_driver(driver, level);
1710 success=add_a_printer_driver_3(driver.info_3);
1716 success=add_a_printer_driver_6(driver.info_6);
1726 /****************************************************************************
1727 ****************************************************************************/
1728 uint32 get_a_printer_driver(NT_PRINTER_DRIVER_INFO_LEVEL *driver, uint32 level,
1729 fstring printername, fstring architecture, uint32 version)
1737 success=get_a_printer_driver_3(&(driver->info_3),
1739 architecture, version);
1747 if (success == 0) dump_a_printer_driver(*driver, level);
1751 /****************************************************************************
1752 ****************************************************************************/
1753 uint32 free_a_printer_driver(NT_PRINTER_DRIVER_INFO_LEVEL driver, uint32 level)
1761 NT_PRINTER_DRIVER_INFO_LEVEL_3 *info3;
1762 if (driver.info_3 != NULL)
1764 info3=driver.info_3;
1765 safe_free(info3->dependentfiles);
1766 ZERO_STRUCTP(info3);
1778 NT_PRINTER_DRIVER_INFO_LEVEL_6 *info6;
1779 if (driver.info_6 != NULL)
1781 info6=driver.info_6;
1782 safe_free(info6->dependentfiles);
1783 safe_free(info6->previousnames);
1784 ZERO_STRUCTP(info6);
1801 /****************************************************************************
1802 ****************************************************************************/
1803 BOOL get_specific_param_by_index(NT_PRINTER_INFO_LEVEL printer, uint32 level, uint32 param_index,
1804 fstring value, uint8 **data, uint32 *type, uint32 *len)
1806 /* right now that's enough ! */
1807 NT_PRINTER_PARAM *param;
1810 param=printer.info_2->specific;
1812 while (param != NULL && i < param_index) {
1820 /* exited because it exist */
1822 StrnCpy(value, param->value, sizeof(fstring)-1);
1823 *data=(uint8 *)malloc(param->data_len*sizeof(uint8));
1826 ZERO_STRUCTP(*data);
1827 memcpy(*data, param->data, param->data_len);
1828 *len=param->data_len;
1832 /****************************************************************************
1833 ****************************************************************************/
1834 BOOL get_specific_param(NT_PRINTER_INFO_LEVEL printer, uint32 level,
1835 fstring value, uint8 **data, uint32 *type, uint32 *len)
1837 /* right now that's enough ! */
1838 NT_PRINTER_PARAM *param;
1840 DEBUG(105, ("get_specific_param\n"));
1842 param=printer.info_2->specific;
1844 while (param != NULL)
1846 if ( !strcmp(value, param->value)
1847 && strlen(value)==strlen(param->value))
1853 DEBUG(106, ("found one param\n"));
1856 /* exited because it exist */
1859 *data=(uint8 *)malloc(param->data_len*sizeof(uint8));
1862 memcpy(*data, param->data, param->data_len);
1863 *len=param->data_len;
1865 DEBUG(106, ("exit of get_specific_param:true\n"));
1868 DEBUG(106, ("exit of get_specific_param:false\n"));
1872 /****************************************************************************
1873 Store a security desc for a printer.
1874 ****************************************************************************/
1876 uint32 nt_printing_setsec(char *printername, SEC_DESC_BUF *secdesc_ctr)
1878 SEC_DESC_BUF *new_secdesc_ctr = NULL;
1879 SEC_DESC_BUF *old_secdesc_ctr = NULL;
1881 TALLOC_CTX *mem_ctx = NULL;
1885 mem_ctx = talloc_init();
1886 if (mem_ctx == NULL)
1889 /* The old owner and group sids of the security descriptor are not
1890 present when new ACEs are added or removed by changing printer
1891 permissions through NT. If they are NULL in the new security
1892 descriptor then copy them over from the old one. */
1894 if (!secdesc_ctr->sec->owner_sid || !secdesc_ctr->sec->grp_sid) {
1895 DOM_SID *owner_sid, *group_sid;
1896 SEC_DESC *psd = NULL;
1899 nt_printing_getsec(printername, &old_secdesc_ctr);
1901 /* Pick out correct owner and group sids */
1903 owner_sid = secdesc_ctr->sec->owner_sid ?
1904 secdesc_ctr->sec->owner_sid :
1905 old_secdesc_ctr->sec->owner_sid;
1907 group_sid = secdesc_ctr->sec->grp_sid ?
1908 secdesc_ctr->sec->grp_sid :
1909 old_secdesc_ctr->sec->grp_sid;
1911 /* Make a deep copy of the security descriptor */
1913 psd = make_sec_desc(secdesc_ctr->sec->revision,
1914 secdesc_ctr->sec->type,
1915 owner_sid, group_sid,
1916 secdesc_ctr->sec->sacl,
1917 secdesc_ctr->sec->dacl,
1920 new_secdesc_ctr = make_sec_desc_buf(size, psd);
1922 /* Free up memory */
1924 free_sec_desc(&psd);
1925 free_sec_desc_buf(&old_secdesc_ctr);
1928 if (!new_secdesc_ctr) {
1929 new_secdesc_ctr = secdesc_ctr;
1932 /* Store the security descriptor in a tdb */
1934 prs_init(&ps, (uint32)sec_desc_size(new_secdesc_ctr->sec) +
1935 sizeof(SEC_DESC_BUF), 4, mem_ctx, MARSHALL);
1937 if (!sec_io_desc_buf("nt_printing_setsec", &new_secdesc_ctr,
1939 status = ERROR_INVALID_FUNCTION;
1943 slprintf(key, sizeof(key), "SECDESC/%s", printername);
1945 if (tdb_prs_store(tdb, key, &ps)==0) {
1948 DEBUG(1,("Failed to store secdesc for %s\n", printername));
1949 status = ERROR_INVALID_FUNCTION;
1952 /* Free mallocated memory */
1955 free_sec_desc_buf(&old_secdesc_ctr);
1957 if (new_secdesc_ctr != secdesc_ctr) {
1958 free_sec_desc_buf(&new_secdesc_ctr);
1963 talloc_destroy(mem_ctx);
1967 /****************************************************************************
1968 Construct a default security descriptor buffer for a printer.
1969 ****************************************************************************/
1971 static SEC_DESC_BUF *construct_default_printer_sdb(void)
1975 SEC_ACL *psa = NULL;
1976 SEC_DESC_BUF *sdb = NULL;
1977 SEC_DESC *psd = NULL;
1980 enum SID_NAME_USE name_type;
1982 /* Create an ACE where Everyone is allowed to print */
1984 init_sec_access(&sa, PRINTER_ACE_PRINT);
1985 init_sec_ace(&ace[0], &global_sid_World, SEC_ACE_TYPE_ACCESS_ALLOWED,
1986 sa, SEC_ACE_FLAG_CONTAINER_INHERIT);
1989 /* Make the security descriptor owned by the Administrators group
1990 on the PDC of the domain. */
1992 if (winbind_lookup_name(lp_workgroup(), &owner_sid, &name_type)) {
1993 sid_append_rid(&owner_sid, DOMAIN_USER_RID_ADMIN);
1996 /* Backup plan - make printer owned by admins or root. This should
1997 emulate a lanman printer as security settings can't be
2000 if (!lookup_name( "Printer Administrators", &owner_sid, &name_type) &&
2001 !lookup_name( "Administrators", &owner_sid, &name_type) &&
2002 !lookup_name( "Administrator", &owner_sid, &name_type) &&
2003 !lookup_name("root", &owner_sid, &name_type)) {
2004 sid_copy(&owner_sid, &global_sid_World);
2008 init_sec_access(&sa, PRINTER_ACE_MANAGE_DOCUMENTS | PRINTER_ACE_PRINT);
2009 init_sec_ace(&ace[1], &owner_sid, SEC_ACE_TYPE_ACCESS_ALLOWED,
2010 sa, SEC_ACE_FLAG_CONTAINER_INHERIT);
2012 /* The ACL revision number in rpc_secdesc.h differs from the one
2013 created by NT when setting ACE entries in printer
2014 descriptors. NT4 complains about the property being edited by a
2017 #define NT4_ACL_REVISION 0x2
2019 if ((psa = make_sec_acl(NT4_ACL_REVISION, 2, ace)) != NULL) {
2020 psd = make_sec_desc(SEC_DESC_REVISION,
2021 SEC_DESC_SELF_RELATIVE |
2022 SEC_DESC_DACL_PRESENT,
2024 NULL, psa, &sd_size);
2029 DEBUG(0,("construct_default_printer_sd: Failed to make SEC_DESC.\n"));
2033 sdb = make_sec_desc_buf(sd_size, psd);
2035 DEBUG(4,("construct_default_printer_sdb: size = %u.\n",
2036 (unsigned int)sd_size));
2038 free_sec_desc(&psd);
2042 /****************************************************************************
2043 Get a security desc for a printer.
2044 ****************************************************************************/
2046 BOOL nt_printing_getsec(char *printername, SEC_DESC_BUF **secdesc_ctr)
2049 TALLOC_CTX *mem_ctx = NULL;
2052 mem_ctx = talloc_init();
2053 if (mem_ctx == NULL)
2056 /* Fetch security descriptor from tdb */
2058 slprintf(key, sizeof(key), "SECDESC/%s", printername);
2060 if (tdb_prs_fetch(tdb, key, &ps, mem_ctx)!=0 ||
2061 !sec_io_desc_buf("nt_printing_getsec", secdesc_ctr, &ps, 1)) {
2063 DEBUG(4,("using default secdesc for %s\n", printername));
2065 if (!(*secdesc_ctr = construct_default_printer_sdb())) {
2066 talloc_destroy(mem_ctx);
2070 talloc_destroy(mem_ctx);
2074 /* If security descriptor is owned by S-1-1-0 and winbindd is up,
2075 this security descriptor has been created when winbindd was
2076 down. Take ownership of security descriptor. */
2078 if (sid_equal((*secdesc_ctr)->sec->owner_sid, &global_sid_World)) {
2080 enum SID_NAME_USE name_type;
2082 /* Change sd owner to workgroup administrator */
2084 if (winbind_lookup_name(lp_workgroup(), &owner_sid,
2086 SEC_DESC_BUF *new_secdesc_ctr = NULL;
2087 SEC_DESC *psd = NULL;
2092 sid_append_rid(&owner_sid, DOMAIN_USER_RID_ADMIN);
2094 psd = make_sec_desc((*secdesc_ctr)->sec->revision,
2095 (*secdesc_ctr)->sec->type,
2097 (*secdesc_ctr)->sec->grp_sid,
2098 (*secdesc_ctr)->sec->sacl,
2099 (*secdesc_ctr)->sec->dacl,
2102 new_secdesc_ctr = make_sec_desc_buf(size, psd);
2104 free_sec_desc(&psd);
2106 /* Swap with other one */
2108 free_sec_desc_buf(secdesc_ctr);
2109 *secdesc_ctr = new_secdesc_ctr;
2113 nt_printing_setsec(printername, *secdesc_ctr);
2118 talloc_destroy(mem_ctx);
2124 1: level not implemented
2125 2: file doesn't exist
2126 3: can't allocate memory
2127 4: can't free memory
2128 5: non existant struct
2132 A printer and a printer driver are 2 different things.
2133 NT manages them separatelly, Samba does the same.
2134 Why ? Simply because it's easier and it makes sense !
2136 Now explanation: You have 3 printers behind your samba server,
2137 2 of them are the same make and model (laser A and B). But laser B
2138 has an 3000 sheet feeder and laser A doesn't such an option.
2139 Your third printer is an old dot-matrix model for the accounting :-).
2141 If the /usr/local/samba/lib directory (default dir), you will have
2142 5 files to describe all of this.
2144 3 files for the printers (1 by printer):
2147 NTprinter_accounting
2148 2 files for the drivers (1 for the laser and 1 for the dot matrix)
2149 NTdriver_printer model X
2150 NTdriver_printer model Y
2152 jfm: I should use this comment for the text file to explain
2153 same thing for the forms BTW.
2154 Je devrais mettre mes commentaires en francais, ca serait mieux :-)
2158 /****************************************************************************
2159 Check a user has permissions to perform the given operation
2161 if user is NULL then use the current_user structure
2162 ****************************************************************************/
2163 BOOL print_access_check(struct current_user *user, int snum,
2164 uint32 required_access)
2166 SEC_DESC_BUF *secdesc = NULL;
2167 uint32 access_granted, status;
2171 extern struct current_user current_user;
2173 if (!user) user = ¤t_user;
2175 /* always allow root or printer admins to do anything */
2177 user_in_list(uidtoname(user->uid), lp_printer_admin(snum))) {
2181 /* Get printer name */
2182 pname = PRINTERNAME(snum);
2183 if (!pname || !*pname)
2184 pname = SERVICE(snum);
2186 if (!pname || !*pname) {
2191 /* Get printer security descriptor */
2192 nt_printing_getsec(pname, &secdesc);
2194 /* The ACE for Full Control in a printer security descriptor
2195 doesn't seem to map properly to the access checking model. For
2196 it to work properly it should be the logical OR of all the other
2197 values, i.e PRINTER_ACE_MANAGE_DOCUMENTS | PRINTER_ACE_PRINT.
2198 This would cause the access check to simply fall out when we
2199 check against any subset of these bits. To get things to work,
2200 change every ACE mask of PRINTER_ACE_FULL_CONTROL to
2201 PRINTER_ACE_MANAGE_DOCUMENTS | PRINTER_ACE_PRINT before
2202 performing the access check. I'm sure there is a better way to
2205 /* You forgot to also change the *required access* from PRINTER_ACE_FULL_CONTROL
2206 to PRINTER_ACE_MANAGE_DOCUMENTS | PRINTER_ACE_PRINT before doing the check.
2207 This took me 3 hours to find !!!!! JRA.
2210 if (required_access & PRINTER_ACE_FULL_CONTROL) {
2211 required_access |= (PRINTER_ACE_MANAGE_DOCUMENTS | PRINTER_ACE_PRINT);
2212 required_access &= ~PRINTER_ACE_FULL_CONTROL;
2215 if (secdesc && secdesc->sec && secdesc->sec->dacl &&
2216 secdesc->sec->dacl->ace) {
2217 for(i = 0; i < secdesc->sec->dacl->num_aces; i++) {
2218 if (secdesc->sec->dacl->ace[i].info.mask ==
2219 PRINTER_ACE_FULL_CONTROL) {
2220 secdesc->sec->dacl->ace[i].info.mask =
2221 PRINTER_ACE_MANAGE_DOCUMENTS |
2229 result = se_access_check(secdesc->sec, user, required_access,
2230 &access_granted, &status);
2232 DEBUG(4, ("access check was %s\n", result ? "SUCCESS" : "FAILURE"));
2234 /* Free mallocated memory */
2235 free_sec_desc_buf(&secdesc);
2243 /****************************************************************************
2244 Check the time parameters allow a print operation.
2245 *****************************************************************************/
2247 BOOL print_time_access_check(int snum)
2249 NT_PRINTER_INFO_LEVEL *printer = NULL;
2251 time_t now = time(NULL);
2255 if (get_a_printer(&printer, 2, lp_servicename(snum))!=0)
2258 if (printer->info_2->starttime == 0 && printer->info_2->untiltime == 0)
2262 mins = (uint32)t->tm_hour*60 + (uint32)t->tm_min;
2264 if (mins >= printer->info_2->starttime && mins <= printer->info_2->untiltime)
2267 free_a_printer(&printer, 2);