Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(77)

Side by Side Diff: printing/backend/print_backend_cups.cc

Issue 10905006: Get semantic capabilities from Print Backend. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: Created 8 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "printing/backend/print_backend.h" 5 #include "printing/backend/print_backend.h"
6 6
7 #include "build/build_config.h" 7 #include "build/build_config.h"
8 8
9 #include <dlfcn.h> 9 #include <dlfcn.h>
10 #include <errno.h> 10 #include <errno.h>
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after
86 LOG(ERROR) << "Cannot find libgnutls"; 86 LOG(ERROR) << "Cannot find libgnutls";
87 } 87 }
88 }; 88 };
89 89
90 base::LazyInstance<GcryptInitializer> g_gcrypt_initializer = 90 base::LazyInstance<GcryptInitializer> g_gcrypt_initializer =
91 LAZY_INSTANCE_INITIALIZER; 91 LAZY_INSTANCE_INITIALIZER;
92 92
93 } // namespace 93 } // namespace
94 #endif // !defined(OS_MACOSX) 94 #endif // !defined(OS_MACOSX)
95 95
96 namespace {
97
98 // This section contains helper code for PPD parsing for semantic capabilities.
99
100 const char kColorDevice[] = "ColorDevice";
101 const char kColorModel[] = "ColorModel";
102 const char kColorMode[] = "ColorMode";
103 const char kProcessColorModel[] = "ProcessColorModel";
104 const char kPrintoutMode[] = "PrintoutMode";
105 const char kDraftGray[] = "Draft.Gray";
106 const char kHighGray[] = "High.Gray";
107
108 const char kDuplex[] = "Duplex";
109 const char kDuplexNone[] = "None";
110
111 bool getBasicColorModelSettings(
112 ppd_file_t* ppd, int* color_model_for_black, int* color_model_for_color,
113 bool* color_is_default) {
114 ppd_option_t* color_model = ppdFindOption(ppd, kColorModel);
115 if (!color_model)
116 return false;
117
118 if (ppdFindChoice(color_model, printing::kBlack))
119 *color_model_for_black = printing::BLACK;
120 else if (ppdFindChoice(color_model, printing::kGray))
121 *color_model_for_black = printing::GRAY;
122 else if (ppdFindChoice(color_model, printing::kGrayscale))
123 *color_model_for_black = printing::GRAYSCALE;
124
125 if (ppdFindChoice(color_model, printing::kColor))
126 *color_model_for_color = printing::COLOR;
127 else if (ppdFindChoice(color_model, printing::kCMYK))
128 *color_model_for_color = printing::CMYK;
129 else if (ppdFindChoice(color_model, printing::kRGB))
130 *color_model_for_color = printing::RGB;
131 else if (ppdFindChoice(color_model, printing::kRGBA))
132 *color_model_for_color = printing::RGBA;
133 else if (ppdFindChoice(color_model, printing::kRGB16))
134 *color_model_for_color = printing::RGB16;
135 else if (ppdFindChoice(color_model, printing::kCMY))
136 *color_model_for_color = printing::CMY;
137 else if (ppdFindChoice(color_model, printing::kKCMY))
138 *color_model_for_color = printing::KCMY;
139 else if (ppdFindChoice(color_model, printing::kCMY_K))
140 *color_model_for_color = printing::CMY_K;
141
142 ppd_choice_t* marked_choice = ppdFindMarkedChoice(ppd, kColorModel);
143 if (!marked_choice)
144 marked_choice = ppdFindChoice(color_model, color_model->defchoice);
145
146 if (marked_choice) {
147 *color_is_default =
148 (base::strcasecmp(marked_choice->choice, printing::kBlack) != 0) &&
149 (base::strcasecmp(marked_choice->choice, printing::kGray) != 0);
150 }
151 return true;
152 }
153
154 bool getPrintOutModeColorSettings(
155 ppd_file_t* ppd, int* color_model_for_black, int* color_model_for_color,
156 bool* color_is_default) {
157 ppd_option_t* printout_mode = ppdFindOption(ppd, kPrintoutMode);
158 if (!printout_mode)
159 return false;
160
161 *color_model_for_color = printing::PRINTOUTMODE_NORMAL;
162 *color_model_for_black = printing::PRINTOUTMODE_NORMAL;
163
164 // Check to see if NORMAL_GRAY value is supported by PrintoutMode.
165 // If NORMAL_GRAY is not supported, NORMAL value is used to
166 // represent grayscale. If NORMAL_GRAY is supported, NORMAL is used to
167 // represent color.
168 if (ppdFindChoice(printout_mode, printing::kNormalGray))
169 *color_model_for_black = printing::PRINTOUTMODE_NORMAL_GRAY;
170
171 // Get the default marked choice to identify the default color setting
172 // value.
173 ppd_choice_t* printout_mode_choice = ppdFindMarkedChoice(ppd, kPrintoutMode);
174 if (!printout_mode_choice) {
175 printout_mode_choice = ppdFindChoice(printout_mode,
176 printout_mode->defchoice);
177 }
178 if (printout_mode_choice) {
179 if ((base::strcasecmp(printout_mode_choice->choice,
180 printing::kNormalGray) == 0) ||
181 (base::strcasecmp(printout_mode_choice->choice, kHighGray) == 0) ||
182 (base::strcasecmp(printout_mode_choice->choice, kDraftGray) == 0)) {
183 *color_model_for_black = printing::PRINTOUTMODE_NORMAL_GRAY;
184 *color_is_default = false;
185 }
186 }
187 return true;
188 }
189
190 bool getColorModeSettings(
191 ppd_file_t* ppd, int* color_model_for_black, int* color_model_for_color,
192 bool* color_is_default) {
193 // Samsung printers use "ColorMode" attribute in their ppds.
194 ppd_option_t* color_mode_option = ppdFindOption(ppd, kColorMode);
195 if (!color_mode_option)
196 return false;
197
198 if (ppdFindChoice(color_mode_option, printing::kColor))
199 *color_model_for_color = printing::COLORMODE_COLOR;
200
201 if (ppdFindChoice(color_mode_option, printing::kMonochrome))
202 *color_model_for_black = printing::COLORMODE_MONOCHROME;
203
204 ppd_choice_t* mode_choice = ppdFindMarkedChoice(ppd, kColorMode);
205 if (!mode_choice) {
206 mode_choice = ppdFindChoice(color_mode_option,
207 color_mode_option->defchoice);
208 }
209
210 if (mode_choice) {
211 *color_is_default =
212 (base::strcasecmp(mode_choice->choice, printing::kColor) == 0);
213 }
214 return true;
215 }
216
217 bool getHPColorSettings(
218 ppd_file_t* ppd, int* color_model_for_black, int* color_model_for_color,
219 bool* color_is_default) {
220 // HP printers use "Color/Color Model" attribute in their ppds.
221 ppd_option_t* color_mode_option = ppdFindOption(ppd, printing::kColor);
222 if (!color_mode_option)
223 return false;
224
225 if (ppdFindChoice(color_mode_option, printing::kColor))
226 *color_model_for_color = printing::HP_COLOR_COLOR;
227 if (ppdFindChoice(color_mode_option, printing::kBlack))
228 *color_model_for_black = printing::HP_COLOR_BLACK;
229
230 ppd_choice_t* mode_choice = ppdFindMarkedChoice(ppd, kColorMode);
231 if (!mode_choice) {
232 mode_choice = ppdFindChoice(color_mode_option,
233 color_mode_option->defchoice);
234 }
235 if (mode_choice) {
236 *color_is_default =
237 (base::strcasecmp(mode_choice->choice, printing::kColor) == 0);
238 }
239 return true;
240 }
241
242 bool getProcessColorModelSettings(
243 ppd_file_t* ppd, int* color_model_for_black, int* color_model_for_color,
244 bool* color_is_default) {
245 // Canon printers use "ProcessColorModel" attribute in their ppds.
246 ppd_option_t* color_mode_option = ppdFindOption(ppd, kProcessColorModel);
247 if (!color_mode_option)
248 return false;
249
250 if (ppdFindChoice(color_mode_option, printing::kRGB))
251 *color_model_for_color = printing::PROCESSCOLORMODEL_RGB;
252 else if (ppdFindChoice(color_mode_option, printing::kCMYK))
253 *color_model_for_color = printing::PROCESSCOLORMODEL_CMYK;
254
255 if (ppdFindChoice(color_mode_option, printing::kGreyscale))
256 *color_model_for_black = printing::PROCESSCOLORMODEL_GREYSCALE;
257
258 ppd_choice_t* mode_choice = ppdFindMarkedChoice(ppd, kProcessColorModel);
259 if (!mode_choice) {
260 mode_choice = ppdFindChoice(color_mode_option,
261 color_mode_option->defchoice);
262 }
263
264 if (mode_choice) {
265 *color_is_default =
266 (base::strcasecmp(mode_choice->choice, printing::kGreyscale) != 0);
267 }
268 return true;
269 }
270
271 bool getColorModelSettings(
272 ppd_file_t* ppd, int* cm_black, int* cm_color, bool* is_color) {
273 bool is_color_device = false;
274 ppd_attr_t* attr = ppdFindAttr(ppd, kColorDevice, NULL);
275 if (attr && attr->value)
276 is_color_device = ppd->color_device;
277
278 *is_color = is_color_device;
279 if (!((is_color_device &&
280 getBasicColorModelSettings(ppd, &cm_black, &cm_color, &is_color)) ||
281 getPrintOutModeColorSettings(ppd, &cm_black, &cm_color, &is_color) ||
282 getColorModeSettings(ppd, &cm_black, &cm_color, &is_color) ||
283 getHPColorSettings(ppd, &cm_black, &cm_color, &is_color) ||
284 getProcessColorModelSettings(ppd, &cm_black, &cm_color, &is_color))) {
285 return false;
286 }
287 return true;
288 }
289
290 bool parsePpdPrinterCapabilities(
291 const std::string& printer_capabilities,
292 printing_internal::PrinterSemanticCapsAndDefaults* printer_info) {
293 FilePath ppd_file_path;
294 if (!file_util::CreateTemporaryFile(&ppd_file_path))
295 return false;
296
297 int data_size = printer_capabilities.length();
298 if (data_size != file_util::WriteFile(
299 ppd_file_path,
300 printer_capabilities.data(),
301 data_size)) {
302 file_util::Delete(ppd_file_path, false);
303 return false;
304 }
305
306 ppd_file_t* ppd = ppdOpenFile(ppd_file_path.value().c_str());
307 if (!ppd)
308 return false;
309
310 PrinterSemanticCapsAndDefaults caps;
311 #if !defined(OS_MACOSX)
312 printing_internal::mark_lpoptions(printer_name, &ppd);
313 #endif
314 ppd_choice_t* duplex_choice = ppdFindMarkedChoice(ppd, kDuplex);
315 if (!duplex_choice) {
316 ppd_option_t* option = ppdFindOption(ppd, kDuplex);
317 if (option)
318 duplex_choice = ppdFindChoice(option, option->defchoice);
319 }
320
321 if (duplex_choice) {
322 caps.duplex_capable = true;
323 if (base::strcasecmp(duplex_choice->choice, kDuplexNone) != 0)
324 caps.duplex_default = printing::LONG_EDGE;
325 else
326 caps.duplex_default = printing::SIMPLEX;
327 }
328
329 bool is_color = false;
330 int cm_color = 0, cm_black = 0;
331 if (!getColorModelSettings(ppd, &cm_black, &cm_color, &is_color)) {
332 VLOG(1) << "Unknown printer color model";
333 }
334
335 caps.color_capable = (cm_color && cm_black && (cm_color != cm_black));
336 caps.color_default = is_color;
337
338 ppdClose(ppd);
339 file_util::Delete(ppd_file_path, false);
340
341 *printer_info = caps;
342 return true;
343 }
344 } // namespace
345
96 namespace printing { 346 namespace printing {
97 347
98 static const char kCUPSPrinterInfoOpt[] = "printer-info"; 348 static const char kCUPSPrinterInfoOpt[] = "printer-info";
99 static const char kCUPSPrinterStateOpt[] = "printer-state"; 349 static const char kCUPSPrinterStateOpt[] = "printer-state";
100 static const char kCUPSPrinterTypeOpt[] = "printer-type"; 350 static const char kCUPSPrinterTypeOpt[] = "printer-type";
101 static const char kCUPSPrinterMakeModelOpt[] = "printer-make-and-model"; 351 static const char kCUPSPrinterMakeModelOpt[] = "printer-make-and-model";
102 352
103 class PrintBackendCUPS : public PrintBackend { 353 class PrintBackendCUPS : public PrintBackend {
104 public: 354 public:
105 PrintBackendCUPS(const GURL& print_server_url, 355 PrintBackendCUPS(const GURL& print_server_url,
106 http_encryption_t encryption, bool blocking); 356 http_encryption_t encryption, bool blocking);
107 357
108 // PrintBackend implementation. 358 // PrintBackend implementation.
109 virtual bool EnumeratePrinters(PrinterList* printer_list) OVERRIDE; 359 virtual bool EnumeratePrinters(PrinterList* printer_list) OVERRIDE;
110 virtual std::string GetDefaultPrinterName() OVERRIDE; 360 virtual std::string GetDefaultPrinterName() OVERRIDE;
361 virtual bool GetPrinterSemanticCapsAndDefaults(
362 const std::string& printer_name,
363 PrinterSemanticCapsAndDefaults* printer_info) OVERRIDE;
111 virtual bool GetPrinterCapsAndDefaults( 364 virtual bool GetPrinterCapsAndDefaults(
112 const std::string& printer_name, 365 const std::string& printer_name,
113 PrinterCapsAndDefaults* printer_info) OVERRIDE; 366 PrinterCapsAndDefaults* printer_info) OVERRIDE;
114 virtual std::string GetPrinterDriverInfo( 367 virtual std::string GetPrinterDriverInfo(
115 const std::string& printer_name) OVERRIDE; 368 const std::string& printer_name) OVERRIDE;
116 virtual bool IsValidPrinter(const std::string& printer_name) OVERRIDE; 369 virtual bool IsValidPrinter(const std::string& printer_name) OVERRIDE;
117 370
118 protected: 371 protected:
119 virtual ~PrintBackendCUPS() {} 372 virtual ~PrintBackendCUPS() {}
120 373
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after
203 } 456 }
204 457
205 std::string PrintBackendCUPS::GetDefaultPrinterName() { 458 std::string PrintBackendCUPS::GetDefaultPrinterName() {
206 // Not using cupsGetDefault() because it lies about the default printer. 459 // Not using cupsGetDefault() because it lies about the default printer.
207 cups_dest_t* dests; 460 cups_dest_t* dests;
208 int num_dests = GetDests(&dests); 461 int num_dests = GetDests(&dests);
209 cups_dest_t* dest = cupsGetDest(NULL, NULL, num_dests, dests); 462 cups_dest_t* dest = cupsGetDest(NULL, NULL, num_dests, dests);
210 return dest ? std::string(dest->name) : std::string(); 463 return dest ? std::string(dest->name) : std::string();
211 } 464 }
212 465
466 bool PrintBackendCUPS::GetPrinterSemanticCapsAndDefaults(
467 const std::string& printer_name,
468 PrinterSemanticCapsAndDefaults* printer_info) {
469 PrinterCapsAndDefaults info;
470 if (!GetPrinterCapsAndDefaults(printer_name, &info) )
471 return false;
472
473 return parsePpdPrinterCapabilities(info.printer_capabilities, printer_info);
474 }
475
213 bool PrintBackendCUPS::GetPrinterCapsAndDefaults( 476 bool PrintBackendCUPS::GetPrinterCapsAndDefaults(
214 const std::string& printer_name, 477 const std::string& printer_name,
215 PrinterCapsAndDefaults* printer_info) { 478 PrinterCapsAndDefaults* printer_info) {
216 DCHECK(printer_info); 479 DCHECK(printer_info);
217 480
218 VLOG(1) << "CUPS: Getting caps and defaults" 481 VLOG(1) << "CUPS: Getting caps and defaults"
219 << ", printer name: " << printer_name; 482 << ", printer name: " << printer_name;
220 483
221 FilePath ppd_path(GetPPD(printer_name.c_str())); 484 FilePath ppd_path(GetPPD(printer_name.c_str()));
222 // In some cases CUPS failed to get ppd file. 485 // In some cases CUPS failed to get ppd file.
(...skipping 130 matching lines...) Expand 10 before | Expand all | Expand 10 after
353 << ", HTTP error: " << http_error; 616 << ", HTTP error: " << http_error;
354 file_util::Delete(ppd_path, false); 617 file_util::Delete(ppd_path, false);
355 ppd_path.clear(); 618 ppd_path.clear();
356 } 619 }
357 } 620 }
358 } 621 }
359 return ppd_path; 622 return ppd_path;
360 } 623 }
361 624
362 } // namespace printing 625 } // namespace printing
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698