diff options
author | Allan Sandfeld Jensen <allan.jensen@qt.io> | 2018-01-29 16:35:13 +0100 |
---|---|---|
committer | Allan Sandfeld Jensen <allan.jensen@qt.io> | 2018-02-01 15:33:35 +0000 |
commit | c8c2d1901aec01e934adf561a9fdf0cc776cdef8 (patch) | |
tree | 9157c3d9815e5870799e070b113813bec53e0535 /chromium/components/printing | |
parent | abefd5095b41dac94ca451d784ab6e27372e981a (diff) | |
download | qtwebengine-chromium-c8c2d1901aec01e934adf561a9fdf0cc776cdef8.tar.gz |
BASELINE: Update Chromium to 64.0.3282.139
Change-Id: I1cae68fe9c94ff7608b26b8382fc19862cdb293a
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
Diffstat (limited to 'chromium/components/printing')
23 files changed, 500 insertions, 380 deletions
diff --git a/chromium/components/printing/DEPS b/chromium/components/printing/DEPS index abfcfb6c9d8..1332b45375b 100644 --- a/chromium/components/printing/DEPS +++ b/chromium/components/printing/DEPS @@ -4,6 +4,7 @@ include_rules = [ "+content/public/common", "+ipc", "+printing", + "+third_party/WebKit/common", "+third_party/WebKit/public", "+ui/gfx" ] diff --git a/chromium/components/printing/browser/BUILD.gn b/chromium/components/printing/browser/BUILD.gn index 3cce73a7647..d910171d52e 100644 --- a/chromium/components/printing/browser/BUILD.gn +++ b/chromium/components/printing/browser/BUILD.gn @@ -4,6 +4,8 @@ static_library("browser") { sources = [ + "print_composite_client.cc", + "print_composite_client.h", "print_manager.cc", "print_manager.h", "print_manager_utils.cc", @@ -17,6 +19,8 @@ static_library("browser") { deps = [ "//base", "//components/printing/common", + "//components/printing/service/public/cpp:client", "//printing", + "//services/service_manager/public/cpp", ] } diff --git a/chromium/components/printing/browser/DEPS b/chromium/components/printing/browser/DEPS index 1c35d9ca694..f67625c944f 100644 --- a/chromium/components/printing/browser/DEPS +++ b/chromium/components/printing/browser/DEPS @@ -1,3 +1,6 @@ include_rules = [ + "+components/printing/service/public/cpp", "+content/public/browser", + "+mojo/public/cpp/system", + "+services/service_manager/public/cpp", ] diff --git a/chromium/components/printing/browser/print_composite_client.cc b/chromium/components/printing/browser/print_composite_client.cc new file mode 100644 index 00000000000..167cdeed469 --- /dev/null +++ b/chromium/components/printing/browser/print_composite_client.cc @@ -0,0 +1,44 @@ +// Copyright 2017 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/printing/browser/print_composite_client.h" + +#include <memory> +#include <utility> + +#include "base/threading/thread_task_runner_handle.h" +#include "content/public/browser/browser_thread.h" +#include "content/public/common/service_manager_connection.h" +#include "services/service_manager/public/cpp/connector.h" + +DEFINE_WEB_CONTENTS_USER_DATA_KEY(printing::PrintCompositeClient); + +namespace printing { + +PrintCompositeClient::PrintCompositeClient(content::WebContents* web_contents) + : for_preview_(false) {} + +PrintCompositeClient::~PrintCompositeClient() {} + +void PrintCompositeClient::CreateConnectorRequest() { + connector_ = service_manager::Connector::Create(&connector_request_); + content::ServiceManagerConnection::GetForProcess() + ->GetConnector() + ->BindConnectorRequest(std::move(connector_request_)); +} + +void PrintCompositeClient::DoComposite( + base::SharedMemoryHandle handle, + uint32_t data_size, + mojom::PdfCompositor::CompositePdfCallback callback) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + DCHECK(data_size); + + if (!connector_) + CreateConnectorRequest(); + Composite(connector_.get(), handle, data_size, std::move(callback), + base::ThreadTaskRunnerHandle::Get()); +} + +} // namespace printing diff --git a/chromium/components/printing/browser/print_composite_client.h b/chromium/components/printing/browser/print_composite_client.h new file mode 100644 index 00000000000..e157eb31611 --- /dev/null +++ b/chromium/components/printing/browser/print_composite_client.h @@ -0,0 +1,40 @@ +// Copyright 2017 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef COMPONENTS_PRINTING_BROWSER_PRINT_COMPOSITE_CLIENT_H_ +#define COMPONENTS_PRINTING_BROWSER_PRINT_COMPOSITE_CLIENT_H_ + +#include "components/printing/service/public/cpp/pdf_compositor_client.h" +#include "content/public/browser/web_contents_observer.h" +#include "content/public/browser/web_contents_user_data.h" + +namespace printing { + +class PrintCompositeClient + : public PdfCompositorClient, + public content::WebContentsUserData<PrintCompositeClient> { + public: + explicit PrintCompositeClient(content::WebContents* web_contents); + ~PrintCompositeClient() override; + + void DoComposite(base::SharedMemoryHandle handle, + uint32_t data_size, + mojom::PdfCompositor::CompositePdfCallback callback); + + void set_for_preview(bool for_preview) { for_preview_ = for_preview; } + bool for_preview() const { return for_preview_; } + + private: + void CreateConnectorRequest(); + + service_manager::mojom::ConnectorRequest connector_request_; + std::unique_ptr<service_manager::Connector> connector_; + bool for_preview_; + + DISALLOW_COPY_AND_ASSIGN(PrintCompositeClient); +}; + +} // namespace printing + +#endif // COMPONENTS_PRINTING_BROWSER_PRINT_COMPOSITE_CLIENT_H_ diff --git a/chromium/components/printing/browser/print_manager_utils.cc b/chromium/components/printing/browser/print_manager_utils.cc index 3d71a985f6b..844fcf5bd23 100644 --- a/chromium/components/printing/browser/print_manager_utils.cc +++ b/chromium/components/printing/browser/print_manager_utils.cc @@ -3,11 +3,43 @@ // found in the LICENSE file. #include "components/printing/browser/print_manager_utils.h" + +#include "base/command_line.h" +#include "components/printing/browser/print_composite_client.h" #include "components/printing/common/print_messages.h" +#include "content/public/common/content_features.h" +#include "content/public/common/content_switches.h" #include "printing/print_settings.h" namespace printing { +// A temporary flag which makes supporting both paths for OOPIF and non-OOPIF +// printing easier. +static bool g_oopif_enabled = false; + +void SetOopifEnabled() { + g_oopif_enabled = true; +} + +bool IsOopifEnabled() { + return g_oopif_enabled; +} + +void CreateCompositeClientIfNeeded(content::WebContents* web_contents, + bool for_preview) { + if (base::CommandLine::ForCurrentProcess()->HasSwitch( + switches::kSitePerProcess) || + base::FeatureList::IsEnabled(features::kTopDocumentIsolation)) { + // For cases need to support OOPIFs. + PrintCompositeClient::CreateForWebContents(web_contents); + if (for_preview) { + PrintCompositeClient::FromWebContents(web_contents) + ->set_for_preview(true); + } + SetOopifEnabled(); + } +} + void RenderParamsFromPrintSettings(const PrintSettings& settings, PrintMsg_Print_Params* params) { params->page_size = settings.page_setup_device_units().physical_size(); @@ -32,7 +64,8 @@ void RenderParamsFromPrintSettings(const PrintSettings& settings, params->display_header_footer = settings.display_header_footer(); params->title = settings.title(); params->url = settings.url(); - params->printed_doc_type = SkiaDocumentType::PDF; + params->printed_doc_type = + IsOopifEnabled() ? SkiaDocumentType::MSKP : SkiaDocumentType::PDF; } } // namespace printing diff --git a/chromium/components/printing/browser/print_manager_utils.h b/chromium/components/printing/browser/print_manager_utils.h index 31e0daaad6b..5b2b62a7dbf 100644 --- a/chromium/components/printing/browser/print_manager_utils.h +++ b/chromium/components/printing/browser/print_manager_utils.h @@ -7,10 +7,22 @@ struct PrintMsg_Print_Params; +namespace content { +class WebContents; +} + namespace printing { class PrintSettings; +void SetOopifEnabled(bool enabled); +bool IsOopifEnabled(); + +// Check on the current feature settings to decide whether we need to +// create a PDF compositor client for this |web_contents|. +void CreateCompositeClientIfNeeded(content::WebContents* web_contents, + bool for_preview); + // Converts given settings to Print_Params and stores them in the output // parameter |params|. void RenderParamsFromPrintSettings(const PrintSettings& settings, diff --git a/chromium/components/printing/common/print_messages.cc b/chromium/components/printing/common/print_messages.cc index 6767c4af66a..5ccf87b2886 100644 --- a/chromium/components/printing/common/print_messages.cc +++ b/chromium/components/printing/common/print_messages.cc @@ -7,32 +7,56 @@ #include "ui/gfx/geometry/size.h" #define IPC_MESSAGE_IMPL +#undef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #include "components/printing/common/print_messages.h" +#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#error "Failed to include header components/printing/common/print_messages.h" +#endif // Generate constructors. #include "ipc/struct_constructor_macros.h" +#undef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #include "components/printing/common/print_messages.h" +#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#error "Failed to include header components/printing/common/print_messages.h" +#endif // Generate destructors. #include "ipc/struct_destructor_macros.h" +#undef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #include "components/printing/common/print_messages.h" +#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#error "Failed to include header components/printing/common/print_messages.h" +#endif // Generate param traits write methods. #include "ipc/param_traits_write_macros.h" namespace IPC { +#undef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #include "components/printing/common/print_messages.h" +#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#error "Failed to include header components/printing/common/print_messages.h" +#endif } // namespace IPC // Generate param traits read methods. #include "ipc/param_traits_read_macros.h" namespace IPC { +#undef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #include "components/printing/common/print_messages.h" +#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#error "Failed to include header components/printing/common/print_messages.h" +#endif } // namespace IPC // Generate param traits log methods. #include "ipc/param_traits_log_macros.h" namespace IPC { +#undef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #include "components/printing/common/print_messages.h" +#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#error "Failed to include header components/printing/common/print_messages.h" +#endif } // namespace IPC PrintMsg_Print_Params::PrintMsg_Print_Params() diff --git a/chromium/components/printing/common/print_messages.h b/chromium/components/printing/common/print_messages.h index ed443d2a811..339e63c3294 100644 --- a/chromium/components/printing/common/print_messages.h +++ b/chromium/components/printing/common/print_messages.h @@ -3,7 +3,8 @@ // found in the LICENSE file. // IPC messages for printing. -// Multiply-included message file, hence no include guard. +#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#define COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #include <stdint.h> @@ -30,8 +31,8 @@ // Force multiple inclusion of the param traits file to generate all methods. #undef COMPONENTS_PRINTING_COMMON_PRINTING_PARAM_TRAITS_MACROS_H_ -#ifndef COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ -#define COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#ifndef INTERNAL_COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#define INTERNAL_COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ struct PrintMsg_Print_Params { PrintMsg_Print_Params(); @@ -97,7 +98,7 @@ struct PrintHostMsg_SetOptionsFromDocument_Params { }; #endif // BUILDFLAG(ENABLE_PRINT_PREVIEW) -#endif // COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ +#endif // INTERNAL_COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #define IPC_MESSAGE_START PrintMsgStart @@ -485,3 +486,5 @@ IPC_MESSAGE_ROUTED1(PrintHostMsg_ShowScriptedPrintPreview, IPC_MESSAGE_ROUTED1(PrintHostMsg_SetOptionsFromDocument, PrintHostMsg_SetOptionsFromDocument_Params /* params */) #endif // BUILDFLAG(ENABLE_PRINT_PREVIEW) + +#endif // COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ diff --git a/chromium/components/printing/renderer/BUILD.gn b/chromium/components/printing/renderer/BUILD.gn index 1902a859479..9d92b864320 100644 --- a/chromium/components/printing/renderer/BUILD.gn +++ b/chromium/components/printing/renderer/BUILD.gn @@ -9,7 +9,6 @@ static_library("renderer") { "print_render_frame_helper_android.cc", "print_render_frame_helper_linux.cc", "print_render_frame_helper_mac.mm", - "print_render_frame_helper_pdf_win.cc", ] deps = [ @@ -20,6 +19,7 @@ static_library("renderer") { "//content/public/renderer", "//net", "//printing", + "//third_party/WebKit/common:blink_common", "//third_party/WebKit/public:blink", "//ui/base", ] diff --git a/chromium/components/printing/renderer/print_render_frame_helper.cc b/chromium/components/printing/renderer/print_render_frame_helper.cc index c6b03ed6ad9..663cd774849 100644 --- a/chromium/components/printing/renderer/print_render_frame_helper.cc +++ b/chromium/components/printing/renderer/print_render_frame_helper.cc @@ -36,6 +36,8 @@ #include "printing/metafile_skia_wrapper.h" #include "printing/pdf_metafile_skia.h" #include "printing/units.h" +#include "third_party/WebKit/common/page/page_visibility_state.mojom.h" +#include "third_party/WebKit/common/sandbox_flags.h" #include "third_party/WebKit/public/platform/Platform.h" #include "third_party/WebKit/public/platform/WebDoubleSize.h" #include "third_party/WebKit/public/platform/WebSize.h" @@ -51,7 +53,6 @@ #include "third_party/WebKit/public/web/WebPluginDocument.h" #include "third_party/WebKit/public/web/WebPrintParams.h" #include "third_party/WebKit/public/web/WebPrintPresetOptions.h" -#include "third_party/WebKit/public/web/WebSandboxFlags.h" #include "third_party/WebKit/public/web/WebScriptSource.h" #include "third_party/WebKit/public/web/WebSettings.h" #include "third_party/WebKit/public/web/WebView.h" @@ -167,8 +168,8 @@ PrintMsg_Print_Params GetCssPrintParams( // Invalid page size and/or margins. We just use the default setting. if (new_content_width < 1 || new_content_height < 1) { - CHECK(frame != NULL); - page_css_params = GetCssPrintParams(NULL, page_index, page_params); + CHECK(frame != nullptr); + page_css_params = GetCssPrintParams(nullptr, page_index, page_params); return page_css_params; } @@ -308,7 +309,7 @@ void ComputeWebKitPrintParamsInDesiredDpi( blink::WebPlugin* GetPlugin(const blink::WebLocalFrame* frame) { return frame->GetDocument().IsPluginDocument() ? frame->GetDocument().To<blink::WebPluginDocument>().Plugin() - : NULL; + : nullptr; } bool PrintingNodeOrPdfFrame(const blink::WebLocalFrame* frame, @@ -529,7 +530,7 @@ FrameReference::FrameReference(blink::WebLocalFrame* frame) { } FrameReference::FrameReference() { - Reset(NULL); + Reset(nullptr); } FrameReference::~FrameReference() {} @@ -545,20 +546,20 @@ void FrameReference::Reset(blink::WebLocalFrame* frame) { DCHECK(view_); frame_ = frame; } else { - view_ = NULL; - frame_ = NULL; + view_ = nullptr; + frame_ = nullptr; } } blink::WebLocalFrame* FrameReference::GetFrame() { - if (view_ == NULL || frame_ == NULL) - return NULL; - for (blink::WebFrame* frame = view_->MainFrame(); frame != NULL; + if (view_ == nullptr || frame_ == nullptr) + return nullptr; + for (blink::WebFrame* frame = view_->MainFrame(); frame != nullptr; frame = frame->TraverseNext()) { if (frame == frame_) return frame_; } - return NULL; + return nullptr; } blink::WebView* FrameReference::view() { @@ -582,8 +583,8 @@ void PrintRenderFrameHelper::PrintHeaderAndFooter( page_layout.margin_top + page_layout.margin_bottom + page_layout.content_height); - blink::WebView* web_view = - blink::WebView::Create(nullptr, blink::kWebPageVisibilityStateVisible); + blink::WebView* web_view = blink::WebView::Create( + nullptr, blink::mojom::PageVisibilityState::kVisible); web_view->GetSettings()->SetJavaScriptEnabled(true); class HeaderAndFooterClient final : public blink::WebFrameClient { @@ -695,12 +696,10 @@ class PrepareFrameAndViewForPrint : public blink::WebViewClient, const blink::WebString& name, const blink::WebString& fallback_name, blink::WebSandboxFlags sandbox_flags, - const blink::WebParsedFeaturePolicy& container_policy, + const blink::ParsedFeaturePolicy& container_policy, const blink::WebFrameOwnerProperties& frame_owner_properties) override; void FrameDetached(DetachType detach_type) override; - std::unique_ptr<blink::WebURLLoader> CreateURLLoader( - const blink::WebURLRequest& request, - scoped_refptr<base::SingleThreadTaskRunner> task_runner) override; + std::unique_ptr<blink::WebURLLoaderFactory> CreateURLLoaderFactory() override; void CallOnReady(); void ResizeForPrinting(); @@ -794,11 +793,11 @@ void PrepareFrameAndViewForPrint::ResizeForPrinting() { } void PrepareFrameAndViewForPrint::StartPrinting() { + ResizeForPrinting(); blink::WebView* web_view = frame_.view(); web_view->GetSettings()->SetShouldPrintBackgrounds(should_print_backgrounds_); expected_pages_count_ = frame()->PrintBegin(web_print_params_, node_to_print_); - ResizeForPrinting(); is_printing_started_ = true; } @@ -828,7 +827,7 @@ void PrepareFrameAndViewForPrint::CopySelection( prefs.javascript_enabled = false; blink::WebView* web_view = - blink::WebView::Create(this, blink::kWebPageVisibilityStateVisible); + blink::WebView::Create(this, blink::mojom::PageVisibilityState::kVisible); owns_web_view_ = true; content::RenderView::ApplyWebPreferences(prefs, web_view); blink::WebLocalFrame* main_frame = @@ -862,7 +861,7 @@ blink::WebLocalFrame* PrepareFrameAndViewForPrint::CreateChildFrame( const blink::WebString& name, const blink::WebString& fallback_name, blink::WebSandboxFlags sandbox_flags, - const blink::WebParsedFeaturePolicy& container_policy, + const blink::ParsedFeaturePolicy& container_policy, const blink::WebFrameOwnerProperties& frame_owner_properties) { // This is called when printing a selection and when this selection contains // an iframe. This is not supported yet. An empty rectangle will be displayed @@ -879,13 +878,9 @@ void PrepareFrameAndViewForPrint::FrameDetached(DetachType detach_type) { frame_.Reset(nullptr); } -std::unique_ptr<blink::WebURLLoader> -PrepareFrameAndViewForPrint::CreateURLLoader( - const blink::WebURLRequest& request, - scoped_refptr<base::SingleThreadTaskRunner> task_runner) { - // TODO(yhirano): Stop using Platform::CreateURLLoader() here. - return blink::Platform::Current()->CreateURLLoader(request, - std::move(task_runner)); +std::unique_ptr<blink::WebURLLoaderFactory> +PrepareFrameAndViewForPrint::CreateURLLoaderFactory() { + return blink::Platform::Current()->CreateDefaultURLLoaderFactory(); } void PrepareFrameAndViewForPrint::CallOnReady() { @@ -928,7 +923,7 @@ void PrepareFrameAndViewForPrint::FinishPrinting() { web_view->Close(); } } - frame_.Reset(NULL); + frame_.Reset(nullptr); on_ready_.Reset(); } @@ -940,12 +935,6 @@ bool PrintRenderFrameHelper::Delegate::IsScriptedPrintEnabled() { return true; } -#if defined(OS_MACOSX) -bool PrintRenderFrameHelper::Delegate::UseSingleMetafile() { - return false; -} -#endif - PrintRenderFrameHelper::PrintRenderFrameHelper( content::RenderFrame* render_frame, std::unique_ptr<Delegate> delegate) @@ -1166,7 +1155,7 @@ void PrintRenderFrameHelper::OnPrintForPrintPreview( // has content in correct position taking into account page size and printable // area. // TODO(vitalybuka) : Make this consistent on all platform. This change - // affects Windows only. On Linux and OSX RenderPagesForPrint does not use + // affects Windows only. Linux and OSX RenderPagesForPrint do not use // printable_area. Also we can't change printable_area deeper inside // RenderPagesForPrint for Windows, because it's used also by native // printing and it expects real printable_area value. @@ -1414,7 +1403,7 @@ bool PrintRenderFrameHelper::RenderPreviewPage( PrintPageInternal(print_params, page_number, print_preview_context_.total_page_count(), print_preview_context_.prepared_frame(), - initial_render_metafile, nullptr, nullptr, nullptr); + initial_render_metafile, nullptr, nullptr); print_preview_context_.RenderedPreviewPage(base::TimeTicks::Now() - begin_time); if (draft_metafile.get()) { @@ -1675,6 +1664,58 @@ void PrintRenderFrameHelper::PrintPages() { } } +#if defined(OS_MACOSX) || defined(OS_WIN) +bool PrintRenderFrameHelper::PrintPagesNative(blink::WebLocalFrame* frame, + int page_count) { + const PrintMsg_PrintPages_Params& params = *print_pages_params_; + const PrintMsg_Print_Params& print_params = params.params; + + std::vector<int> printed_pages = GetPrintedPages(params, page_count); + if (printed_pages.empty()) + return false; + + PdfMetafileSkia metafile(print_params.printed_doc_type); + CHECK(metafile.Init()); + + std::vector<gfx::Size> page_size_in_dpi(printed_pages.size()); + std::vector<gfx::Rect> content_area_in_dpi(printed_pages.size()); + for (size_t i = 0; i < printed_pages.size(); ++i) { + PrintPageInternal(print_params, printed_pages[i], page_count, frame, + &metafile, &page_size_in_dpi[i], &content_area_in_dpi[i]); + } + + // blink::printEnd() for PDF should be called before metafile is closed. + FinishFramePrinting(); + + metafile.FinishDocument(); + + PrintHostMsg_DidPrintPage_Params page_params; + if (!CopyMetafileDataToSharedMem(metafile, + &page_params.metafile_data_handle)) { + return false; + } + + page_params.data_size = metafile.GetDataSize(); + page_params.document_cookie = print_params.document_cookie; +#if defined(OS_WIN) + page_params.physical_offsets = printer_printable_area_.origin(); +#endif + for (size_t i = 0; i < printed_pages.size(); ++i) { + page_params.page_number = printed_pages[i]; + page_params.page_size = page_size_in_dpi[i]; + page_params.content_area = content_area_in_dpi[i]; + Send(new PrintHostMsg_DidPrintPage(routing_id(), page_params)); + // Send the rest of the pages with an invalid metafile handle. + // TODO(erikchen): Fix semantics. See https://crbug.com/640840 + if (page_params.metafile_data_handle.IsValid()) { + page_params.metafile_data_handle = base::SharedMemoryHandle(); + page_params.data_size = 0; + } + } + return true; +} +#endif // defined(OS_MACOSX) || defined(OS_WIN) + void PrintRenderFrameHelper::FinishFramePrinting() { prep_frame_view_.reset(); } @@ -1923,40 +1964,34 @@ void PrintRenderFrameHelper::PrintPageInternal( blink::WebLocalFrame* frame, PdfMetafileSkia* metafile, gfx::Size* page_size_in_dpi, - gfx::Rect* content_area_in_dpi, - gfx::Rect* printable_area_in_dpi) { - PageSizeMargins page_layout_in_points; - - double css_scale_factor = 1.0f; - if (params.scale_factor >= kEpsilon) - css_scale_factor = params.scale_factor; + gfx::Rect* content_area_in_dpi) { + double css_scale_factor = + params.scale_factor >= kEpsilon ? params.scale_factor : 1.0f; // Save the original page size here to avoid rounding errors incurred by // converting to pixels and back and by scaling the page for reflow and // scaling back. Windows uses |page_size_in_dpi| for the actual page size // so requires an accurate value. gfx::Size original_page_size = params.page_size; + PageSizeMargins page_layout_in_points; ComputePageLayoutInPointsForCss(frame, page_number, params, ignore_css_margins_, &css_scale_factor, &page_layout_in_points); + gfx::Size page_size; gfx::Rect content_area; GetPageSizeAndContentAreaFromPageLayout(page_layout_in_points, &page_size, &content_area); // Calculate the actual page size and content area in dpi. - if (page_size_in_dpi) { + if (page_size_in_dpi) *page_size_in_dpi = original_page_size; - } if (content_area_in_dpi) { // Output PDF matches paper size and should be printer edge to edge. *content_area_in_dpi = gfx::Rect(0, 0, page_size_in_dpi->width(), page_size_in_dpi->height()); } - if (printable_area_in_dpi) { - *printable_area_in_dpi = printer_printable_area_; - } gfx::Rect canvas_area = params.display_header_footer ? gfx::Rect(page_size) : content_area; @@ -1995,8 +2030,8 @@ void PrintRenderFrameHelper::PrintPageInternal( DCHECK_GT(webkit_scale_factor, 0.0f); // Done printing. Close the canvas to retrieve the compiled metafile. - if (!metafile->FinishPage()) - NOTREACHED() << "metafile failed"; + bool ret = metafile->FinishPage(); + DCHECK(ret); } #endif // !defined(OS_MACOSX) diff --git a/chromium/components/printing/renderer/print_render_frame_helper.h b/chromium/components/printing/renderer/print_render_frame_helper.h index a9fe8cb7dca..cd174ca6508 100644 --- a/chromium/components/printing/renderer/print_render_frame_helper.h +++ b/chromium/components/printing/renderer/print_render_frame_helper.h @@ -110,15 +110,6 @@ class PrintRenderFrameHelper // Returns true if printing is overridden and the default behavior should be // skipped for |frame|. virtual bool OverridePrint(blink::WebLocalFrame* frame) = 0; - -#if defined(OS_MACOSX) - // If true, all the printed pages are returned in the first - // PrintHostMsg_DidPrintPage metafile, like on Linux and Windows. - // NOTE: PrintHostMsg_DidPrintPage messages for all pages contain the same - // page and content area, which may lead to bug when these two parameters - // are different per page. - virtual bool UseSingleMetafile(); -#endif }; PrintRenderFrameHelper(content::RenderFrame* render_frame, @@ -284,6 +275,7 @@ class PrintRenderFrameHelper #endif // BUILDFLAG(ENABLE_BASIC_PRINTING) // Page Printing / Rendering ------------------------------------------------ + #if BUILDFLAG(ENABLE_BASIC_PRINTING) void OnFramePreparedForPrintPages(); void PrintPages(); @@ -294,34 +286,14 @@ class PrintRenderFrameHelper const blink::WebNode& node); #endif // BUILDFLAG(ENABLE_BASIC_PRINTING) - // Prints the page listed in |params|. -#if defined(OS_MACOSX) - void PrintPagesInternal(const PrintMsg_Print_Params& params, - const std::vector<int>& printed_pages, - int page_count, - blink::WebLocalFrame* frame); -#else + // Platform-specific helper function for rendering page(s) to |metafile|. void PrintPageInternal(const PrintMsg_Print_Params& params, int page_number, int page_count, blink::WebLocalFrame* frame, PdfMetafileSkia* metafile, gfx::Size* page_size_in_dpi, - gfx::Rect* content_area_in_dpi, - gfx::Rect* printable_area_in_dpi); -#endif // defined(OS_MACOSX) - - // Platform specific helper function for rendering page(s) to |metafile|. -#if defined(OS_MACOSX) - void RenderPage(const PrintMsg_Print_Params& params, - int page_number, - int page_count, - blink::WebLocalFrame* frame, - bool is_preview, - PdfMetafileSkia* metafile, - gfx::Size* page_size, - gfx::Rect* content_rect); -#endif // defined(OS_MACOSX) + gfx::Rect* content_area_in_dpi); // Renders page contents from |frame| to |content_area| of |canvas|. // |page_number| is zero-based. diff --git a/chromium/components/printing/renderer/print_render_frame_helper_linux.cc b/chromium/components/printing/renderer/print_render_frame_helper_linux.cc index f5ae4cdcfe3..769976b3830 100644 --- a/chromium/components/printing/renderer/print_render_frame_helper_linux.cc +++ b/chromium/components/printing/renderer/print_render_frame_helper_linux.cc @@ -48,16 +48,17 @@ bool PrintRenderFrameHelper::PrintPagesNative(blink::WebLocalFrame* frame, int page_count) { const PrintMsg_PrintPages_Params& params = *print_pages_params_; const PrintMsg_Print_Params& print_params = params.params; - PdfMetafileSkia metafile(print_params.printed_doc_type); - CHECK(metafile.Init()); std::vector<int> printed_pages = GetPrintedPages(params, page_count); if (printed_pages.empty()) return false; + PdfMetafileSkia metafile(print_params.printed_doc_type); + CHECK(metafile.Init()); + for (int page_number : printed_pages) { - PrintPageInternal(params.params, page_number, page_count, frame, &metafile, - nullptr, nullptr, nullptr); + PrintPageInternal(print_params, page_number, page_count, frame, &metafile, + nullptr, nullptr); } // blink::printEnd() for PDF should be called before metafile is closed. @@ -80,21 +81,22 @@ bool PrintRenderFrameHelper::PrintPagesNative(blink::WebLocalFrame* frame, routing_id(), sequence_number, printed_pages.size())); return true; #else - PrintHostMsg_DidPrintPage_Params printed_page_params; - + PrintHostMsg_DidPrintPage_Params page_params; if (!CopyMetafileDataToSharedMem(metafile, - &printed_page_params.metafile_data_handle)) { + &page_params.metafile_data_handle)) { return false; } - printed_page_params.data_size = metafile.GetDataSize(); - printed_page_params.document_cookie = params.params.document_cookie; - + page_params.data_size = metafile.GetDataSize(); + page_params.document_cookie = print_params.document_cookie; for (size_t i = 0; i < printed_pages.size(); ++i) { - printed_page_params.page_number = printed_pages[i]; - Send(new PrintHostMsg_DidPrintPage(routing_id(), printed_page_params)); + page_params.page_number = printed_pages[i]; + Send(new PrintHostMsg_DidPrintPage(routing_id(), page_params)); // Send the rest of the pages with an invalid metafile handle. - printed_page_params.metafile_data_handle.Release(); + if (page_params.metafile_data_handle.IsValid()) { + page_params.metafile_data_handle = base::SharedMemoryHandle(); + page_params.data_size = 0; + } } return true; #endif // defined(OS_ANDROID) diff --git a/chromium/components/printing/renderer/print_render_frame_helper_mac.mm b/chromium/components/printing/renderer/print_render_frame_helper_mac.mm index 42149955ee2..8cc4806de50 100644 --- a/chromium/components/printing/renderer/print_render_frame_helper_mac.mm +++ b/chromium/components/printing/renderer/print_render_frame_helper_mac.mm @@ -18,64 +18,6 @@ namespace printing { -#if BUILDFLAG(ENABLE_BASIC_PRINTING) -bool PrintRenderFrameHelper::PrintPagesNative(blink::WebLocalFrame* frame, - int page_count) { - const PrintMsg_PrintPages_Params& params = *print_pages_params_; - const PrintMsg_Print_Params& print_params = params.params; - - std::vector<int> printed_pages = GetPrintedPages(params, page_count); - if (printed_pages.empty()) - return false; - - if (delegate_->UseSingleMetafile()) { - PrintPagesInternal(print_params, printed_pages, page_count, frame); - return true; - } - - for (int page_number : printed_pages) - PrintPagesInternal(print_params, std::vector<int>{page_number}, page_count, - frame); - return true; -} -#endif // BUILDFLAG(ENABLE_BASIC_PRINTING) - -void PrintRenderFrameHelper::PrintPagesInternal( - const PrintMsg_Print_Params& params, - const std::vector<int>& printed_pages, - int page_count, - blink::WebLocalFrame* frame) { - PdfMetafileSkia metafile(params.printed_doc_type); - CHECK(metafile.Init()); - - gfx::Size page_size_in_dpi; - gfx::Rect content_area_in_dpi; - for (int page_number : printed_pages) { - RenderPage(params, page_number, page_count, frame, false, &metafile, - &page_size_in_dpi, &content_area_in_dpi); - } - metafile.FinishDocument(); - - PrintHostMsg_DidPrintPage_Params page_params; - page_params.data_size = metafile.GetDataSize(); - page_params.document_cookie = params.document_cookie; - page_params.page_size = page_size_in_dpi; - page_params.content_area = content_area_in_dpi; - - // Ask the browser to create the shared memory for us. - if (!CopyMetafileDataToSharedMem(metafile, - &page_params.metafile_data_handle)) { - // TODO(thestig): Fail and return false instead. - page_params.data_size = 0; - } - - for (int page_number : printed_pages) { - page_params.page_number = page_number; - Send(new PrintHostMsg_DidPrintPage(routing_id(), page_params)); - page_params.metafile_data_handle = base::SharedMemoryHandle(); - } -} - #if BUILDFLAG(ENABLE_PRINT_PREVIEW) bool PrintRenderFrameHelper::RenderPreviewPage( int page_number, @@ -94,11 +36,10 @@ bool PrintRenderFrameHelper::RenderPreviewPage( } base::TimeTicks begin_time = base::TimeTicks::Now(); - gfx::Size page_size; - RenderPage(print_params, page_number, - print_preview_context_.total_page_count(), - print_preview_context_.prepared_frame(), true, - initial_render_metafile, &page_size, NULL); + PrintPageInternal(print_params, page_number, + print_preview_context_.total_page_count(), + print_preview_context_.prepared_frame(), + initial_render_metafile, nullptr, nullptr); print_preview_context_.RenderedPreviewPage(base::TimeTicks::Now() - begin_time); @@ -117,52 +58,55 @@ bool PrintRenderFrameHelper::RenderPreviewPage( } #endif // BUILDFLAG(ENABLE_PRINT_PREVIEW) -void PrintRenderFrameHelper::RenderPage(const PrintMsg_Print_Params& params, - int page_number, - int page_count, - blink::WebLocalFrame* frame, - bool is_preview, - PdfMetafileSkia* metafile, - gfx::Size* page_size, - gfx::Rect* content_rect) { - double scale_factor = +void PrintRenderFrameHelper::PrintPageInternal( + const PrintMsg_Print_Params& params, + int page_number, + int page_count, + blink::WebLocalFrame* frame, + PdfMetafileSkia* metafile, + gfx::Size* page_size_in_dpi, + gfx::Rect* content_rect_in_dpi) { + double css_scale_factor = params.scale_factor >= kEpsilon ? params.scale_factor : 1.0f; - double webkit_shrink_factor = frame->GetPrintPageShrink(page_number); - PageSizeMargins page_layout_in_points; - gfx::Rect content_area; + PageSizeMargins page_layout_in_points; ComputePageLayoutInPointsForCss(frame, page_number, params, - ignore_css_margins_, &scale_factor, + ignore_css_margins_, &css_scale_factor, &page_layout_in_points); - GetPageSizeAndContentAreaFromPageLayout(page_layout_in_points, page_size, + + gfx::Size page_size; + gfx::Rect content_area; + GetPageSizeAndContentAreaFromPageLayout(page_layout_in_points, &page_size, &content_area); - if (content_rect) - *content_rect = content_area; - scale_factor *= webkit_shrink_factor; + if (page_size_in_dpi) + *page_size_in_dpi = page_size; + + if (content_rect_in_dpi) + *content_rect_in_dpi = content_area; gfx::Rect canvas_area = - params.display_header_footer ? gfx::Rect(*page_size) : content_area; - - { - cc::PaintCanvas* canvas = metafile->GetVectorCanvasForNewPage( - *page_size, canvas_area, scale_factor); - if (!canvas) - return; - - MetafileSkiaWrapper::SetMetafileOnCanvas(canvas, metafile); - cc::SetIsPreviewMetafile(canvas, is_preview); - if (params.display_header_footer) { - PrintHeaderAndFooter(static_cast<blink::WebCanvas*>(canvas), - page_number + 1, page_count, *frame, scale_factor, - page_layout_in_points, params); - } - RenderPageContent(frame, page_number, canvas_area, content_area, - scale_factor, static_cast<blink::WebCanvas*>(canvas)); + params.display_header_footer ? gfx::Rect(page_size) : content_area; + + double webkit_page_shrink_factor = frame->GetPrintPageShrink(page_number); + float scale_factor = css_scale_factor * webkit_page_shrink_factor; + + cc::PaintCanvas* canvas = + metafile->GetVectorCanvasForNewPage(page_size, canvas_area, scale_factor); + if (!canvas) + return; + + MetafileSkiaWrapper::SetMetafileOnCanvas(canvas, metafile); + if (params.display_header_footer) { + PrintHeaderAndFooter(canvas, page_number + 1, page_count, *frame, + scale_factor, page_layout_in_points, params); } + RenderPageContent(frame, page_number, canvas_area, content_area, scale_factor, + canvas); - // Done printing. Close the device context to retrieve the compiled metafile. - metafile->FinishPage(); + // Done printing. Close the canvas to retrieve the compiled metafile. + bool ret = metafile->FinishPage(); + DCHECK(ret); } } // namespace printing diff --git a/chromium/components/printing/renderer/print_render_frame_helper_pdf_win.cc b/chromium/components/printing/renderer/print_render_frame_helper_pdf_win.cc deleted file mode 100644 index a746fd9e97f..00000000000 --- a/chromium/components/printing/renderer/print_render_frame_helper_pdf_win.cc +++ /dev/null @@ -1,70 +0,0 @@ -// Copyright 2014 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "components/printing/renderer/print_render_frame_helper.h" - -#include <stddef.h> - -#include "base/logging.h" -#include "base/process/process_handle.h" -#include "components/printing/common/print_messages.h" -#include "printing/features/features.h" -#include "printing/metafile_skia_wrapper.h" - -namespace printing { - -#if BUILDFLAG(ENABLE_BASIC_PRINTING) -bool PrintRenderFrameHelper::PrintPagesNative(blink::WebLocalFrame* frame, - int page_count) { - const PrintMsg_PrintPages_Params& params = *print_pages_params_; - std::vector<int> printed_pages = GetPrintedPages(params, page_count); - if (printed_pages.empty()) - return false; - - std::vector<gfx::Size> page_size_in_dpi(printed_pages.size()); - std::vector<gfx::Rect> content_area_in_dpi(printed_pages.size()); - std::vector<gfx::Rect> printable_area_in_dpi(printed_pages.size()); - - PdfMetafileSkia metafile(params.params.printed_doc_type); - CHECK(metafile.Init()); - - for (size_t i = 0; i < printed_pages.size(); ++i) { - PrintPageInternal(params.params, printed_pages[i], page_count, frame, - &metafile, &page_size_in_dpi[i], &content_area_in_dpi[i], - &printable_area_in_dpi[i]); - } - - // blink::printEnd() for PDF should be called before metafile is closed. - FinishFramePrinting(); - - metafile.FinishDocument(); - - PrintHostMsg_DidPrintPage_Params printed_page_params; - if (!CopyMetafileDataToSharedMem(metafile, - &printed_page_params.metafile_data_handle)) { - return false; - } - - printed_page_params.content_area = params.params.printable_area; - printed_page_params.data_size = metafile.GetDataSize(); - printed_page_params.document_cookie = params.params.document_cookie; - printed_page_params.page_size = params.params.page_size; - - for (size_t i = 0; i < printed_pages.size(); ++i) { - printed_page_params.page_number = printed_pages[i]; - printed_page_params.page_size = page_size_in_dpi[i]; - printed_page_params.content_area = content_area_in_dpi[i]; - printed_page_params.physical_offsets = - gfx::Point(printable_area_in_dpi[i].x(), printable_area_in_dpi[i].y()); - Send(new PrintHostMsg_DidPrintPage(routing_id(), printed_page_params)); - // Send the rest of the pages with an invalid metafile handle. - // TODO(erikchen): Fix semantics. See https://crbug.com/640840 - if (printed_page_params.metafile_data_handle.IsValid()) - printed_page_params.metafile_data_handle = base::SharedMemoryHandle(); - } - return true; -} -#endif // BUILDFLAG(ENABLE_BASIC_PRINTING) - -} // namespace printing diff --git a/chromium/components/printing/service/BUILD.gn b/chromium/components/printing/service/BUILD.gn index fb42f33f5ba..40434536df6 100644 --- a/chromium/components/printing/service/BUILD.gn +++ b/chromium/components/printing/service/BUILD.gn @@ -2,6 +2,7 @@ # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. +import("//printing/features/features.gni") import("//services/service_manager/public/cpp/service.gni") import("//services/service_manager/public/service_manifest.gni") import("//services/service_manager/public/tools/test/service_test.gni") @@ -26,6 +27,7 @@ static_library("service") { ] public_deps = [ + "//components/printing/service/public/cpp:utils", "//components/printing/service/public/interfaces", "//services/service_manager/public/cpp", ] @@ -36,48 +38,31 @@ service_manifest("pdf_compositor_manifest") { source = "pdf_compositor_manifest.json" } -service("pdf_compositor_test_service") { - testonly = true +if (enable_basic_printing || enable_print_preview) { + source_set("unit_tests") { + testonly = true + sources = [ + "pdf_compositor_service_unittest.cc", + ] - sources = [ - "test_service_main.cc", - ] - - deps = [ - ":service", - "//base", - "//base/test:test_support", - ] -} - -service_test("pdf_compositor_service_unittest") { - testonly = true - - sources = [ - "pdf_compositor_service_unittest.cc", - ] - - catalog = ":pdf_compositor_service_unittest_catalog" - - include_dirs = [ "testing/gmock/include" ] - deps = [ - ":pdf_compositor_test_service", - "//base", - "//components/printing/service/public/interfaces", - "//mojo/common", - "//services/service_manager/public/cpp:service_test_support", - "//testing/gmock", - "//testing/gtest", - ] -} - -service_manifest("pdf_compositor_service_unittest_manifest") { - name = "pdf_compositor_service_unittest" - source = "pdf_compositor_service_unittest_manifest.json" -} + include_dirs = [ "testing/gmock/include" ] + deps = [ + ":service", + "//base/test:test_support", + "//components/printing/service/public/interfaces", + "//mojo/common", + "//services/service_manager/public/cpp:service_test_support", + "//testing/gmock", + "//testing/gtest", + ] + data = [ + "//components/test/data/printing/google.mskp", + ] + } -catalog("pdf_compositor_service_unittest_catalog") { - testonly = true - embedded_services = [ ":pdf_compositor_service_unittest_manifest" ] - standalone_services = [ ":pdf_compositor_manifest" ] + service_manifest("pdf_compositor_service_unittest_manifest") { + name = "pdf_compositor_service_unittest" + source = "pdf_compositor_service_unittest_manifest.json" + packaged_services = [ ":pdf_compositor_manifest" ] + } } diff --git a/chromium/components/printing/service/DEPS b/chromium/components/printing/service/DEPS index d3ca2e285c0..0145b6a4187 100644 --- a/chromium/components/printing/service/DEPS +++ b/chromium/components/printing/service/DEPS @@ -5,12 +5,7 @@ include_rules = [ "+mojo/public/cpp", "+printing/common", "+services/service_manager/public/cpp", + "+services/service_manager/public/interfaces", "+skia", "+third_party/skia", ] - -specific_include_rules = { - "test_service_main\.cc": [ - "+services/service_manager/public/c", - ] -} diff --git a/chromium/components/printing/service/pdf_compositor_impl.cc b/chromium/components/printing/service/pdf_compositor_impl.cc index c22998a7bc9..212514a8ee4 100644 --- a/chromium/components/printing/service/pdf_compositor_impl.cc +++ b/chromium/components/printing/service/pdf_compositor_impl.cc @@ -10,6 +10,7 @@ #include "base/logging.h" #include "base/memory/shared_memory.h" #include "base/memory/shared_memory_handle.h" +#include "components/printing/service/public/cpp/pdf_service_mojo_utils.h" #include "mojo/public/cpp/system/platform_handle.h" #include "printing/common/pdf_metafile_utils.h" #include "third_party/skia/include/core/SkCanvas.h" @@ -30,25 +31,10 @@ void PdfCompositorImpl::CompositePdf( mojom::PdfCompositor::CompositePdfCallback callback) { DCHECK(sk_handle.is_valid()); - base::SharedMemoryHandle memory_handle; - size_t memory_size = 0; - bool read_only_flag = false; - - const MojoResult result = mojo::UnwrapSharedMemoryHandle( - std::move(sk_handle), &memory_handle, &memory_size, &read_only_flag); - DCHECK_EQ(MOJO_RESULT_OK, result); - DCHECK_GT(memory_size, 0u); - std::unique_ptr<base::SharedMemory> shm = - base::MakeUnique<base::SharedMemory>(memory_handle, true); - if (!shm->Map(memory_size)) { - DLOG(ERROR) << "CompositePdf: Shared memory map failed."; - std::move(callback).Run(mojom::PdfCompositor::Status::HANDLE_MAP_ERROR, - mojo::ScopedSharedBufferHandle()); - return; - } + GetShmFromMojoHandle(std::move(sk_handle)); - SkMemoryStream stream(shm->memory(), memory_size); + SkMemoryStream stream(shm->memory(), shm->mapped_size()); int page_count = SkMultiPictureDocumentReadPageCount(&stream); if (!page_count) { DLOG(ERROR) << "CompositePdf: No page is read."; diff --git a/chromium/components/printing/service/pdf_compositor_service_unittest.cc b/chromium/components/printing/service/pdf_compositor_service_unittest.cc index b005a7031ae..3b15e55c6f5 100644 --- a/chromium/components/printing/service/pdf_compositor_service_unittest.cc +++ b/chromium/components/printing/service/pdf_compositor_service_unittest.cc @@ -10,14 +10,71 @@ #include "base/memory/shared_memory.h" #include "base/path_service.h" #include "base/run_loop.h" +#include "base/test/test_discardable_memory_allocator.h" +#include "components/printing/service/pdf_compositor_service.h" #include "components/printing/service/public/interfaces/pdf_compositor.mojom.h" +#include "mojo/public/cpp/bindings/binding_set.h" #include "mojo/public/cpp/system/platform_handle.h" +#include "services/service_manager/public/cpp/binder_registry.h" +#include "services/service_manager/public/cpp/service_context.h" #include "services/service_manager/public/cpp/service_test.h" +#include "services/service_manager/public/interfaces/service_factory.mojom.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" namespace printing { +// In order to test PdfCompositorService, this class overrides PrepareToStart() +// to do nothing. So the test discardable memory allocator set up by +// PdfCompositorServiceTest will be used. +class PdfCompositorTestService : public printing::PdfCompositorService { + public: + explicit PdfCompositorTestService(const std::string& creator) + : PdfCompositorService(creator) {} + ~PdfCompositorTestService() override {} + + // PdfCompositorService: + void PrepareToStart() override {} +}; + +class PdfServiceTestClient : public service_manager::test::ServiceTestClient, + public service_manager::mojom::ServiceFactory { + public: + explicit PdfServiceTestClient(service_manager::test::ServiceTest* test) + : service_manager::test::ServiceTestClient(test) { + registry_.AddInterface<service_manager::mojom::ServiceFactory>( + base::Bind(&PdfServiceTestClient::Create, base::Unretained(this))); + } + ~PdfServiceTestClient() override {} + + // service_manager::Service + void OnBindInterface(const service_manager::BindSourceInfo& source_info, + const std::string& interface_name, + mojo::ScopedMessagePipeHandle interface_pipe) override { + registry_.BindInterface(interface_name, std::move(interface_pipe)); + } + + // service_manager::mojom::ServiceFactory + void CreateService(service_manager::mojom::ServiceRequest request, + const std::string& name) override { + if (!name.compare(mojom::kServiceName)) { + service_context_ = std::make_unique<service_manager::ServiceContext>( + std::make_unique<PdfCompositorTestService>("pdf_compositor_unittest"), + std::move(request)); + } + } + + void Create(service_manager::mojom::ServiceFactoryRequest request) { + service_factory_bindings_.AddBinding(this, std::move(request)); + } + + private: + service_manager::BinderRegistry registry_; + mojo::BindingSet<service_manager::mojom::ServiceFactory> + service_factory_bindings_; + std::unique_ptr<service_manager::ServiceContext> service_context_; +}; + class PdfCompositorServiceTest : public service_manager::test::ServiceTest { public: PdfCompositorServiceTest() : ServiceTest("pdf_compositor_service_unittest") {} @@ -39,18 +96,25 @@ class PdfCompositorServiceTest : public service_manager::test::ServiceTest { protected: // service_manager::test::ServiceTest: void SetUp() override { + base::DiscardableMemoryAllocator::SetInstance( + &discardable_memory_allocator_); ServiceTest::SetUp(); ASSERT_FALSE(compositor_); connector()->BindInterface(mojom::kServiceName, &compositor_); ASSERT_TRUE(compositor_); - run_loop_ = base::MakeUnique<base::RunLoop>(); + run_loop_ = std::make_unique<base::RunLoop>(); } void TearDown() override { // Clean up compositor_.reset(); + base::DiscardableMemoryAllocator::SetInstance(nullptr); + } + + std::unique_ptr<service_manager::Service> CreateService() override { + return std::make_unique<PdfServiceTestClient>(this); } base::SharedMemoryHandle LoadFileInSharedMemory() { @@ -69,9 +133,7 @@ class PdfCompositorServiceTest : public service_manager::test::ServiceTest { base::SharedMemory shared_memory; if (shared_memory.Create(options) && shared_memory.Map(len)) { memcpy(shared_memory.memory(), content.data(), len); - base::SharedMemoryHandle handle = shared_memory.handle(); - if (len == handle.GetSize()) - return base::SharedMemory::DuplicateHandle(handle); + return base::SharedMemory::DuplicateHandle(shared_memory.handle()); } return invalid_handle; } @@ -91,6 +153,7 @@ class PdfCompositorServiceTest : public service_manager::test::ServiceTest { std::unique_ptr<base::RunLoop> run_loop_; mojom::PdfCompositorPtr compositor_; + base::TestDiscardableMemoryAllocator discardable_memory_allocator_; private: DISALLOW_COPY_AND_ASSIGN(PdfCompositorServiceTest); @@ -98,19 +161,11 @@ class PdfCompositorServiceTest : public service_manager::test::ServiceTest { // Test callback is called on error conditions in service. TEST_F(PdfCompositorServiceTest, InvokeCallbackOnContentError) { - auto handle = LoadFileInSharedMemory(); - ASSERT_TRUE(handle.IsValid()); - mojo::ScopedSharedBufferHandle buffer_handle = - mojo::WrapSharedMemoryHandle(handle, 10, true); - // The size of mapped area is not equal to the original buffer, - // so the content is invalid. - ASSERT_LT(10u, handle.GetSize()); - ASSERT_TRUE(buffer_handle->is_valid()); EXPECT_CALL(*this, CallbackOnError( mojom::PdfCompositor::Status::CONTENT_FORMAT_ERROR)) .Times(1); compositor_->CompositePdf( - std::move(buffer_handle), + mojo::SharedBufferHandle::Create(10), base::BindOnce(&PdfCompositorServiceTest::OnCallback, base::Unretained(this))); run_loop_->Run(); diff --git a/chromium/components/printing/service/public/cpp/BUILD.gn b/chromium/components/printing/service/public/cpp/BUILD.gn index f0c9b84f773..83110a4b6bd 100644 --- a/chromium/components/printing/service/public/cpp/BUILD.gn +++ b/chromium/components/printing/service/public/cpp/BUILD.gn @@ -33,3 +33,14 @@ source_set("factory") { "//services/service_manager/public/cpp", ] } + +source_set("utils") { + sources = [ + "pdf_service_mojo_utils.cc", + "pdf_service_mojo_utils.h", + ] + + public_deps = [ + "//mojo/public/cpp/system:system", + ] +} diff --git a/chromium/components/printing/service/public/cpp/pdf_service_mojo_utils.cc b/chromium/components/printing/service/public/cpp/pdf_service_mojo_utils.cc new file mode 100644 index 00000000000..f5f6c890b03 --- /dev/null +++ b/chromium/components/printing/service/public/cpp/pdf_service_mojo_utils.cc @@ -0,0 +1,46 @@ +// Copyright 2017 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/printing/service/public/cpp/pdf_service_mojo_utils.h" + +#include "base/memory/ref_counted_memory.h" +#include "base/memory/shared_memory.h" +#include "mojo/public/cpp/system/platform_handle.h" + +namespace printing { + +std::unique_ptr<base::SharedMemory> GetShmFromMojoHandle( + mojo::ScopedSharedBufferHandle handle) { + base::SharedMemoryHandle memory_handle; + size_t memory_size = 0; + bool read_only_flag = false; + + const MojoResult result = mojo::UnwrapSharedMemoryHandle( + std::move(handle), &memory_handle, &memory_size, &read_only_flag); + if (result != MOJO_RESULT_OK) + return nullptr; + DCHECK_GT(memory_size, 0u); + + std::unique_ptr<base::SharedMemory> shm = + std::make_unique<base::SharedMemory>(memory_handle, read_only_flag); + if (!shm->Map(memory_size)) { + DLOG(ERROR) << "Map shared memory failed."; + return nullptr; + } + return shm; +} + +scoped_refptr<base::RefCountedBytes> GetDataFromMojoHandle( + mojo::ScopedSharedBufferHandle handle) { + std::unique_ptr<base::SharedMemory> shm = + GetShmFromMojoHandle(std::move(handle)); + if (!shm) + return nullptr; + + return base::MakeRefCounted<base::RefCountedBytes>( + reinterpret_cast<const unsigned char*>(shm->memory()), + shm->mapped_size()); +} + +} // namespace printing diff --git a/chromium/components/printing/service/public/cpp/pdf_service_mojo_utils.h b/chromium/components/printing/service/public/cpp/pdf_service_mojo_utils.h new file mode 100644 index 00000000000..11a2ebed268 --- /dev/null +++ b/chromium/components/printing/service/public/cpp/pdf_service_mojo_utils.h @@ -0,0 +1,28 @@ +// Copyright 2017 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef COMPONENTS_PRINTING_SERVICE_PUBLIC_CPP_PDF_SERVICE_MOJO_UTILS_H_ +#define COMPONENTS_PRINTING_SERVICE_PUBLIC_CPP_PDF_SERVICE_MOJO_UTILS_H_ + +#include <memory> + +#include "base/memory/scoped_refptr.h" +#include "mojo/public/cpp/system/buffer.h" + +namespace base { +class RefCountedBytes; +class SharedMemory; +} // namespace base + +namespace printing { + +std::unique_ptr<base::SharedMemory> GetShmFromMojoHandle( + mojo::ScopedSharedBufferHandle handle); + +scoped_refptr<base::RefCountedBytes> GetDataFromMojoHandle( + mojo::ScopedSharedBufferHandle handle); + +} // namespace printing + +#endif // COMPONENTS_PRINTING_SERVICE_PUBLIC_CPP_PDF_SERVICE_MOJO_UTILS_H_ diff --git a/chromium/components/printing/service/test_service_main.cc b/chromium/components/printing/service/test_service_main.cc deleted file mode 100644 index dd8b2c464c3..00000000000 --- a/chromium/components/printing/service/test_service_main.cc +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/test/test_discardable_memory_allocator.h" -#include "components/printing/service/pdf_compositor_service.h" -#include "services/service_manager/public/c/main.h" -#include "services/service_manager/public/cpp/service_runner.h" - -// In order to test PdfCompositorService, this class overrides and -// uses a test discardable memory allocator. -class PdfCompositorTestService : public printing::PdfCompositorService { - public: - explicit PdfCompositorTestService(const std::string& creator) - : PdfCompositorService(creator) {} - ~PdfCompositorTestService() override {} - - // PdfCompositorService: - void PrepareToStart() override; - - private: - base::TestDiscardableMemoryAllocator mem_allocator_; -}; - -void PdfCompositorTestService::PrepareToStart() { - base::DiscardableMemoryAllocator::SetInstance(&mem_allocator_); -} - -MojoResult ServiceMain(MojoHandle service_request_handle) { - service_manager::ServiceRunner runner( - new PdfCompositorTestService("pdf_compositor_service_unittest")); - return runner.Run(service_request_handle); -} |