print_system_win.cc revision f2477e01787aa58f445919b809d89e252beef54f
15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "chrome/service/cloud_print/print_system_win.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/utf_string_conversions.h" 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/win/object_watcher.h" 9d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)#include "chrome/common/crash_keys.h" 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "printing/backend/win_helper.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 12f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)namespace cloud_print { 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class PrintSystemWatcherWin : public base::win::ObjectWatcher::Delegate { 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PrintSystemWatcherWin() 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : delegate_(NULL), 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) did_signal_(false) { 215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ~PrintSystemWatcherWin() { 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Stop(); 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) class Delegate { 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~Delegate() {} 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnPrinterAdded() = 0; 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnPrinterDeleted() = 0; 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnPrinterChanged() = 0; 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnJobChanged() = 0; 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) }; 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool Start(const std::string& printer_name, Delegate* delegate) { 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_refptr<printing::PrintBackend> print_backend( 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printing::PrintBackend::CreateInstance(NULL)); 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printer_info_ = print_backend->GetPrinterDriverInfo(printer_name); 39d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) crash_keys::ScopedPrinterInfo crash_key(printer_info_); 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delegate_ = delegate; 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // An empty printer name means watch the current server, we need to pass 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // NULL to OpenPrinter. 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) LPTSTR printer_name_to_use = NULL; 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::wstring printer_name_wide; 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!printer_name.empty()) { 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printer_name_wide = UTF8ToWide(printer_name); 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printer_name_to_use = const_cast<LPTSTR>(printer_name_wide.c_str()); 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool ret = false; 517d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) if (printer_.OpenPrinter(printer_name_to_use)) { 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printer_change_.Set(FindFirstPrinterChangeNotification( 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printer_, PRINTER_CHANGE_PRINTER|PRINTER_CHANGE_JOB, 0, NULL)); 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (printer_change_.IsValid()) { 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ret = watcher_.StartWatching(printer_change_, this); 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!ret) { 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Stop(); 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return ret; 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 63f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) 645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool Stop() { 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) watcher_.StopWatching(); 665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printer_.Close(); 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printer_change_.Close(); 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return true; 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // base::ObjectWatcher::Delegate method 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnObjectSignaled(HANDLE object) { 73d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) crash_keys::ScopedPrinterInfo crash_key(printer_info_); 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DWORD change = 0; 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FindNextPrinterChangeNotification(object, &change, NULL, NULL); 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (change != ((PRINTER_CHANGE_PRINTER|PRINTER_CHANGE_JOB) & 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (~PRINTER_CHANGE_FAILED_CONNECTION_PRINTER))) { 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // For printer connections, we get spurious change notifications with 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // all flags set except PRINTER_CHANGE_FAILED_CONNECTION_PRINTER. 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Ignore these. 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (change & PRINTER_CHANGE_ADD_PRINTER) { 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delegate_->OnPrinterAdded(); 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else if (change & PRINTER_CHANGE_DELETE_PRINTER) { 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delegate_->OnPrinterDeleted(); 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else if (change & PRINTER_CHANGE_SET_PRINTER) { 875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delegate_->OnPrinterChanged(); 885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (change & PRINTER_CHANGE_JOB) { 905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) delegate_->OnJobChanged(); 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) watcher_.StartWatching(printer_change_, this); 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool GetCurrentPrinterInfo(printing::PrinterBasicInfo* printer_info) { 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(printer_info); 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return InitBasicPrinterInfo(printer_, printer_info); 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::win::ObjectWatcher watcher_; 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printing::ScopedPrinterHandle printer_; // The printer being watched 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Returned by FindFirstPrinterChangeNotifier. 105f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) printing::ScopedPrinterChangeHandle printer_change_; 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Delegate* delegate_; // Delegate to notify 1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool did_signal_; // DoneWaiting was called 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string printer_info_; // For crash reporting. 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 111f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)class PrintServerWatcherWin 112f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) : public PrintSystem::PrintServerWatcher, 113f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) public PrintSystemWatcherWin::Delegate { 1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 115f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) PrintServerWatcherWin() : delegate_(NULL) {} 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 117f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) // PrintSystem::PrintServerWatcher implementation. 118f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual bool StartWatching( 119f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) PrintSystem::PrintServerWatcher::Delegate* delegate) OVERRIDE{ 120f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_ = delegate; 121f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) return watcher_.Start(std::string(), this); 122f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 124f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual bool StopWatching() OVERRIDE{ 125f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) bool ret = watcher_.Stop(); 126f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_ = NULL; 127f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) return ret; 128f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 130f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) // PrintSystemWatcherWin::Delegate implementation. 131f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnPrinterAdded() OVERRIDE { 132f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_->OnPrinterAdded(); 133f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 134f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnPrinterDeleted() OVERRIDE {} 135f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnPrinterChanged() OVERRIDE {} 136f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnJobChanged() OVERRIDE {} 1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 138f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) protected: 139f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual ~PrintServerWatcherWin() {} 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 141f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) private: 142f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) PrintSystem::PrintServerWatcher::Delegate* delegate_; 143f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) PrintSystemWatcherWin watcher_; 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 145f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(PrintServerWatcherWin); 146f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)}; 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 148f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)class PrinterWatcherWin 149f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) : public PrintSystem::PrinterWatcher, 150f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) public PrintSystemWatcherWin::Delegate { 151f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) public: 152f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) explicit PrinterWatcherWin(const std::string& printer_name) 153f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) : printer_name_(printer_name), 154f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_(NULL) { 155f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 157f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) // PrintSystem::PrinterWatcher implementation. 158f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual bool StartWatching( 159f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) PrintSystem::PrinterWatcher::Delegate* delegate) OVERRIDE { 160f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_ = delegate; 161f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) return watcher_.Start(printer_name_, this); 162f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 164f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual bool StopWatching() OVERRIDE { 165f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) bool ret = watcher_.Stop(); 166f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_ = NULL; 167f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) return ret; 168f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 170f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual bool GetCurrentPrinterInfo( 171f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) printing::PrinterBasicInfo* printer_info) OVERRIDE { 172f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) return watcher_.GetCurrentPrinterInfo(printer_info); 173f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 175f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) // PrintSystemWatcherWin::Delegate implementation. 176f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnPrinterAdded() OVERRIDE { 177f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) NOTREACHED(); 178f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 179f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnPrinterDeleted() OVERRIDE { 180f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_->OnPrinterDeleted(); 181f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 182f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnPrinterChanged() OVERRIDE { 183f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_->OnPrinterChanged(); 184f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 185f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual void OnJobChanged() OVERRIDE { 186f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) delegate_->OnJobChanged(); 187f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) } 1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 189f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) protected: 190f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) virtual ~PrinterWatcherWin() {} 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 193f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) std::string printer_name_; 194f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) PrintSystem::PrinterWatcher::Delegate* delegate_; 195f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) PrintSystemWatcherWin watcher_; 196f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) 197f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(PrinterWatcherWin); 1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 200f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)} // namespace 201f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) 2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PrintSystemWin::PrintSystemWin() { 2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) print_backend_ = printing::PrintBackend::CreateInstance(NULL); 2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 206f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)PrintSystemWin::~PrintSystemWin() { 2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PrintSystem::PrintSystemResult PrintSystemWin::EnumeratePrinters( 2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printing::PrinterList* printer_list) { 2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool ret = print_backend_->EnumeratePrinters(printer_list); 2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return PrintSystemResult(ret, std::string()); 2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool PrintSystemWin::IsValidPrinter(const std::string& printer_name) { 2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return print_backend_->IsValidPrinter(printer_name); 2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool PrintSystemWin::GetJobDetails(const std::string& printer_name, 2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PlatformJobId job_id, 2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PrintJobDetails *job_details) { 222d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) crash_keys::ScopedPrinterInfo crash_key( 2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) print_backend_->GetPrinterDriverInfo(printer_name)); 2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(job_details); 2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) printing::ScopedPrinterHandle printer_handle; 2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::wstring printer_name_wide = UTF8ToWide(printer_name); 2277d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) printer_handle.OpenPrinter(printer_name_wide.c_str()); 2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(printer_handle.IsValid()); 2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool ret = false; 2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (printer_handle.IsValid()) { 2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DWORD bytes_needed = 0; 2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetJob(printer_handle, job_id, 1, NULL, 0, &bytes_needed); 2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DWORD last_error = GetLastError(); 2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (ERROR_INVALID_PARAMETER != last_error) { 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // ERROR_INVALID_PARAMETER normally means that the job id is not valid. 2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(last_error == ERROR_INSUFFICIENT_BUFFER); 237c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) scoped_ptr<BYTE[]> job_info_buffer(new BYTE[bytes_needed]); 2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (GetJob(printer_handle, job_id, 1, job_info_buffer.get(), bytes_needed, 2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &bytes_needed)) { 2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) JOB_INFO_1 *job_info = 2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) reinterpret_cast<JOB_INFO_1 *>(job_info_buffer.get()); 2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (job_info->pStatus) { 2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) WideToUTF8(job_info->pStatus, wcslen(job_info->pStatus), 2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &job_details->status_message); 2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) job_details->platform_status_flags = job_info->Status; 2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if ((job_info->Status & JOB_STATUS_COMPLETE) || 2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (job_info->Status & JOB_STATUS_PRINTED)) { 2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) job_details->status = PRINT_JOB_STATUS_COMPLETED; 2505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else if (job_info->Status & JOB_STATUS_ERROR) { 2515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) job_details->status = PRINT_JOB_STATUS_ERROR; 2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 2535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) job_details->status = PRINT_JOB_STATUS_IN_PROGRESS; 2545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) job_details->total_pages = job_info->TotalPages; 2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) job_details->pages_printed = job_info->PagesPrinted; 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ret = true; 2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return ret; 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PrintSystem::PrintServerWatcher* 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PrintSystemWin::CreatePrintServerWatcher() { 2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return new PrintServerWatcherWin(); 2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PrintSystem::PrinterWatcher* PrintSystemWin::CreatePrinterWatcher( 2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const std::string& printer_name) { 2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(!printer_name.empty()); 2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return new PrinterWatcherWin(printer_name); 2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 275f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)std::string PrintSystemWin::GetPrinterDriverInfo( 276f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) const std::string& printer_name) const { 277f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) return print_backend_->GetPrinterDriverInfo(printer_name); 2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace cloud_print 281