Bug 1770539 p9 - Move nsPrintData::mPrintObject to nsPrintJob. r=emilio
authorJonathan Watt <jwatt@jwatt.org>
Sun, 22 May 2022 09:37:58 +0000
changeset 618501 d0bb4f6201a04831e67ba1f1f4591d96586fd8f0
parent 618500 853cf247e8703644e30a20956eaf14b091efa6f9
child 618504 0a002a56525bf101a39fadcba190d053dcedd10c
push id163296
push userjwatt@jwatt.org
push dateSun, 22 May 2022 09:41:02 +0000
treeherderautoland@d0bb4f6201a0 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersemilio
bugs1770539
milestone102.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1770539 p9 - Move nsPrintData::mPrintObject to nsPrintJob. r=emilio Differential Revision: https://phabricator.services.mozilla.com/D146980
layout/printing/nsPrintData.h
layout/printing/nsPrintJob.cpp
layout/printing/nsPrintJob.h
--- a/layout/printing/nsPrintData.h
+++ b/layout/printing/nsPrintData.h
@@ -33,18 +33,16 @@ class nsPrintData {
   void DoOnProgressChange(int32_t aProgress, int32_t aMaxProgress,
                           bool aDoStartStop, int32_t aFlag);
 
   void DoOnStatusChange(nsresult aStatus);
 
   ePrintDataType mType;  // the type of data this is (Printing or Print Preview)
   RefPtr<nsDeviceContext> mPrintDC;
 
-  mozilla::UniquePtr<nsPrintObject> mPrintObject;
-
   nsCOMArray<nsIWebProgressListener> mPrintProgressListeners;
 
   bool mOnStartSent;
   bool mIsAborted;  // tells us the document is being aborted
 
  private:
   nsPrintData() = delete;
   nsPrintData& operator=(const nsPrintData& aOther) = delete;
--- a/layout/printing/nsPrintJob.cpp
+++ b/layout/printing/nsPrintJob.cpp
@@ -130,19 +130,19 @@ static void DumpPrintObjectsListStart(co
 static void DumpPrintObjectsTree(nsPrintObject* aPO, int aLevel = 0,
                                  FILE* aFD = nullptr);
 static void DumpPrintObjectsTreeLayout(const UniquePtr<nsPrintObject>& aPO,
                                        nsDeviceContext* aDC, int aLevel = 0,
                                        FILE* aFD = nullptr);
 
 #  define DUMP_DOC_LIST(_title) \
     DumpPrintObjectsListStart((_title), mPrintDocList);
-#  define DUMP_DOC_TREE DumpPrintObjectsTree(mPrt->mPrintObject.get());
+#  define DUMP_DOC_TREE DumpPrintObjectsTree(mPrintObject.get());
 #  define DUMP_DOC_TREELAYOUT \
-    DumpPrintObjectsTreeLayout(mPrt->mPrintObject, mPrt->mPrintDC);
+    DumpPrintObjectsTreeLayout(mPrintObject, mPrt->mPrintDC);
 #else
 #  define DUMP_DOC_LIST(_title)
 #  define DUMP_DOC_TREE
 #  define DUMP_DOC_TREELAYOUT
 #endif
 
 // -------------------------------------------------------
 // Helpers
@@ -164,17 +164,17 @@ void nsPrintJob::BuildNestedPrintObjects
   if (aParentPO->mFrameType == eIFrame &&
       aParentPO->mDocument->GetProperty(nsGkAtoms::printisfocuseddoc)) {
     mSelectionRoot = aParentPO.get();
   } else if (!mSelectionRoot && aParentPO->HasSelection()) {
     // If there is no focused iframe but there is a selection in one or more
     // frames then we want to set the root nsPrintObject as the focus root so
     // that later EnablePrintingSelectionOnly can search for and enable all
     // nsPrintObjects containing selections.
-    mSelectionRoot = mPrt->mPrintObject.get();
+    mSelectionRoot = mPrintObject.get();
   }
 
   for (auto& bc : aParentPO->mDocShell->GetBrowsingContext()->Children()) {
     nsCOMPtr<nsIDocShell> docShell = bc->GetDocShell();
     if (!docShell) {
       if (auto* cc = dom::ContentChild::GetSingleton()) {
         nsCOMPtr<nsIPrintSettingsService> printSettingsService =
             do_GetService(sPrintSettingsServiceContractID);
@@ -240,17 +240,20 @@ void nsPrintJob::Destroy() {
   mIsDestroying = true;
 
   DestroyPrintingData();
 
   mDocViewerPrint = nullptr;
 }
 
 //-------------------------------------------------------
-void nsPrintJob::DestroyPrintingData() { mPrt = nullptr; }
+void nsPrintJob::DestroyPrintingData() {
+  mPrintObject = nullptr;
+  mPrt = nullptr;
+}
 
 //---------------------------------------------------------------------------------
 //-- Section: Methods needed by the DocViewer
 //---------------------------------------------------------------------------------
 
 //--------------------------------------------------------
 nsresult nsPrintJob::Initialize(nsIDocumentViewerPrint* aDocViewerPrint,
                                 nsIDocShell* aDocShell, Document* aOriginalDoc,
@@ -286,17 +289,17 @@ nsresult nsPrintJob::Initialize(nsIDocum
 
 //-----------------------------------------------------------------
 std::tuple<nsPageSequenceFrame*, int32_t>
 nsPrintJob::GetSeqFrameAndCountSheets() const {
   if (NS_WARN_IF(!mPrt)) {
     return {nullptr, 0};
   }
 
-  const nsPrintObject* po = mPrt->mPrintObject.get();
+  const nsPrintObject* po = mPrintObject.get();
   if (NS_WARN_IF(!po)) {
     return {nullptr, 0};
   }
 
   // This is sometimes incorrectly called before the pres shell has been created
   // (bug 1141756). MOZ_DIAGNOSTIC_ASSERT so we'll still see the crash in
   // Nightly/Aurora in case the other patch fixes this.
   if (!po->mPresShell) {
@@ -402,39 +405,38 @@ nsresult nsPrintJob::DoCommonPrint(bool 
   // if they don't pass in a PrintSettings, then get the Global PS
   mPrintSettings = aPrintSettings;
   if (!mPrintSettings) {
     MOZ_TRY(GetDefaultPrintSettings(getter_AddRefs(mPrintSettings)));
   }
 
   {
     nsAutoScriptBlocker scriptBlocker;
-    printData->mPrintObject = MakeUnique<nsPrintObject>();
-    rv = printData->mPrintObject->InitAsRootObject(docShell, aDoc,
-                                                   mIsCreatingPrintPreview);
+    mPrintObject = MakeUnique<nsPrintObject>();
+    rv =
+        mPrintObject->InitAsRootObject(docShell, aDoc, mIsCreatingPrintPreview);
     NS_ENSURE_SUCCESS(rv, rv);
 
-    mPrintDocList.AppendElement(printData->mPrintObject.get());
+    mPrintDocList.AppendElement(mPrintObject.get());
 
-    printData->mPrintObject->mFrameType = eDoc;
+    mPrintObject->mFrameType = eDoc;
 
-    BuildNestedPrintObjects(printData->mPrintObject);
+    BuildNestedPrintObjects(mPrintObject);
   }
 
   // The nsAutoScriptBlocker above will now have been destroyed, which may
   // cause our print/print-preview operation to finish. In this case, we
   // should immediately return an error code so that the root caller knows
   // it shouldn't continue to do anything with this instance.
   if (mIsDestroying) {
     return NS_ERROR_FAILURE;
   }
 
   // XXX This isn't really correct...
-  if (!printData->mPrintObject->mDocument ||
-      !printData->mPrintObject->mDocument->GetRootElement())
+  if (!mPrintObject->mDocument || !mPrintObject->mDocument->GetRootElement())
     return NS_ERROR_GFX_PRINTER_STARTDOC;
 
   mPrintSettings->GetShrinkToFit(&mShrinkToFit);
 
   bool printingViaParent =
       XRE_IsContentProcess() && StaticPrefs::print_print_via_parent();
   nsCOMPtr<nsIDeviceContextSpec> devspec;
   if (printingViaParent) {
@@ -769,47 +771,46 @@ nsresult nsPrintJob::ReconstructAndReflo
 }
 
 //-------------------------------------------------------
 nsresult nsPrintJob::SetupToPrintContent() {
   // This method may be called while DoCommonPrint() initializes the instance
   // when its script blocker goes out of scope.  In such case, this cannot do
   // its job as expected because some objects in mPrt have not been initialized
   // yet but they are necessary.
-  // Note: it shouldn't be possible for mPrt->mPrintObject to be null; we check
+  // Note: it shouldn't be possible for mPrintObject to be null; we check
   // it for good measure (after we check its owner) before we start
   // dereferencing it below.
-  if (NS_WARN_IF(!mPrt) || NS_WARN_IF(!mPrt->mPrintObject)) {
+  if (NS_WARN_IF(!mPrt) || NS_WARN_IF(!mPrintObject)) {
     return NS_ERROR_FAILURE;
   }
 
-  // If this is creating print preview, mPrt->mPrintObject->mPresContext and
-  // mPrt->mPrintObject->mPresShell need to be non-nullptr because this cannot
+  // If this is creating print preview, mPrintObject->mPresContext and
+  // mPrintObject->mPresShell need to be non-nullptr because this cannot
   // initialize page sequence frame without them at end of this method since
   // page sequence frame has already been destroyed or not been created yet.
-  if (mIsCreatingPrintPreview &&
-      (NS_WARN_IF(!mPrt->mPrintObject->mPresContext) ||
-       NS_WARN_IF(!mPrt->mPrintObject->mPresShell))) {
+  if (mIsCreatingPrintPreview && (NS_WARN_IF(!mPrintObject->mPresContext) ||
+                                  NS_WARN_IF(!mPrintObject->mPresShell))) {
     return NS_ERROR_FAILURE;
   }
 
   // If this is printing some documents (not print-previewing the documents),
-  // mPrt->mPrintObject->mPresContext and mPrt->mPrintObject->mPresShell can be
-  // nullptr only when mPrt->mPrintObject->PrintingIsEnabled() is false.  E.g.,
+  // mPrintObject->mPresContext and mPrintObject->mPresShell can be
+  // nullptr only when mPrintObject->PrintingIsEnabled() is false.  E.g.,
   // if the document has a <frameset> element and it's printing only content in
   // a <frame> element or all <frame> elements separately.
   MOZ_ASSERT(
-      (!mIsCreatingPrintPreview && !mPrt->mPrintObject->PrintingIsEnabled()) ||
-          (mPrt->mPrintObject->mPresContext && mPrt->mPrintObject->mPresShell),
+      (!mIsCreatingPrintPreview && !mPrintObject->PrintingIsEnabled()) ||
+          (mPrintObject->mPresContext && mPrintObject->mPresShell),
       "mPresContext and mPresShell shouldn't be nullptr when printing the "
       "document or creating print-preview");
 
   bool didReconstruction = false;
 
-  // This method works with mPrt->mPrintObject.  So, we need to guarantee that
+  // This method works with mPrintObject.  So, we need to guarantee that
   // it won't be deleted in this method.  We achieve this by holding a strong
   // local reference to mPrt, which in turn keeps mPrintObject alive.
   RefPtr<nsPrintData> printData = mPrt;
 
   // If some new content got loaded since the initial reflow rebuild
   // everything.
   if (mDidLoadDataForPrinting) {
     nsresult rv = ReconstructAndReflow();
@@ -822,33 +823,33 @@ nsresult nsPrintJob::SetupToPrintContent
       return NS_ERROR_FAILURE;
     }
     didReconstruction = true;
   }
 
   // Here is where we figure out if extra reflow for shrinking the content
   // is required.
   if (mShrinkToFit) {
-    mShrinkToFitFactor = printData->mPrintObject->mShrinkRatio;
+    mShrinkToFitFactor = mPrintObject->mShrinkRatio;
 
     if (mShrinkToFitFactor < 0.998f) {
       nsresult rv = ReconstructAndReflow();
       if (NS_WARN_IF(NS_FAILED(rv))) {
         return rv;
       }
       // If the printing was canceled or restarted with different data,
       // let's stop doing this printing.
       if (NS_WARN_IF(mPrt != printData)) {
         return NS_ERROR_FAILURE;
       }
       didReconstruction = true;
     }
 
     if (MOZ_LOG_TEST(gPrintingLog, LogLevel::Debug)) {
-      float calcRatio = printData->mPrintObject->mShrinkRatio;
+      float calcRatio = mPrintObject->mShrinkRatio;
       PR_PL(
           ("*******************************************************************"
            "*******\n"));
       PR_PL(("STF Ratio is: %8.5f Effective Ratio: %8.5f Diff: %8.5f\n",
              mShrinkToFitFactor, calcRatio, mShrinkToFitFactor - calcRatio));
       PR_PL(
           ("*******************************************************************"
            "*******\n"));
@@ -890,17 +891,17 @@ nsresult nsPrintJob::SetupToPrintContent
   if (mPrintSettings->GetOutputDestination() ==
       nsIPrintSettings::kOutputDestinationFile) {
     // On some platforms the BeginDocument needs to know the name of the file.
     mPrintSettings->GetToFileName(fileNameStr);
   }
 
   nsAutoString docTitleStr;
   nsAutoString docURLStr;
-  GetDisplayTitleAndURL(*printData->mPrintObject->mDocument, mPrintSettings,
+  GetDisplayTitleAndURL(*mPrintObject->mDocument, mPrintSettings,
                         DocTitleDefault::eDocURLElseFallback, docTitleStr,
                         docURLStr);
 
   int32_t startPage = 1;
   int32_t endPage = mNumPrintablePages;
 
   nsTArray<int32_t> ranges;
   mPrintSettings->GetPageRanges(ranges);
@@ -918,20 +919,20 @@ nsresult nsPrintJob::SetupToPrintContent
     rv = printData->mPrintDC->BeginDocument(docTitleStr, fileNameStr, startPage,
                                             endPage);
   }
 
   if (mIsCreatingPrintPreview) {
     // Copy docTitleStr and docURLStr to the pageSequenceFrame, to be displayed
     // in the header
     nsPageSequenceFrame* seqFrame =
-        printData->mPrintObject->mPresShell->GetPageSequenceFrame();
+        mPrintObject->mPresShell->GetPageSequenceFrame();
     if (seqFrame) {
-      seqFrame->StartPrint(printData->mPrintObject->mPresContext,
-                           mPrintSettings, docTitleStr, docURLStr);
+      seqFrame->StartPrint(mPrintObject->mPresContext, mPrintSettings,
+                           docTitleStr, docURLStr);
     }
   }
 
   PR_PL(("****************** Begin Document ************************\n"));
 
   if (NS_FAILED(rv)) {
     NS_WARNING_ASSERTION(rv == NS_ERROR_ABORT,
                          "Failed to begin document for printing");
@@ -939,17 +940,17 @@ nsresult nsPrintJob::SetupToPrintContent
   }
 
   // This will print the docshell document
   // when it completes asynchronously in the DonePrintingSheets method
   // it will check to see if there are more docshells to be printed and
   // then PrintDocContent will be called again.
 
   if (mIsDoingPrinting) {
-    PrintDocContent(printData->mPrintObject, rv);  // ignore return value
+    PrintDocContent(mPrintObject, rv);  // ignore return value
   }
 
   return rv;
 }
 
 //-------------------------------------------------------
 // Recursively reflow each sub-doc and then calc
 // all the frame locations of the sub-docs
@@ -986,50 +987,49 @@ void nsPrintJob::FirePrintPreviewUpdateE
     nsCOMPtr<nsIContentViewer> cv = do_QueryInterface(mDocViewerPrint);
     (new AsyncEventDispatcher(cv->GetDocument(), u"printPreviewUpdate"_ns,
                               CanBubble::eYes, ChromeOnlyDispatch::eYes))
         ->RunDOMEventWhenSafe();
   }
 }
 
 nsresult nsPrintJob::InitPrintDocConstruction(bool aHandleError) {
-  // Guarantee that mPrt->mPrintObject won't be deleted.  It's owned by mPrt.
-  // So, we should grab it with local variable.
+  // Guarantee that mPrintObject won't be deleted.
   RefPtr<nsPrintData> printData = mPrt;
 
   if (NS_WARN_IF(!printData)) {
     return NS_ERROR_FAILURE;
   }
 
   // Attach progressListener to catch network requests.
   mDidLoadDataForPrinting = false;
 
   {
     AutoRestore<bool> restore{mDoingInitialReflow};
     mDoingInitialReflow = true;
 
     nsCOMPtr<nsIWebProgress> webProgress =
-        do_QueryInterface(printData->mPrintObject->mDocShell);
+        do_QueryInterface(mPrintObject->mDocShell);
     webProgress->AddProgressListener(static_cast<nsIWebProgressListener*>(this),
                                      nsIWebProgress::NOTIFY_STATE_REQUEST);
 
-    MOZ_TRY(ReflowDocList(printData->mPrintObject));
+    MOZ_TRY(ReflowDocList(mPrintObject));
 
     FirePrintPreviewUpdateEvent();
   }
 
   MaybeResumePrintAfterResourcesLoaded(aHandleError);
   return NS_OK;
 }
 
 bool nsPrintJob::ShouldResumePrint() const {
   if (mDoingInitialReflow) {
     return false;
   }
-  Document* doc = mPrt->mPrintObject->mDocument;
+  Document* doc = mPrintObject->mDocument;
   MOZ_ASSERT(doc);
   NS_ENSURE_TRUE(doc, true);
   nsCOMPtr<nsILoadGroup> lg = doc->GetDocumentLoadGroup();
   NS_ENSURE_TRUE(lg, true);
   bool pending = false;
   nsresult rv = lg->IsPending(&pending);
   NS_ENSURE_SUCCESS(rv, true);
   return !pending;
@@ -1038,27 +1038,27 @@ bool nsPrintJob::ShouldResumePrint() con
 nsresult nsPrintJob::MaybeResumePrintAfterResourcesLoaded(
     bool aCleanupOnError) {
   if (!ShouldResumePrint()) {
     mDidLoadDataForPrinting = true;
     return NS_OK;
   }
   // If Destroy() has already been called, mPtr is nullptr.  Then, the instance
   // needs to do nothing anymore in this method.
-  // Note: it shouldn't be possible for mPrt->mPrintObject to be null; we
+  // Note: it shouldn't be possible for mPrintObject to be null; we
   // just check it for good measure, as we check its owner.
-  // Note: it shouldn't be possible for mPrt->mPrintObject->mDocShell to be
+  // Note: it shouldn't be possible for mPrintObject->mDocShell to be
   // null; we just check it for good measure, as we check its owner.
-  if (!mPrt || NS_WARN_IF(!mPrt->mPrintObject) ||
-      NS_WARN_IF(!mPrt->mPrintObject->mDocShell)) {
+  if (!mPrt || NS_WARN_IF(!mPrintObject) ||
+      NS_WARN_IF(!mPrintObject->mDocShell)) {
     return NS_ERROR_FAILURE;
   }
 
   nsCOMPtr<nsIWebProgress> webProgress =
-      do_QueryInterface(mPrt->mPrintObject->mDocShell);
+      do_QueryInterface(mPrintObject->mDocShell);
 
   webProgress->RemoveProgressListener(
       static_cast<nsIWebProgressListener*>(this));
 
   nsresult rv;
   if (mIsDoingPrinting) {
     rv = DocumentReadyForPrinting();
   } else {
@@ -1880,24 +1880,24 @@ bool nsPrintJob::DonePrintingSheets(nsPr
   // If there is a pageSeqFrame, make sure there are no more printCanvas active
   // that might call |Notify| on the pagePrintTimer after things are cleaned up
   // and printing was marked as being done.
   if (mPageSeqFrame.IsAlive()) {
     nsPageSequenceFrame* pageSeqFrame = do_QueryFrame(mPageSeqFrame.GetFrame());
     pageSeqFrame->ResetPrintCanvasList();
   }
 
-  // Guarantee that mPrt and mPrt->mPrintObject won't be deleted during a
+  // Guarantee that mPrt and mPrintObject won't be deleted during a
   // call of PrintDocContent() and FirePrintCompletionEvent().
   RefPtr<nsPrintData> printData = mPrt;
 
   if (aPO && !printData->mIsAborted) {
     aPO->mHasBeenPrinted = true;
     nsresult rv;
-    bool didPrint = PrintDocContent(printData->mPrintObject, rv);
+    bool didPrint = PrintDocContent(mPrintObject, rv);
     if (NS_SUCCEEDED(rv) && didPrint) {
       PR_PL(
           ("****** In DV::DonePrintingSheets PO: %p (%s) didPrint:%s (Not Done "
            "Printing)\n",
            aPO, gFrameTypesStr[aPO->mFrameType], PRT_YESNO(didPrint)));
       return false;
     }
   }
@@ -1929,17 +1929,17 @@ nsresult nsPrintJob::EnablePOsForPrintin
   if (!printData || !mPrintSettings) {
     return NS_ERROR_FAILURE;
   }
 
   PR_PL(("\n"));
   PR_PL(("********* nsPrintJob::EnablePOsForPrinting *********\n"));
 
   if (!mPrintSettings->GetPrintSelectionOnly()) {
-    printData->mPrintObject->EnablePrinting(true);
+    mPrintObject->EnablePrinting(true);
     return NS_OK;
   }
 
   // This means we are either printing a selected iframe or
   // we are printing the current selection.
   NS_ENSURE_STATE(!mDisallowSelectionPrint && mSelectionRoot);
 
   // If mSelectionRoot is a selected iframe without a selection, then just
@@ -1998,24 +1998,23 @@ nsresult nsPrintJob::FinishPrintPreview(
     return rv;
   }
 
   if (mPrintPreviewCallback) {
     const bool hasSelection = !mDisallowSelectionPrint && mSelectionRoot;
     // Determine if there is a specified page size, and if we should set the
     // paper orientation to match it.
     const Maybe<bool> maybeLandscape =
-        printData->mPrintObject->mPresShell->StyleSet()
-            ->GetDefaultPageOrientation()
-            .map([](StylePageOrientation o) -> bool {
+        mPrintObject->mPresShell->StyleSet()->GetDefaultPageOrientation().map(
+            [](StylePageOrientation o) -> bool {
               return o == StylePageOrientation::Landscape;
             });
     mPrintPreviewCallback(PrintPreviewResultInfo(
         GetPrintPreviewNumSheets(), GetRawNumPages(), GetIsEmpty(),
-        hasSelection, hasSelection && printData->mPrintObject->HasSelection(),
+        hasSelection, hasSelection && mPrintObject->HasSelection(),
         maybeLandscape));
     mPrintPreviewCallback = nullptr;
   }
 
   // At this point we are done preparing everything
   // before it is to be created
 
   printData->OnEndPrinting();
--- a/layout/printing/nsPrintJob.h
+++ b/layout/printing/nsPrintJob.h
@@ -250,16 +250,19 @@ class nsPrintJob final : public nsIWebPr
   // member-data.
   RefPtr<nsPrintData> mPrt;
 
   RefPtr<nsPagePrintTimer> mPagePrintTimer;
 
   // Only set if this nsPrintJob was created for a real print.
   RefPtr<RemotePrintJobChild> mRemotePrintJob;
 
+  // The root print object.
+  mozilla::UniquePtr<nsPrintObject> mPrintObject;
+
   // If there is a focused iframe, mSelectionRoot is set to its nsPrintObject.
   // Otherwise, if there is a selection, it is set to the root nsPrintObject.
   // Otherwise, it is unset.
   nsPrintObject* mSelectionRoot = nullptr;
 
   // Array of non-owning pointers to all the nsPrintObjects owned by this
   // nsPrintJob. This includes mPrintObject, as well as all of its mKids (and
   // their mKids, etc.)