Update Go library to last weekly.

From-SVN: r180552
This commit is contained in:
Ian Lance Taylor 2011-10-26 23:57:58 +00:00
parent e0c39d66d4
commit d8f412571f
537 changed files with 43765 additions and 12999 deletions

View file

@ -29,6 +29,9 @@ type parser struct {
head, form *Node
// Other parsing state flags (section 11.2.3.5).
scripting, framesetOK bool
// originalIM is the insertion mode to go back to after completing a text
// or inTableText insertion mode.
originalIM insertionMode
}
func (p *parser) top() *Node {
@ -64,21 +67,37 @@ var (
// popUntil([]string{"html, "table"}, "table") would return true and leave:
// ["html", "body", "font"]
func (p *parser) popUntil(stopTags []string, matchTags ...string) bool {
if i := p.indexOfElementInScope(stopTags, matchTags...); i != -1 {
p.oe = p.oe[:i]
return true
}
return false
}
// indexOfElementInScope returns the index in p.oe of the highest element
// whose tag is in matchTags that is in scope according to stopTags.
// If no matching element is in scope, it returns -1.
func (p *parser) indexOfElementInScope(stopTags []string, matchTags ...string) int {
for i := len(p.oe) - 1; i >= 0; i-- {
tag := p.oe[i].Data
for _, t := range matchTags {
if t == tag {
p.oe = p.oe[:i]
return true
return i
}
}
for _, t := range stopTags {
if t == tag {
return false
return -1
}
}
}
return false
return -1
}
// elementInScope is like popUntil, except that it doesn't modify the stack of
// open elements.
func (p *parser) elementInScope(stopTags []string, matchTags ...string) bool {
return p.indexOfElementInScope(stopTags, matchTags...) != -1
}
// addChild adds a child node n to the top element, and pushes n onto the stack
@ -198,12 +217,23 @@ type insertionMode func(*parser) (insertionMode, bool)
// Section 11.2.3.1, "using the rules for".
func useTheRulesFor(p *parser, actual, delegate insertionMode) (insertionMode, bool) {
im, consumed := delegate(p)
// TODO: do we need to update p.originalMode if it equals delegate?
if im != delegate {
return im, consumed
}
return actual, consumed
}
// setOriginalIM sets the insertion mode to return to after completing a text or
// inTableText insertion mode.
// Section 11.2.3.1, "using the rules for".
func (p *parser) setOriginalIM(im insertionMode) {
if p.originalIM != nil {
panic("html: bad parser state: originalIM was set twice")
}
p.originalIM = im
}
// Section 11.2.5.4.1.
func initialIM(p *parser) (insertionMode, bool) {
if p.tok.Type == DoctypeToken {
@ -302,8 +332,10 @@ func inHeadIM(p *parser) (insertionMode, bool) {
switch p.tok.Data {
case "meta":
// TODO.
case "script":
// TODO.
case "script", "title":
p.addElement(p.tok.Data, p.tok.Attr)
p.setOriginalIM(inHeadIM)
return textIM, true
default:
implied = true
}
@ -365,7 +397,6 @@ func afterHeadIM(p *parser) (insertionMode, bool) {
// Section 11.2.5.4.7.
func inBodyIM(p *parser) (insertionMode, bool) {
var endP bool
switch p.tok.Type {
case TextToken:
p.reconstructActiveFormattingElements()
@ -374,15 +405,10 @@ func inBodyIM(p *parser) (insertionMode, bool) {
case StartTagToken:
switch p.tok.Data {
case "address", "article", "aside", "blockquote", "center", "details", "dir", "div", "dl", "fieldset", "figcaption", "figure", "footer", "header", "hgroup", "menu", "nav", "ol", "p", "section", "summary", "ul":
// TODO: Do the proper "does the stack of open elements has a p element in button scope" algorithm in section 11.2.3.2.
n := p.top()
if n.Type == ElementNode && n.Data == "p" {
endP = true
} else {
p.addElement(p.tok.Data, p.tok.Attr)
}
p.popUntil(buttonScopeStopTags, "p")
p.addElement(p.tok.Data, p.tok.Attr)
case "h1", "h2", "h3", "h4", "h5", "h6":
// TODO: auto-insert </p> if necessary.
p.popUntil(buttonScopeStopTags, "p")
switch n := p.top(); n.Data {
case "h1", "h2", "h3", "h4", "h5", "h6":
p.oe.pop()
@ -399,6 +425,11 @@ func inBodyIM(p *parser) (insertionMode, bool) {
case "b", "big", "code", "em", "font", "i", "s", "small", "strike", "strong", "tt", "u":
p.reconstructActiveFormattingElements()
p.addFormattingElement(p.tok.Data, p.tok.Attr)
case "applet", "marquee", "object":
p.reconstructActiveFormattingElements()
p.addElement(p.tok.Data, p.tok.Attr)
p.afe = append(p.afe, &scopeMarker)
p.framesetOK = false
case "area", "br", "embed", "img", "input", "keygen", "wbr":
p.reconstructActiveFormattingElements()
p.addElement(p.tok.Data, p.tok.Attr)
@ -406,12 +437,12 @@ func inBodyIM(p *parser) (insertionMode, bool) {
p.acknowledgeSelfClosingTag()
p.framesetOK = false
case "table":
// TODO: auto-insert </p> if necessary, depending on quirks mode.
p.popUntil(buttonScopeStopTags, "p") // TODO: skip this step in quirks mode.
p.addElement(p.tok.Data, p.tok.Attr)
p.framesetOK = false
return inTableIM, true
case "hr":
// TODO: auto-insert </p> if necessary.
p.popUntil(buttonScopeStopTags, "p")
p.addElement(p.tok.Data, p.tok.Attr)
p.oe.pop()
p.acknowledgeSelfClosingTag()
@ -425,6 +456,11 @@ func inBodyIM(p *parser) (insertionMode, bool) {
case "body":
// TODO: autoclose the stack of open elements.
return afterBodyIM, true
case "p":
if !p.elementInScope(buttonScopeStopTags, "p") {
p.addElement("p", nil)
}
p.popUntil(buttonScopeStopTags, "p")
case "a", "b", "big", "code", "em", "font", "i", "nobr", "s", "small", "strike", "strong", "tt", "u":
p.inBodyEndTagFormatting(p.tok.Data)
default:
@ -434,14 +470,8 @@ func inBodyIM(p *parser) (insertionMode, bool) {
}
}
}
if endP {
// TODO: do the proper algorithm.
n := p.oe.pop()
if n.Type != ElementNode || n.Data != "p" {
panic("unreachable")
}
}
return inBodyIM, !endP
return inBodyIM, true
}
func (p *parser) inBodyEndTagFormatting(tag string) {
@ -560,6 +590,20 @@ func (p *parser) inBodyEndTagFormatting(tag string) {
}
}
// Section 11.2.5.4.8.
func textIM(p *parser) (insertionMode, bool) {
switch p.tok.Type {
case TextToken:
p.addText(p.tok.Data)
return textIM, true
case EndTagToken:
p.oe.pop()
}
o := p.originalIM
p.originalIM = nil
return o, p.tok.Type == EndTagToken
}
// Section 11.2.5.4.9.
func inTableIM(p *parser) (insertionMode, bool) {
var (