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 2008 Sun Microsystems, Inc.  All rights reserved.
  24  * Use is subject to license terms.
  25  *
  26  */
  27 
  28 /* $Id: lpr.c 146 2006-03-24 00:26:54Z njacobs $ */
  29 
  30 #pragma ident   "%Z%%M% %I%     %E% SMI"
  31 
  32 #include <stdio.h>
  33 #include <stdlib.h>
  34 #include <unistd.h>
  35 #include <string.h>
  36 #include <locale.h>
  37 #include <libintl.h>
  38 #include <papi.h>
  39 #include "common.h"
  40 
  41 #ifdef HAVE_LIBMAGIC    /* for mimetype auto-detection */
  42 #include <magic.h>
  43 #endif /* HAVE_LIBMAGIC */
  44 
  45 static void
  46 usage(char *program)
  47 {
  48         char *name;
  49 
  50         if ((name = strrchr(program, '/')) == NULL)
  51                 name = program;
  52         else
  53                 name++;
  54 
  55         fprintf(stdout,
  56                 gettext("Usage: %s [-P printer] [-# copies] [-C class] "
  57                                 "[-J job] [-T title] "
  58                                 "[-p [-i indent] [-w width]] "
  59                                 "[-1|-2|-3|-4 font] [-m] [-h] [-s] "
  60                                 "[-filter_option] [file ..]\n"), name);
  61         exit(1);
  62 }
  63 
  64 int
  65 main(int ac, char *av[])
  66 {
  67         papi_status_t status;
  68         papi_service_t svc = NULL;
  69         papi_attribute_t **list = NULL;
  70         papi_job_t job = NULL;
  71         int exit_code = 0;
  72         char *printer = NULL;
  73         char prefetch[3];
  74         int prefetch_len = sizeof (prefetch);
  75         papi_encryption_t encryption = PAPI_ENCRYPT_NEVER;
  76         int dump = 0;
  77         int validate = 0;
  78         int remove = 0;
  79         int copy = 1;   /* default is to copy the data */
  80         char *document_format = "text/plain";
  81         int c;
  82 
  83         (void) setlocale(LC_ALL, "");
  84         (void) textdomain("SUNW_OST_OSCMD");
  85 
  86         while ((c = getopt(ac, av,
  87                         "EP:#:C:DVJ:T:w:i:hplrstdgvcfmn1:2:3:4:")) != EOF)
  88                 switch (c) {
  89                 case 'E':
  90                         encryption = PAPI_ENCRYPT_REQUIRED;
  91                         break;
  92                 case 'P':
  93                         printer = optarg;
  94                         break;
  95                 case '#':
  96                         papiAttributeListAddInteger(&list, PAPI_ATTR_EXCL,
  97                                         "copies", atoi(optarg));
  98                         break;
  99                 case 'C':
 100                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 101                                         "rfc-1179-class", optarg);
 102                         break;
 103                 case 'D':
 104                         dump = 1;
 105                         break;
 106                 case 'J':
 107                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 108                                         "job-name", optarg);
 109                         break;
 110                 case 'T':
 111                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 112                                         "pr-title", optarg);
 113                         break;
 114                 case 'p':
 115                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 116                                 "document-format", "application/x-pr");
 117                         papiAttributeListAddBoolean(&list, PAPI_ATTR_EXCL,
 118                                         "pr-filter", 1);
 119                         break;
 120                 case 'i':
 121                         papiAttributeListAddInteger(&list, PAPI_ATTR_EXCL,
 122                                         "pr-indent", atoi(optarg));
 123                         break;
 124                 case 'w':
 125                         papiAttributeListAddInteger(&list, PAPI_ATTR_EXCL,
 126                                         "pr-width", atoi(optarg));
 127                         break;
 128                 case 'h':
 129                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 130                                         "job-sheets", "none");
 131                         break;
 132                 case 'l':
 133                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 134                                 "document-format", "application/octet-stream");
 135                         break;
 136                 case 'o':
 137                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 138                                 "document-format", "application/postscript");
 139                         break;
 140                 case 'c':
 141                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 142                                 "document-format", "application/x-cif");
 143                         break;
 144                 case 'd':
 145                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 146                                 "document-format", "application/x-dvi");
 147                         break;
 148                 case 'f':
 149                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 150                                 "document-format", "application/x-fortran");
 151                         break;
 152                 case 'g':
 153                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 154                                 "document-format", "application/x-plot");
 155                         break;
 156                 case 'n':
 157                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 158                                 "document-format", "application/x-ditroff");
 159                         break;
 160                 case 't':
 161                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 162                                 "document-format", "application/x-troff");
 163                         break;
 164                 case 'v':
 165                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 166                                 "document-format", "application/x-raster");
 167                         break;
 168                 case 'm':
 169                         papiAttributeListAddBoolean(&list, PAPI_ATTR_EXCL,
 170                                 "rfc-1179-mail", 1);
 171                         break;
 172                 case 'r':
 173                         remove = 1;
 174                         break;
 175                 case 's':
 176                         copy = 0;
 177                         break;
 178                 case 'V':       /* validate */
 179                         validate = 1;
 180                         break;
 181                 case '1':
 182                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 183                                 "rfc-1179-font-r", optarg);
 184                         break;
 185                 case '2':
 186                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 187                                 "rfc-1179-font-i", optarg);
 188                         break;
 189                 case '3':
 190                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 191                                 "rfc-1179-font-b", optarg);
 192                         break;
 193                 case '4':
 194                         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 195                                 "rfc-1179-font-s", optarg);
 196                         break;
 197                 default:
 198                         usage(av[0]);
 199                 }
 200 
 201         if ((printer == NULL) &&
 202             ((printer = getenv("PRINTER")) == NULL) &&
 203             ((printer = getenv("LPDEST")) == NULL))
 204                 printer = DEFAULT_DEST;
 205 
 206         if (((optind + 1) == ac) && (strcmp(av[optind], "-") == 0))
 207                 optind = ac;
 208 
 209         if (optind != ac) {
 210                 /* get the mime type of the file data */
 211 #ifdef MAGIC_MIME
 212                 magic_t ms;
 213 
 214                 if ((ms = magic_open(MAGIC_MIME)) != NULL) {
 215                         document_format = magic_file(ms, av[optind]);
 216                         magic_close(ms);
 217                 }
 218 #else
 219                 if (is_postscript(av[optind]) == 1)
 220                         document_format = "application/postscript";
 221 #endif
 222         } else {
 223                 if (is_postscript_stream(0, prefetch, &prefetch_len) == 1)
 224                         document_format = "application/postscript";
 225         }
 226 
 227         papiAttributeListAddInteger(&list, PAPI_ATTR_EXCL, "copies", 1);
 228         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 229                                 "document-format", document_format);
 230         papiAttributeListAddString(&list, PAPI_ATTR_EXCL,
 231                                 "job-sheets", "standard");
 232 
 233         status = papiServiceCreate(&svc, printer, NULL, NULL, cli_auth_callback,
 234                                         encryption, NULL);
 235         if (status != PAPI_OK) {
 236                 fprintf(stderr, gettext(
 237                         "Failed to contact service for %s: %s\n"), printer,
 238                         verbose_papi_message(svc, status));
 239                 exit(1);
 240         }
 241 
 242         if (validate == 1)      /* validate the request can be processed */
 243                 status = papiJobValidate(svc, printer, list,
 244                                         NULL, &av[optind], &job);
 245         else if (optind == ac)  /* no file list, use stdin */
 246                 status = jobSubmitSTDIN(svc, printer, prefetch, prefetch_len,
 247                                         list, &job);
 248         else if (copy == 0)     /* reference the files in the job, default */
 249                 status = papiJobSubmitByReference(svc, printer, list,
 250                                         NULL, &av[optind], &job);
 251         else                    /* copy the files before return, -c */
 252                 status = papiJobSubmit(svc, printer, list,
 253                                         NULL, &av[optind], &job);
 254 
 255         papiAttributeListFree(list);
 256 
 257         if (status != PAPI_OK) {
 258                 fprintf(stderr, gettext("%s: %s\n"), printer,
 259                         verbose_papi_message(svc, status));
 260                 papiJobFree(job);
 261                 papiServiceDestroy(svc);
 262                 exit(1);
 263         }
 264 
 265         if (dump != 0) {
 266                 list = papiJobGetAttributeList(job);
 267                 printf("job attributes:\n");
 268                 papiAttributeListPrint(stdout, list, "\t");
 269                 printf("\n");
 270         }
 271 
 272         papiJobFree(job);
 273         papiServiceDestroy(svc);
 274 
 275         return (exit_code);
 276 }