Fix NULL pointer constant issues in cmd/{truss,tic,stat,refer,print,oamuser,krb5...
[unleashed.git] / usr / src / cmd / print / lpset / lpset.c
blob1b590dec67ad34a74097611ba3b2cccb6c570919
1 /*
2 * CDDL HEADER START
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
19 * CDDL HEADER END
22 * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
23 * Use is subject to license terms.
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <sys/types.h>
29 #include <stdarg.h>
30 #include <unistd.h>
31 #include <limits.h>
32 #include <string.h>
33 #include <syslog.h>
34 #include <errno.h>
35 #include <locale.h>
36 #ifndef SUNOS_4
37 #include <libintl.h>
38 #endif
39 #include <pwd.h>
40 #include <alloca.h>
42 #include <ns.h>
43 #include <list.h>
45 extern char *optarg;
46 extern int optind, opterr, optopt;
47 extern char *getenv(const char *);
49 static void _decode_ldapResult(int result, char *printerName);
51 static int
52 authorized()
54 struct passwd *pw;
55 uid_t uid;
56 gid_t *list;
57 int len;
58 int maxgrp;
60 if ((uid = getuid()) == 0)
61 return (1); /* "root" is authorized */
63 if (((pw = getpwnam("lp")) != NULL) && (uid == pw->pw_uid))
64 return (1); /* "lp" is authorized */
66 if ((pw = getpwuid(uid)) == NULL)
67 return (0); /* intruders are not authorized */
69 if (chkauthattr("solaris.print.admin", pw->pw_name) == 1)
70 return (1); /* "solaris.print.admin" is authorized */
72 /* How many supplemental groups do we have? */
73 maxgrp = getgroups(0, NULL);
74 list = alloca(maxgrp * sizeof (gid_t));
76 if ((len = getgroups(maxgrp, list)) != -1)
77 while (len-- > 0)
78 if (list[len] == 14)
79 return (1); /* group 14 is authorized */
81 return (0); /* nobody else is authorized */
84 static void
85 Usage(char *name)
87 (void) fprintf(stderr,
88 gettext("Usage: %s [-n files | ldap] [-x] "
89 "[-h ldaphost] [-D binddn] [-w passwd] "
90 "[-a key=value] [-d key] (printer)\n"),
91 name);
92 exit(1);
97 * main() calls the appropriate routine to parse the command line arguments
98 * and then calls the local remove routine, followed by the remote remove
99 * routine to remove jobs.
102 main(int ac, char *av[])
104 int result = 0;
105 int delete_printer = 0;
106 int c;
107 char *program = NULL,
108 *printer = NULL,
109 *host = NULL,
110 *binddn = NULL,
111 *passwd = NULL,
112 *ins = NULL,
113 *ons = "files";
114 char **changes = NULL;
115 ns_cred_t *cred = NULL;
116 ns_printer_t *printer_obj = NULL;
118 (void) setlocale(LC_ALL, "");
120 #if !defined(TEXT_DOMAIN)
121 #define TEXT_DOMAIN "SYS_TEST"
122 #endif
123 (void) textdomain(TEXT_DOMAIN);
125 if ((program = strrchr(av[0], '/')) == NULL)
126 program = av[0];
127 else
128 program++;
130 openlog(program, LOG_PID, LOG_LPR);
132 if (ac < 2)
133 Usage(program);
135 while ((c = getopt(ac, av, "a:d:D:h:n:r:w:x")) != EOF)
136 switch (c) {
137 case 'd':
138 if (strchr(optarg, '=') != NULL)
139 Usage(program);
140 /* FALLTHRU */
141 case 'a':
142 changes = (char **)list_append((void**)changes,
143 (void *)strdup(optarg));
144 break;
145 case 'D':
146 binddn = optarg;
147 break;
148 case 'h':
149 host = optarg;
150 break;
151 case 'n':
152 ons = optarg;
153 break;
154 case 'r':
155 ins = optarg;
156 break;
157 case 'w':
158 passwd = optarg;
159 break;
160 case 'x':
161 delete_printer++;
162 break;
163 default:
164 Usage(program);
167 if (optind != ac-1)
168 Usage(program);
171 * Check required options have been given: [ -x | [ -a | -d ]]
173 if ((changes == NULL) && (delete_printer == 0)) {
174 Usage(program);
177 printer = av[optind];
179 if (strchr(printer, ':') != NULL) {
180 (void) fprintf(stderr, gettext(
181 "POSIX-Style names are not valid destinations (%s)\n"),
182 printer);
183 return (1);
186 ins = normalize_ns_name(ins);
187 ons = normalize_ns_name(ons);
188 if (ins == NULL)
189 ins = ons;
191 /* check / set the name service for writing */
192 if (strcasecmp("user", ons) == 0) {
193 (void) setuid(getuid());
194 ons = "user";
195 } else if (strcasecmp("files", ons) == 0) {
196 if (authorized() == 0) {
197 (void) fprintf(stderr, gettext(
198 "Permission denied: not authorized\n"));
199 return (1);
201 ons = "files";
202 } else if (strcasecmp("ldap", ons) == 0) {
203 if ((cred = calloc(1, sizeof (*cred))) == NULL) {
204 (void) fprintf(stderr,
205 gettext("could not initialize credential\n"));
206 return (1);
209 if (binddn == NULL) {
210 (void) fprintf(stderr,
211 gettext("Distinguished Name is required.\n"));
212 return (1);
215 if (passwd == NULL) {
216 passwd = getpassphrase(gettext("Bind Password:"));
220 * Setup LDAP bind credentials, so that it uses
221 * the default ldap port, and the NS domain for this
222 * ldapclient box. Note: passwdType is currently not
223 * used but once the ldap native function can select
224 * secure or insure password it will pass the user selected
225 * security type.
227 cred->passwd = passwd;
228 cred->passwdType = NS_PW_INSECURE; /* use default */
229 cred->binddn = binddn;
230 cred->host = host;
231 cred->port = 0; /* use default */
232 cred->domainDN = NULL; /* use default */
234 ons = "ldap";
235 (void) setuid(getuid());
236 } else {
237 (void) fprintf(stderr,
238 gettext("%s is not a supported name service.\n"),
239 ons);
240 return (1);
243 if (strcasecmp(NS_SVC_LDAP, ons) != 0) {
245 /* Naming Service is not LDAP */
247 /* get the printer object */
248 if ((printer_obj = ns_printer_get_name(printer, ins)) == NULL) {
249 if (delete_printer != 0) {
250 (void) fprintf(stderr, gettext
251 ("%s: unknown printer\n"), printer);
252 return (1);
254 if ((printer_obj = calloc(1, sizeof (*printer_obj)))
255 == NULL) {
256 (void) fprintf(stderr, gettext(
257 "could not initialize printer object\n"));
258 return (1);
260 printer_obj->name = strdup(printer);
263 printer_obj->source = ons;
265 if (cred != NULL) {
266 printer_obj->cred = cred;
269 /* make the changes to it */
270 while (changes != NULL && *changes != NULL) {
271 int has_equals = (strchr(*changes, '=') != NULL);
272 char *p, *key = NULL, *value = NULL;
274 key = *(changes++);
276 for (p = key; ((p != NULL) && (*p != '\0')); p++)
277 if (*p == '=') {
278 *p = '\0';
279 value = ++p;
280 break;
281 } else if (*p == '\\')
282 p++;
284 if ((value != NULL) && (*value == '\0'))
285 value = NULL;
287 if ((key != NULL) && (key[0] != '\0')) {
288 if ((value == NULL) &&
289 (ns_get_value(key, printer_obj) == NULL) &&
290 (has_equals == 0)) {
291 fprintf(stderr,
292 gettext("%s: unknown attribute\n"),
293 key);
294 result = 1;
295 } else
296 (void) ns_set_value_from_string(key, value,
297 printer_obj);
300 if (delete_printer != 0)
301 printer_obj->attributes = NULL;
303 /* write it back */
304 if (ns_printer_put(printer_obj) != 0) {
305 (void) fprintf(stderr,
306 gettext("Failed to write into %s database\n"),
307 ons);
308 result = 1;
312 else {
314 * Naming Service is LDAP
316 * Action the request by calling ns ldap functions to
317 * add, modify or delete the printer object.
320 if ((printer_obj = calloc(1, sizeof (*printer_obj))) == NULL) {
321 (void) fprintf(stderr, gettext(
322 "could not initialize printer object\n"));
323 return (1);
326 if ((cred != NULL) && (printer_obj != NULL)) {
327 printer_obj->name = strdup(printer);
328 printer_obj->cred = cred;
329 printer_obj->cred->domainDN = NULL; /* use default */
330 printer_obj->source = ons;
331 printer_obj->nsdata = malloc(sizeof (NS_LDAPDATA));
333 if (printer_obj->nsdata != NULL) {
335 * Update the LDAP directory for this printer
338 if (delete_printer != 0) {
339 /* Delete the printer object */
340 ((NS_LDAPDATA *)
341 (printer_obj->nsdata))->attrList
342 = NULL;
343 } else {
344 /* Add or modify the printer object */
345 ((NS_LDAPDATA *)
346 (printer_obj->nsdata))->attrList =
347 changes;
350 result = ns_printer_put(printer_obj);
351 if (result != 0) {
352 /* display LDAP specific message */
353 _decode_ldapResult(result, printer);
355 (void) fprintf(stderr, gettext(
356 "Failed to update %s database\n"), ons);
357 result = 1;
360 free(printer_obj->nsdata);
363 else {
364 _decode_ldapResult(NSL_ERR_MEMORY, NULL);
365 result = 1;
369 else {
370 result = 1;
371 (void) fprintf(stderr,
372 gettext("Error - no LDAP credentials\n"));
375 if (printer_obj != NULL) {
376 if (printer_obj->name != NULL) {
377 free(printer_obj->name);
379 free(printer_obj);
384 return (result);
385 } /* main */
391 * *****************************************************************************
393 * Function: _decode_ldapResult()
395 * Description: Decode the ldap_put_printer specific error codes and display
396 * the appropriate error message.
398 * Parameters:
399 * Input: int result - contains the NSL_RESULT codes
400 * char *printerName - name of printer
401 * Output: None
403 * Returns: void
405 * *****************************************************************************
408 static void
409 _decode_ldapResult(int result, char *printerName)
412 NSL_RESULT lresult = (NSL_RESULT)result;
414 /* ------------- */
416 switch (lresult)
418 case NSL_OK:
420 break;
423 case NSL_ERR_INTERNAL:
425 (void) fprintf(stderr,
426 gettext("Unexpected software error\n"));
427 break;
430 case NSL_ERR_ADD_FAILED:
432 (void) fprintf(stderr, "%s %s\n",
433 gettext("Failed to add printer:"), printerName);
434 break;
437 case NSL_ERR_MOD_FAILED:
439 (void) fprintf(stderr, "%s %s\n",
440 gettext("Failed to modify printer:"),
441 printerName);
442 break;
445 case NSL_ERR_DEL_FAILED:
447 (void) fprintf(stderr, "%s %s\n",
448 gettext("Failed to delete printer:"),
449 printerName);
450 break;
454 case NSL_ERR_UNKNOWN_PRINTER:
456 (void) fprintf(stderr, "%s %s\n",
457 gettext("Unknown printer:"), printerName);
458 break;
461 case NSL_ERR_CREDENTIALS:
463 (void) fprintf(stderr, "%s\n",
464 gettext("Missing LDAP credential information for printer:"));
465 break;
468 case NSL_ERR_CONNECT:
470 (void) fprintf(stderr, "%s\n",
471 gettext("Failed to connect to LDAP server"));
472 break;
475 case NSL_ERR_BIND:
477 (void) fprintf(stderr, gettext("LDAP bind failed\n"));
478 break;
481 case NSL_ERR_RENAME:
483 (void) fprintf(stderr, "%s %s\n",
484 gettext("Object rename not allowed for printer:"),
485 printerName);
486 break;
489 case NSL_ERR_KVP:
491 (void) fprintf(stderr, "%s",
492 gettext("Setting sun-printer-kvp attribute is "
493 "not supported through this command.\n"));
494 break;
497 case NSL_ERR_BSDADDR:
499 (void) fprintf(stderr, "%s",
500 gettext("Setting sun-printer-bsdaddr attribute is "
501 "not supported through this command.\n"
502 "Use the bsaddr attribute instead.\n"));
503 break;
506 case NSL_ERR_PNAME:
508 (void) fprintf(stderr, "%s",
509 gettext("Setting printer-name attribute is "
510 "not supported through this command.\n"));
511 break;
514 case NSL_ERR_MEMORY:
516 (void) fprintf(stderr,
517 gettext("Memory allocation error\n"));
518 break;
521 case NSL_ERR_MULTIOP:
523 (void) fprintf(stderr,
524 gettext("Delete and add operation on the "
525 "same key attribute is not allowed\n"));
526 break;
529 case NSL_ERR_NOTALLOWED:
531 (void) fprintf(stderr,
532 gettext("KVP attribute is not allowed\n"));
533 break;
536 default:
538 (void) fprintf(stderr,
539 gettext("Error code = %d\n"), result);
540 break;
544 } /* _decode_ldapResult */