1 /* 2 * CDDL HEADER START 3 * 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. 7 * 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. 12 * 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] 18 * 19 * CDDL HEADER END 20 */ 21 22 /* 23 * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 * 26 */ 27 28 /* $Id: lpstat.c 173 2006-05-25 04:52:06Z njacobs $ */ 29 30 31 #include <stdio.h> 32 #include <stdlib.h> 33 #include <unistd.h> 34 #include <string.h> 35 #include <locale.h> 36 #include <libintl.h> 37 #include <ctype.h> 38 #include <pwd.h> 39 #include <papi.h> 40 #include <uri.h> 41 #include "common.h" 42 #include "lp.h" 43 44 static void 45 usage(char *program) 46 { 47 char *name; 48 49 if ((name = strrchr(program, '/')) == NULL) 50 name = program; 51 else 52 name++; 53 54 fprintf(stdout, gettext("Usage: %s [-d] [-r] [-s] [-t] [-a [list]] " 55 "[-c [list]] [-o [list] [-l]] [-R [list] [-l]] " 56 "[-p [list] [-D] [-l]] [-v [list]] [-S [list] [-l]] " 57 "[-f [list] [-l]] [-u list]\n"), 58 name); 59 exit(1); 60 } 61 62 static char * 63 nctime(time_t *t) 64 { 65 static char buf[64]; 66 struct tm *tm = localtime(t); 67 68 (void) strftime(buf, sizeof (buf), "%c", tm); 69 70 return (buf); 71 } 72 73 static char * 74 printer_name(papi_printer_t printer) 75 { 76 papi_attribute_t **attributes = papiPrinterGetAttributeList(printer); 77 char *result = NULL; 78 79 if (attributes != NULL) 80 papiAttributeListGetString(attributes, NULL, 81 "printer-name", &result); 82 83 return (result); 84 } 85 86 static int 87 lpstat_default_printer(papi_encryption_t encryption) 88 { 89 papi_status_t status; 90 papi_service_t svc = NULL; 91 papi_printer_t p = NULL; 92 char *name = NULL; 93 94 status = papiServiceCreate(&svc, NULL, NULL, NULL, cli_auth_callback, 95 encryption, NULL); 96 if (status == PAPI_OK) { 97 char *req[] = { "printer-name", NULL }; 98 99 status = papiPrinterQuery(svc, DEFAULT_DEST, req, NULL, &p); 100 if (p != NULL) 101 name = printer_name(p); 102 } 103 if (name != NULL) 104 printf(gettext("system default printer: %s\n"), name); 105 else 106 printf(gettext("no system default destination\n")); 107 papiPrinterFree(p); 108 papiServiceDestroy(svc); 109 110 return (0); 111 } 112 113 static int 114 lpstat_service_status(papi_encryption_t encryption) 115 { 116 papi_status_t status; 117 papi_service_t svc = NULL; 118 char *name = NULL; 119 120 if (((name = getenv("PAPI_SERVICE_URI")) == NULL) && 121 ((name = getenv("IPP_SERVER")) == NULL) && 122 ((name = getenv("CUPS_SERVER")) == NULL)) 123 name = DEFAULT_SERVICE_URI; 124 125 status = papiServiceCreate(&svc, name, NULL, NULL, cli_auth_callback, 126 encryption, NULL); 127 if (status != PAPI_OK) { 128 printf(gettext("scheduler is not running\n")); 129 } else 130 printf(gettext("scheduler is running\n")); 131 papiServiceDestroy(svc); 132 133 return (0); 134 } 135 136 static char * 137 get_device_uri(papi_service_t svc, char *name) 138 { 139 papi_status_t status; 140 papi_printer_t p = NULL; 141 char *keys[] = { "device-uri", NULL }; 142 char *result = NULL; 143 144 status = papiPrinterQuery(svc, name, keys, NULL, &p); 145 if ((status == PAPI_OK) && (p != NULL)) { 146 papi_attribute_t **attrs = papiPrinterGetAttributeList(p); 147 148 (void) papiAttributeListGetString(attrs, NULL, 149 "device-uri", &result); 150 if (result != NULL) 151 result = strdup(result); 152 153 papiPrinterFree(p); 154 } 155 156 return (result); 157 } 158 159 static void 160 print_description(papi_attribute_t **list, char *printer_name) 161 { 162 char *str = ""; 163 164 (void) papiAttributeListGetString(list, NULL, 165 "printer-info", &str); 166 167 /* 168 * If no printer-info is read then 169 * by default the printer-info is <printer-name>@<server> 170 */ 171 if (str[0] == '\0') { 172 char *uri = NULL; 173 uri_t *u = NULL; 174 175 (void) papiAttributeListGetString(list, NULL, 176 "printer-uri-supported", &uri); 177 178 if ((uri != NULL) && (uri_from_string(uri, &u) == 0)) { 179 char *nodename = localhostname(); 180 181 if ((u->host == NULL) || 182 (strcasecmp(u->host, "localhost") == 0) || 183 (strcasecmp(u->host, nodename) == 0)) 184 printf(gettext("\tDescription:\n")); 185 else 186 printf(gettext("\tDescription: %s@%s\n"), 187 printer_name, u->host); 188 189 uri_free(u); 190 } else 191 printf(gettext("\tDescription:\n")); 192 } else 193 printf(gettext("\tDescription: %s\n"), str); 194 } 195 196 static char *report_device_keys[] = { "printer-name", "printer-uri-supported", 197 NULL }; 198 /* ARGSUSED2 */ 199 static int 200 report_device(papi_service_t svc, char *name, papi_printer_t printer, 201 int verbose, int description) 202 { 203 papi_status_t status; 204 papi_attribute_t **attrs = papiPrinterGetAttributeList(printer); 205 char *uri = NULL; 206 char *device = NULL; 207 uri_t *u = NULL; 208 209 if (name == NULL) { 210 status = papiAttributeListGetString(attrs, NULL, 211 "printer-name", &name); 212 if (status != PAPI_OK) 213 status = papiAttributeListGetString(attrs, NULL, 214 "printer-uri-supported", &name); 215 } 216 217 if (name == NULL) 218 return (-1); 219 220 (void) papiAttributeListGetString(attrs, NULL, 221 "printer-uri-supported", &uri); 222 223 if ((uri != NULL) && (uri_from_string(uri, &u) == 0)) { 224 char *nodename = localhostname(); 225 226 if ((u->host == NULL) || 227 (strcasecmp(u->host, "localhost") == 0) || 228 (strcasecmp(u->host, nodename) == 0)) 229 device = get_device_uri(svc, name); 230 231 if (device != NULL) { 232 printf(gettext("device for %s: %s\n"), name, device); 233 return (0); 234 } else if (uri != NULL) { 235 printf(gettext("system for %s: %s (as %s)\n"), name, 236 u->host?u->host:"localhost", uri); 237 return (0); 238 } 239 240 uri_free(u); 241 } 242 243 return (0); 244 } 245 246 static char *report_accepting_keys[] = { "printer-name", 247 "printer-uri-supported", "printer-is-accepting-jobs", 248 "printer-up-time", "printer-state-time", 249 "lpsched-reject-date", "lpsched-reject-reason", NULL }; 250 /* ARGSUSED2 */ 251 static int 252 report_accepting(papi_service_t svc, char *name, papi_printer_t printer, 253 int verbose, int description) 254 { 255 papi_status_t status; 256 papi_attribute_t **attrs = papiPrinterGetAttributeList(printer); 257 time_t curr; 258 char boolean = PAPI_FALSE; 259 260 if (name == NULL) { 261 status = papiAttributeListGetString(attrs, NULL, 262 "printer-name", &name); 263 if (status != PAPI_OK) 264 status = papiAttributeListGetString(attrs, NULL, 265 "printer-uri-supported", &name); 266 } 267 if (name == NULL) 268 return (-1); 269 270 (void) papiAttributeListGetBoolean(attrs, NULL, 271 "printer-is-accepting-jobs", &boolean); 272 (void) time(&curr); 273 (void) papiAttributeListGetDatetime(attrs, NULL, 274 "printer-up-time", &curr); 275 (void) papiAttributeListGetDatetime(attrs, NULL, 276 "printer-state-time", &curr); 277 (void) papiAttributeListGetDatetime(attrs, NULL, 278 "lpsched-reject-date", &curr); 279 280 if (boolean == PAPI_TRUE) { 281 printf(gettext("%s accepting requests since %s\n"), 282 name, nctime(&curr)); 283 } else { 284 char *reason = "unknown reason"; 285 286 (void) papiAttributeListGetString(attrs, NULL, 287 "lpsched-reject-reason", &reason); 288 289 printf(gettext("%s not accepting requests since %s\n\t%s\n"), 290 name, nctime(&curr), reason); 291 } 292 293 return (0); 294 } 295 296 static char *report_class_keys[] = { "printer-name", "printer-uri-supported", 297 "member-names", NULL }; 298 /* ARGSUSED2 */ 299 static int 300 report_class(papi_service_t svc, char *name, papi_printer_t printer, 301 int verbose, int description) 302 { 303 papi_status_t status; 304 papi_attribute_t **attrs = papiPrinterGetAttributeList(printer); 305 char *member = NULL; 306 void *iter = NULL; 307 308 status = papiAttributeListGetString(attrs, &iter, 309 "member-names", &member); 310 if (status == PAPI_NOT_FOUND) /* it's not a class */ 311 return (0); 312 313 if (name == NULL) { 314 status = papiAttributeListGetString(attrs, NULL, 315 "printer-name", &name); 316 if (status != PAPI_OK) 317 status = papiAttributeListGetString(attrs, NULL, 318 "printer-uri-supported", &name); 319 } 320 if (name == NULL) 321 return (-1); 322 323 printf(gettext("members of class %s:\n\t%s\n"), name, member); 324 while (papiAttributeListGetString(attrs, &iter, NULL, &member) 325 == PAPI_OK) 326 printf("\t%s\n", member); 327 328 return (0); 329 } 330 331 static int 332 get_remote_hostname(papi_attribute_t **attrs, char **host) 333 { 334 char *uri = NULL; 335 uri_t *u; 336 char *nodename; 337 338 *host = NULL; 339 (void) papiAttributeListGetString(attrs, NULL, 340 "job-originating-host-name", host); 341 (void) papiAttributeListGetString(attrs, NULL, 342 "printer-uri-supported", &uri); 343 if (*host == NULL) { 344 if (uri != NULL) { 345 if (uri_from_string(uri, &u) == 0) { 346 if (u->host == NULL) { 347 uri_free(u); 348 return (0); 349 } 350 *host = strdup(u->host); 351 uri_free(u); 352 } else { 353 return (0); 354 } 355 } else { 356 return (0); 357 } 358 } 359 nodename = localhostname(); 360 if ((strcasecmp(*host, "localhost") == 0) || 361 (strcasecmp(*host, nodename) == 0)) { 362 return (0); 363 } 364 return (1); 365 } 366 367 static char *report_printer_keys[] = { "printer-name", 368 "printer-uri-supported", "printer-state", 369 "printer-up-time", "printer-state-time", 370 "lpsched-disable-date", "printer-state-reasons", 371 "lpsched-disable-reason", NULL }; 372 /* ARGSUSED2 */ 373 static int 374 report_printer(papi_service_t svc, char *name, papi_printer_t printer, 375 int verbose, int description) 376 { 377 papi_status_t status; 378 papi_attribute_t **attrs = papiPrinterGetAttributeList(printer); 379 time_t curr; 380 int32_t pstat = 0; 381 char *member = NULL; 382 papi_job_t *j = NULL; 383 384 status = papiAttributeListGetString(attrs, NULL, 385 "member-names", &member); 386 if (status == PAPI_OK) /* it's a class */ 387 return (0); 388 389 if (name == NULL) { 390 status = papiAttributeListGetString(attrs, NULL, 391 "printer-name", &name); 392 if (status != PAPI_OK) 393 status = papiAttributeListGetString(attrs, NULL, 394 "printer-uri-supported", &name); 395 } 396 if (name == NULL) 397 return (-1); 398 399 printf(gettext("printer %s "), name); 400 401 status = papiAttributeListGetInteger(attrs, NULL, 402 "printer-state", &pstat); 403 404 switch (pstat) { 405 case 0x03: /* idle */ 406 printf(gettext("idle. enabled")); 407 break; 408 case 0x04: /* processing */ 409 status = papiPrinterListJobs(svc, name, NULL, 410 0, 0, &j); 411 412 if (status == PAPI_OK) { 413 if (j != NULL) { 414 int i = 0; 415 int32_t jobid = 0; 416 int32_t jstate = 0; 417 int flag = 0; 418 419 for (i = 0; j[i] != NULL; ++i) { 420 papi_attribute_t **attr = 421 papiJobGetAttributeList(j[i]); 422 423 papiAttributeListGetInteger(attr, 424 NULL, "job-state", &jstate); 425 papiAttributeListGetInteger(attr, 426 NULL, "job-id", &jobid); 427 428 /* 429 * If the job-state is in 430 * RS_PRINTING then only print. 431 */ 432 if (jstate == 0x0008) { 433 if (flag == 0) 434 printf(gettext 435 ("now printing"\ 436 " %s-%d. enabled"), 437 name, jobid); 438 flag = 1; 439 } 440 } 441 papiJobListFree(j); 442 } 443 } 444 break; 445 case 0x05: /* stopped */ 446 printf(gettext("disabled")); 447 break; 448 default: 449 printf(gettext("unknown state(0x%x)."), pstat); 450 break; 451 } 452 453 (void) time(&curr); 454 (void) papiAttributeListGetDatetime(attrs, NULL, 455 "printer-up-time", &curr); 456 (void) papiAttributeListGetDatetime(attrs, NULL, 457 "printer-state-time", &curr); 458 (void) papiAttributeListGetDatetime(attrs, NULL, 459 "lpsched-disable-date", &curr); 460 printf(gettext(" since %s. available.\n"), nctime(&curr)); 461 462 if (pstat == 0x05) { 463 char *reason = "unknown reason"; 464 465 (void) papiAttributeListGetString(attrs, NULL, 466 "printer-state-reasons", &reason); 467 (void) papiAttributeListGetString(attrs, NULL, 468 "lpsched-disable-reason", &reason); 469 printf(gettext("\t%s\n"), reason); 470 } 471 472 if (verbose == 1) { 473 void *iter; 474 char *str; 475 char *host = NULL; 476 477 if ((get_remote_hostname(attrs, &host)) != 0) { 478 (void) printf( 479 gettext("\tRemote Name: %s\n\tRemote Server: " 480 "%s\n"), name, host); 481 free(host); 482 return (0); 483 } 484 str = ""; 485 (void) papiAttributeListGetString(attrs, NULL, 486 "form-ready", &str); 487 printf(gettext("\tForm mounted: %s\n"), str); 488 489 str = ""; 490 iter = NULL; 491 (void) papiAttributeListGetString(attrs, &iter, 492 "document-format-supported", &str); 493 printf(gettext("\tContent types: %s"), str); 494 while (papiAttributeListGetString(attrs, &iter, NULL, &str) 495 == PAPI_OK) 496 printf(", %s", str); 497 printf("\n"); 498 499 /* Display the printer description */ 500 print_description(attrs, name); 501 502 str = ""; 503 iter = NULL; 504 (void) papiAttributeListGetString(attrs, &iter, 505 "lpsched-printer-type", &str); 506 printf(gettext("\tPrinter types: %s"), str); 507 while (papiAttributeListGetString(attrs, &iter, NULL, &str) 508 == PAPI_OK) 509 printf(", %s", str); 510 printf("\n"); 511 512 str = ""; 513 (void) papiAttributeListGetString(attrs, NULL, 514 "lpsched-dial-info", &str); 515 printf(gettext("\tConnection: %s\n"), 516 ((str[0] == '\0') ? gettext("direct") : str)); 517 518 str = ""; 519 (void) papiAttributeListGetString(attrs, NULL, 520 "lpsched-interface-script", &str); 521 printf(gettext("\tInterface: %s\n"), str); 522 523 str = NULL; 524 (void) papiAttributeListGetString(attrs, NULL, 525 "ppd-file-uri", &str); 526 (void) papiAttributeListGetString(attrs, NULL, 527 "lpsched-ppd-source-path", &str); 528 if (str != NULL) 529 printf(gettext("\tPPD: %s\n"), str); 530 531 str = NULL; 532 (void) papiAttributeListGetString(attrs, NULL, 533 "lpsched-fault-alert-command", &str); 534 if (str != NULL) 535 printf(gettext("\tOn fault: %s\n"), str); 536 537 str = ""; 538 (void) papiAttributeListGetString(attrs, NULL, 539 "lpsched-fault-recovery", &str); 540 printf(gettext("\tAfter fault: %s\n"), 541 ((str[0] == '\0') ? gettext("continue") : str)); 542 543 str = "(all)"; 544 iter = NULL; 545 (void) papiAttributeListGetString(attrs, &iter, 546 "requesting-user-name-allowed", &str); 547 printf(gettext("\tUsers allowed:\n\t\t%s\n"), 548 ((str[0] == '\0') ? gettext("(none)") : str)); 549 if ((str != NULL) && (str[0] != '\0')) 550 while (papiAttributeListGetString(attrs, &iter, NULL, 551 &str) == PAPI_OK) 552 printf("\t\t%s\n", str); 553 554 str = NULL; 555 iter = NULL; 556 (void) papiAttributeListGetString(attrs, &iter, 557 "requesting-user-name-denied", &str); 558 if (str != NULL) { 559 printf(gettext("\tUsers denied:\n\t\t%s\n"), 560 ((str[0] == '\0') ? gettext("(none)") : str)); 561 if ((str != NULL) && (str[0] != '\0')) 562 while (papiAttributeListGetString(attrs, &iter, 563 NULL, &str) == PAPI_OK) 564 printf("\t\t%s\n", str); 565 } 566 567 str = "none"; 568 iter = NULL; 569 (void) papiAttributeListGetString(attrs, &iter, 570 "form-supported", &str); 571 printf(gettext("\tForms allowed:\n\t\t(%s)\n"), 572 ((str[0] == '\0') ? gettext("none") : str)); 573 if ((str != NULL) && (str[0] != '\0')) 574 while (papiAttributeListGetString(attrs, &iter, NULL, 575 &str) == PAPI_OK) 576 printf("\t\t(%s)\n", str); 577 578 str = ""; 579 iter = NULL; 580 (void) papiAttributeListGetString(attrs, &iter, 581 "media-supported", &str); 582 printf(gettext("\tMedia supported:\n\t\t%s\n"), 583 ((str[0] == '\0') ? gettext("(none)") : str)); 584 if ((str != NULL) && (str[0] != '\0')) 585 while (papiAttributeListGetString(attrs, &iter, NULL, 586 &str) == PAPI_OK) 587 printf("\t\t%s\n", str); 588 589 str = ""; 590 (void) papiAttributeListGetString(attrs, NULL, 591 "job-sheets-supported", &str); 592 if ((strcasecmp(str, "none")) == 0) 593 str = gettext("page never printed"); 594 else if (strcasecmp(str, "optional") == 0) 595 str = gettext("not required"); 596 else 597 str = gettext("required"); 598 599 printf(gettext("\tBanner %s\n"), str); 600 601 602 str = ""; 603 iter = NULL; 604 (void) papiAttributeListGetString(attrs, &iter, 605 "lpsched-print-wheels", &str); 606 printf(gettext("\tCharacter sets:\n\t\t%s\n"), 607 ((str[0] == '\0') ? gettext("(none)") : str)); 608 if ((str != NULL) && (str[0] != '\0')) 609 while (papiAttributeListGetString(attrs, &iter, NULL, 610 &str) == PAPI_OK) 611 printf("\t\t%s\n", str); 612 613 printf(gettext("\tDefault pitch:\n")); 614 printf(gettext("\tDefault page size:\n")); 615 printf(gettext("\tDefault port setting:\n")); 616 617 str = ""; 618 iter = NULL; 619 (void) papiAttributeListGetString(attrs, &iter, 620 "lpsched-options", &str); 621 if (str != NULL) { 622 printf(gettext("\tOptions: %s"), str); 623 while (papiAttributeListGetString(attrs, &iter, NULL, 624 &str) == PAPI_OK) 625 printf(", %s", str); 626 printf("\n"); 627 } 628 629 } else if (description == 1) 630 /* Display printer description */ 631 print_description(attrs, name); 632 else if (verbose > 1) 633 papiAttributeListPrint(stdout, attrs, "\t"); 634 635 if (verbose > 0) 636 printf("\n"); 637 638 return (0); 639 } 640 641 static int 642 printer_query(char *name, int (*report)(papi_service_t, char *, papi_printer_t, 643 int, int), papi_encryption_t encryption, 644 int verbose, int description) 645 { 646 int result = 0, i = 0; 647 papi_status_t status; 648 papi_service_t svc = NULL; 649 char **list = getlist(name, LP_WS, LP_SEP); 650 651 if (list == NULL) { 652 list = (char **)malloc(sizeof (char *)); 653 list[0] = name; 654 } 655 656 /* 657 * The for loop executes once for every printer 658 * entry in list. If list is NULL that implies 659 * name is also NULL, the loop runs only one time. 660 */ 661 662 for (i = 0; name == NULL || list[i] != NULL; i++) { 663 name = list[i]; 664 665 status = papiServiceCreate(&svc, name, NULL, NULL, 666 cli_auth_callback, encryption, NULL); 667 if (status != PAPI_OK) { 668 if (status == PAPI_NOT_FOUND) 669 fprintf(stderr, 670 gettext("%s: unknown printer\n"), 671 name ? name : "(NULL)"); 672 else 673 fprintf(stderr, gettext( 674 "Failed to contact service for %s: %s\n"), 675 name ? name : "(NULL)", 676 verbose_papi_message(svc, status)); 677 papiServiceDestroy(svc); 678 result--; 679 continue; 680 } 681 682 if (name == NULL) { /* all */ 683 char **interest = interest_list(svc); 684 685 if (interest != NULL) { 686 int i; 687 688 for (i = 0; interest[i] != NULL; i++) 689 result += printer_query(interest[i], 690 report, encryption, verbose, 691 description); 692 } 693 } else { 694 papi_printer_t printer = NULL; 695 char **keys = NULL; 696 697 /* 698 * Limit the query to only required data 699 * to reduce the need to go remote for 700 * information. 701 */ 702 if (report == report_device) 703 keys = report_device_keys; 704 else if (report == report_class) 705 keys = report_class_keys; 706 else if (report == report_accepting) 707 keys = report_accepting_keys; 708 else if ((report == report_printer) && (verbose == 0)) 709 keys = report_printer_keys; 710 711 status = papiPrinterQuery(svc, name, keys, 712 NULL, &printer); 713 if (status != PAPI_OK) { 714 fprintf(stderr, gettext( 715 "Failed to get printer info for %s: %s\n"), 716 name, verbose_papi_message(svc, status)); 717 papiServiceDestroy(svc); 718 result--; 719 continue; 720 } 721 722 if (printer != NULL) 723 result += report(svc, name, printer, verbose, 724 description); 725 726 papiPrinterFree(printer); 727 } 728 729 papiServiceDestroy(svc); 730 731 if (name == NULL) 732 break; 733 } 734 735 freelist(list); 736 737 return (result); 738 } 739 740 static int 741 match_user(char *user, char **list) 742 { 743 int i; 744 745 for (i = 0; list[i] != NULL; i++) { 746 if (strcmp(user, list[i]) == 0) 747 return (0); 748 } 749 750 return (-1); 751 } 752 753 static char **users = NULL; 754 755 static int 756 report_job(char *printer, papi_job_t job, int show_rank, int verbose) 757 { 758 papi_attribute_t **attrs = papiJobGetAttributeList(job); 759 time_t clock = 0; 760 char date[24]; 761 char request[26]; 762 char *user = "unknown"; 763 char *host = NULL; 764 int32_t size = 0; 765 int32_t jstate = 0; 766 char User[50]; 767 768 char *destination = "unknown"; 769 int32_t id = -1; 770 static int check = 0; 771 static char *uri = NULL; 772 773 (void) papiAttributeListGetString(attrs, NULL, 774 "job-originating-user-name", &user); 775 776 if ((users != NULL) && (match_user(user, users) < 0)) 777 return (0); 778 779 (void) papiAttributeListGetString(attrs, NULL, 780 "job-originating-host-name", &host); 781 782 if (check == 0) { 783 /* 784 * Read the attribute "job-printer-uri" 785 * just once 786 */ 787 (void) papiAttributeListGetString(attrs, NULL, 788 "job-printer-uri", &uri); 789 check = 1; 790 } 791 792 if (host) { 793 /* Check if it is local printer or remote printer */ 794 uri_t *u = NULL; 795 796 if ((uri != NULL) && (uri_from_string(uri, &u) == 0)) { 797 char *nodename = localhostname(); 798 799 if ((u->host == NULL) || 800 (strcasecmp(u->host, "localhost") == 0) || 801 (strcasecmp(u->host, nodename) == 0)) { 802 803 if (strcasecmp(host, nodename) == 0) { 804 /* 805 * Request submitted locally 806 * for the local queue. 807 * Hostname will not be displayed 808 */ 809 snprintf(User, sizeof (User), "%s", 810 user); 811 } 812 else 813 snprintf(User, sizeof (User), "%s@%s", 814 user, host); 815 } else if (uri != NULL) { 816 /* 817 * It's a remote printer. 818 * In case of remote printers hostname is 819 * always displayed. 820 */ 821 snprintf(User, sizeof (User), "%s@%s", 822 user, host); 823 } 824 uri_free(u); 825 } else { 826 /* 827 * If attribute "job-printer-uri" 828 * cannot be read 829 * by default append the hostname 830 */ 831 snprintf(User, sizeof (User), "%s@%s", user, host); 832 } 833 } else { 834 /* 835 * When print server is s10u4 and ipp service is used 836 * "job-originating-hostname" attribute is not set 837 * So get the host information from the uri 838 */ 839 uri_t *u = NULL; 840 if ((uri != NULL) && (uri_from_string(uri, &u) == 0)) { 841 if ((u != NULL) && (u->host != NULL)) 842 snprintf(User, sizeof (User), "%s@%s", 843 user, u->host); 844 else 845 snprintf(User, sizeof (User), "%s", user); 846 847 uri_free(u); 848 } else 849 snprintf(User, sizeof (User), "%s", user); 850 } 851 (void) papiAttributeListGetInteger(attrs, NULL, "job-k-octets", &size); 852 size *= 1024; /* for the approximate byte size */ 853 (void) papiAttributeListGetInteger(attrs, NULL, "job-octets", &size); 854 855 (void) time(&clock); 856 (void) papiAttributeListGetInteger(attrs, NULL, 857 "time-at-creation", (int32_t *)&clock); 858 (void) strftime(date, sizeof (date), "%b %d %R", localtime(&clock)); 859 860 (void) papiAttributeListGetString(attrs, NULL, 861 "job-printer-uri", &destination); 862 (void) papiAttributeListGetString(attrs, NULL, 863 "printer-name", &destination); 864 (void) papiAttributeListGetInteger(attrs, NULL, 865 "job-id", &id); 866 (void) papiAttributeListGetInteger(attrs, NULL, 867 "job-id-requested", &id); 868 869 870 snprintf(request, sizeof (request), "%s-%d", printer, id); 871 872 if (show_rank != 0) { 873 int32_t rank = -1; 874 875 (void) papiAttributeListGetInteger(attrs, NULL, 876 "number-of-intervening-jobs", &rank); 877 rank++; 878 879 printf("%3d %-21s %-14s %7ld %s", 880 rank, request, User, size, date); 881 } else 882 printf("%-23s %-14s %7ld %s", request, User, size, date); 883 884 (void) papiAttributeListGetInteger(attrs, NULL, 885 "job-state", &jstate); 886 887 if (jstate == 0x0001) 888 printf(gettext(" being held")); 889 else if (jstate == 0x0800) 890 printf(gettext(" notifying user")); 891 else if (jstate == 0x0040) 892 printf(gettext(" cancelled")); 893 else if (jstate == 0x0010) 894 printf(gettext(" finished printing")); 895 else if (jstate == 0x0008) 896 printf(gettext(" on %s"), destination); 897 else if (jstate == 0x2000) 898 printf(gettext(" held by admin")); 899 else if (jstate == 0x0002) 900 printf(gettext(" being filtered")); 901 else if (jstate == 0x0004) 902 printf(gettext(" filtered")); 903 else if (jstate == 0x0020) 904 printf(gettext(" held for change")); 905 906 if (verbose == 1) { 907 char *form = NULL; 908 909 (void) papiAttributeListGetString(attrs, NULL, 910 "output-device-assigned", &destination); 911 printf("\n\t assigned %s", destination); 912 913 (void) papiAttributeListGetString(attrs, NULL, "form", &form); 914 if (form != NULL) 915 printf(", form %s", form); 916 } else if (verbose > 1) { 917 printf("\n"); 918 papiAttributeListPrint(stdout, attrs, "\t"); 919 } 920 921 printf("\n"); 922 923 return (0); 924 } 925 926 static int 927 job_query(char *request, int (*report)(char *, papi_job_t, int, int), 928 papi_encryption_t encryption, int show_rank, int verbose) 929 { 930 int result = 0; 931 papi_status_t status; 932 papi_service_t svc = NULL; 933 char *printer = request; 934 int32_t id = -1; 935 int flag1 = 0; 936 int flag = 1; 937 int print_flag = 0; 938 939 do { 940 status = papiServiceCreate(&svc, printer, NULL, NULL, 941 cli_auth_callback, encryption, NULL); 942 943 if ((status == PAPI_OK) && (printer != NULL)) 944 print_flag = 1; 945 946 /* <name>-# printer name does not exist */ 947 if (status != PAPI_OK) { 948 /* 949 * Check if <name>-# is a request-id 950 * Once this check is done flag1 is set 951 */ 952 if (flag1 == 1) 953 break; 954 955 get_printer_id(printer, &printer, &id); 956 957 status = papiServiceCreate(&svc, printer, NULL, NULL, 958 cli_auth_callback, encryption, NULL); 959 960 if (status != PAPI_OK) { 961 fprintf(stderr, gettext( 962 "Failed to contact service for %s: %s\n"), 963 (printer ? printer : "all"), 964 verbose_papi_message(svc, status)); 965 return (-1); 966 } 967 } 968 969 if (printer == NULL) { /* all */ 970 char **interest = interest_list(svc); 971 972 if (interest != NULL) { 973 int i; 974 975 for (i = 0; interest[i] != NULL; i++) 976 result += job_query(interest[i], report, 977 encryption, show_rank, verbose); 978 } 979 } else if (id == -1) { /* a printer */ 980 papi_job_t *jobs = NULL; 981 982 status = papiPrinterListJobs(svc, printer, NULL, 983 0, 0, &jobs); 984 if (status != PAPI_OK) { 985 fprintf(stderr, gettext( 986 "Failed to get job list: %s\n"), 987 verbose_papi_message(svc, status)); 988 papiServiceDestroy(svc); 989 return (-1); 990 } 991 992 if (jobs != NULL) { 993 int i; 994 995 for (i = 0; jobs[i] != NULL; i++) 996 result += report(printer, 997 jobs[i], show_rank, 998 verbose); 999 } 1000 1001 papiJobListFree(jobs); 1002 } else { /* a job */ 1003 papi_job_t job = NULL; 1004 int rid = id; 1005 1006 /* Once a job has been found stop processing */ 1007 flag = 0; 1008 1009 /* 1010 * Job-id could be the job-id requested 1011 * Check if it is job-id or job-id-requested 1012 */ 1013 id = job_to_be_queried(svc, printer, id); 1014 1015 if (id > 0) 1016 status = papiJobQuery(svc, printer, id, 1017 NULL, &job); 1018 else 1019 status = papiJobQuery(svc, printer, rid, 1020 NULL, &job); 1021 1022 if (status != PAPI_OK) { 1023 if (!print_flag) 1024 fprintf(stderr, gettext( 1025 "Failed to get job"\ 1026 " info for %s: %s\n"), 1027 request, 1028 verbose_papi_message(svc, status)); 1029 papiServiceDestroy(svc); 1030 return (-1); 1031 } 1032 1033 if (job != NULL) 1034 result = report(printer, job, 1035 show_rank, verbose); 1036 1037 papiJobFree(job); 1038 } 1039 1040 if (flag) { 1041 id = -1; 1042 get_printer_id(printer, &printer, &id); 1043 if (id == -1) 1044 flag = 0; 1045 else 1046 flag1 = 1; 1047 } 1048 } while (flag); 1049 1050 papiServiceDestroy(svc); 1051 1052 return (result); 1053 } 1054 1055 static int 1056 report_form(char *name, papi_attribute_t **attrs, int verbose) 1057 { 1058 papi_status_t status; 1059 char *form = NULL; 1060 void *iter = NULL; 1061 1062 for (status = papiAttributeListGetString(attrs, &iter, 1063 "form-supported", &form); 1064 status == PAPI_OK; 1065 status = papiAttributeListGetString(attrs, &iter, 1066 NULL, &form)) { 1067 if ((name == NULL) || (strcmp(name, form) == 0)) { 1068 printf(gettext("form %s is available to you\n"), form); 1069 if (verbose != 0) { 1070 char *detail = NULL; 1071 status = papiAttributeListGetString(attrs, NULL, 1072 "form-supported-detail", &detail); 1073 if (status == PAPI_OK) 1074 printf("%s\n", detail); 1075 } 1076 } 1077 } 1078 1079 return (0); 1080 } 1081 1082 static int 1083 report_print_wheels(char *name, papi_attribute_t **attrs, int verbose) 1084 { 1085 papi_status_t status; 1086 char *pw = NULL; 1087 void *iter = NULL; 1088 1089 for (status = papiAttributeListGetString(attrs, &iter, 1090 "pw-supported", &pw); 1091 status == PAPI_OK; 1092 status = papiAttributeListGetString(attrs, &iter, NULL, &pw)) { 1093 if ((name == NULL) || (strcmp(name, pw) == 0)) { 1094 printf(gettext("charset %s is available\n"), pw); 1095 if (verbose != 0) { 1096 char *info = NULL; 1097 status = papiAttributeListGetString(attrs, NULL, 1098 "pw-supported-extra", &info); 1099 if (status == PAPI_OK) 1100 printf("%s\n", info); 1101 } 1102 } 1103 } 1104 1105 return (0); 1106 } 1107 1108 static int 1109 service_query(char *name, int (*report)(char *, papi_attribute_t **, int), 1110 papi_encryption_t encryption, int verbose) 1111 { 1112 int result = 0; 1113 papi_status_t status; 1114 papi_service_t svc = NULL; 1115 papi_attribute_t **attrs = NULL; 1116 1117 status = papiServiceCreate(&svc, name, NULL, NULL, cli_auth_callback, 1118 encryption, NULL); 1119 if (status != PAPI_OK) { 1120 papiServiceDestroy(svc); 1121 return (-1); 1122 } 1123 1124 attrs = papiServiceGetAttributeList(svc); 1125 if (attrs != NULL) { 1126 result = report(name, attrs, verbose); 1127 1128 if (verbose > 1) { 1129 printf("\n"); 1130 papiAttributeListPrint(stdout, attrs, "\t"); 1131 printf("\n"); 1132 } 1133 } 1134 1135 papiServiceDestroy(svc); 1136 1137 return (result); 1138 } 1139 1140 int 1141 main(int ac, char *av[]) 1142 { 1143 int exit_code = 0; 1144 papi_encryption_t encryption = PAPI_ENCRYPT_NEVER; 1145 int rank = 0; 1146 int verbose = 0; 1147 int description = 0; 1148 int c; 1149 char **argv; 1150 1151 (void) setlocale(LC_ALL, ""); 1152 (void) textdomain("SUNW_OST_OSCMD"); 1153 1154 argv = (char **)calloc((ac + 1), sizeof (char *)); 1155 for (c = 0; c < ac; c++) { 1156 if ((av[c][0] == '-') && (av[c][1] == 'l') && 1157 (isalpha(av[c][2]) != 0)) { 1158 /* preserve old "-l[po...]" behavior */ 1159 argv[c] = &av[c][1]; 1160 argv[c][0] = '-'; 1161 verbose = 1; 1162 1163 } else 1164 argv[c] = av[c]; 1165 } 1166 1167 argv[c++] = "--"; 1168 ac = c; 1169 1170 /* preprocess argument list looking for '-l' or '-R' so it can trail */ 1171 while ((c = getopt(ac, argv, "LEDf:S:stc:p:a:drs:v:l:o:R:u:")) != EOF) { 1172 switch (c) { /* these may or may not have an option */ 1173 case 'a': 1174 case 'c': 1175 case 'p': 1176 case 'o': 1177 case 'R': 1178 case 'u': 1179 case 'v': 1180 case 'l': 1181 case 'f': 1182 case 'S': 1183 if (optarg[0] == '-') { 1184 /* this check stop a possible infinite loop */ 1185 if ((optind > 1) && (argv[optind-1][1] != c)) 1186 optind--; 1187 optarg = NULL; 1188 } else if (strcmp(optarg, "all") == 0) 1189 optarg = NULL; 1190 } 1191 1192 switch (c) { 1193 case 'l': 1194 if ((optarg == NULL) || (optarg[0] == '-')) 1195 optarg = "1"; 1196 verbose = atoi(optarg); 1197 break; 1198 case 'D': 1199 description = 1; 1200 break; 1201 case 'R': 1202 rank = 1; 1203 break; 1204 case 'E': 1205 encryption = PAPI_ENCRYPT_REQUIRED; 1206 break; 1207 default: 1208 break; 1209 } 1210 } 1211 optind = 1; 1212 1213 /* process command line arguments */ 1214 while ((c = getopt(ac, argv, "LEDf:S:stc:p:a:drs:v:l:o:R:u:")) != EOF) { 1215 switch (c) { /* these may or may not have an option */ 1216 case 'a': 1217 case 'c': 1218 case 'p': 1219 case 'o': 1220 case 'R': 1221 case 'u': 1222 case 'v': 1223 case 'l': 1224 case 'f': 1225 case 'S': 1226 if (optarg[0] == '-') { 1227 /* this check stop a possible infinite loop */ 1228 if ((optind > 1) && (argv[optind-1][1] != c)) 1229 optind--; 1230 optarg = NULL; 1231 } else if (strcmp(optarg, "all") == 0) 1232 optarg = NULL; 1233 } 1234 1235 switch (c) { 1236 case 'a': 1237 exit_code += printer_query(optarg, report_accepting, 1238 encryption, verbose, 0); 1239 break; 1240 case 'c': 1241 exit_code += printer_query(optarg, report_class, 1242 encryption, verbose, 0); 1243 break; 1244 case 'p': 1245 exit_code += printer_query(optarg, report_printer, 1246 encryption, verbose, description); 1247 break; 1248 case 'd': 1249 exit_code += lpstat_default_printer(encryption); 1250 break; 1251 case 'r': 1252 exit_code += lpstat_service_status(encryption); 1253 break; 1254 case 'u': 1255 if (optarg != NULL) 1256 users = strsplit(optarg, ", \n"); 1257 exit_code += job_query(NULL, report_job, 1258 encryption, rank, verbose); 1259 if (users != NULL) { 1260 free(users); 1261 users = NULL; 1262 } 1263 break; 1264 case 'v': 1265 exit_code += printer_query(optarg, report_device, 1266 encryption, verbose, 0); 1267 break; 1268 case 'R': /* set "rank" flag in first pass */ 1269 case 'o': 1270 exit_code += job_query(optarg, report_job, 1271 encryption, rank, verbose); 1272 break; 1273 case 'f': 1274 exit_code += service_query(optarg, report_form, 1275 encryption, verbose); 1276 break; 1277 case 'S': 1278 exit_code += service_query(optarg, report_print_wheels, 1279 encryption, verbose); 1280 break; 1281 case 's': 1282 exit_code += lpstat_service_status(encryption); 1283 exit_code += lpstat_default_printer(encryption); 1284 exit_code += printer_query(NULL, report_class, 1285 encryption, verbose, 0); 1286 exit_code += printer_query(NULL, report_device, 1287 encryption, verbose, 0); 1288 exit_code += service_query(optarg, report_form, 1289 encryption, verbose); 1290 exit_code += service_query(optarg, report_print_wheels, 1291 encryption, verbose); 1292 break; 1293 case 't': 1294 exit_code += lpstat_service_status(encryption); 1295 exit_code += lpstat_default_printer(encryption); 1296 exit_code += printer_query(NULL, report_class, 1297 encryption, verbose, 0); 1298 exit_code += printer_query(NULL, report_device, 1299 encryption, verbose, 0); 1300 exit_code += printer_query(NULL, report_accepting, 1301 encryption, verbose, 0); 1302 exit_code += printer_query(NULL, report_printer, 1303 encryption, verbose, 0); 1304 exit_code += service_query(optarg, report_form, 1305 encryption, verbose); 1306 exit_code += service_query(optarg, report_print_wheels, 1307 encryption, verbose); 1308 exit_code += job_query(NULL, report_job, 1309 encryption, rank, verbose); 1310 break; 1311 case 'L': /* local-only, ignored */ 1312 case 'l': /* increased verbose level in first pass */ 1313 case 'D': /* set "description" flag in first pass */ 1314 case 'E': /* set encryption in the first pass */ 1315 break; 1316 default: 1317 usage(av[0]); 1318 } 1319 } 1320 ac--; 1321 1322 if (ac == 1) { /* report on my jobs */ 1323 struct passwd *pw = getpwuid(getuid()); 1324 1325 if (pw != NULL) 1326 users = strsplit(pw->pw_name, ""); 1327 exit_code += job_query(NULL, report_job, encryption, 1328 rank, verbose); 1329 if (users != NULL) { 1330 free(users); 1331 users = NULL; 1332 } 1333 } else { 1334 for (c = optind; c < ac; c++) 1335 exit_code += job_query(argv[c], report_job, encryption, 1336 rank, verbose); 1337 } 1338 1339 1340 if (exit_code != 0) 1341 exit_code = 1; 1342 1343 return (exit_code); 1344 } 1345