Fix a crash when a form control is in a past naems map of a demoted form element.

Note that we wanted to add the protector in FormAssociatedElement::setForm(),
but we couldn't do it because it is called from the constructor.

BUG=326854
TEST=automated.

Review URL: https://codereview.chromium.org/105693013

git-svn-id: svn://svn.chromium.org/blink/trunk@163680 bbb929c8-8fbe-4397-9dbb-9b2b20218538
diff --git a/LayoutTests/fast/forms/past-names-crash-expected.txt b/LayoutTests/fast/forms/past-names-crash-expected.txt
new file mode 100644
index 0000000..86cf193
--- /dev/null
+++ b/LayoutTests/fast/forms/past-names-crash-expected.txt
@@ -0,0 +1,4 @@
+PASS successfullyParsed is true
+
+TEST COMPLETE
+PASS if not crashed.
diff --git a/LayoutTests/fast/forms/past-names-crash.html b/LayoutTests/fast/forms/past-names-crash.html
new file mode 100644
index 0000000..1e9fd17
--- /dev/null
+++ b/LayoutTests/fast/forms/past-names-crash.html
@@ -0,0 +1,28 @@
+<!DOCTYPE html>
+<html>
+<body>
+<script src="../../resources/js-test.js"></script>
+<div id="container">
+<table>
+<form id="form1">
+<td>
+<input name="q"/>
+<script>
+jsTestIsAsync = true;
+var form1 = document.getElementById("form1");
+var container = document.getElementById("container");
+form1['q'];
+container.innerHTML = '';
+setTimeout(function() {
+    container.insertBefore(form1, null);
+    gc();
+    container.innerHTML = 'PASS if not crashed.';
+    finishJSTest();
+}, 0);
+</script>
+</td>
+</form>
+</table>
+</div>
+</body>
+</html>
diff --git a/Source/core/html/FormAssociatedElement.cpp b/Source/core/html/FormAssociatedElement.cpp
index 5b45b8b..f0d92cb 100644
--- a/Source/core/html/FormAssociatedElement.cpp
+++ b/Source/core/html/FormAssociatedElement.cpp
@@ -122,8 +122,10 @@
 void FormAssociatedElement::formRemovedFromTree(const Node* formRoot)
 {
     ASSERT(m_form);
-    if (toHTMLElement(this)->highestAncestor() != formRoot)
-        setForm(0);
+    if (toHTMLElement(this)->highestAncestor() == formRoot)
+        return;
+    RefPtr<HTMLElement> protector(toHTMLElement(this));
+    setForm(0);
 }
 
 void FormAssociatedElement::setForm(HTMLFormElement* newForm)