]> Cypherpunks repositories - gostls13.git/commitdiff
html: handle end tags in foreign objects.
authorNigel Tao <nigeltao@golang.org>
Thu, 15 Dec 2011 22:36:50 +0000 (09:36 +1100)
committerNigel Tao <nigeltao@golang.org>
Thu, 15 Dec 2011 22:36:50 +0000 (09:36 +1100)
I'm not 100% sure I get all the corner cases right, for end tags, but
I'll let the test suite smoke it out.

Pass tests10.dat, test 1:
<!DOCTYPE html><svg></svg><![CDATA[a]]>

| <!DOCTYPE html>
| <html>
|   <head>
|   <body>
|     <svg svg>
|     <!-- [CDATA[a]] -->

Also pass tests through test 5:
<!DOCTYPE html><body><table><svg></svg></table>

R=andybalholm
CC=golang-dev
https://golang.org/cl/5495044

src/pkg/html/const.go
src/pkg/html/parse.go
src/pkg/html/parse_test.go

index 832e9dbc096677bf0e40b2562fcfbe1c41920dde..d7cc8bb9a9931f33a925b98c3a2930ddf112bf82 100644 (file)
@@ -7,7 +7,7 @@ package html
 // Section 12.2.3.2 of the HTML5 specification says "The following elements
 // have varying levels of special parsing rules".
 // http://www.whatwg.org/specs/web-apps/current-work/multipage/parsing.html#the-stack-of-open-elements
-var isSpecialElement = map[string]bool{
+var isSpecialElementMap = map[string]bool{
        "address":    true,
        "applet":     true,
        "area":       true,
@@ -88,3 +88,13 @@ var isSpecialElement = map[string]bool{
        "wbr":        true,
        "xmp":        true,
 }
+
+func isSpecialElement(element *Node) bool {
+       switch element.Namespace {
+       case "", "html":
+               return isSpecialElementMap[element.Data]
+       case "svg":
+               return element.Data == "foreignObject"
+       }
+       return false
+}
index 4cb246969e54ca1c3b860b167d718bfd0376c4be..104adc1b7baf17b7c399b188cf3080d002610013 100644 (file)
@@ -705,7 +705,7 @@ func inBodyIM(p *parser) bool {
                                case "address", "div", "p":
                                        continue
                                default:
-                                       if !isSpecialElement[node.Data] {
+                                       if !isSpecialElement(node) {
                                                continue
                                        }
                                }
@@ -723,7 +723,7 @@ func inBodyIM(p *parser) bool {
                                case "address", "div", "p":
                                        continue
                                default:
-                                       if !isSpecialElement[node.Data] {
+                                       if !isSpecialElement(node) {
                                                continue
                                        }
                                }
@@ -895,7 +895,7 @@ func (p *parser) inBodyEndTagFormatting(tag string) {
                // Steps 5-6. Find the furthest block.
                var furthestBlock *Node
                for _, e := range p.oe[feIndex:] {
-                       if isSpecialElement[e.Data] {
+                       if isSpecialElement(e) {
                                furthestBlock = e
                                break
                        }
@@ -988,7 +988,7 @@ func (p *parser) inBodyEndTagOther(tag string) {
                        p.oe = p.oe[:i]
                        break
                }
-               if isSpecialElement[p.oe[i].Data] {
+               if isSpecialElement(p.oe[i]) {
                        break
                }
        }
@@ -1606,7 +1606,18 @@ func inForeignContentIM(p *parser) bool {
                // TODO: adjust foreign attributes.
                p.addElement(p.tok.Data, p.tok.Attr)
        case EndTagToken:
-               // TODO.
+               for i := len(p.oe) - 1; i >= 0; i-- {
+                       if p.oe[i].Namespace == "" {
+                               inBodyIM(p)
+                               break
+                       }
+                       if strings.EqualFold(p.oe[i].Data, p.tok.Data) {
+                               p.oe = p.oe[:i]
+                               break
+                       }
+               }
+               p.resetInsertionMode()
+               return true
        default:
                // Ignore the token.
        }
index e887631c63d70d5ff00749f8b8cb82d3f21c7a4e..f501915759d1c28674f54285b19c4813c1c700a8 100644 (file)
@@ -173,6 +173,7 @@ func TestParser(t *testing.T) {
                {"tests4.dat", -1},
                {"tests5.dat", -1},
                {"tests6.dat", 36},
+               {"tests10.dat", 6},
        }
        for _, tf := range testFiles {
                f, err := os.Open("testdata/webkit/" + tf.filename)