root/examples/printing/prtpub.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. PrintLastError
  2. map_orientation
  3. map_resolution
  4. map_extents
  5. map_printrateunit
  6. map_generic_boolean
  7. map_generic_dword
  8. map_generic_multi_sz
  9. main

   1 /*
   2  *  Set printer capabilities in DsDriver Keys on remote printer
   3  *  Copyright (C) Jim McDonough <jmcd@us.ibm.com> 2002.
   4  *
   5  *  This program is free software; you can redistribute it and/or modify
   6  *  it under the terms of the GNU General Public License as published by
   7  *  the Free Software Foundation; either version 3 of the License, or
   8  *  (at your option) any later version.
   9  *
  10  *  This program is distributed in the hope that it will be useful,
  11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13  *  GNU General Public License for more details.
  14  *
  15  *  You should have received a copy of the GNU General Public License
  16  *  along with this program; if not, see <http://www.gnu.org/licenses/>.
  17  */
  18 
  19 /* This needs to be defined for certain compilers */
  20 #define WINVER 0x0500
  21 
  22 #include <tchar.h>
  23 #include <windows.h>
  24 #include <stdio.h>
  25 
  26 #define SAMBA_PORT _T("Samba")
  27 
  28 TCHAR *PrintLastError(void)
     /* [<][>][^][v][top][bottom][index][help] */
  29 {
  30         static TCHAR msgtxt[1024*sizeof(TCHAR)];
  31 
  32         FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM,
  33                         NULL, GetLastError(), 
  34                         0, msgtxt, 0, NULL);
  35 
  36         return msgtxt;
  37 }
  38 
  39 void map_orientation(HANDLE ph, TCHAR *printer, TCHAR *port)
     /* [<][>][^][v][top][bottom][index][help] */
  40 {
  41         DWORD rot;
  42         TCHAR portrait_only[] = _T("PORTRAIT\0");
  43         TCHAR both[] = _T("LANDSCAPE\0PORTRAIT\0");
  44 
  45         /* orentation of 90 or 270 indicates landscape supported, 0 means it isn't */
  46         rot = DeviceCapabilities(printer, port, DC_BINNAMES, NULL, NULL);
  47         
  48         printf("printOrientationsSupported:\n");
  49 
  50         if (rot) {
  51                 printf("\tPORTRAIT\n\tLANDSCAPE\n");
  52                 SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printOrientationsSupported"), REG_MULTI_SZ,
  53                         both, sizeof(both));
  54         } else {
  55                 printf("\tPORTRAIT\n");
  56                 SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printOrientationsSupported"), REG_MULTI_SZ,
  57                         portrait_only, sizeof(portrait_only));
  58         }
  59 }
  60 
  61 void map_resolution(HANDLE ph, TCHAR *printer, TCHAR *port)
     /* [<][>][^][v][top][bottom][index][help] */
  62 {
  63         DWORD num, *res, maxres = 0, i;
  64 
  65         num = DeviceCapabilities(printer, port, DC_ENUMRESOLUTIONS, NULL, NULL);
  66         if ((DWORD) -1 == num)
  67                 return;
  68         res = malloc(num*2*sizeof(DWORD));
  69         num = DeviceCapabilities(printer, port, DC_ENUMRESOLUTIONS, (BYTE *) res, NULL);
  70         for (i=0; i < num*2; i++) {
  71                 maxres = (res[i] > maxres) ? res[i] : maxres;
  72         }
  73         printf("printMaxResolutionSupported: %d\n", maxres);
  74         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printMaxResolutionSupported"), REG_DWORD, 
  75                 (BYTE *) &maxres, sizeof(maxres));
  76 }
  77 
  78 void map_extents(HANDLE ph, TCHAR *printer, TCHAR *port)
     /* [<][>][^][v][top][bottom][index][help] */
  79 {
  80         DWORD extentval, xval, yval;
  81 
  82         extentval = DeviceCapabilities(printer, port, DC_MINEXTENT, NULL, NULL);
  83         xval = (DWORD) (LOWORD(extentval));
  84         yval = (DWORD) (HIWORD(extentval));
  85         printf("printMinXExtent: %d\n", xval);
  86         printf("printMinYExtent: %d\n", yval);
  87         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printMinXExtent"), REG_DWORD, (BYTE *) &xval, sizeof(xval));
  88         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printMinYExtent"), REG_DWORD, (BYTE *) &yval, sizeof(yval));
  89         extentval = DeviceCapabilities(printer, port, DC_MAXEXTENT, NULL, NULL);
  90         xval = (DWORD) (LOWORD(extentval));
  91         yval = (DWORD) (HIWORD(extentval));
  92         printf("printMaxXExtent: %d\n", xval);
  93         printf("printMaxYExtent: %d\n", yval);
  94         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printMaxXExtent"), REG_DWORD, (BYTE *) &xval, sizeof(xval));
  95         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printMaxYExtent"), REG_DWORD, (BYTE *) &yval, sizeof(yval));
  96 }
  97 
  98 void map_printrateunit(HANDLE ph, TCHAR *printer, TCHAR *port)
     /* [<][>][^][v][top][bottom][index][help] */
  99 {
 100         DWORD unit;
 101         TCHAR ppm[] = _T("PagesPerMinute");
 102         TCHAR ipm[] = _T("InchesPerMinute");
 103         TCHAR lpm[] = _T("LinesPerMinute");
 104         TCHAR cps[] = _T("CharactersPerSecond");
 105 
 106         unit = DeviceCapabilities(printer, port, DC_PRINTRATEUNIT, NULL, NULL);
 107         switch(unit) {
 108         case PRINTRATEUNIT_PPM:
 109                 printf("printRateUnit: %s\n", ppm);
 110                 SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printRateUnit"), REG_SZ, ppm, sizeof(ppm));
 111                 break;
 112         case PRINTRATEUNIT_IPM:
 113                 printf("printRateUnit: %s\n", ipm);
 114                 SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printRateUnit"), REG_SZ, ipm, sizeof(ipm));
 115                 break;
 116         case PRINTRATEUNIT_LPM:
 117                 printf("printRateUnit: %s\n", lpm);
 118                 SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printRateUnit"), REG_SZ, lpm, sizeof(lpm));
 119                 break;
 120         case PRINTRATEUNIT_CPS:
 121                 printf("printRateUnit: %s\n", cps);
 122                 SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, _T("printRateUnit"), REG_SZ, cps, sizeof(cps));
 123                 break;
 124         default:
 125                 printf("printRateUnit: unknown value %d\n", unit);
 126         }
 127 }
 128 
 129 void map_generic_boolean(HANDLE ph, TCHAR *printer, TCHAR *port, WORD cap, TCHAR *key)
     /* [<][>][^][v][top][bottom][index][help] */
 130 {
 131         BYTE boolval;
 132         /* DeviceCapabilities doesn't always return 1 for true...just nonzero */
 133         boolval = (BYTE) (DeviceCapabilities(printer, port, cap, NULL, NULL) ? 1 : 0);
 134         printf("%s: %s\n", key, boolval ? "TRUE" : "FALSE");
 135         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, key, REG_BINARY, &boolval, sizeof(boolval));
 136 }
 137 
 138 void map_generic_dword(HANDLE ph, TCHAR *printer, TCHAR *port, WORD cap, TCHAR *key)
     /* [<][>][^][v][top][bottom][index][help] */
 139 {
 140         DWORD dword;
 141 
 142         dword = DeviceCapabilities(printer, port, cap, NULL, NULL);
 143         if ((DWORD) -1 == dword)
 144                 return;
 145 
 146         printf("%s: %d\n", key, dword);
 147         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, key, REG_DWORD, (BYTE *) &dword, sizeof(dword));
 148 }
 149 
 150 void map_generic_multi_sz(HANDLE ph, TCHAR *printer, TCHAR *port, WORD cap, TCHAR *key, int size)
     /* [<][>][^][v][top][bottom][index][help] */
 151 {
 152         TCHAR *strings_in;
 153         TCHAR *strings_out, *strings_cur;
 154         DWORD num_items, i;
 155 
 156         num_items = DeviceCapabilities(printer, port, cap, NULL, NULL);
 157         if ((DWORD) -1 == num_items)
 158                 return;
 159         strings_in = malloc(num_items * size);
 160         strings_out = calloc(num_items, size);
 161         num_items = DeviceCapabilities(printer, port, cap, strings_in, NULL);
 162         printf("%s:\n", key);
 163         for (i=0, strings_cur = strings_out; i < num_items; i++) {
 164                 _tcsncpy(strings_cur, &strings_in[i*size], size);
 165                 printf("\t%s\n", strings_cur);
 166                 strings_cur += _tcslen(strings_cur) + 1;
 167         }
 168                 
 169         SetPrinterDataEx(ph, SPLDS_DRIVER_KEY, key, REG_MULTI_SZ, strings_out, 
 170                 (strings_cur - strings_out + 1) * sizeof(TCHAR));
 171 
 172         free(strings_in);
 173         free(strings_out);
 174 }
 175 
 176 int main(int argc, char *argv[])
     /* [<][>][^][v][top][bottom][index][help] */
 177 {
 178         HANDLE ph;
 179         BYTE *driver_info;
 180         DWORD needed;
 181         TCHAR *printer;
 182         TCHAR *port = SAMBA_PORT;
 183         PRINTER_DEFAULTS admin_access = {NULL, NULL, PRINTER_ACCESS_ADMINISTER};
 184         PRINTER_INFO_7 publish = {NULL, DSPRINT_PUBLISH};
 185         
 186         if (argc < 2) {
 187                 printf("Usage: %s <printername>\n", argv[0]);
 188                 return -1;
 189         }
 190 
 191         printer = argv[1];
 192 
 193         if (!(OpenPrinter(printer, &ph, &admin_access))) {
 194                 printf("OpenPrinter failed, error = %s\n", PrintLastError());
 195                 return -1;
 196         }
 197 
 198         GetPrinterDriver(ph, NULL, 1, NULL, 0, &needed);
 199         if (!needed) {
 200                 printf("GetPrinterDriver failed, error = %s\n", PrintLastError());
 201                 ClosePrinter(ph);
 202                 return -1;
 203         }
 204         driver_info = malloc(needed);
 205         if (!(GetPrinterDriver(ph, NULL, 1, driver_info, needed, &needed))) {
 206                 printf("GetPrinterDriver failed, error = %s\n", PrintLastError());
 207                 ClosePrinter(ph);
 208                 return -1;
 209         }
 210 
 211         map_generic_multi_sz(ph, printer, port, DC_BINNAMES, _T("printBinNames"), 24);
 212         map_generic_boolean(ph, printer, port, DC_COLLATE, _T("printCollate"));
 213         map_generic_dword(ph, printer, port, DC_COPIES, _T("printMaxCopies"));
 214         map_generic_dword(ph, printer, port, DC_DRIVER, _T("driverVersion"));
 215         map_generic_boolean(ph, printer, port, DC_DUPLEX, _T("printDuplexSupported"));
 216         map_extents(ph, printer, port);
 217         map_resolution(ph, printer, port);
 218         map_orientation(ph, printer, port);
 219         map_generic_multi_sz(ph, printer, port, DC_PAPERNAMES, _T("printMediaSupported"), 64);
 220 #if (WINVER >= 0x0500)
 221         map_generic_boolean(ph, printer, port, DC_COLORDEVICE, _T("printColor"));
 222         map_generic_multi_sz(ph, printer, port, DC_PERSONALITY, _T("printLanguage"), 64);
 223         map_generic_multi_sz(ph, printer, port, DC_MEDIAREADY, _T("printMediaReady"),64);
 224         map_generic_dword(ph, printer, port, DC_PRINTERMEM, _T("printMemory"));
 225         map_generic_dword(ph, printer, port, DC_PRINTRATE, _T("printRate"));
 226         map_printrateunit(ph, printer, port);
 227 #ifdef DC_STAPLE
 228         map_generic_boolean(ph, printer, port, DC_STAPLE, _T("printStaplingSupported"));
 229 #endif
 230 #ifdef DC_PRINTRATEPPM
 231         map_generic_dword(ph, printer, port, DC_PRINTRATEPPM, _T("printPagesPerMinute"));
 232 #endif
 233 #endif
 234         SetPrinter(ph, 7, (BYTE *) &publish, 0);
 235         ClosePrinter(ph);
 236         return 0;
 237 }

/* [<][>][^][v][top][bottom][index][help] */