Bug 1460509 - part 77: Make HTMLEditRules::MoveNodeSmart() return NS_ERROR_EDITOR_DESTROYED if it causes destroying the editor r?m_kato draft
authorMasayuki Nakano <masayuki@d-toybox.com>
Fri, 18 May 2018 00:02:00 +0900
changeset 798795 97f28b39d4d325c7f74c0a1f24118e9a65fa4e87
parent 798794 42b5fcdcebaef787f5746fe750a1f8df5f5ad84c
child 798796 f5c3002d1913b0adb7bffccae797e61a0a3d8b2f
push id110840
push usermasayuki@d-toybox.com
push dateWed, 23 May 2018 13:41:58 +0000
reviewersm_kato
bugs1460509
milestone62.0a1
Bug 1460509 - part 77: Make HTMLEditRules::MoveNodeSmart() return NS_ERROR_EDITOR_DESTROYED if it causes destroying the editor r?m_kato MozReview-Commit-ID: D9mgBt2ftuz
editor/libeditor/HTMLEditRules.cpp
editor/libeditor/HTMLEditRules.h
--- a/editor/libeditor/HTMLEditRules.cpp
+++ b/editor/libeditor/HTMLEditRules.cpp
@@ -3708,16 +3708,21 @@ HTMLEditRules::MoveBlock(Element& aLeftB
       rv = HTMLEditorRef().DeleteNodeWithTransaction(*arrayOfNodes[i]);
       NS_WARNING_ASSERTION(NS_SUCCEEDED(rv),
         "Failed to remove a block node");
       ret.MarkAsHandled();
     } else {
       // Otherwise move the content as is, checking against the DTD.
       ret |=
         MoveNodeSmart(*arrayOfNodes[i]->AsContent(), aLeftBlock, &aLeftOffset);
+      if (NS_WARN_IF(ret.Rv() == NS_ERROR_EDITOR_DESTROYED)) {
+        return ret;
+      }
+      NS_WARNING_ASSERTION(NS_SUCCEEDED(rv),
+        "Failed to move current node to the left block");
     }
   }
 
   // XXX We're only checking return value of the last iteration
   if (NS_WARN_IF(ret.Failed())) {
     return ret;
   }
 
@@ -3733,23 +3738,29 @@ HTMLEditRules::MoveNodeSmart(nsIContent&
   MOZ_ASSERT(aInOutDestOffset);
 
   // Check if this node can go into the destination node
   if (HTMLEditorRef().CanContain(aDestElement, aNode)) {
     // If it can, move it there.
     if (*aInOutDestOffset == -1) {
       nsresult rv =
         HTMLEditorRef().MoveNodeToEndWithTransaction(aNode, aDestElement);
+      if (NS_WARN_IF(!CanHandleEditAction())) {
+        return EditActionIgnored(NS_ERROR_EDITOR_DESTROYED);
+      }
       if (NS_WARN_IF(NS_FAILED(rv))) {
         return EditActionIgnored(rv);
       }
     } else {
       EditorRawDOMPoint pointToInsert(&aDestElement, *aInOutDestOffset);
       nsresult rv =
         HTMLEditorRef().MoveNodeWithTransaction(aNode, pointToInsert);
+      if (NS_WARN_IF(!CanHandleEditAction())) {
+        return EditActionIgnored(NS_ERROR_EDITOR_DESTROYED);
+      }
       if (NS_WARN_IF(NS_FAILED(rv))) {
         return EditActionIgnored(rv);
       }
     }
     if (*aInOutDestOffset != -1) {
       (*aInOutDestOffset)++;
     }
     // XXX Should we check if the node is actually moved in this case?
@@ -3761,16 +3772,19 @@ HTMLEditRules::MoveNodeSmart(nsIContent&
   if (aNode.IsElement()) {
     ret = MoveContents(*aNode.AsElement(), aDestElement, aInOutDestOffset);
     if (NS_WARN_IF(ret.Failed())) {
       return ret;
     }
   }
 
   nsresult rv = HTMLEditorRef().DeleteNodeWithTransaction(aNode);
+  if (NS_WARN_IF(!CanHandleEditAction())) {
+    return ret.SetResult(NS_ERROR_EDITOR_DESTROYED);
+  }
   if (NS_WARN_IF(NS_FAILED(rv))) {
     return ret.SetResult(rv);
   }
   return ret.MarkAsHandled();
 }
 
 EditActionResult
 HTMLEditRules::MoveContents(Element& aElement,
--- a/editor/libeditor/HTMLEditRules.h
+++ b/editor/libeditor/HTMLEditRules.h
@@ -306,18 +306,19 @@ protected:
    * MoveNodeSmart() moves aNode to (aDestElement, aInOutDestOffset).
    * DTD containment rules are followed throughout.
    *
    * @param aOffset                 returns the point after inserted content.
    * @return                        Sets true to handled if this actually moves
    *                                the nodes.
    *                                canceled is always false.
    */
-  EditActionResult MoveNodeSmart(nsIContent& aNode, Element& aDestElement,
-                                 int32_t* aInOutDestOffset);
+  MOZ_MUST_USE EditActionResult
+  MoveNodeSmart(nsIContent& aNode, Element& aDestElement,
+                int32_t* aInOutDestOffset);
 
   /**
    * MoveContents() moves the contents of aElement to (aDestElement,
    * aInOutDestOffset).  DTD containment rules are followed throughout.
    *
    * @param aInOutDestOffset        updated to point after inserted content.
    * @return                        Sets true to handled if this actually moves
    *                                the nodes.