2 * Set printer capabilities in DsDriver Keys on remote printer
3 * Copyright (C) Jim McDonough <jmcd@us.ibm.com> 2002.
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.
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.
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/>.
19 /* This needs to be defined for certain compilers */
26 #define SAMBA_PORT _T("Samba")
28 TCHAR
*PrintLastError(void)
30 static TCHAR msgtxt
[1024*sizeof(TCHAR
)];
32 FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM
,
39 void map_orientation(HANDLE ph
, TCHAR
*printer
, TCHAR
*port
)
42 TCHAR portrait_only
[] = _T("PORTRAIT\0");
43 TCHAR both
[] = _T("LANDSCAPE\0PORTRAIT\0");
45 /* orentation of 90 or 270 indicates landscape supported, 0 means it isn't */
46 rot
= DeviceCapabilities(printer
, port
, DC_BINNAMES
, NULL
, NULL
);
48 printf("printOrientationsSupported:\n");
51 printf("\tPORTRAIT\n\tLANDSCAPE\n");
52 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, _T("printOrientationsSupported"), REG_MULTI_SZ
,
55 printf("\tPORTRAIT\n");
56 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, _T("printOrientationsSupported"), REG_MULTI_SZ
,
57 portrait_only
, sizeof(portrait_only
));
61 void map_resolution(HANDLE ph
, TCHAR
*printer
, TCHAR
*port
)
63 DWORD num
, *res
, maxres
= 0, i
;
65 num
= DeviceCapabilities(printer
, port
, DC_ENUMRESOLUTIONS
, NULL
, NULL
);
66 if ((DWORD
) -1 == num
)
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
;
73 printf("printMaxResolutionSupported: %d\n", maxres
);
74 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, _T("printMaxResolutionSupported"), REG_DWORD
,
75 (BYTE
*) &maxres
, sizeof(maxres
));
78 void map_extents(HANDLE ph
, TCHAR
*printer
, TCHAR
*port
)
80 DWORD extentval
, xval
, yval
;
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
));
98 void map_printrateunit(HANDLE ph
, TCHAR
*printer
, TCHAR
*port
)
101 TCHAR ppm
[] = _T("PagesPerMinute");
102 TCHAR ipm
[] = _T("InchesPerMinute");
103 TCHAR lpm
[] = _T("LinesPerMinute");
104 TCHAR cps
[] = _T("CharactersPerSecond");
106 unit
= DeviceCapabilities(printer
, port
, DC_PRINTRATEUNIT
, NULL
, NULL
);
108 case PRINTRATEUNIT_PPM
:
109 printf("printRateUnit: %s\n", ppm
);
110 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, _T("printRateUnit"), REG_SZ
, ppm
, sizeof(ppm
));
112 case PRINTRATEUNIT_IPM
:
113 printf("printRateUnit: %s\n", ipm
);
114 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, _T("printRateUnit"), REG_SZ
, ipm
, sizeof(ipm
));
116 case PRINTRATEUNIT_LPM
:
117 printf("printRateUnit: %s\n", lpm
);
118 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, _T("printRateUnit"), REG_SZ
, lpm
, sizeof(lpm
));
120 case PRINTRATEUNIT_CPS
:
121 printf("printRateUnit: %s\n", cps
);
122 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, _T("printRateUnit"), REG_SZ
, cps
, sizeof(cps
));
125 printf("printRateUnit: unknown value %d\n", unit
);
129 void map_generic_boolean(HANDLE ph
, TCHAR
*printer
, TCHAR
*port
, WORD cap
, TCHAR
*key
)
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
));
138 void map_generic_dword(HANDLE ph
, TCHAR
*printer
, TCHAR
*port
, WORD cap
, TCHAR
*key
)
142 dword
= DeviceCapabilities(printer
, port
, cap
, NULL
, NULL
);
143 if ((DWORD
) -1 == dword
)
146 printf("%s: %d\n", key
, dword
);
147 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, key
, REG_DWORD
, (BYTE
*) &dword
, sizeof(dword
));
150 void map_generic_multi_sz(HANDLE ph
, TCHAR
*printer
, TCHAR
*port
, WORD cap
, TCHAR
*key
, int size
)
153 TCHAR
*strings_out
, *strings_cur
;
156 num_items
= DeviceCapabilities(printer
, port
, cap
, NULL
, NULL
);
157 if ((DWORD
) -1 == num_items
)
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;
169 SetPrinterDataEx(ph
, SPLDS_DRIVER_KEY
, key
, REG_MULTI_SZ
, strings_out
,
170 (strings_cur
- strings_out
+ 1) * sizeof(TCHAR
));
176 int main(int argc
, char *argv
[])
182 TCHAR
*port
= SAMBA_PORT
;
183 PRINTER_DEFAULTS admin_access
= {NULL
, NULL
, PRINTER_ACCESS_ADMINISTER
};
184 PRINTER_INFO_7 publish
= {NULL
, DSPRINT_PUBLISH
};
187 printf("Usage: %s <printername>\n", argv
[0]);
193 if (!(OpenPrinter(printer
, &ph
, &admin_access
))) {
194 printf("OpenPrinter failed, error = %s\n", PrintLastError());
198 GetPrinterDriver(ph
, NULL
, 1, NULL
, 0, &needed
);
200 printf("GetPrinterDriver failed, error = %s\n", PrintLastError());
204 driver_info
= malloc(needed
);
205 if (!(GetPrinterDriver(ph
, NULL
, 1, driver_info
, needed
, &needed
))) {
206 printf("GetPrinterDriver failed, error = %s\n", PrintLastError());
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
);
228 map_generic_boolean(ph
, printer
, port
, DC_STAPLE
, _T("printStaplingSupported"));
230 #ifdef DC_PRINTRATEPPM
231 map_generic_dword(ph
, printer
, port
, DC_PRINTRATEPPM
, _T("printPagesPerMinute"));
234 SetPrinter(ph
, 7, (BYTE
*) &publish
, 0);