Bug 1290904 - Fix assertion failure on removing/adding a fieldsets on a nested fieldset; r?smaug draft
authorEdgar Chen <echen@mozilla.com>
Fri, 04 Nov 2016 14:38:19 +0800
changeset 434235 2ce2fa8b854cccc45da637586f388a2e69146347
parent 433968 b9116948bbe44a2ee69774b366b44ef4ac3e2a26
child 536050 722fb88866c330dfa2031d36b96f34a6e7657fa3
push id34751
push userechen@mozilla.com
push dateSat, 05 Nov 2016 06:07:19 +0000
reviewerssmaug
bugs1290904
milestone52.0a1
Bug 1290904 - Fix assertion failure on removing/adding a fieldsets on a nested fieldset; r?smaug MozReview-Commit-ID: LVoz6Y0BWDN
dom/html/HTMLFieldSetElement.cpp
dom/html/crashtests/1290904.html
dom/html/crashtests/crashtests.list
--- a/dom/html/HTMLFieldSetElement.cpp
+++ b/dom/html/HTMLFieldSetElement.cpp
@@ -219,24 +219,18 @@ void
 HTMLFieldSetElement::AddElement(nsGenericHTMLFormElement* aElement)
 {
   mDependentElements.AppendElement(aElement);
 
   // If the element that we are adding aElement is a fieldset, then all the
   // invalid elements in aElement are also invalid elements of this.
   HTMLFieldSetElement* fieldSet = FromContent(aElement);
   if (fieldSet) {
-    if (fieldSet->mInvalidElementsCount > 0) {
-      // The order we call UpdateValidity and adjust mInvalidElementsCount is
-      // important. We need to first call UpdateValidity in case
-      // mInvalidElementsCount was 0 before the call and will be incremented to
-      // 1 and so we need to change state to invalid. After that is done, we
-      // are free to increment mInvalidElementsCount to the correct amount.
+    for (int32_t i = 0; i < fieldSet->mInvalidElementsCount; i++) {
       UpdateValidity(false);
-      mInvalidElementsCount += fieldSet->mInvalidElementsCount - 1;
     }
     return;
   }
 
   // We need to update the validity of the fieldset.
   nsCOMPtr<nsIConstraintValidation> cvElmt = do_QueryObject(aElement);
   if (cvElmt &&
       cvElmt->IsCandidateForConstraintValidation() && !cvElmt->IsValid()) {
@@ -267,22 +261,17 @@ void
 HTMLFieldSetElement::RemoveElement(nsGenericHTMLFormElement* aElement)
 {
   mDependentElements.RemoveElement(aElement);
 
   // If the element that we are removing aElement is a fieldset, then all the
   // invalid elements in aElement are also removed from this.
   HTMLFieldSetElement* fieldSet = FromContent(aElement);
   if (fieldSet) {
-    if (fieldSet->mInvalidElementsCount > 0) {
-      // The order we update mInvalidElementsCount and call UpdateValidity is
-      // important. We need to first decrement mInvalidElementsCount and then
-      // call UpdateValidity, in case mInvalidElementsCount hits 0 in the call
-      // of UpdateValidity and we have to change state to valid.
-      mInvalidElementsCount -= fieldSet->mInvalidElementsCount - 1;
+    for (int32_t i = 0; i < fieldSet->mInvalidElementsCount; i++) {
       UpdateValidity(true);
     }
     return;
   }
 
   // We need to update the validity of the fieldset.
   nsCOMPtr<nsIConstraintValidation> cvElmt = do_QueryObject(aElement);
   if (cvElmt &&
new file mode 100644
--- /dev/null
+++ b/dom/html/crashtests/1290904.html
@@ -0,0 +1,37 @@
+<!DOCTYPE html>
+<html>
+  <body>
+    <fieldset id="outer">
+      <fieldset id="inner">
+      </fieldset>
+    </fieldset>
+  </body>
+</html>
+<script>
+function appendTextareaToFieldset(fieldset) {
+  var textarea = document.createElement("textarea");
+  textarea.setAttribute("required", "");
+  fieldset.appendChild(textarea);
+}
+
+var innerFieldset = document.getElementById('inner');
+var outerFieldset = document.getElementById('outer');
+
+var fieldset = document.createElement('fieldset');
+appendTextareaToFieldset(fieldset);
+appendTextareaToFieldset(fieldset);
+appendTextareaToFieldset(fieldset);
+appendTextareaToFieldset(fieldset);
+
+// Adding a fieldset to a nested fieldset.
+innerFieldset.appendChild(fieldset);
+appendTextareaToFieldset(fieldset);
+appendTextareaToFieldset(fieldset);
+// This triggers mInvalidElementsCount checks in outer fieldset.
+appendTextareaToFieldset(outerFieldset);
+
+// Removing a fieldset from a nested fieldset.
+innerFieldset.removeChild(fieldset);
+// This triggers mInvalidElementsCount checks in outer fieldset.
+appendTextareaToFieldset(outerFieldset);
+</script>
--- a/dom/html/crashtests/crashtests.list
+++ b/dom/html/crashtests/crashtests.list
@@ -71,9 +71,10 @@ load 903106.html
 load 916322-1.html
 load 916322-2.html
 load 1032654.html
 load 1141260.html
 load 1228876.html
 load 1230110.html
 load 1237633.html
 load 1281972-1.html
-load 1282894.html
\ No newline at end of file
+load 1282894.html
+load 1290904.html
\ No newline at end of file