/[suikacvs]/markup/html/whatpm/Whatpm/HTML.pm.src
Suika

Diff of /markup/html/whatpm/Whatpm/HTML.pm.src

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.123 by wakaba, Sun Apr 6 10:32:00 2008 UTC revision 1.128 by wakaba, Sat Apr 12 15:31:56 2008 UTC
# Line 12  use Error qw(:try); Line 12  use Error qw(:try);
12  ## TODO: 1252 parse error (revision 1264)  ## TODO: 1252 parse error (revision 1264)
13  ## TODO: 8859-11 = 874 (revision 1271)  ## TODO: 8859-11 = 874 (revision 1271)
14    
15    my $HTML_NS = q<http://www.w3.org/1999/xhtml>;
16    my $MML_NS = q<http://www.w3.org/1998/Math/MathML>;
17    my $SVG_NS = q<http://www.w3.org/2000/svg>;
18    my $XLINK_NS = q<http://www.w3.org/1999/xlink>;
19    my $XML_NS = q<http://www.w3.org/XML/1998/namespace>;
20    my $XMLNS_NS = q<http://www.w3.org/2000/xmlns/>;
21    
22  sub A_EL () { 0b1 }  sub A_EL () { 0b1 }
23  sub ADDRESS_EL () { 0b10 }  sub ADDRESS_EL () { 0b10 }
24  sub BODY_EL () { 0b100 }  sub BODY_EL () { 0b100 }
# Line 37  sub TABLE_ROW_EL () { 0b1000000000000000 Line 44  sub TABLE_ROW_EL () { 0b1000000000000000
44  sub TABLE_ROW_GROUP_EL () { 0b10000000000000000000000 }  sub TABLE_ROW_GROUP_EL () { 0b10000000000000000000000 }
45  sub MISC_SCOPING_EL () { 0b100000000000000000000000 }  sub MISC_SCOPING_EL () { 0b100000000000000000000000 }
46  sub MISC_SPECIAL_EL () { 0b1000000000000000000000000 }  sub MISC_SPECIAL_EL () { 0b1000000000000000000000000 }
47    sub FOREIGN_EL () { 0b10000000000000000000000000 }
48    sub FOREIGN_FLOW_CONTENT_EL () { 0b100000000000000000000000000 }
49    sub MML_AXML_EL () { 0b1000000000000000000000000000 }
50    
51  sub TABLE_ROWS_EL () {  sub TABLE_ROWS_EL () {
52    TABLE_EL |    TABLE_EL |
# Line 185  my $el_category = { Line 195  my $el_category = {
195    wbr => MISC_SPECIAL_EL,    wbr => MISC_SPECIAL_EL,
196  };  };
197    
198  my $permitted_slash_tag_name = {  my $el_category_f = {
199    base => 1,    $MML_NS => {
200    link => 1,      'annotation-xml' => MML_AXML_EL,
201    meta => 1,      mi => FOREIGN_FLOW_CONTENT_EL,
202    hr => 1,      mo => FOREIGN_FLOW_CONTENT_EL,
203    br => 1,      mn => FOREIGN_FLOW_CONTENT_EL,
204    img => 1,      ms => FOREIGN_FLOW_CONTENT_EL,
205    embed => 1,      mtext => FOREIGN_FLOW_CONTENT_EL,
206    param => 1,    },
207    area => 1,    $SVG_NS => {
208    col => 1,      foreignobject => FOREIGN_FLOW_CONTENT_EL, ## TODO: case
209    input => 1,      desc => FOREIGN_FLOW_CONTENT_EL,
210        title => FOREIGN_FLOW_CONTENT_EL,
211      },
212      ## NOTE: In addition, FOREIGN_EL is set to non-HTML elements.
213  };  };
214    
215  my $c1_entity_char = {  my $c1_entity_char = {
# Line 234  my $c1_entity_char = { Line 247  my $c1_entity_char = {
247    0x9F => 0x0178,    0x9F => 0x0178,
248  }; # $c1_entity_char  }; # $c1_entity_char
249    
 my $special_category = {  
   address => 1, area => 1, base => 1, basefont => 1, bgsound => 1,  
   blockquote => 1, body => 1, br => 1, center => 1, col => 1, colgroup => 1,  
   dd => 1, dir => 1, div => 1, dl => 1, dt => 1, embed => 1, fieldset => 1,  
   form => 1, frame => 1, frameset => 1, h1 => 1, h2 => 1, h3 => 1,  
   h4 => 1, h5 => 1, h6 => 1, head => 1, hr => 1, iframe => 1, image => 1,  
   img => 1, input => 1, isindex => 1, li => 1, link => 1, listing => 1,  
   menu => 1, meta => 1, noembed => 1, noframes => 1, noscript => 1,  
   ol => 1, optgroup => 1, option => 1, p => 1, param => 1, plaintext => 1,  
   pre => 1, script => 1, select => 1, spacer => 1, style => 1, tbody => 1,  
   textarea => 1, tfoot => 1, thead => 1, title => 1, tr => 1, ul => 1, wbr => 1,  
 };  
 my $scoping_category = {  
   applet => 1, button => 1, caption => 1, html => 1, marquee => 1, object => 1,  
   table => 1, td => 1, th => 1,  
 };  
 my $formatting_category = {  
   a => 1, b => 1, big => 1, em => 1, font => 1, i => 1, nobr => 1,  
   s => 1, small => 1, strile => 1, strong => 1, tt => 1, u => 1,  
 };  
 # $phrasing_category: all other elements  
   
250  sub parse_byte_string ($$$$;$) {  sub parse_byte_string ($$$$;$) {
251    my $self = ref $_[0] ? shift : shift->new;    my $self = ref $_[0] ? shift : shift->new;
252    my $charset = shift;    my $charset = shift;
# Line 468  sub DOCTYPE_SYSTEM_IDENTIFIER_SINGLE_QUO Line 459  sub DOCTYPE_SYSTEM_IDENTIFIER_SINGLE_QUO
459  sub AFTER_DOCTYPE_SYSTEM_IDENTIFIER_STATE () { 31 }  sub AFTER_DOCTYPE_SYSTEM_IDENTIFIER_STATE () { 31 }
460  sub BOGUS_DOCTYPE_STATE () { 32 }  sub BOGUS_DOCTYPE_STATE () { 32 }
461  sub AFTER_ATTRIBUTE_VALUE_QUOTED_STATE () { 33 }  sub AFTER_ATTRIBUTE_VALUE_QUOTED_STATE () { 33 }
462    sub SELF_CLOSING_START_TAG_STATE () { 34 }
463    sub CDATA_BLOCK_STATE () { 35 }
464    
465  sub DOCTYPE_TOKEN () { 1 }  sub DOCTYPE_TOKEN () { 1 }
466  sub COMMENT_TOKEN () { 2 }  sub COMMENT_TOKEN () { 2 }
# Line 485  sub ROW_IMS ()        { 0b10000000 } Line 478  sub ROW_IMS ()        { 0b10000000 }
478  sub BODY_AFTER_IMS () { 0b100000000 }  sub BODY_AFTER_IMS () { 0b100000000 }
479  sub FRAME_IMS ()      { 0b1000000000 }  sub FRAME_IMS ()      { 0b1000000000 }
480  sub SELECT_IMS ()     { 0b10000000000 }  sub SELECT_IMS ()     { 0b10000000000 }
481    sub IN_FOREIGN_CONTENT_IM () { 0b100000000000 }
482        ## NOTE: "in foreign content" insertion mode is special; it is combined
483        ## with the secondary insertion mode.  In this parser, they are stored
484        ## together in the bit-or'ed form.
485    
486  ## NOTE: "initial" and "before html" insertion modes have no constants.  ## NOTE: "initial" and "before html" insertion modes have no constants.
487    
# Line 521  sub _initialize_tokenizer ($) { Line 518  sub _initialize_tokenizer ($) {
518    undef $self->{current_attribute};    undef $self->{current_attribute};
519    undef $self->{last_emitted_start_tag_name};    undef $self->{last_emitted_start_tag_name};
520    undef $self->{last_attribute_value_state};    undef $self->{last_attribute_value_state};
521      delete $self->{self_closing};
522    $self->{char} = [];    $self->{char} = [];
523    # $self->{next_char}    # $self->{next_char}
524    !!!next-input-character;    !!!next-input-character;
# Line 541  sub _initialize_tokenizer ($) { Line 539  sub _initialize_tokenizer ($) {
539  ##        ->{value}  ##        ->{value}
540  ##        ->{has_reference} == 1 or 0  ##        ->{has_reference} == 1 or 0
541  ##   ->{data} (COMMENT_TOKEN, CHARACTER_TOKEN)  ##   ->{data} (COMMENT_TOKEN, CHARACTER_TOKEN)
542    ## NOTE: The "self-closing flag" is hold as |$self->{self_closing}|.
543    ##     |->{self_closing}| is used to save the value of |$self->{self_closing}|
544    ##     while the token is pushed back to the stack.
545    
546    ## ISSUE: "When a DOCTYPE token is created, its
547    ## <i>self-closing flag</i> must be unset (its other state is that it
548    ## be set), and its attributes list must be empty.": Wrong subject?
549    
550  ## Emitted token MUST immediately be handled by the tree construction state.  ## Emitted token MUST immediately be handled by the tree construction state.
551    
# Line 567  sub _initialize_tokenizer ($) { Line 572  sub _initialize_tokenizer ($) {
572    
573  sub _get_next_token ($) {  sub _get_next_token ($) {
574    my $self = shift;    my $self = shift;
575    
576      if ($self->{self_closing}) {
577        !!!parse-error (type => 'nestc', token => $self->{current_token});
578        ## NOTE: The |self_closing| flag is only set by start tag token.
579        ## In addition, when a start tag token is emitted, it is always set to
580        ## |current_token|.
581        delete $self->{self_closing};
582      }
583    
584    if (@{$self->{token}}) {    if (@{$self->{token}}) {
585        $self->{self_closing} = $self->{token}->[0]->{self_closing};
586      return shift @{$self->{token}};      return shift @{$self->{token}};
587    }    }
588    
# Line 938  sub _get_next_token ($) { Line 953  sub _get_next_token ($) {
953    
954          redo A;          redo A;
955        } elsif ($self->{next_char} == 0x002F) { # /        } elsif ($self->{next_char} == 0x002F) { # /
956            !!!cp (42);
957            $self->{state} = SELF_CLOSING_START_TAG_STATE;
958          !!!next-input-character;          !!!next-input-character;
         if ($self->{next_char} == 0x003E and # >  
             $self->{current_token}->{type} == START_TAG_TOKEN and  
             $permitted_slash_tag_name->{$self->{current_token}->{tag_name}}) {  
           # permitted slash  
           !!!cp (42);  
           #  
         } else {  
           !!!cp (43);  
           !!!parse-error (type => 'nestc');  
         }  
         $self->{state} = BEFORE_ATTRIBUTE_NAME_STATE;  
         # next-input-character is already done  
959          redo A;          redo A;
960        } else {        } else {
961          !!!cp (44);          !!!cp (44);
# Line 1002  sub _get_next_token ($) { Line 1007  sub _get_next_token ($) {
1007          !!!next-input-character;          !!!next-input-character;
1008          redo A;          redo A;
1009        } elsif ($self->{next_char} == 0x002F) { # /        } elsif ($self->{next_char} == 0x002F) { # /
1010            !!!cp (50);
1011            $self->{state} = SELF_CLOSING_START_TAG_STATE;
1012          !!!next-input-character;          !!!next-input-character;
         if ($self->{next_char} == 0x003E and # >  
             $self->{current_token}->{type} == START_TAG_TOKEN and  
             $permitted_slash_tag_name->{$self->{current_token}->{tag_name}}) {  
           # permitted slash  
           !!!cp (50);  
           #  
         } else {  
           !!!cp (51);  
           !!!parse-error (type => 'nestc');  
         }  
         ## Stay in the state  
         # next-input-character is already done  
1013          redo A;          redo A;
1014        } elsif ($self->{next_char} == -1) {        } elsif ($self->{next_char} == -1) {
1015          !!!parse-error (type => 'unclosed tag');          !!!parse-error (type => 'unclosed tag');
# Line 1115  sub _get_next_token ($) { Line 1110  sub _get_next_token ($) {
1110          !!!next-input-character;          !!!next-input-character;
1111          redo A;          redo A;
1112        } elsif ($self->{next_char} == 0x002F) { # /        } elsif ($self->{next_char} == 0x002F) { # /
1113            !!!cp (64);
1114          $before_leave->();          $before_leave->();
1115            $self->{state} = SELF_CLOSING_START_TAG_STATE;
1116          !!!next-input-character;          !!!next-input-character;
         if ($self->{next_char} == 0x003E and # >  
             $self->{current_token}->{type} == START_TAG_TOKEN and  
             $permitted_slash_tag_name->{$self->{current_token}->{tag_name}}) {  
           # permitted slash  
           !!!cp (64);  
           #  
         } else {  
           !!!cp (65);  
           !!!parse-error (type => 'nestc');  
         }  
         $self->{state} = BEFORE_ATTRIBUTE_NAME_STATE;  
         # next-input-character is already done  
1117          redo A;          redo A;
1118        } elsif ($self->{next_char} == -1) {        } elsif ($self->{next_char} == -1) {
1119          !!!parse-error (type => 'unclosed tag');          !!!parse-error (type => 'unclosed tag');
# Line 1215  sub _get_next_token ($) { Line 1200  sub _get_next_token ($) {
1200          !!!next-input-character;          !!!next-input-character;
1201          redo A;          redo A;
1202        } elsif ($self->{next_char} == 0x002F) { # /        } elsif ($self->{next_char} == 0x002F) { # /
1203            !!!cp (77);
1204            $self->{state} = SELF_CLOSING_START_TAG_STATE;
1205          !!!next-input-character;          !!!next-input-character;
         if ($self->{next_char} == 0x003E and # >  
             $self->{current_token}->{type} == START_TAG_TOKEN and  
             $permitted_slash_tag_name->{$self->{current_token}->{tag_name}}) {  
           # permitted slash  
           !!!cp (77);  
           #  
         } else {  
           !!!cp (78);  
           !!!parse-error (type => 'nestc');  
           ## TODO: Different error type for <aa / bb> than <aa/>  
         }  
         $self->{state} = BEFORE_ATTRIBUTE_NAME_STATE;  
         # next-input-character is already done  
1206          redo A;          redo A;
1207        } elsif ($self->{next_char} == -1) {        } elsif ($self->{next_char} == -1) {
1208          !!!parse-error (type => 'unclosed tag');          !!!parse-error (type => 'unclosed tag');
# Line 1561  sub _get_next_token ($) { Line 1535  sub _get_next_token ($) {
1535    
1536          redo A;          redo A;
1537        } elsif ($self->{next_char} == 0x002F) { # /        } elsif ($self->{next_char} == 0x002F) { # /
1538            !!!cp (122);
1539            $self->{state} = SELF_CLOSING_START_TAG_STATE;
1540          !!!next-input-character;          !!!next-input-character;
         if ($self->{next_char} == 0x003E and # >  
             $self->{current_token}->{type} == START_TAG_TOKEN and  
             $permitted_slash_tag_name->{$self->{current_token}->{tag_name}}) {  
           # permitted slash  
           !!!cp (122);  
           #  
         } else {  
           !!!cp (123);  
           !!!parse-error (type => 'nestc');  
         }  
         $self->{state} = BEFORE_ATTRIBUTE_NAME_STATE;  
         # next-input-character is already done  
1541          redo A;          redo A;
1542        } else {        } else {
1543          !!!cp (124);          !!!cp ('124.1');
1544          !!!parse-error (type => 'no space between attributes');          !!!parse-error (type => 'no space between attributes');
1545          $self->{state} = BEFORE_ATTRIBUTE_NAME_STATE;          $self->{state} = BEFORE_ATTRIBUTE_NAME_STATE;
1546          ## reconsume          ## reconsume
1547          redo A;          redo A;
1548        }        }
1549        } elsif ($self->{state} == SELF_CLOSING_START_TAG_STATE) {
1550          if ($self->{next_char} == 0x003E) { # >
1551            if ($self->{current_token}->{type} == END_TAG_TOKEN) {
1552              !!!cp ('124.2');
1553              !!!parse-error (type => 'nestc', token => $self->{current_token});
1554              ## TODO: Different type than slash in start tag
1555              $self->{content_model} = PCDATA_CONTENT_MODEL; # MUST
1556              if ($self->{current_token}->{attributes}) {
1557                !!!cp ('124.4');
1558                !!!parse-error (type => 'end tag attribute');
1559              } else {
1560                !!!cp ('124.5');
1561              }
1562              ## TODO: Test |<title></title/>|
1563            } else {
1564              !!!cp ('124.3');
1565              $self->{self_closing} = 1;
1566            }
1567    
1568            $self->{state} = DATA_STATE;
1569            !!!next-input-character;
1570    
1571            !!!emit ($self->{current_token}); # start tag or end tag
1572    
1573            redo A;
1574          } else {
1575            !!!cp ('124.4');
1576            !!!parse-error (type => 'nestc');
1577            ## TODO: This error type is wrong.
1578            $self->{state} = BEFORE_ATTRIBUTE_NAME_STATE;
1579            ## Reconsume.
1580            redo A;
1581          }
1582      } elsif ($self->{state} == BOGUS_COMMENT_STATE) {      } elsif ($self->{state} == BOGUS_COMMENT_STATE) {
1583        ## (only happen if PCDATA state)        ## (only happen if PCDATA state)
1584                
# Line 1689  sub _get_next_token ($) { Line 1686  sub _get_next_token ($) {
1686          } else {          } else {
1687            !!!cp (135);            !!!cp (135);
1688          }          }
1689          } elsif ($self->{insertion_mode} & IN_FOREIGN_CONTENT_IM and
1690                   $self->{open_elements}->[-1]->[1] & FOREIGN_EL and
1691                   $self->{next_char} == 0x005B) { # [
1692            !!!next-input-character;
1693            push @next_char, $self->{next_char};
1694            if ($self->{next_char} == 0x0043) { # C
1695              !!!next-input-character;
1696              push @next_char, $self->{next_char};
1697              if ($self->{next_char} == 0x0044) { # D
1698                !!!next-input-character;
1699                push @next_char, $self->{next_char};
1700                if ($self->{next_char} == 0x0041) { # A
1701                  !!!next-input-character;
1702                  push @next_char, $self->{next_char};
1703                  if ($self->{next_char} == 0x0054) { # T
1704                    !!!next-input-character;
1705                    push @next_char, $self->{next_char};
1706                    if ($self->{next_char} == 0x0041) { # A
1707                      !!!next-input-character;
1708                      push @next_char, $self->{next_char};
1709                      if ($self->{next_char} == 0x005B) { # [
1710                        !!!cp (135.1);
1711                        $self->{state} = CDATA_BLOCK_STATE;
1712                        !!!next-input-character;
1713                        redo A;
1714                      } else {
1715                        !!!cp (135.2);
1716                      }
1717                    } else {
1718                      !!!cp (135.3);
1719                    }
1720                  } else {
1721                    !!!cp (135.4);                
1722                  }
1723                } else {
1724                  !!!cp (135.5);
1725                }
1726              } else {
1727                !!!cp (135.6);
1728              }
1729            } else {
1730              !!!cp (135.7);
1731            }
1732        } else {        } else {
1733          !!!cp (136);          !!!cp (136);
1734        }        }
# Line 2413  sub _get_next_token ($) { Line 2453  sub _get_next_token ($) {
2453          !!!next-input-character;          !!!next-input-character;
2454          redo A;          redo A;
2455        }        }
2456        } elsif ($self->{state} == CDATA_BLOCK_STATE) {
2457          my $s = '';
2458          
2459          my ($l, $c) = ($self->{line}, $self->{column});
2460    
2461          CS: while ($self->{next_char} != -1) {
2462            if ($self->{next_char} == 0x005D) { # ]
2463              !!!next-input-character;
2464              if ($self->{next_char} == 0x005D) { # ]
2465                !!!next-input-character;
2466                MDC: {
2467                  if ($self->{next_char} == 0x003E) { # >
2468                    !!!cp (221.1);
2469                    !!!next-input-character;
2470                    last CS;
2471                  } elsif ($self->{next_char} == 0x005D) { # ]
2472                    !!!cp (221.2);
2473                    $s .= ']';
2474                    !!!next-input-character;
2475                    redo MDC;
2476                  } else {
2477                    !!!cp (221.3);
2478                    $s .= ']]';
2479                    #
2480                  }
2481                } # MDC
2482              } else {
2483                !!!cp (221.4);
2484                $s .= ']';
2485                #
2486              }
2487            } else {
2488              !!!cp (221.5);
2489              #
2490            }
2491            $s .= chr $self->{next_char};
2492            !!!next-input-character;
2493          } # CS
2494    
2495          $self->{state} = DATA_STATE;
2496          ## next-input-character done or EOF, which is reconsumed.
2497    
2498          if (length $s) {
2499            !!!cp (221.6);
2500            !!!emit ({type => CHARACTER_TOKEN, data => $s,
2501                      line => $l, column => $c});
2502          } else {
2503            !!!cp (221.7);
2504          }
2505    
2506          redo A;
2507    
2508          ## ISSUE: "text tokens" in spec.
2509          ## TODO: Streaming support
2510      } else {      } else {
2511        die "$0: $self->{state}: Unknown state";        die "$0: $self->{state}: Unknown state";
2512      }      }
# Line 2563  sub _tokenize_attempt_to_consume_an_enti Line 2657  sub _tokenize_attempt_to_consume_an_enti
2657      require Whatpm::_NamedEntityList;      require Whatpm::_NamedEntityList;
2658      our $EntityChar;      our $EntityChar;
2659    
2660      while (length $entity_name < 10 and      while (length $entity_name < 30 and
2661             ## NOTE: Some number greater than the maximum length of entity name             ## NOTE: Some number greater than the maximum length of entity name
2662             ((0x0041 <= $self->{next_char} and # a             ((0x0041 <= $self->{next_char} and # a
2663               $self->{next_char} <= 0x005A) or # x               $self->{next_char} <= 0x005A) or # x
# Line 2843  sub _tree_construction_initial ($) { Line 2937  sub _tree_construction_initial ($) {
2937        $self->{document}->manakai_compat_mode ('quirks');        $self->{document}->manakai_compat_mode ('quirks');
2938        ## Go to the "before html" insertion mode.        ## Go to the "before html" insertion mode.
2939        ## reprocess        ## reprocess
2940          !!!ack-later;
2941        return;        return;
2942      } elsif ($token->{type} == CHARACTER_TOKEN) {      } elsif ($token->{type} == CHARACTER_TOKEN) {
2943        if ($token->{data} =~ s/^([\x09\x0A\x0B\x0C\x20]+)//) { # \x0D        if ($token->{data} =~ s/^([\x09\x0A\x0B\x0C\x20]+)//) { # \x0D
# Line 2923  sub _tree_construction_root_element ($) Line 3018  sub _tree_construction_root_element ($)
3018        } elsif ($token->{type} == START_TAG_TOKEN) {        } elsif ($token->{type} == START_TAG_TOKEN) {
3019          if ($token->{tag_name} eq 'html') {          if ($token->{tag_name} eq 'html') {
3020            my $root_element;            my $root_element;
3021            !!!create-element ($root_element, $token->{tag_name}, $token->{attributes}, $token);            !!!create-element ($root_element, $HTML_NS, $token->{tag_name}, $token->{attributes}, $token);
3022            $self->{document}->append_child ($root_element);            $self->{document}->append_child ($root_element);
3023            push @{$self->{open_elements}},            push @{$self->{open_elements}},
3024                [$root_element, $el_category->{html}];                [$root_element, $el_category->{html}];
# Line 2941  sub _tree_construction_root_element ($) Line 3036  sub _tree_construction_root_element ($)
3036              $self->{application_cache_selection}->(undef);              $self->{application_cache_selection}->(undef);
3037            }            }
3038    
3039              !!!nack ('t25c');
3040    
3041            !!!next-token;            !!!next-token;
3042            return; ## Go to the "before head" insertion mode.            return; ## Go to the "before head" insertion mode.
3043          } else {          } else {
# Line 2957  sub _tree_construction_root_element ($) Line 3054  sub _tree_construction_root_element ($)
3054          die "$0: $token->{type}: Unknown token type";          die "$0: $token->{type}: Unknown token type";
3055        }        }
3056    
3057      my $root_element; !!!create-element ($root_element, 'html',, $token);      my $root_element;
3058        !!!create-element ($root_element, $HTML_NS, 'html',, $token);
3059      $self->{document}->append_child ($root_element);      $self->{document}->append_child ($root_element);
3060      push @{$self->{open_elements}}, [$root_element, $el_category->{html}];      push @{$self->{open_elements}}, [$root_element, $el_category->{html}];
3061    
3062      $self->{application_cache_selection}->(undef);      $self->{application_cache_selection}->(undef);
3063    
3064      ## NOTE: Reprocess the token.      ## NOTE: Reprocess the token.
3065        !!!ack-later;
3066      return; ## Go to the "before head" insertion mode.      return; ## Go to the "before head" insertion mode.
3067    
3068      ## ISSUE: There is an issue in the spec      ## ISSUE: There is an issue in the spec
# Line 2997  sub _reset_insertion_mode ($) { Line 3096  sub _reset_insertion_mode ($) {
3096          }          }
3097        }        }
3098            
3099        ## Step 4..13      ## Step 4..14
3100        my $new_mode = {      my $new_mode;
3101        if ($node->[1] & FOREIGN_EL) {
3102          ## NOTE: Strictly spaking, the line below only applies to MathML and
3103          ## SVG elements.  Currently the HTML syntax supports only MathML and
3104          ## SVG elements as foreigners.
3105          $new_mode = $self->{insertion_mode} | IN_FOREIGN_CONTENT_IM;
3106          ## ISSUE: What is set as the secondary insertion mode?
3107        } else {
3108          $new_mode = {
3109                        select => IN_SELECT_IM,                        select => IN_SELECT_IM,
3110                        ## NOTE: |option| and |optgroup| do not set                        ## NOTE: |option| and |optgroup| do not set
3111                        ## insertion mode to "in select" by themselves.                        ## insertion mode to "in select" by themselves.
# Line 3015  sub _reset_insertion_mode ($) { Line 3122  sub _reset_insertion_mode ($) {
3122                        body => IN_BODY_IM,                        body => IN_BODY_IM,
3123                        frameset => IN_FRAMESET_IM,                        frameset => IN_FRAMESET_IM,
3124                       }->{$node->[0]->manakai_local_name};                       }->{$node->[0]->manakai_local_name};
3125                       ## TODO: Foreign namespace case OK?      }
3126        $self->{insertion_mode} = $new_mode and return if defined $new_mode;      $self->{insertion_mode} = $new_mode and return if defined $new_mode;
3127                
3128        ## Step 14        ## Step 15
3129        if ($node->[1] & HTML_EL) {        if ($node->[1] & HTML_EL) {
3130          unless (defined $self->{head_element}) {          unless (defined $self->{head_element}) {
3131            !!!cp ('t29');            !!!cp ('t29');
# Line 3033  sub _reset_insertion_mode ($) { Line 3140  sub _reset_insertion_mode ($) {
3140          !!!cp ('t31');          !!!cp ('t31');
3141        }        }
3142                
3143        ## Step 15        ## Step 16
3144        $self->{insertion_mode} = IN_BODY_IM and return if $last;        $self->{insertion_mode} = IN_BODY_IM and return if $last;
3145                
3146        ## Step 16        ## Step 17
3147        $i--;        $i--;
3148        $node = $self->{open_elements}->[$i];        $node = $self->{open_elements}->[$i];
3149                
3150        ## Step 17        ## Step 18
3151        redo S3;        redo S3;
3152      } # S3      } # S3
3153    
# Line 3152  sub _tree_construction_main ($) { Line 3259  sub _tree_construction_main ($) {
3259      ## Step 1      ## Step 1
3260      my $start_tag_name = $token->{tag_name};      my $start_tag_name = $token->{tag_name};
3261      my $el;      my $el;
3262      !!!create-element ($el, $start_tag_name, $token->{attributes}, $token);      !!!create-element ($el, $HTML_NS, $start_tag_name, $token->{attributes}, $token);
3263    
3264      ## Step 2      ## Step 2
3265      $insert->($el);      $insert->($el);
# Line 3163  sub _tree_construction_main ($) { Line 3270  sub _tree_construction_main ($) {
3270    
3271      ## Step 4      ## Step 4
3272      my $text = '';      my $text = '';
3273        !!!nack ('t40.1');
3274      !!!next-token;      !!!next-token;
3275      while ($token->{type} == CHARACTER_TOKEN) { # or until stop tokenizing      while ($token->{type} == CHARACTER_TOKEN) { # or until stop tokenizing
3276        !!!cp ('t40');        !!!cp ('t40');
# Line 3202  sub _tree_construction_main ($) { Line 3310  sub _tree_construction_main ($) {
3310    
3311    my $script_start_tag = sub () {    my $script_start_tag = sub () {
3312      my $script_el;      my $script_el;
3313      !!!create-element ($script_el, 'script', $token->{attributes}, $token);      !!!create-element ($script_el, $HTML_NS, 'script', $token->{attributes}, $token);
3314      ## TODO: mark as "parser-inserted"      ## TODO: mark as "parser-inserted"
3315    
3316      $self->{content_model} = CDATA_CONTENT_MODEL;      $self->{content_model} = CDATA_CONTENT_MODEL;
3317      delete $self->{escape}; # MUST      delete $self->{escape}; # MUST
3318            
3319      my $text = '';      my $text = '';
3320        !!!nack ('t45.1');
3321      !!!next-token;      !!!next-token;
3322      while ($token->{type} == CHARACTER_TOKEN) {      while ($token->{type} == CHARACTER_TOKEN) {
3323        !!!cp ('t45');        !!!cp ('t45');
# Line 3524  sub _tree_construction_main ($) { Line 3633  sub _tree_construction_main ($) {
3633      }      }
3634    }; # $insert_to_foster    }; # $insert_to_foster
3635    
3636    B: {    B: while (1) {
3637      if ($token->{type} == DOCTYPE_TOKEN) {      if ($token->{type} == DOCTYPE_TOKEN) {
3638        !!!cp ('t73');        !!!cp ('t73');
3639        !!!parse-error (type => 'DOCTYPE in the middle', token => $token);        !!!parse-error (type => 'DOCTYPE in the middle', token => $token);
3640        ## Ignore the token        ## Ignore the token
3641        ## Stay in the phase        ## Stay in the phase
3642        !!!next-token;        !!!next-token;
3643        redo B;        next B;
3644      } elsif ($token->{type} == START_TAG_TOKEN and      } elsif ($token->{type} == START_TAG_TOKEN and
3645               $token->{tag_name} eq 'html') {               $token->{tag_name} eq 'html') {
3646        if ($self->{insertion_mode} == AFTER_HTML_BODY_IM) {        if ($self->{insertion_mode} == AFTER_HTML_BODY_IM) {
# Line 3557  sub _tree_construction_main ($) { Line 3666  sub _tree_construction_main ($) {
3666               $token->{attributes}->{$attr_name}->{value});               $token->{attributes}->{$attr_name}->{value});
3667          }          }
3668        }        }
3669          !!!nack ('t84.1');
3670        !!!next-token;        !!!next-token;
3671        redo B;        next B;
3672      } elsif ($token->{type} == COMMENT_TOKEN) {      } elsif ($token->{type} == COMMENT_TOKEN) {
3673        my $comment = $self->{document}->create_comment ($token->{data});        my $comment = $self->{document}->create_comment ($token->{data});
3674        if ($self->{insertion_mode} & AFTER_HTML_IMS) {        if ($self->{insertion_mode} & AFTER_HTML_IMS) {
# Line 3572  sub _tree_construction_main ($) { Line 3682  sub _tree_construction_main ($) {
3682          $self->{open_elements}->[-1]->[0]->append_child ($comment);          $self->{open_elements}->[-1]->[0]->append_child ($comment);
3683        }        }
3684        !!!next-token;        !!!next-token;
3685        redo B;        next B;
3686      } elsif ($self->{insertion_mode} & HEAD_IMS) {      } elsif ($self->{insertion_mode} & IN_FOREIGN_CONTENT_IM) {
3687          if ($token->{type} == CHARACTER_TOKEN) {
3688            !!!cp ('t87.1');
3689            $self->{open_elements}->[-1]->[0]->manakai_append_text ($token->{data});
3690            !!!next-token;
3691            next B;
3692          } elsif ($token->{type} == START_TAG_TOKEN) {
3693            if ($self->{open_elements}->[-1]->[1] & FOREIGN_FLOW_CONTENT_EL or
3694                not ($self->{open_elements}->[-1]->[1] & FOREIGN_EL) or
3695                ($token->{tag_name} eq 'svg' and
3696                 $self->{open_elements}->[-1]->[1] & MML_AXML_EL)) {
3697              ## NOTE: "using the rules for secondary insertion mode"then"continue"
3698              !!!cp ('t87.2');
3699              #
3700            } elsif ({
3701      ## TODO:
3702                     }->{$token->{tag_name}}) {
3703              !!!cp ('t87.2');
3704              !!!parse-error (type => 'not closed',
3705                              value => $self->{open_elements}->[-1]->[0]
3706                                  ->manakai_local_name,
3707                              token => $token);
3708    
3709              pop @{$self->{open_elements}}
3710                  while $self->{open_elements}->[-1]->[1] & FOREIGN_EL;
3711    
3712              $self->{insertion_mode} &= ~ $self->{insertion_mode};
3713              ## Reprocess.
3714              next B;
3715            } else {
3716              ## TODO: case fixup
3717    
3718              !!!insert-element-f ($self->{open_elements}->[-1]->[0]->namespace_uri, $token);
3719    
3720              if ($self->{self_closing}) {
3721                pop @{$self->{open_elements}};
3722                !!!ack ('t87.3');
3723              } else {
3724                !!!cp ('t87.4');
3725              }
3726    
3727              !!!next-token;
3728              next B;
3729            }
3730          } elsif ($token->{type} == END_TAG_TOKEN) {
3731            ## NOTE: "using the rules for secondary insertion mode" then "continue"
3732            !!!cp ('t87.5');
3733            #
3734          } elsif ($token->{type} == END_OF_FILE_TOKEN) {
3735            ## NOTE: "using the rules for secondary insertion mode" then "continue"
3736            !!!cp ('t87.6');
3737            #
3738            ## TODO: ...
3739          } else {
3740            die "$0: $token->{type}: Unknown token type";        
3741          }
3742        }
3743    
3744        if ($self->{insertion_mode} & HEAD_IMS) {
3745        if ($token->{type} == CHARACTER_TOKEN) {        if ($token->{type} == CHARACTER_TOKEN) {
3746          if ($token->{data} =~ s/^([\x09\x0A\x0B\x0C\x20]+)//) {          if ($token->{data} =~ s/^([\x09\x0A\x0B\x0C\x20]+)//) {
3747            unless ($self->{insertion_mode} == BEFORE_HEAD_IM) {            unless ($self->{insertion_mode} == BEFORE_HEAD_IM) {
# Line 3583  sub _tree_construction_main ($) { Line 3751  sub _tree_construction_main ($) {
3751              !!!cp ('t88.1');              !!!cp ('t88.1');
3752              ## Ignore the token.              ## Ignore the token.
3753              !!!next-token;              !!!next-token;
3754              redo B;              next B;
3755            }            }
3756            unless (length $token->{data}) {            unless (length $token->{data}) {
3757              !!!cp ('t88');              !!!cp ('t88');
3758              !!!next-token;              !!!next-token;
3759              redo B;              next B;
3760            }            }
3761          }          }
3762    
3763          if ($self->{insertion_mode} == BEFORE_HEAD_IM) {          if ($self->{insertion_mode} == BEFORE_HEAD_IM) {
3764            !!!cp ('t89');            !!!cp ('t89');
3765            ## As if <head>            ## As if <head>
3766            !!!create-element ($self->{head_element}, 'head',, $token);            !!!create-element ($self->{head_element}, $HTML_NS, 'head',, $token);
3767            $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});            $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});
3768            push @{$self->{open_elements}},            push @{$self->{open_elements}},
3769                [$self->{head_element}, $el_category->{head}];                [$self->{head_element}, $el_category->{head}];
# Line 3629  sub _tree_construction_main ($) { Line 3797  sub _tree_construction_main ($) {
3797          !!!insert-element ('body',, $token);          !!!insert-element ('body',, $token);
3798          $self->{insertion_mode} = IN_BODY_IM;          $self->{insertion_mode} = IN_BODY_IM;
3799          ## reprocess          ## reprocess
3800          redo B;          next B;
3801        } elsif ($token->{type} == START_TAG_TOKEN) {        } elsif ($token->{type} == START_TAG_TOKEN) {
3802          if ($token->{tag_name} eq 'head') {          if ($token->{tag_name} eq 'head') {
3803            if ($self->{insertion_mode} == BEFORE_HEAD_IM) {            if ($self->{insertion_mode} == BEFORE_HEAD_IM) {
3804              !!!cp ('t93');              !!!cp ('t93');
3805              !!!create-element ($self->{head_element}, $token->{tag_name}, $token->{attributes}, $token);              !!!create-element ($self->{head_element}, $HTML_NS, $token->{tag_name}, $token->{attributes}, $token);
3806              $self->{open_elements}->[-1]->[0]->append_child              $self->{open_elements}->[-1]->[0]->append_child
3807                  ($self->{head_element});                  ($self->{head_element});
3808              push @{$self->{open_elements}},              push @{$self->{open_elements}},
3809                  [$self->{head_element}, $el_category->{head}];                  [$self->{head_element}, $el_category->{head}];
3810              $self->{insertion_mode} = IN_HEAD_IM;              $self->{insertion_mode} = IN_HEAD_IM;
3811                !!!nack ('t93.1');
3812              !!!next-token;              !!!next-token;
3813              redo B;              next B;
3814                } elsif ($self->{insertion_mode} == AFTER_HEAD_IM) {            } elsif ($self->{insertion_mode} == AFTER_HEAD_IM) {
3815                  !!!cp ('t94');              !!!cp ('t94');
3816                  #              #
3817                } else {            } else {
3818                  !!!cp ('t95');              !!!cp ('t95');
3819                  !!!parse-error (type => 'in head:head', token => $token); # or in head noscript              !!!parse-error (type => 'in head:head', token => $token); # or in head noscript
3820                  ## Ignore the token              ## Ignore the token
3821                  !!!next-token;              !!!nack ('t95.1');
3822                  redo B;              !!!next-token;
3823                }              next B;
3824              } elsif ($self->{insertion_mode} == BEFORE_HEAD_IM) {            }
3825                !!!cp ('t96');          } elsif ($self->{insertion_mode} == BEFORE_HEAD_IM) {
3826                ## As if <head>            !!!cp ('t96');
3827                !!!create-element ($self->{head_element}, 'head',, $token);            ## As if <head>
3828                $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});            !!!create-element ($self->{head_element}, $HTML_NS, 'head',, $token);
3829                push @{$self->{open_elements}},            $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});
3830                    [$self->{head_element}, $el_category->{head}];            push @{$self->{open_elements}},
3831                  [$self->{head_element}, $el_category->{head}];
3832    
3833                $self->{insertion_mode} = IN_HEAD_IM;            $self->{insertion_mode} = IN_HEAD_IM;
3834                ## Reprocess in the "in head" insertion mode...            ## Reprocess in the "in head" insertion mode...
3835              } else {          } else {
3836                !!!cp ('t97');            !!!cp ('t97');
3837              }          }
3838    
3839              if ($token->{tag_name} eq 'base') {              if ($token->{tag_name} eq 'base') {
3840                if ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {                if ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {
# Line 3692  sub _tree_construction_main ($) { Line 3862  sub _tree_construction_main ($) {
3862                pop @{$self->{open_elements}}; ## ISSUE: This step is missing in the spec.                pop @{$self->{open_elements}}; ## ISSUE: This step is missing in the spec.
3863                pop @{$self->{open_elements}} # <head>                pop @{$self->{open_elements}} # <head>
3864                    if $self->{insertion_mode} == AFTER_HEAD_IM;                    if $self->{insertion_mode} == AFTER_HEAD_IM;
3865                  !!!nack ('t101.1');
3866                !!!next-token;                !!!next-token;
3867                redo B;                next B;
3868              } elsif ($token->{tag_name} eq 'link') {              } elsif ($token->{tag_name} eq 'link') {
3869                ## NOTE: There is a "as if in head" code clone.                ## NOTE: There is a "as if in head" code clone.
3870                if ($self->{insertion_mode} == AFTER_HEAD_IM) {                if ($self->{insertion_mode} == AFTER_HEAD_IM) {
# Line 3708  sub _tree_construction_main ($) { Line 3879  sub _tree_construction_main ($) {
3879                pop @{$self->{open_elements}}; ## ISSUE: This step is missing in the spec.                pop @{$self->{open_elements}}; ## ISSUE: This step is missing in the spec.
3880                pop @{$self->{open_elements}} # <head>                pop @{$self->{open_elements}} # <head>
3881                    if $self->{insertion_mode} == AFTER_HEAD_IM;                    if $self->{insertion_mode} == AFTER_HEAD_IM;
3882                  !!!ack ('t103.1');
3883                !!!next-token;                !!!next-token;
3884                redo B;                next B;
3885              } elsif ($token->{tag_name} eq 'meta') {              } elsif ($token->{tag_name} eq 'meta') {
3886                ## NOTE: There is a "as if in head" code clone.                ## NOTE: There is a "as if in head" code clone.
3887                if ($self->{insertion_mode} == AFTER_HEAD_IM) {                if ($self->{insertion_mode} == AFTER_HEAD_IM) {
# Line 3772  sub _tree_construction_main ($) { Line 3944  sub _tree_construction_main ($) {
3944    
3945                pop @{$self->{open_elements}} # <head>                pop @{$self->{open_elements}} # <head>
3946                    if $self->{insertion_mode} == AFTER_HEAD_IM;                    if $self->{insertion_mode} == AFTER_HEAD_IM;
3947                  !!!ack ('t110.1');
3948                !!!next-token;                !!!next-token;
3949                redo B;                next B;
3950              } elsif ($token->{tag_name} eq 'title') {              } elsif ($token->{tag_name} eq 'title') {
3951                if ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {                if ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {
3952                  !!!cp ('t111');                  !!!cp ('t111');
# Line 3798  sub _tree_construction_main ($) { Line 3971  sub _tree_construction_main ($) {
3971                $parse_rcdata->(RCDATA_CONTENT_MODEL);                $parse_rcdata->(RCDATA_CONTENT_MODEL);
3972                pop @{$self->{open_elements}} # <head>                pop @{$self->{open_elements}} # <head>
3973                    if $self->{insertion_mode} == AFTER_HEAD_IM;                    if $self->{insertion_mode} == AFTER_HEAD_IM;
3974                redo B;                next B;
3975              } elsif ($token->{tag_name} eq 'style') {              } elsif ($token->{tag_name} eq 'style') {
3976                ## NOTE: Or (scripting is enabled and tag_name eq 'noscript' and                ## NOTE: Or (scripting is enabled and tag_name eq 'noscript' and
3977                ## insertion mode IN_HEAD_IM)                ## insertion mode IN_HEAD_IM)
# Line 3814  sub _tree_construction_main ($) { Line 3987  sub _tree_construction_main ($) {
3987                $parse_rcdata->(CDATA_CONTENT_MODEL);                $parse_rcdata->(CDATA_CONTENT_MODEL);
3988                pop @{$self->{open_elements}} # <head>                pop @{$self->{open_elements}} # <head>
3989                    if $self->{insertion_mode} == AFTER_HEAD_IM;                    if $self->{insertion_mode} == AFTER_HEAD_IM;
3990                redo B;                next B;
3991              } elsif ($token->{tag_name} eq 'noscript') {              } elsif ($token->{tag_name} eq 'noscript') {
3992                if ($self->{insertion_mode} == IN_HEAD_IM) {                if ($self->{insertion_mode} == IN_HEAD_IM) {
3993                  !!!cp ('t116');                  !!!cp ('t116');
3994                  ## NOTE: and scripting is disalbed                  ## NOTE: and scripting is disalbed
3995                  !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);                  !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);
3996                  $self->{insertion_mode} = IN_HEAD_NOSCRIPT_IM;                  $self->{insertion_mode} = IN_HEAD_NOSCRIPT_IM;
3997                    !!!nack ('t116.1');
3998                  !!!next-token;                  !!!next-token;
3999                  redo B;                  next B;
4000                } elsif ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {                } elsif ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {
4001                  !!!cp ('t117');                  !!!cp ('t117');
4002                  !!!parse-error (type => 'in noscript:noscript', token => $token);                  !!!parse-error (type => 'in noscript:noscript', token => $token);
4003                  ## Ignore the token                  ## Ignore the token
4004                    !!!nack ('t117.1');
4005                  !!!next-token;                  !!!next-token;
4006                  redo B;                  next B;
4007                } else {                } else {
4008                  !!!cp ('t118');                  !!!cp ('t118');
4009                  #                  #
# Line 3855  sub _tree_construction_main ($) { Line 4030  sub _tree_construction_main ($) {
4030                $script_start_tag->();                $script_start_tag->();
4031                pop @{$self->{open_elements}} # <head>                pop @{$self->{open_elements}} # <head>
4032                    if $self->{insertion_mode} == AFTER_HEAD_IM;                    if $self->{insertion_mode} == AFTER_HEAD_IM;
4033                redo B;                next B;
4034              } elsif ($token->{tag_name} eq 'body' or              } elsif ($token->{tag_name} eq 'body' or
4035                       $token->{tag_name} eq 'frameset') {                       $token->{tag_name} eq 'frameset') {
4036                if ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {                if ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {
# Line 3889  sub _tree_construction_main ($) { Line 4064  sub _tree_construction_main ($) {
4064                } else {                } else {
4065                  die "$0: tag name: $self->{tag_name}";                  die "$0: tag name: $self->{tag_name}";
4066                }                }
4067                  !!!nack ('t127.1');
4068                !!!next-token;                !!!next-token;
4069                redo B;                next B;
4070              } else {              } else {
4071                !!!cp ('t128');                !!!cp ('t128');
4072                #                #
# Line 3922  sub _tree_construction_main ($) { Line 4098  sub _tree_construction_main ($) {
4098              !!!insert-element ('body',, $token);              !!!insert-element ('body',, $token);
4099              $self->{insertion_mode} = IN_BODY_IM;              $self->{insertion_mode} = IN_BODY_IM;
4100              ## reprocess              ## reprocess
4101              redo B;              !!!ack-later;
4102                next B;
4103            } elsif ($token->{type} == END_TAG_TOKEN) {            } elsif ($token->{type} == END_TAG_TOKEN) {
4104              if ($token->{tag_name} eq 'head') {              if ($token->{tag_name} eq 'head') {
4105                if ($self->{insertion_mode} == BEFORE_HEAD_IM) {                if ($self->{insertion_mode} == BEFORE_HEAD_IM) {
4106                  !!!cp ('t132');                  !!!cp ('t132');
4107                  ## As if <head>                  ## As if <head>
4108                  !!!create-element ($self->{head_element}, 'head',, $token);                  !!!create-element ($self->{head_element}, $HTML_NS, 'head',, $token);
4109                  $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});                  $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});
4110                  push @{$self->{open_elements}},                  push @{$self->{open_elements}},
4111                      [$self->{head_element}, $el_category->{head}];                      [$self->{head_element}, $el_category->{head}];
# Line 3937  sub _tree_construction_main ($) { Line 4114  sub _tree_construction_main ($) {
4114                  pop @{$self->{open_elements}};                  pop @{$self->{open_elements}};
4115                  $self->{insertion_mode} = AFTER_HEAD_IM;                  $self->{insertion_mode} = AFTER_HEAD_IM;
4116                  !!!next-token;                  !!!next-token;
4117                  redo B;                  next B;
4118                } elsif ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {                } elsif ($self->{insertion_mode} == IN_HEAD_NOSCRIPT_IM) {
4119                  !!!cp ('t133');                  !!!cp ('t133');
4120                  ## As if </noscript>                  ## As if </noscript>
# Line 3948  sub _tree_construction_main ($) { Line 4125  sub _tree_construction_main ($) {
4125                  pop @{$self->{open_elements}};                  pop @{$self->{open_elements}};
4126                  $self->{insertion_mode} = AFTER_HEAD_IM;                  $self->{insertion_mode} = AFTER_HEAD_IM;
4127                  !!!next-token;                  !!!next-token;
4128                  redo B;                  next B;
4129                } elsif ($self->{insertion_mode} == IN_HEAD_IM) {                } elsif ($self->{insertion_mode} == IN_HEAD_IM) {
4130                  !!!cp ('t134');                  !!!cp ('t134');
4131                  pop @{$self->{open_elements}};                  pop @{$self->{open_elements}};
4132                  $self->{insertion_mode} = AFTER_HEAD_IM;                  $self->{insertion_mode} = AFTER_HEAD_IM;
4133                  !!!next-token;                  !!!next-token;
4134                  redo B;                  next B;
4135                } else {                } else {
4136                  !!!cp ('t135');                  !!!cp ('t135');
4137                  #                  #
# Line 3965  sub _tree_construction_main ($) { Line 4142  sub _tree_construction_main ($) {
4142                  pop @{$self->{open_elements}};                  pop @{$self->{open_elements}};
4143                  $self->{insertion_mode} = IN_HEAD_IM;                  $self->{insertion_mode} = IN_HEAD_IM;
4144                  !!!next-token;                  !!!next-token;
4145                  redo B;                  next B;
4146                } elsif ($self->{insertion_mode} == BEFORE_HEAD_IM) {                } elsif ($self->{insertion_mode} == BEFORE_HEAD_IM) {
4147                  !!!cp ('t137');                  !!!cp ('t137');
4148                  !!!parse-error (type => 'unmatched end tag:noscript', token => $token);                  !!!parse-error (type => 'unmatched end tag:noscript', token => $token);
4149                  ## Ignore the token ## ISSUE: An issue in the spec.                  ## Ignore the token ## ISSUE: An issue in the spec.
4150                  !!!next-token;                  !!!next-token;
4151                  redo B;                  next B;
4152                } else {                } else {
4153                  !!!cp ('t138');                  !!!cp ('t138');
4154                  #                  #
# Line 3982  sub _tree_construction_main ($) { Line 4159  sub _tree_construction_main ($) {
4159                if ($self->{insertion_mode} == BEFORE_HEAD_IM) {                if ($self->{insertion_mode} == BEFORE_HEAD_IM) {
4160                  !!!cp ('t139');                  !!!cp ('t139');
4161                  ## As if <head>                  ## As if <head>
4162                  !!!create-element ($self->{head_element}, 'head',, $token);                  !!!create-element ($self->{head_element}, $HTML_NS, 'head',, $token);
4163                  $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});                  $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});
4164                  push @{$self->{open_elements}},                  push @{$self->{open_elements}},
4165                      [$self->{head_element}, $el_category->{head}];                      [$self->{head_element}, $el_category->{head}];
# Line 3994  sub _tree_construction_main ($) { Line 4171  sub _tree_construction_main ($) {
4171                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4172                  ## Ignore the token                  ## Ignore the token
4173                  !!!next-token;                  !!!next-token;
4174                  redo B;                  next B;
4175                } else {                } else {
4176                  !!!cp ('t141');                  !!!cp ('t141');
4177                }                }
# Line 4006  sub _tree_construction_main ($) { Line 4183  sub _tree_construction_main ($) {
4183                if ($self->{insertion_mode} == BEFORE_HEAD_IM) {                if ($self->{insertion_mode} == BEFORE_HEAD_IM) {
4184                  !!!cp ('t142');                  !!!cp ('t142');
4185                  ## As if <head>                  ## As if <head>
4186                  !!!create-element ($self->{head_element}, 'head',, $token);                  !!!create-element ($self->{head_element}, $HTML_NS, 'head',, $token);
4187                  $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});                  $self->{open_elements}->[-1]->[0]->append_child ($self->{head_element});
4188                  push @{$self->{open_elements}},                  push @{$self->{open_elements}},
4189                      [$self->{head_element}, $el_category->{head}];                      [$self->{head_element}, $el_category->{head}];
# Line 4027  sub _tree_construction_main ($) { Line 4204  sub _tree_construction_main ($) {
4204                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4205                  ## Ignore the token                  ## Ignore the token
4206                  !!!next-token;                  !!!next-token;
4207                  redo B;                  next B;
4208                }                }
4209              }              }
4210    
# Line 4054  sub _tree_construction_main ($) { Line 4231  sub _tree_construction_main ($) {
4231                !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4232                ## Ignore the token ## ISSUE: An issue in the spec.                ## Ignore the token ## ISSUE: An issue in the spec.
4233                !!!next-token;                !!!next-token;
4234                redo B;                next B;
4235              } else {              } else {
4236                !!!cp ('t149');                !!!cp ('t149');
4237              }              }
# Line 4064  sub _tree_construction_main ($) { Line 4241  sub _tree_construction_main ($) {
4241              !!!insert-element ('body',, $token);              !!!insert-element ('body',, $token);
4242              $self->{insertion_mode} = IN_BODY_IM;              $self->{insertion_mode} = IN_BODY_IM;
4243              ## reprocess              ## reprocess
4244              redo B;              next B;
4245        } elsif ($token->{type} == END_OF_FILE_TOKEN) {        } elsif ($token->{type} == END_OF_FILE_TOKEN) {
4246          if ($self->{insertion_mode} == BEFORE_HEAD_IM) {          if ($self->{insertion_mode} == BEFORE_HEAD_IM) {
4247            !!!cp ('t149.1');            !!!cp ('t149.1');
4248    
4249            ## NOTE: As if <head>            ## NOTE: As if <head>
4250            !!!create-element ($self->{head_element}, 'head',, $token);            !!!create-element ($self->{head_element}, $HTML_NS, 'head',, $token);
4251            $self->{open_elements}->[-1]->[0]->append_child            $self->{open_elements}->[-1]->[0]->append_child
4252                ($self->{head_element});                ($self->{head_element});
4253            #push @{$self->{open_elements}},            #push @{$self->{open_elements}},
# Line 4118  sub _tree_construction_main ($) { Line 4295  sub _tree_construction_main ($) {
4295          !!!insert-element ('body',, $token);          !!!insert-element ('body',, $token);
4296          $self->{insertion_mode} = IN_BODY_IM;          $self->{insertion_mode} = IN_BODY_IM;
4297          ## NOTE: Reprocess.          ## NOTE: Reprocess.
4298          redo B;          next B;
4299        } else {        } else {
4300          die "$0: $token->{type}: Unknown token type";          die "$0: $token->{type}: Unknown token type";
4301        }        }
# Line 4133  sub _tree_construction_main ($) { Line 4310  sub _tree_construction_main ($) {
4310              $self->{open_elements}->[-1]->[0]->manakai_append_text ($token->{data});              $self->{open_elements}->[-1]->[0]->manakai_append_text ($token->{data});
4311    
4312              !!!next-token;              !!!next-token;
4313              redo B;              next B;
4314            } elsif ($token->{type} == START_TAG_TOKEN) {            } elsif ($token->{type} == START_TAG_TOKEN) {
4315              if ({              if ({
4316                   caption => 1, col => 1, colgroup => 1, tbody => 1,                   caption => 1, col => 1, colgroup => 1, tbody => 1,
# Line 4147  sub _tree_construction_main ($) { Line 4324  sub _tree_construction_main ($) {
4324                      !!!cp ('t151');                      !!!cp ('t151');
4325    
4326                      ## Close the cell                      ## Close the cell
4327                      !!!back-token; # <?>                      !!!back-token; # <x>
4328                      $token = {type => END_TAG_TOKEN,                      $token = {type => END_TAG_TOKEN,
4329                                tag_name => $node->[0]->manakai_local_name,                                tag_name => $node->[0]->manakai_local_name,
4330                                line => $token->{line},                                line => $token->{line},
4331                                column => $token->{column}};                                column => $token->{column}};
4332                      redo B;                      next B;
4333                    } elsif ($node->[1] & TABLE_SCOPING_EL) {                    } elsif ($node->[1] & TABLE_SCOPING_EL) {
4334                      !!!cp ('t152');                      !!!cp ('t152');
4335                      ## ISSUE: This case can never be reached, maybe.                      ## ISSUE: This case can never be reached, maybe.
# Line 4164  sub _tree_construction_main ($) { Line 4341  sub _tree_construction_main ($) {
4341                  !!!parse-error (type => 'start tag not allowed',                  !!!parse-error (type => 'start tag not allowed',
4342                      value => $token->{tag_name}, token => $token);                      value => $token->{tag_name}, token => $token);
4343                  ## Ignore the token                  ## Ignore the token
4344                    !!!nack ('t153.1');
4345                  !!!next-token;                  !!!next-token;
4346                  redo B;                  next B;
4347                } elsif ($self->{insertion_mode} == IN_CAPTION_IM) {                } elsif ($self->{insertion_mode} == IN_CAPTION_IM) {
4348                  !!!parse-error (type => 'not closed:caption', token => $token);                  !!!parse-error (type => 'not closed:caption', token => $token);
4349                                    
# Line 4189  sub _tree_construction_main ($) { Line 4367  sub _tree_construction_main ($) {
4367                    !!!parse-error (type => 'start tag not allowed',                    !!!parse-error (type => 'start tag not allowed',
4368                                    value => $token->{tag_name}, token => $token);                                    value => $token->{tag_name}, token => $token);
4369                    ## Ignore the token                    ## Ignore the token
4370                      !!!nack ('t157.1');
4371                    !!!next-token;                    !!!next-token;
4372                    redo B;                    next B;
4373                  } # INSCOPE                  } # INSCOPE
4374                                    
4375                  ## generate implied end tags                  ## generate implied end tags
# Line 4217  sub _tree_construction_main ($) { Line 4396  sub _tree_construction_main ($) {
4396                  $self->{insertion_mode} = IN_TABLE_IM;                  $self->{insertion_mode} = IN_TABLE_IM;
4397                                    
4398                  ## reprocess                  ## reprocess
4399                  redo B;                  !!!ack-later;
4400                    next B;
4401                } else {                } else {
4402                  !!!cp ('t161');                  !!!cp ('t161');
4403                  #                  #
# Line 4247  sub _tree_construction_main ($) { Line 4427  sub _tree_construction_main ($) {
4427                      !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                      !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4428                      ## Ignore the token                      ## Ignore the token
4429                      !!!next-token;                      !!!next-token;
4430                      redo B;                      next B;
4431                    }                    }
4432                                    
4433                  ## generate implied end tags                  ## generate implied end tags
# Line 4275  sub _tree_construction_main ($) { Line 4455  sub _tree_construction_main ($) {
4455                  $self->{insertion_mode} = IN_ROW_IM;                  $self->{insertion_mode} = IN_ROW_IM;
4456                                    
4457                  !!!next-token;                  !!!next-token;
4458                  redo B;                  next B;
4459                } elsif ($self->{insertion_mode} == IN_CAPTION_IM) {                } elsif ($self->{insertion_mode} == IN_CAPTION_IM) {
4460                  !!!cp ('t169');                  !!!cp ('t169');
4461                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4462                  ## Ignore the token                  ## Ignore the token
4463                  !!!next-token;                  !!!next-token;
4464                  redo B;                  next B;
4465                } else {                } else {
4466                  !!!cp ('t170');                  !!!cp ('t170');
4467                  #                  #
# Line 4308  sub _tree_construction_main ($) { Line 4488  sub _tree_construction_main ($) {
4488                                    value => $token->{tag_name}, token => $token);                                    value => $token->{tag_name}, token => $token);
4489                    ## Ignore the token                    ## Ignore the token
4490                    !!!next-token;                    !!!next-token;
4491                    redo B;                    next B;
4492                  } # INSCOPE                  } # INSCOPE
4493                                    
4494                  ## generate implied end tags                  ## generate implied end tags
# Line 4335  sub _tree_construction_main ($) { Line 4515  sub _tree_construction_main ($) {
4515                  $self->{insertion_mode} = IN_TABLE_IM;                  $self->{insertion_mode} = IN_TABLE_IM;
4516                                    
4517                  !!!next-token;                  !!!next-token;
4518                  redo B;                  next B;
4519                } elsif ($self->{insertion_mode} == IN_CELL_IM) {                } elsif ($self->{insertion_mode} == IN_CELL_IM) {
4520                  !!!cp ('t177');                  !!!cp ('t177');
4521                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4522                  ## Ignore the token                  ## Ignore the token
4523                  !!!next-token;                  !!!next-token;
4524                  redo B;                  next B;
4525                } else {                } else {
4526                  !!!cp ('t178');                  !!!cp ('t178');
4527                  #                  #
# Line 4362  sub _tree_construction_main ($) { Line 4542  sub _tree_construction_main ($) {
4542                      $i = $_;                      $i = $_;
4543    
4544                      ## Close the cell                      ## Close the cell
4545                      !!!back-token; # </?>                      !!!back-token; # </x>
4546                      $token = {type => END_TAG_TOKEN, tag_name => $tn,                      $token = {type => END_TAG_TOKEN, tag_name => $tn,
4547                                line => $token->{line},                                line => $token->{line},
4548                                column => $token->{column}};                                column => $token->{column}};
4549                      redo B;                      next B;
4550                    } elsif ($node->[1] & TABLE_CELL_EL) {                    } elsif ($node->[1] & TABLE_CELL_EL) {
4551                      !!!cp ('t180');                      !!!cp ('t180');
4552                      $tn = $node->[0]->manakai_local_name;                      $tn = $node->[0]->manakai_local_name;
# Line 4384  sub _tree_construction_main ($) { Line 4564  sub _tree_construction_main ($) {
4564                      value => $token->{tag_name}, token => $token);                      value => $token->{tag_name}, token => $token);
4565                  ## Ignore the token                  ## Ignore the token
4566                  !!!next-token;                  !!!next-token;
4567                  redo B;                  next B;
4568                } # INSCOPE                } # INSCOPE
4569              } elsif ($token->{tag_name} eq 'table' and              } elsif ($token->{tag_name} eq 'table' and
4570                       $self->{insertion_mode} == IN_CAPTION_IM) {                       $self->{insertion_mode} == IN_CAPTION_IM) {
# Line 4409  sub _tree_construction_main ($) { Line 4589  sub _tree_construction_main ($) {
4589                  !!!parse-error (type => 'unmatched end tag:caption', token => $token);                  !!!parse-error (type => 'unmatched end tag:caption', token => $token);
4590                  ## Ignore the token                  ## Ignore the token
4591                  !!!next-token;                  !!!next-token;
4592                  redo B;                  next B;
4593                }                }
4594                                
4595                ## generate implied end tags                ## generate implied end tags
# Line 4435  sub _tree_construction_main ($) { Line 4615  sub _tree_construction_main ($) {
4615                $self->{insertion_mode} = IN_TABLE_IM;                $self->{insertion_mode} = IN_TABLE_IM;
4616    
4617                ## reprocess                ## reprocess
4618                redo B;                next B;
4619              } elsif ({              } elsif ({
4620                        body => 1, col => 1, colgroup => 1, html => 1,                        body => 1, col => 1, colgroup => 1, html => 1,
4621                       }->{$token->{tag_name}}) {                       }->{$token->{tag_name}}) {
# Line 4444  sub _tree_construction_main ($) { Line 4624  sub _tree_construction_main ($) {
4624                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4625                  ## Ignore the token                  ## Ignore the token
4626                  !!!next-token;                  !!!next-token;
4627                  redo B;                  next B;
4628                } else {                } else {
4629                  !!!cp ('t191');                  !!!cp ('t191');
4630                  #                  #
# Line 4458  sub _tree_construction_main ($) { Line 4638  sub _tree_construction_main ($) {
4638                !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4639                ## Ignore the token                ## Ignore the token
4640                !!!next-token;                !!!next-token;
4641                redo B;                next B;
4642              } else {              } else {
4643                !!!cp ('t193');                !!!cp ('t193');
4644                #                #
# Line 4489  sub _tree_construction_main ($) { Line 4669  sub _tree_construction_main ($) {
4669            unless (length $token->{data}) {            unless (length $token->{data}) {
4670              !!!cp ('t194');              !!!cp ('t194');
4671              !!!next-token;              !!!next-token;
4672              redo B;              next B;
4673            } else {            } else {
4674              !!!cp ('t195');              !!!cp ('t195');
4675            }            }
# Line 4544  sub _tree_construction_main ($) { Line 4724  sub _tree_construction_main ($) {
4724          }          }
4725                            
4726          !!!next-token;          !!!next-token;
4727          redo B;          next B;
4728        } elsif ($token->{type} == START_TAG_TOKEN) {        } elsif ($token->{type} == START_TAG_TOKEN) {
4729              if ({              if ({
4730                   tr => ($self->{insertion_mode} != IN_ROW_IM),                   tr => ($self->{insertion_mode} != IN_ROW_IM),
# Line 4581  sub _tree_construction_main ($) { Line 4761  sub _tree_construction_main ($) {
4761                  if ($token->{tag_name} eq 'tr') {                  if ($token->{tag_name} eq 'tr') {
4762                    !!!cp ('t204');                    !!!cp ('t204');
4763                    !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);                    !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);
4764                      !!!nack ('t204');
4765                    !!!next-token;                    !!!next-token;
4766                    redo B;                    next B;
4767                  } else {                  } else {
4768                    !!!cp ('t205');                    !!!cp ('t205');
4769                    !!!insert-element ('tr',, $token);                    !!!insert-element ('tr',, $token);
# Line 4604  sub _tree_construction_main ($) { Line 4785  sub _tree_construction_main ($) {
4785    
4786                push @$active_formatting_elements, ['#marker', ''];                push @$active_formatting_elements, ['#marker', ''];
4787                                
4788                  !!!nack ('t207.1');
4789                !!!next-token;                !!!next-token;
4790                redo B;                next B;
4791              } elsif ({              } elsif ({
4792                        caption => 1, col => 1, colgroup => 1,                        caption => 1, col => 1, colgroup => 1,
4793                        tbody => 1, tfoot => 1, thead => 1,                        tbody => 1, tfoot => 1, thead => 1,
# Line 4627  sub _tree_construction_main ($) { Line 4809  sub _tree_construction_main ($) {
4809                    }                    }
4810                  } # INSCOPE                  } # INSCOPE
4811                  unless (defined $i) {                  unless (defined $i) {
4812                   !!!cp ('t210');                    !!!cp ('t210');
4813  ## TODO: This type is wrong.  ## TODO: This type is wrong.
4814                   !!!parse-error (type => 'unmacthed end tag:'.$token->{tag_name}, token => $token);                    !!!parse-error (type => 'unmacthed end tag:'.$token->{tag_name}, token => $token);
4815                    ## Ignore the token                    ## Ignore the token
4816                      !!!nack ('t210.1');
4817                    !!!next-token;                    !!!next-token;
4818                    redo B;                    next B;
4819                  }                  }
4820                                    
4821                  ## Clear back to table row context                  ## Clear back to table row context
# Line 4648  sub _tree_construction_main ($) { Line 4831  sub _tree_construction_main ($) {
4831                  if ($token->{tag_name} eq 'tr') {                  if ($token->{tag_name} eq 'tr') {
4832                    !!!cp ('t212');                    !!!cp ('t212');
4833                    ## reprocess                    ## reprocess
4834                    redo B;                    !!!ack-later;
4835                      next B;
4836                  } else {                  } else {
4837                    !!!cp ('t213');                    !!!cp ('t213');
4838                    ## reprocess in the "in table body" insertion mode...                    ## reprocess in the "in table body" insertion mode...
# Line 4674  sub _tree_construction_main ($) { Line 4858  sub _tree_construction_main ($) {
4858  ## TODO: This erorr type ios wrong.  ## TODO: This erorr type ios wrong.
4859                    !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                    !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
4860                    ## Ignore the token                    ## Ignore the token
4861                      !!!nack ('t216.1');
4862                    !!!next-token;                    !!!next-token;
4863                    redo B;                    next B;
4864                  }                  }
4865    
4866                  ## Clear back to table body context                  ## Clear back to table body context
# Line 4712  sub _tree_construction_main ($) { Line 4897  sub _tree_construction_main ($) {
4897                  !!!insert-element ('colgroup',, $token);                  !!!insert-element ('colgroup',, $token);
4898                  $self->{insertion_mode} = IN_COLUMN_GROUP_IM;                  $self->{insertion_mode} = IN_COLUMN_GROUP_IM;
4899                  ## reprocess                  ## reprocess
4900                  redo B;                  !!!ack-later;
4901                    next B;
4902                } elsif ({                } elsif ({
4903                          caption => 1,                          caption => 1,
4904                          colgroup => 1,                          colgroup => 1,
# Line 4738  sub _tree_construction_main ($) { Line 4924  sub _tree_construction_main ($) {
4924                                             thead => IN_TABLE_BODY_IM,                                             thead => IN_TABLE_BODY_IM,
4925                                            }->{$token->{tag_name}};                                            }->{$token->{tag_name}};
4926                  !!!next-token;                  !!!next-token;
4927                  redo B;                  !!!nack ('t220.1');
4928                    next B;
4929                } else {                } else {
4930                  die "$0: in table: <>: $token->{tag_name}";                  die "$0: in table: <>: $token->{tag_name}";
4931                }                }
# Line 4767  sub _tree_construction_main ($) { Line 4954  sub _tree_construction_main ($) {
4954  ## TODO: The following is wrong, maybe.  ## TODO: The following is wrong, maybe.
4955                  !!!parse-error (type => 'unmatched end tag:table', token => $token);                  !!!parse-error (type => 'unmatched end tag:table', token => $token);
4956                  ## Ignore tokens </table><table>                  ## Ignore tokens </table><table>
4957                    !!!nack ('t223.1');
4958                  !!!next-token;                  !!!next-token;
4959                  redo B;                  next B;
4960                }                }
4961                                
4962  ## TODO: Followings are removed from the latest spec.  ## TODO: Followings are removed from the latest spec.
# Line 4794  sub _tree_construction_main ($) { Line 4982  sub _tree_construction_main ($) {
4982    
4983                $self->_reset_insertion_mode;                $self->_reset_insertion_mode;
4984    
4985                ## reprocess            ## reprocess
4986                redo B;            !!!ack-later;
4987              next B;
4988          } elsif ($token->{tag_name} eq 'style') {          } elsif ($token->{tag_name} eq 'style') {
4989            if (not $open_tables->[-1]->[1]) { # tainted            if (not $open_tables->[-1]->[1]) { # tainted
4990              !!!cp ('t227.8');              !!!cp ('t227.8');
4991              ## NOTE: This is a "as if in head" code clone.              ## NOTE: This is a "as if in head" code clone.
4992              $parse_rcdata->(CDATA_CONTENT_MODEL);              $parse_rcdata->(CDATA_CONTENT_MODEL);
4993              redo B;              next B;
4994            } else {            } else {
4995              !!!cp ('t227.7');              !!!cp ('t227.7');
4996              #              #
# Line 4811  sub _tree_construction_main ($) { Line 5000  sub _tree_construction_main ($) {
5000              !!!cp ('t227.6');              !!!cp ('t227.6');
5001              ## NOTE: This is a "as if in head" code clone.              ## NOTE: This is a "as if in head" code clone.
5002              $script_start_tag->();              $script_start_tag->();
5003              redo B;              next B;
5004            } else {            } else {
5005              !!!cp ('t227.5');              !!!cp ('t227.5');
5006              #              #
# Line 4831  sub _tree_construction_main ($) { Line 5020  sub _tree_construction_main ($) {
5020                  pop @{$self->{open_elements}};                  pop @{$self->{open_elements}};
5021    
5022                  !!!next-token;                  !!!next-token;
5023                  redo B;                  !!!ack ('t227.2.1');
5024                    next B;
5025                } else {                } else {
5026                  !!!cp ('t227.2');                  !!!cp ('t227.2');
5027                  #                  #
# Line 4873  sub _tree_construction_main ($) { Line 5063  sub _tree_construction_main ($) {
5063                  !!!cp ('t230');                  !!!cp ('t230');
5064                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5065                  ## Ignore the token                  ## Ignore the token
5066                    !!!nack ('t230.1');
5067                  !!!next-token;                  !!!next-token;
5068                  redo B;                  next B;
5069                } else {                } else {
5070                  !!!cp ('t232');                  !!!cp ('t232');
5071                }                }
# Line 4890  sub _tree_construction_main ($) { Line 5081  sub _tree_construction_main ($) {
5081                pop @{$self->{open_elements}}; # tr                pop @{$self->{open_elements}}; # tr
5082                $self->{insertion_mode} = IN_TABLE_BODY_IM;                $self->{insertion_mode} = IN_TABLE_BODY_IM;
5083                !!!next-token;                !!!next-token;
5084                redo B;                !!!nack ('t231.1');
5085                  next B;
5086              } elsif ($token->{tag_name} eq 'table') {              } elsif ($token->{tag_name} eq 'table') {
5087                if ($self->{insertion_mode} == IN_ROW_IM) {                if ($self->{insertion_mode} == IN_ROW_IM) {
5088                  ## As if </tr>                  ## As if </tr>
# Line 4912  sub _tree_construction_main ($) { Line 5104  sub _tree_construction_main ($) {
5104  ## TODO: The following is wrong.  ## TODO: The following is wrong.
5105                    !!!parse-error (type => 'unmatched end tag:'.$token->{type}, token => $token);                    !!!parse-error (type => 'unmatched end tag:'.$token->{type}, token => $token);
5106                    ## Ignore the token                    ## Ignore the token
5107                      !!!nack ('t236.1');
5108                    !!!next-token;                    !!!next-token;
5109                    redo B;                    next B;
5110                  }                  }
5111                                    
5112                  ## Clear back to table row context                  ## Clear back to table row context
# Line 4947  sub _tree_construction_main ($) { Line 5140  sub _tree_construction_main ($) {
5140                    !!!cp ('t239');                    !!!cp ('t239');
5141                    !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                    !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5142                    ## Ignore the token                    ## Ignore the token
5143                      !!!nack ('t239.1');
5144                    !!!next-token;                    !!!next-token;
5145                    redo B;                    next B;
5146                  }                  }
5147                                    
5148                  ## Clear back to table body context                  ## Clear back to table body context
# Line 4992  sub _tree_construction_main ($) { Line 5186  sub _tree_construction_main ($) {
5186                  !!!cp ('t243');                  !!!cp ('t243');
5187                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5188                  ## Ignore the token                  ## Ignore the token
5189                    !!!nack ('t243.1');
5190                  !!!next-token;                  !!!next-token;
5191                  redo B;                  next B;
5192                }                }
5193                                    
5194                splice @{$self->{open_elements}}, $i;                splice @{$self->{open_elements}}, $i;
# Line 5002  sub _tree_construction_main ($) { Line 5197  sub _tree_construction_main ($) {
5197                $self->_reset_insertion_mode;                $self->_reset_insertion_mode;
5198                                
5199                !!!next-token;                !!!next-token;
5200                redo B;                next B;
5201              } elsif ({              } elsif ({
5202                        tbody => 1, tfoot => 1, thead => 1,                        tbody => 1, tfoot => 1, thead => 1,
5203                       }->{$token->{tag_name}} and                       }->{$token->{tag_name}} and
# Line 5025  sub _tree_construction_main ($) { Line 5220  sub _tree_construction_main ($) {
5220                      !!!cp ('t249');                      !!!cp ('t249');
5221                      !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                      !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5222                      ## Ignore the token                      ## Ignore the token
5223                        !!!nack ('t249.1');
5224                      !!!next-token;                      !!!next-token;
5225                      redo B;                      next B;
5226                    }                    }
5227                                    
5228                  ## As if </tr>                  ## As if </tr>
# Line 5047  sub _tree_construction_main ($) { Line 5243  sub _tree_construction_main ($) {
5243                      !!!cp ('t252');                      !!!cp ('t252');
5244                      !!!parse-error (type => 'unmatched end tag:tr', token => $token);                      !!!parse-error (type => 'unmatched end tag:tr', token => $token);
5245                      ## Ignore the token                      ## Ignore the token
5246                        !!!nack ('t252.1');
5247                      !!!next-token;                      !!!next-token;
5248                      redo B;                      next B;
5249                    }                    }
5250                                    
5251                  ## Clear back to table row context                  ## Clear back to table row context
# Line 5081  sub _tree_construction_main ($) { Line 5278  sub _tree_construction_main ($) {
5278                  !!!cp ('t256');                  !!!cp ('t256');
5279                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);                  !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5280                  ## Ignore the token                  ## Ignore the token
5281                    !!!nack ('t256.1');
5282                  !!!next-token;                  !!!next-token;
5283                  redo B;                  next B;
5284                }                }
5285    
5286                ## Clear back to table body context                ## Clear back to table body context
# Line 5095  sub _tree_construction_main ($) { Line 5293  sub _tree_construction_main ($) {
5293    
5294                pop @{$self->{open_elements}};                pop @{$self->{open_elements}};
5295                $self->{insertion_mode} = IN_TABLE_IM;                $self->{insertion_mode} = IN_TABLE_IM;
5296                  !!!nack ('t257.1');
5297                !!!next-token;                !!!next-token;
5298                redo B;                next B;
5299              } elsif ({              } elsif ({
5300                        body => 1, caption => 1, col => 1, colgroup => 1,                        body => 1, caption => 1, col => 1, colgroup => 1,
5301                        html => 1, td => 1, th => 1,                        html => 1, td => 1, th => 1,
5302                        tr => 1, # $self->{insertion_mode} == IN_ROW_IM                        tr => 1, # $self->{insertion_mode} == IN_ROW_IM
5303                        tbody => 1, tfoot => 1, thead => 1, # $self->{insertion_mode} == IN_TABLE_IM                        tbody => 1, tfoot => 1, thead => 1, # $self->{insertion_mode} == IN_TABLE_IM
5304                       }->{$token->{tag_name}}) {                       }->{$token->{tag_name}}) {
5305                !!!cp ('t258');            !!!cp ('t258');
5306                !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);            !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5307                ## Ignore the token            ## Ignore the token
5308                !!!next-token;            !!!nack ('t258.1');
5309                redo B;             !!!next-token;
5310              next B;
5311          } else {          } else {
5312            !!!cp ('t259');            !!!cp ('t259');
5313            !!!parse-error (type => 'in table:/'.$token->{tag_name}, token => $token);            !!!parse-error (type => 'in table:/'.$token->{tag_name}, token => $token);
# Line 5138  sub _tree_construction_main ($) { Line 5338  sub _tree_construction_main ($) {
5338                unless (length $token->{data}) {                unless (length $token->{data}) {
5339                  !!!cp ('t260');                  !!!cp ('t260');
5340                  !!!next-token;                  !!!next-token;
5341                  redo B;                  next B;
5342                }                }
5343              }              }
5344                            
# Line 5149  sub _tree_construction_main ($) { Line 5349  sub _tree_construction_main ($) {
5349                !!!cp ('t262');                !!!cp ('t262');
5350                !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);                !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);
5351                pop @{$self->{open_elements}};                pop @{$self->{open_elements}};
5352                  !!!ack ('t262.1');
5353                !!!next-token;                !!!next-token;
5354                redo B;                next B;
5355              } else {              } else {
5356                !!!cp ('t263');                !!!cp ('t263');
5357                #                #
# Line 5162  sub _tree_construction_main ($) { Line 5363  sub _tree_construction_main ($) {
5363                  !!!parse-error (type => 'unmatched end tag:colgroup', token => $token);                  !!!parse-error (type => 'unmatched end tag:colgroup', token => $token);
5364                  ## Ignore the token                  ## Ignore the token
5365                  !!!next-token;                  !!!next-token;
5366                  redo B;                  next B;
5367                } else {                } else {
5368                  !!!cp ('t265');                  !!!cp ('t265');
5369                  pop @{$self->{open_elements}}; # colgroup                  pop @{$self->{open_elements}}; # colgroup
5370                  $self->{insertion_mode} = IN_TABLE_IM;                  $self->{insertion_mode} = IN_TABLE_IM;
5371                  !!!next-token;                  !!!next-token;
5372                  redo B;                              next B;            
5373                }                }
5374              } elsif ($token->{tag_name} eq 'col') {              } elsif ($token->{tag_name} eq 'col') {
5375                !!!cp ('t266');                !!!cp ('t266');
5376                !!!parse-error (type => 'unmatched end tag:col', token => $token);                !!!parse-error (type => 'unmatched end tag:col', token => $token);
5377                ## Ignore the token                ## Ignore the token
5378                !!!next-token;                !!!next-token;
5379                redo B;                next B;
5380              } else {              } else {
5381                !!!cp ('t267');                !!!cp ('t267');
5382                #                #
# Line 5192  sub _tree_construction_main ($) { Line 5393  sub _tree_construction_main ($) {
5393            pop @{$self->{open_elements}}; # colgroup            pop @{$self->{open_elements}}; # colgroup
5394            $self->{insertion_mode} = IN_TABLE_IM;            $self->{insertion_mode} = IN_TABLE_IM;
5395            ## Reprocess.            ## Reprocess.
5396            redo B;            next B;
5397          }          }
5398        } else {        } else {
5399          die "$0: $token->{type}: Unknown token type";          die "$0: $token->{type}: Unknown token type";
# Line 5204  sub _tree_construction_main ($) { Line 5405  sub _tree_construction_main ($) {
5405  ## TODO: Wrong error type?  ## TODO: Wrong error type?
5406              !!!parse-error (type => 'unmatched end tag:colgroup', token => $token);              !!!parse-error (type => 'unmatched end tag:colgroup', token => $token);
5407              ## Ignore the token              ## Ignore the token
5408                !!!nack ('t269.1');
5409              !!!next-token;              !!!next-token;
5410              redo B;              next B;
5411            } else {            } else {
5412              !!!cp ('t270');              !!!cp ('t270');
5413              pop @{$self->{open_elements}}; # colgroup              pop @{$self->{open_elements}}; # colgroup
5414              $self->{insertion_mode} = IN_TABLE_IM;              $self->{insertion_mode} = IN_TABLE_IM;
5415                !!!ack-later;
5416              ## reprocess              ## reprocess
5417              redo B;              next B;
5418            }            }
5419      } elsif ($self->{insertion_mode} & SELECT_IMS) {      } elsif ($self->{insertion_mode} & SELECT_IMS) {
5420        if ($token->{type} == CHARACTER_TOKEN) {        if ($token->{type} == CHARACTER_TOKEN) {
5421          !!!cp ('t271');          !!!cp ('t271');
5422          $self->{open_elements}->[-1]->[0]->manakai_append_text ($token->{data});          $self->{open_elements}->[-1]->[0]->manakai_append_text ($token->{data});
5423          !!!next-token;          !!!next-token;
5424          redo B;          next B;
5425        } elsif ($token->{type} == START_TAG_TOKEN) {        } elsif ($token->{type} == START_TAG_TOKEN) {
5426          if ($token->{tag_name} eq 'option') {          if ($token->{tag_name} eq 'option') {
5427            if ($self->{open_elements}->[-1]->[1] & OPTION_EL) {            if ($self->{open_elements}->[-1]->[1] & OPTION_EL) {
# Line 5230  sub _tree_construction_main ($) { Line 5433  sub _tree_construction_main ($) {
5433            }            }
5434    
5435            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);
5436              !!!nack ('t273.1');
5437            !!!next-token;            !!!next-token;
5438            redo B;            next B;
5439          } elsif ($token->{tag_name} eq 'optgroup') {          } elsif ($token->{tag_name} eq 'optgroup') {
5440            if ($self->{open_elements}->[-1]->[1] & OPTION_EL) {            if ($self->{open_elements}->[-1]->[1] & OPTION_EL) {
5441              !!!cp ('t274');              !!!cp ('t274');
# Line 5250  sub _tree_construction_main ($) { Line 5454  sub _tree_construction_main ($) {
5454            }            }
5455    
5456            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);
5457              !!!nack ('t277.1');
5458            !!!next-token;            !!!next-token;
5459            redo B;            next B;
5460          } elsif ($token->{tag_name} eq 'select' or          } elsif ($token->{tag_name} eq 'select' or
5461                   $token->{tag_name} eq 'input' or                   $token->{tag_name} eq 'input' or
5462                   ($self->{insertion_mode} == IN_SELECT_IN_TABLE_IM and                   ($self->{insertion_mode} == IN_SELECT_IN_TABLE_IM and
# Line 5281  sub _tree_construction_main ($) { Line 5486  sub _tree_construction_main ($) {
5486              !!!cp ('t280');              !!!cp ('t280');
5487              !!!parse-error (type => 'unmatched end tag:select', token => $token);              !!!parse-error (type => 'unmatched end tag:select', token => $token);
5488              ## Ignore the token              ## Ignore the token
5489                !!!nack ('t280.1');
5490              !!!next-token;              !!!next-token;
5491              redo B;              next B;
5492            }            }
5493                                
5494            !!!cp ('t281');            !!!cp ('t281');
# Line 5291  sub _tree_construction_main ($) { Line 5497  sub _tree_construction_main ($) {
5497            $self->_reset_insertion_mode;            $self->_reset_insertion_mode;
5498    
5499            if ($token->{tag_name} eq 'select') {            if ($token->{tag_name} eq 'select') {
5500              !!!cp ('t281.2');              !!!nack ('t281.2');
5501              !!!next-token;              !!!next-token;
5502              redo B;              next B;
5503            } else {            } else {
5504              !!!cp ('t281.1');              !!!cp ('t281.1');
5505                !!!ack-later;
5506              ## Reprocess the token.              ## Reprocess the token.
5507              redo B;              next B;
5508            }            }
5509          } else {          } else {
5510            !!!cp ('t282');            !!!cp ('t282');
5511            !!!parse-error (type => 'in select:'.$token->{tag_name}, token => $token);            !!!parse-error (type => 'in select:'.$token->{tag_name}, token => $token);
5512            ## Ignore the token            ## Ignore the token
5513              !!!nack ('t282.1');
5514            !!!next-token;            !!!next-token;
5515            redo B;            next B;
5516          }          }
5517        } elsif ($token->{type} == END_TAG_TOKEN) {        } elsif ($token->{type} == END_TAG_TOKEN) {
5518          if ($token->{tag_name} eq 'optgroup') {          if ($token->{tag_name} eq 'optgroup') {
# Line 5321  sub _tree_construction_main ($) { Line 5529  sub _tree_construction_main ($) {
5529              !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);              !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5530              ## Ignore the token              ## Ignore the token
5531            }            }
5532              !!!nack ('t285.1');
5533            !!!next-token;            !!!next-token;
5534            redo B;            next B;
5535          } elsif ($token->{tag_name} eq 'option') {          } elsif ($token->{tag_name} eq 'option') {
5536            if ($self->{open_elements}->[-1]->[1] & OPTION_EL) {            if ($self->{open_elements}->[-1]->[1] & OPTION_EL) {
5537              !!!cp ('t286');              !!!cp ('t286');
# Line 5332  sub _tree_construction_main ($) { Line 5541  sub _tree_construction_main ($) {
5541              !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);              !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5542              ## Ignore the token              ## Ignore the token
5543            }            }
5544              !!!nack ('t287.1');
5545            !!!next-token;            !!!next-token;
5546            redo B;            next B;
5547          } elsif ($token->{tag_name} eq 'select') {          } elsif ($token->{tag_name} eq 'select') {
5548            ## have an element in table scope            ## have an element in table scope
5549            my $i;            my $i;
# Line 5352  sub _tree_construction_main ($) { Line 5562  sub _tree_construction_main ($) {
5562              !!!cp ('t290');              !!!cp ('t290');
5563              !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);              !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
5564              ## Ignore the token              ## Ignore the token
5565                !!!nack ('t290.1');
5566              !!!next-token;              !!!next-token;
5567              redo B;              next B;
5568            }            }
5569                                
5570            !!!cp ('t291');            !!!cp ('t291');
# Line 5361  sub _tree_construction_main ($) { Line 5572  sub _tree_construction_main ($) {
5572    
5573            $self->_reset_insertion_mode;            $self->_reset_insertion_mode;
5574    
5575              !!!nack ('t291.1');
5576            !!!next-token;            !!!next-token;
5577            redo B;            next B;
5578          } elsif ($self->{insertion_mode} == IN_SELECT_IN_TABLE_IM and          } elsif ($self->{insertion_mode} == IN_SELECT_IN_TABLE_IM and
5579                   {                   {
5580                    caption => 1, table => 1, tbody => 1,                    caption => 1, table => 1, tbody => 1,
# Line 5387  sub _tree_construction_main ($) { Line 5599  sub _tree_construction_main ($) {
5599            unless (defined $i) {            unless (defined $i) {
5600              !!!cp ('t294');              !!!cp ('t294');
5601              ## Ignore the token              ## Ignore the token
5602                !!!nack ('t294.1');
5603              !!!next-token;              !!!next-token;
5604              redo B;              next B;
5605            }            }
5606                                
5607            ## As if </select>            ## As if </select>
# Line 5411  sub _tree_construction_main ($) { Line 5624  sub _tree_construction_main ($) {
5624  ## TODO: The following error type is correct?  ## TODO: The following error type is correct?
5625              !!!parse-error (type => 'unmatched end tag:select', token => $token);              !!!parse-error (type => 'unmatched end tag:select', token => $token);
5626              ## Ignore the </select> token              ## Ignore the </select> token
5627                !!!nack ('t297.1');
5628              !!!next-token; ## TODO: ok?              !!!next-token; ## TODO: ok?
5629              redo B;              next B;
5630            }            }
5631                                
5632            !!!cp ('t298');            !!!cp ('t298');
# Line 5420  sub _tree_construction_main ($) { Line 5634  sub _tree_construction_main ($) {
5634    
5635            $self->_reset_insertion_mode;            $self->_reset_insertion_mode;
5636    
5637              !!!ack-later;
5638            ## reprocess            ## reprocess
5639            redo B;            next B;
5640          } else {          } else {
5641            !!!cp ('t299');            !!!cp ('t299');
5642            !!!parse-error (type => 'in select:/'.$token->{tag_name}, token => $token);            !!!parse-error (type => 'in select:/'.$token->{tag_name}, token => $token);
5643            ## Ignore the token            ## Ignore the token
5644              !!!nack ('t299.3');
5645            !!!next-token;            !!!next-token;
5646            redo B;            next B;
5647          }          }
5648        } elsif ($token->{type} == END_OF_FILE_TOKEN) {        } elsif ($token->{type} == END_OF_FILE_TOKEN) {
5649          unless ($self->{open_elements}->[-1]->[1] & HTML_EL and          unless ($self->{open_elements}->[-1]->[1] & HTML_EL and
# Line 5455  sub _tree_construction_main ($) { Line 5671  sub _tree_construction_main ($) {
5671            unless (length $token->{data}) {            unless (length $token->{data}) {
5672              !!!cp ('t300');              !!!cp ('t300');
5673              !!!next-token;              !!!next-token;
5674              redo B;              next B;
5675            }            }
5676          }          }
5677                    
# Line 5473  sub _tree_construction_main ($) { Line 5689  sub _tree_construction_main ($) {
5689    
5690          $self->{insertion_mode} = IN_BODY_IM;          $self->{insertion_mode} = IN_BODY_IM;
5691          ## reprocess          ## reprocess
5692          redo B;          next B;
5693        } elsif ($token->{type} == START_TAG_TOKEN) {        } elsif ($token->{type} == START_TAG_TOKEN) {
5694          if ($self->{insertion_mode} == AFTER_HTML_BODY_IM) {          if ($self->{insertion_mode} == AFTER_HTML_BODY_IM) {
5695            !!!cp ('t303');            !!!cp ('t303');
# Line 5488  sub _tree_construction_main ($) { Line 5704  sub _tree_construction_main ($) {
5704          !!!parse-error (type => 'after body:'.$token->{tag_name}, token => $token);          !!!parse-error (type => 'after body:'.$token->{tag_name}, token => $token);
5705    
5706          $self->{insertion_mode} = IN_BODY_IM;          $self->{insertion_mode} = IN_BODY_IM;
5707            !!!ack-later;
5708          ## reprocess          ## reprocess
5709          redo B;          next B;
5710        } elsif ($token->{type} == END_TAG_TOKEN) {        } elsif ($token->{type} == END_TAG_TOKEN) {
5711          if ($self->{insertion_mode} == AFTER_HTML_BODY_IM) {          if ($self->{insertion_mode} == AFTER_HTML_BODY_IM) {
5712            !!!cp ('t305');            !!!cp ('t305');
# Line 5508  sub _tree_construction_main ($) { Line 5725  sub _tree_construction_main ($) {
5725              !!!parse-error (type => 'unmatched end tag:html', token => $token);              !!!parse-error (type => 'unmatched end tag:html', token => $token);
5726              ## Ignore the token              ## Ignore the token
5727              !!!next-token;              !!!next-token;
5728              redo B;              next B;
5729            } else {            } else {
5730              !!!cp ('t308');              !!!cp ('t308');
5731              $self->{insertion_mode} = AFTER_HTML_BODY_IM;              $self->{insertion_mode} = AFTER_HTML_BODY_IM;
5732              !!!next-token;              !!!next-token;
5733              redo B;              next B;
5734            }            }
5735          } else {          } else {
5736            !!!cp ('t309');            !!!cp ('t309');
# Line 5521  sub _tree_construction_main ($) { Line 5738  sub _tree_construction_main ($) {
5738    
5739            $self->{insertion_mode} = IN_BODY_IM;            $self->{insertion_mode} = IN_BODY_IM;
5740            ## reprocess            ## reprocess
5741            redo B;            next B;
5742          }          }
5743        } elsif ($token->{type} == END_OF_FILE_TOKEN) {        } elsif ($token->{type} == END_OF_FILE_TOKEN) {
5744          !!!cp ('t309.2');          !!!cp ('t309.2');
# Line 5538  sub _tree_construction_main ($) { Line 5755  sub _tree_construction_main ($) {
5755            unless (length $token->{data}) {            unless (length $token->{data}) {
5756              !!!cp ('t310');              !!!cp ('t310');
5757              !!!next-token;              !!!next-token;
5758              redo B;              next B;
5759            }            }
5760          }          }
5761                    
# Line 5566  sub _tree_construction_main ($) { Line 5783  sub _tree_construction_main ($) {
5783              !!!cp ('t315');              !!!cp ('t315');
5784              !!!next-token;              !!!next-token;
5785            }            }
5786            redo B;            next B;
5787          }          }
5788                    
5789          die qq[$0: Character "$token->{data}"];          die qq[$0: Character "$token->{data}"];
# Line 5585  sub _tree_construction_main ($) { Line 5802  sub _tree_construction_main ($) {
5802              $self->{insertion_mode} == IN_FRAMESET_IM) {              $self->{insertion_mode} == IN_FRAMESET_IM) {
5803            !!!cp ('t318');            !!!cp ('t318');
5804            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);
5805              !!!nack ('t318.1');
5806            !!!next-token;            !!!next-token;
5807            redo B;            next B;
5808          } elsif ($token->{tag_name} eq 'frame' and          } elsif ($token->{tag_name} eq 'frame' and
5809                   $self->{insertion_mode} == IN_FRAMESET_IM) {                   $self->{insertion_mode} == IN_FRAMESET_IM) {
5810            !!!cp ('t319');            !!!cp ('t319');
5811            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);            !!!insert-element ($token->{tag_name}, $token->{attributes}, $token);
5812            pop @{$self->{open_elements}};            pop @{$self->{open_elements}};
5813              !!!ack ('t319.1');
5814            !!!next-token;            !!!next-token;
5815            redo B;            next B;
5816          } elsif ($token->{tag_name} eq 'noframes') {          } elsif ($token->{tag_name} eq 'noframes') {
5817            !!!cp ('t320');            !!!cp ('t320');
5818            ## NOTE: As if in body.            ## NOTE: As if in body.
5819            $parse_rcdata->(CDATA_CONTENT_MODEL);            $parse_rcdata->(CDATA_CONTENT_MODEL);
5820            redo B;            next B;
5821          } else {          } else {
5822            if ($self->{insertion_mode} == IN_FRAMESET_IM) {            if ($self->{insertion_mode} == IN_FRAMESET_IM) {
5823              !!!cp ('t321');              !!!cp ('t321');
# Line 5608  sub _tree_construction_main ($) { Line 5827  sub _tree_construction_main ($) {
5827              !!!parse-error (type => 'after frameset:'.$token->{tag_name}, token => $token);              !!!parse-error (type => 'after frameset:'.$token->{tag_name}, token => $token);
5828            }            }
5829            ## Ignore the token            ## Ignore the token
5830              !!!nack ('t322.1');
5831            !!!next-token;            !!!next-token;
5832            redo B;            next B;
5833          }          }
5834        } elsif ($token->{type} == END_TAG_TOKEN) {        } elsif ($token->{type} == END_TAG_TOKEN) {
5835          if ($self->{insertion_mode} == AFTER_HTML_FRAMESET_IM) {          if ($self->{insertion_mode} == AFTER_HTML_FRAMESET_IM) {
# Line 5643  sub _tree_construction_main ($) { Line 5863  sub _tree_construction_main ($) {
5863            } else {            } else {
5864              !!!cp ('t328');              !!!cp ('t328');
5865            }            }
5866            redo B;            next B;
5867          } elsif ($token->{tag_name} eq 'html' and          } elsif ($token->{tag_name} eq 'html' and
5868                   $self->{insertion_mode} == AFTER_FRAMESET_IM) {                   $self->{insertion_mode} == AFTER_FRAMESET_IM) {
5869            !!!cp ('t329');            !!!cp ('t329');
5870            $self->{insertion_mode} = AFTER_HTML_FRAMESET_IM;            $self->{insertion_mode} = AFTER_HTML_FRAMESET_IM;
5871            !!!next-token;            !!!next-token;
5872            redo B;            next B;
5873          } else {          } else {
5874            if ($self->{insertion_mode} == IN_FRAMESET_IM) {            if ($self->{insertion_mode} == IN_FRAMESET_IM) {
5875              !!!cp ('t330');              !!!cp ('t330');
# Line 5660  sub _tree_construction_main ($) { Line 5880  sub _tree_construction_main ($) {
5880            }            }
5881            ## Ignore the token            ## Ignore the token
5882            !!!next-token;            !!!next-token;
5883            redo B;            next B;
5884          }          }
5885        } elsif ($token->{type} == END_OF_FILE_TOKEN) {        } elsif ($token->{type} == END_OF_FILE_TOKEN) {
5886          unless ($self->{open_elements}->[-1]->[1] & HTML_EL and          unless ($self->{open_elements}->[-1]->[1] & HTML_EL and
# Line 5688  sub _tree_construction_main ($) { Line 5908  sub _tree_construction_main ($) {
5908          !!!cp ('t332');          !!!cp ('t332');
5909          ## NOTE: This is an "as if in head" code clone          ## NOTE: This is an "as if in head" code clone
5910          $script_start_tag->();          $script_start_tag->();
5911          redo B;          next B;
5912        } elsif ($token->{tag_name} eq 'style') {        } elsif ($token->{tag_name} eq 'style') {
5913          !!!cp ('t333');          !!!cp ('t333');
5914          ## NOTE: This is an "as if in head" code clone          ## NOTE: This is an "as if in head" code clone
5915          $parse_rcdata->(CDATA_CONTENT_MODEL);          $parse_rcdata->(CDATA_CONTENT_MODEL);
5916          redo B;          next B;
5917        } elsif ({        } elsif ({
5918                  base => 1, link => 1,                  base => 1, link => 1,
5919                 }->{$token->{tag_name}}) {                 }->{$token->{tag_name}}) {
# Line 5701  sub _tree_construction_main ($) { Line 5921  sub _tree_construction_main ($) {
5921          ## NOTE: This is an "as if in head" code clone, only "-t" differs          ## NOTE: This is an "as if in head" code clone, only "-t" differs
5922          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);
5923          pop @{$self->{open_elements}}; ## ISSUE: This step is missing in the spec.          pop @{$self->{open_elements}}; ## ISSUE: This step is missing in the spec.
5924            !!!ack ('t334.1');
5925          !!!next-token;          !!!next-token;
5926          redo B;          next B;
5927        } elsif ($token->{tag_name} eq 'meta') {        } elsif ($token->{tag_name} eq 'meta') {
5928          ## NOTE: This is an "as if in head" code clone, only "-t" differs          ## NOTE: This is an "as if in head" code clone, only "-t" differs
5929          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);
# Line 5751  sub _tree_construction_main ($) { Line 5972  sub _tree_construction_main ($) {
5972            }            }
5973          }          }
5974    
5975            !!!ack ('t338.1');
5976          !!!next-token;          !!!next-token;
5977          redo B;          next B;
5978        } elsif ($token->{tag_name} eq 'title') {        } elsif ($token->{tag_name} eq 'title') {
5979          !!!cp ('t341');          !!!cp ('t341');
5980          ## NOTE: This is an "as if in head" code clone          ## NOTE: This is an "as if in head" code clone
5981          $parse_rcdata->(RCDATA_CONTENT_MODEL);          $parse_rcdata->(RCDATA_CONTENT_MODEL);
5982          redo B;          next B;
5983        } elsif ($token->{tag_name} eq 'body') {        } elsif ($token->{tag_name} eq 'body') {
5984          !!!parse-error (type => 'in body:body', token => $token);          !!!parse-error (type => 'in body:body', token => $token);
5985                                
# Line 5776  sub _tree_construction_main ($) { Line 5998  sub _tree_construction_main ($) {
5998              }              }
5999            }            }
6000          }          }
6001            !!!nack ('t343.1');
6002          !!!next-token;          !!!next-token;
6003          redo B;          next B;
6004        } elsif ({        } elsif ({
6005                  address => 1, blockquote => 1, center => 1, dir => 1,                  address => 1, blockquote => 1, center => 1, dir => 1,
6006                  div => 1, dl => 1, fieldset => 1,                  div => 1, dl => 1, fieldset => 1,
# Line 5792  sub _tree_construction_main ($) { Line 6015  sub _tree_construction_main ($) {
6015            !!!cp ('t350');            !!!cp ('t350');
6016            !!!parse-error (type => 'in form:form', token => $token);            !!!parse-error (type => 'in form:form', token => $token);
6017            ## Ignore the token            ## Ignore the token
6018              !!!nack ('t350.1');
6019            !!!next-token;            !!!next-token;
6020            redo B;            next B;
6021          }          }
6022    
6023          ## has a p element in scope          ## has a p element in scope
6024          INSCOPE: for (reverse @{$self->{open_elements}}) {          INSCOPE: for (reverse @{$self->{open_elements}}) {
6025            if ($_->[1] & P_EL) {            if ($_->[1] & P_EL) {
6026              !!!cp ('t344');              !!!cp ('t344');
6027              !!!back-token;              !!!back-token; # <form>
6028              $token = {type => END_TAG_TOKEN, tag_name => 'p',              $token = {type => END_TAG_TOKEN, tag_name => 'p',
6029                        line => $token->{line}, column => $token->{column}};                        line => $token->{line}, column => $token->{column}};
6030              redo B;              next B;
6031            } elsif ($_->[1] & SCOPING_EL) {            } elsif ($_->[1] & SCOPING_EL) {
6032              !!!cp ('t345');              !!!cp ('t345');
6033              last INSCOPE;              last INSCOPE;
# Line 5812  sub _tree_construction_main ($) { Line 6036  sub _tree_construction_main ($) {
6036                        
6037          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);
6038          if ($token->{tag_name} eq 'pre' or $token->{tag_name} eq 'listing') {          if ($token->{tag_name} eq 'pre' or $token->{tag_name} eq 'listing') {
6039              !!!nack ('t346.1');
6040            !!!next-token;            !!!next-token;
6041            if ($token->{type} == CHARACTER_TOKEN) {            if ($token->{type} == CHARACTER_TOKEN) {
6042              $token->{data} =~ s/^\x0A//;              $token->{data} =~ s/^\x0A//;
# Line 5828  sub _tree_construction_main ($) { Line 6053  sub _tree_construction_main ($) {
6053            !!!cp ('t347.1');            !!!cp ('t347.1');
6054            $self->{form_element} = $self->{open_elements}->[-1]->[0];            $self->{form_element} = $self->{open_elements}->[-1]->[0];
6055    
6056              !!!nack ('t347.2');
6057            !!!next-token;            !!!next-token;
6058          } elsif ($token->{tag_name} eq 'table') {          } elsif ($token->{tag_name} eq 'table') {
6059            !!!cp ('t382');            !!!cp ('t382');
# Line 5835  sub _tree_construction_main ($) { Line 6061  sub _tree_construction_main ($) {
6061                        
6062            $self->{insertion_mode} = IN_TABLE_IM;            $self->{insertion_mode} = IN_TABLE_IM;
6063    
6064              !!!nack ('t382.1');
6065            !!!next-token;            !!!next-token;
6066          } elsif ($token->{tag_name} eq 'hr') {          } elsif ($token->{tag_name} eq 'hr') {
6067            !!!cp ('t386');            !!!cp ('t386');
6068            pop @{$self->{open_elements}};            pop @{$self->{open_elements}};
6069                    
6070              !!!nack ('t386.1');
6071            !!!next-token;            !!!next-token;
6072          } else {          } else {
6073            !!!cp ('t347');            !!!nack ('t347.1');
6074            !!!next-token;            !!!next-token;
6075          }          }
6076          redo B;          next B;
6077        } elsif ({li => 1, dt => 1, dd => 1}->{$token->{tag_name}}) {        } elsif ({li => 1, dt => 1, dd => 1}->{$token->{tag_name}}) {
6078          ## has a p element in scope          ## has a p element in scope
6079          INSCOPE: for (reverse @{$self->{open_elements}}) {          INSCOPE: for (reverse @{$self->{open_elements}}) {
6080            if ($_->[1] & P_EL) {            if ($_->[1] & P_EL) {
6081              !!!cp ('t353');              !!!cp ('t353');
6082              !!!back-token;              !!!back-token; # <x>
6083              $token = {type => END_TAG_TOKEN, tag_name => 'p',              $token = {type => END_TAG_TOKEN, tag_name => 'p',
6084                        line => $token->{line}, column => $token->{column}};                        line => $token->{line}, column => $token->{column}};
6085              redo B;              next B;
6086            } elsif ($_->[1] & SCOPING_EL) {            } elsif ($_->[1] & SCOPING_EL) {
6087              !!!cp ('t354');              !!!cp ('t354');
6088              last INSCOPE;              last INSCOPE;
# Line 5904  sub _tree_construction_main ($) { Line 6132  sub _tree_construction_main ($) {
6132          } # LI          } # LI
6133                        
6134          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);
6135            !!!nack ('t359.1');
6136          !!!next-token;          !!!next-token;
6137          redo B;          next B;
6138        } elsif ($token->{tag_name} eq 'plaintext') {        } elsif ($token->{tag_name} eq 'plaintext') {
6139          ## has a p element in scope          ## has a p element in scope
6140          INSCOPE: for (reverse @{$self->{open_elements}}) {          INSCOPE: for (reverse @{$self->{open_elements}}) {
6141            if ($_->[1] & P_EL) {            if ($_->[1] & P_EL) {
6142              !!!cp ('t367');              !!!cp ('t367');
6143              !!!back-token;              !!!back-token; # <plaintext>
6144              $token = {type => END_TAG_TOKEN, tag_name => 'p',              $token = {type => END_TAG_TOKEN, tag_name => 'p',
6145                        line => $token->{line}, column => $token->{column}};                        line => $token->{line}, column => $token->{column}};
6146              redo B;              next B;
6147            } elsif ($_->[1] & SCOPING_EL) {            } elsif ($_->[1] & SCOPING_EL) {
6148              !!!cp ('t368');              !!!cp ('t368');
6149              last INSCOPE;              last INSCOPE;
# Line 5925  sub _tree_construction_main ($) { Line 6154  sub _tree_construction_main ($) {
6154                        
6155          $self->{content_model} = PLAINTEXT_CONTENT_MODEL;          $self->{content_model} = PLAINTEXT_CONTENT_MODEL;
6156                        
6157            !!!nack ('t368.1');
6158          !!!next-token;          !!!next-token;
6159          redo B;          next B;
6160        } elsif ($token->{tag_name} eq 'a') {        } elsif ($token->{tag_name} eq 'a') {
6161          AFE: for my $i (reverse 0..$#$active_formatting_elements) {          AFE: for my $i (reverse 0..$#$active_formatting_elements) {
6162            my $node = $active_formatting_elements->[$i];            my $node = $active_formatting_elements->[$i];
# Line 5934  sub _tree_construction_main ($) { Line 6164  sub _tree_construction_main ($) {
6164              !!!cp ('t371');              !!!cp ('t371');
6165              !!!parse-error (type => 'in a:a', token => $token);              !!!parse-error (type => 'in a:a', token => $token);
6166                            
6167              !!!back-token;              !!!back-token; # <a>
6168              $token = {type => END_TAG_TOKEN, tag_name => 'a',              $token = {type => END_TAG_TOKEN, tag_name => 'a',
6169                        line => $token->{line}, column => $token->{column}};                        line => $token->{line}, column => $token->{column}};
6170              $formatting_end_tag->($token);              $formatting_end_tag->($token);
# Line 5965  sub _tree_construction_main ($) { Line 6195  sub _tree_construction_main ($) {
6195          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);
6196          push @$active_formatting_elements, $self->{open_elements}->[-1];          push @$active_formatting_elements, $self->{open_elements}->[-1];
6197    
6198            !!!nack ('t374.1');
6199          !!!next-token;          !!!next-token;
6200          redo B;          next B;
6201        } elsif ($token->{tag_name} eq 'nobr') {        } elsif ($token->{tag_name} eq 'nobr') {
6202          $reconstruct_active_formatting_elements->($insert_to_current);          $reconstruct_active_formatting_elements->($insert_to_current);
6203    
# Line 5976  sub _tree_construction_main ($) { Line 6207  sub _tree_construction_main ($) {
6207            if ($node->[1] & NOBR_EL) {            if ($node->[1] & NOBR_EL) {
6208              !!!cp ('t376');              !!!cp ('t376');
6209              !!!parse-error (type => 'in nobr:nobr', token => $token);              !!!parse-error (type => 'in nobr:nobr', token => $token);
6210              !!!back-token;              !!!back-token; # <nobr>
6211              $token = {type => END_TAG_TOKEN, tag_name => 'nobr',              $token = {type => END_TAG_TOKEN, tag_name => 'nobr',
6212                        line => $token->{line}, column => $token->{column}};                        line => $token->{line}, column => $token->{column}};
6213              redo B;              next B;
6214            } elsif ($node->[1] & SCOPING_EL) {            } elsif ($node->[1] & SCOPING_EL) {
6215              !!!cp ('t377');              !!!cp ('t377');
6216              last INSCOPE;              last INSCOPE;
# Line 5989  sub _tree_construction_main ($) { Line 6220  sub _tree_construction_main ($) {
6220          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);          !!!insert-element-t ($token->{tag_name}, $token->{attributes}, $token);
6221          push @$active_formatting_elements, $self->{open_elements}->[-1];          push @$active_formatting_elements, $self->{open_elements}->[-1];
6222                    
6223            !!!nack ('t377.1');
6224          !!!next-token;          !!!next-token;
6225          redo B;          next B;
6226        } elsif ($token->{tag_name} eq 'button') {        } elsif ($token->{tag_name} eq 'button') {
6227          ## has a button element in scope          ## has a button element in scope
6228          INSCOPE: for (reverse 0..$#{$self->{open_elements}}) {          INSCOPE: for (reverse 0..$#{$self->{open_elements}}) {
# Line 5998  sub _tree_construction_main ($) { Line 6230  sub _tree_construction_main ($) {
6230            if ($node->[1] & BUTTON_EL) {            if ($node->[1] & BUTTON_EL) {
6231              !!!cp ('t378');              !!!cp ('t378');
6232              !!!parse-error (type => 'in button:button', token => $token);              !!!parse-error (type => 'in button:button', token => $token);
6233              !!!back-token;              !!!back-token; # <button>
6234              $token = {type => END_TAG_TOKEN, tag_name => 'button',              $token = {type => END_TAG_TOKEN, tag_name => 'button',
6235                        line => $token->{line}, column => $token->{column}};                        line => $token->{line}, column => $token->{column}};
6236              redo B;              next B;
6237            } elsif ($node->[1] & SCOPING_EL) {            } elsif ($node->[1] & SCOPING_EL) {
6238              !!!cp ('t379');              !!!cp ('t379');
6239              last INSCOPE;              last INSCOPE;
# Line 6016  sub _tree_construction_main ($) { Line 6248  sub _tree_construction_main ($) {
6248    
6249          push @$active_formatting_elements, ['#marker', ''];          push @$active_formatting_elements, ['#marker', ''];
6250    
6251            !!!nack ('t379.1');
6252          !!!next-token;          !!!next-token;
6253          redo B;          next B;
6254        } elsif ({        } elsif ({
6255                  xmp => 1,                  xmp => 1,
6256                  iframe => 1,                  iframe => 1,
# Line 6033  sub _tree_construction_main ($) { Line 6266  sub _tree_construction_main ($) {
6266          }          }
6267          ## NOTE: There is an "as if in body" code clone.          ## NOTE: There is an "as if in body" code clone.
6268          $parse_rcdata->(CDATA_CONTENT_MODEL);          $parse_rcdata->(CDATA_CONTENT_MODEL);
6269          redo B;          next B;
6270        } elsif ($token->{tag_name} eq 'isindex') {        } elsif ($token->{tag_name} eq 'isindex') {
6271          !!!parse-error (type => 'isindex', token => $token);          !!!parse-error (type => 'isindex', token => $token);
6272                    
6273          if (defined $self->{form_element}) {          if (defined $self->{form_element}) {
6274            !!!cp ('t389');            !!!cp ('t389');
6275            ## Ignore the token            ## Ignore the token
6276              !!!nack ('t389'); ## NOTE: Not acknowledged.
6277            !!!next-token;            !!!next-token;
6278            redo B;            next B;
6279          } else {          } else {
6280            my $at = $token->{attributes};            my $at = $token->{attributes};
6281            my $form_attrs;            my $form_attrs;
# Line 6086  sub _tree_construction_main ($) { Line 6320  sub _tree_construction_main ($) {
6320                           line => $token->{line}, column => $token->{column}},                           line => $token->{line}, column => $token->{column}},
6321                          {type => END_TAG_TOKEN, tag_name => 'form',                          {type => END_TAG_TOKEN, tag_name => 'form',
6322                           line => $token->{line}, column => $token->{column}};                           line => $token->{line}, column => $token->{column}};
6323            $token = shift @tokens;            !!!nack ('t391.1'); ## NOTE: Not acknowledged.
6324            !!!back-token (@tokens);            !!!back-token (@tokens);
6325            redo B;            !!!next-token;
6326              next B;
6327          }          }
6328        } elsif ($token->{tag_name} eq 'textarea') {        } elsif ($token->{tag_name} eq 'textarea') {
6329          my $tag_name = $token->{tag_name};          my $tag_name = $token->{tag_name};
6330          my $el;          my $el;
6331          !!!create-element ($el, $token->{tag_name}, $token->{attributes}, $token);          !!!create-element ($el, $HTML_NS, $token->{tag_name}, $token->{attributes}, $token);
6332                    
6333          ## TODO: $self->{form_element} if defined          ## TODO: $self->{form_element} if defined
6334          $self->{content_model} = RCDATA_CONTENT_MODEL;          $self->{content_model} = RCDATA_CONTENT_MODEL;
# Line 6102  sub _tree_construction_main ($) { Line 6337  sub _tree_construction_main ($) {
6337          $insert->($el);          $insert->($el);
6338                    
6339          my $text = '';          my $text = '';
6340            !!!nack ('t392.1');
6341          !!!next-token;          !!!next-token;
6342          if ($token->{type} == CHARACTER_TOKEN) {          if ($token->{type} == CHARACTER_TOKEN) {
6343            $token->{data} =~ s/^\x0A//;            $token->{data} =~ s/^\x0A//;
# Line 6135  sub _tree_construction_main ($) { Line 6371  sub _tree_construction_main ($) {
6371            !!!parse-error (type => 'in RCDATA:#'.$token->{type}, token => $token);            !!!parse-error (type => 'in RCDATA:#'.$token->{type}, token => $token);
6372          }          }
6373          !!!next-token;          !!!next-token;
6374          redo B;          next B;
6375          } elsif ($token->{tag_name} eq 'math' or
6376                   $token->{tag_name} eq 'svg') {
6377            $reconstruct_active_formatting_elements->($insert_to_current);
6378            
6379            !!!insert-element-f ($token->{tag_name} eq 'math' ? $MML_NS : $SVG_NS, $token);
6380            
6381            if ($self->{self_closing}) {
6382              pop @{$self->{open_elements}};
6383              !!!ack ('t398.1');
6384            } else {
6385              !!!cp ('t398.2');
6386              $self->{insertion_mode} |= IN_FOREIGN_CONTENT_IM;
6387              ## NOTE: |<body><math><mi><svg>| -> "in foreign content" insertion
6388              ## mode, "in body" (not "in foreign content") secondary insertion
6389              ## mode, maybe.
6390            }
6391    
6392            !!!next-token;
6393            next B;
6394        } elsif ({        } elsif ({
6395                  caption => 1, col => 1, colgroup => 1, frame => 1,                  caption => 1, col => 1, colgroup => 1, frame => 1,
6396                  frameset => 1, head => 1, option => 1, optgroup => 1,                  frameset => 1, head => 1, option => 1, optgroup => 1,
# Line 6145  sub _tree_construction_main ($) { Line 6400  sub _tree_construction_main ($) {
6400          !!!cp ('t401');          !!!cp ('t401');
6401          !!!parse-error (type => 'in body:'.$token->{tag_name}, token => $token);          !!!parse-error (type => 'in body:'.$token->{tag_name}, token => $token);
6402          ## Ignore the token          ## Ignore the token
6403            !!!nack ('t401.1'); ## NOTE: |<col/>| or |<frame/>| here is an error.
6404          !!!next-token;          !!!next-token;
6405          redo B;          next B;
6406                    
6407          ## ISSUE: An issue on HTML5 new elements in the spec.          ## ISSUE: An issue on HTML5 new elements in the spec.
6408        } else {        } else {
# Line 6168  sub _tree_construction_main ($) { Line 6424  sub _tree_construction_main ($) {
6424              }->{$token->{tag_name}}) {              }->{$token->{tag_name}}) {
6425            !!!cp ('t380');            !!!cp ('t380');
6426            push @$active_formatting_elements, ['#marker', ''];            push @$active_formatting_elements, ['#marker', ''];
6427              !!!nack ('t380.1');
6428          } elsif ({          } elsif ({
6429                    b => 1, big => 1, em => 1, font => 1, i => 1,                    b => 1, big => 1, em => 1, font => 1, i => 1,
6430                    s => 1, small => 1, strile => 1,                    s => 1, small => 1, strile => 1,
# Line 6175  sub _tree_construction_main ($) { Line 6432  sub _tree_construction_main ($) {
6432                   }->{$token->{tag_name}}) {                   }->{$token->{tag_name}}) {
6433            !!!cp ('t375');            !!!cp ('t375');
6434            push @$active_formatting_elements, $self->{open_elements}->[-1];            push @$active_formatting_elements, $self->{open_elements}->[-1];
6435              !!!nack ('t375.1');
6436          } elsif ($token->{tag_name} eq 'input') {          } elsif ($token->{tag_name} eq 'input') {
6437            !!!cp ('t388');            !!!cp ('t388');
6438            ## TODO: associate with $self->{form_element} if defined            ## TODO: associate with $self->{form_element} if defined
6439            pop @{$self->{open_elements}};            pop @{$self->{open_elements}};
6440              !!!ack ('t388.2');
6441          } elsif ({          } elsif ({
6442                    area => 1, basefont => 1, bgsound => 1, br => 1,                    area => 1, basefont => 1, bgsound => 1, br => 1,
6443                    embed => 1, img => 1, param => 1, spacer => 1, wbr => 1,                    embed => 1, img => 1, param => 1, spacer => 1, wbr => 1,
# Line 6186  sub _tree_construction_main ($) { Line 6445  sub _tree_construction_main ($) {
6445                   }->{$token->{tag_name}}) {                   }->{$token->{tag_name}}) {
6446            !!!cp ('t388.1');            !!!cp ('t388.1');
6447            pop @{$self->{open_elements}};            pop @{$self->{open_elements}};
6448              !!!ack ('t388.3');
6449          } elsif ($token->{tag_name} eq 'select') {          } elsif ($token->{tag_name} eq 'select') {
6450            ## TODO: associate with $self->{form_element} if defined            ## TODO: associate with $self->{form_element} if defined
6451                    
# Line 6198  sub _tree_construction_main ($) { Line 6458  sub _tree_construction_main ($) {
6458              !!!cp ('t400.2');              !!!cp ('t400.2');
6459              $self->{insertion_mode} = IN_SELECT_IM;              $self->{insertion_mode} = IN_SELECT_IM;
6460            }            }
6461              !!!nack ('t400.3');
6462          } else {          } else {
6463            !!!cp ('t402');            !!!nack ('t402');
6464          }          }
6465                    
6466          !!!next-token;          !!!next-token;
6467          redo B;          next B;
6468        }        }
6469      } elsif ($token->{type} == END_TAG_TOKEN) {      } elsif ($token->{type} == END_TAG_TOKEN) {
6470        if ($token->{tag_name} eq 'body') {        if ($token->{tag_name} eq 'body') {
# Line 6225  sub _tree_construction_main ($) { Line 6486  sub _tree_construction_main ($) {
6486                            value => $token->{tag_name}, token => $token);                            value => $token->{tag_name}, token => $token);
6487            ## NOTE: Ignore the token.            ## NOTE: Ignore the token.
6488            !!!next-token;            !!!next-token;
6489            redo B;            next B;
6490          } # INSCOPE          } # INSCOPE
6491    
6492          for (@{$self->{open_elements}}) {          for (@{$self->{open_elements}}) {
# Line 6242  sub _tree_construction_main ($) { Line 6503  sub _tree_construction_main ($) {
6503    
6504          $self->{insertion_mode} = AFTER_BODY_IM;          $self->{insertion_mode} = AFTER_BODY_IM;
6505          !!!next-token;          !!!next-token;
6506          redo B;          next B;
6507        } elsif ($token->{tag_name} eq 'html') {        } elsif ($token->{tag_name} eq 'html') {
6508          ## TODO: Update this code.  It seems that the code below is not          ## TODO: Update this code.  It seems that the code below is not
6509          ## up-to-date, though it has same effect as speced.          ## up-to-date, though it has same effect as speced.
# Line 6260  sub _tree_construction_main ($) { Line 6521  sub _tree_construction_main ($) {
6521            }            }
6522            $self->{insertion_mode} = AFTER_BODY_IM;            $self->{insertion_mode} = AFTER_BODY_IM;
6523            ## reprocess            ## reprocess
6524            redo B;            next B;
6525          } else {          } else {
6526            !!!cp ('t408');            !!!cp ('t408');
6527            !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);            !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
6528            ## Ignore the token            ## Ignore the token
6529            !!!next-token;            !!!next-token;
6530            redo B;            next B;
6531          }          }
6532        } elsif ({        } elsif ({
6533                  address => 1, blockquote => 1, center => 1, dir => 1,                  address => 1, blockquote => 1, center => 1, dir => 1,
# Line 6326  sub _tree_construction_main ($) { Line 6587  sub _tree_construction_main ($) {
6587                }->{$token->{tag_name}};                }->{$token->{tag_name}};
6588          }          }
6589          !!!next-token;          !!!next-token;
6590          redo B;          next B;
6591        } elsif ($token->{tag_name} eq 'form') {        } elsif ($token->{tag_name} eq 'form') {
6592          undef $self->{form_element};          undef $self->{form_element};
6593    
# Line 6371  sub _tree_construction_main ($) { Line 6632  sub _tree_construction_main ($) {
6632          }          }
6633    
6634          !!!next-token;          !!!next-token;
6635          redo B;          next B;
6636        } elsif ({        } elsif ({
6637                  h1 => 1, h2 => 1, h3 => 1, h4 => 1, h5 => 1, h6 => 1,                  h1 => 1, h2 => 1, h3 => 1, h4 => 1, h5 => 1, h6 => 1,
6638                 }->{$token->{tag_name}}) {                 }->{$token->{tag_name}}) {
# Line 6413  sub _tree_construction_main ($) { Line 6674  sub _tree_construction_main ($) {
6674          }          }
6675                    
6676          !!!next-token;          !!!next-token;
6677          redo B;          next B;
6678        } elsif ($token->{tag_name} eq 'p') {        } elsif ($token->{tag_name} eq 'p') {
6679          ## has an element in scope          ## has an element in scope
6680          my $i;          my $i;
# Line 6449  sub _tree_construction_main ($) { Line 6710  sub _tree_construction_main ($) {
6710            !!!cp ('t415.1');            !!!cp ('t415.1');
6711            ## As if <p>, then reprocess the current token            ## As if <p>, then reprocess the current token
6712            my $el;            my $el;
6713            !!!create-element ($el, 'p',, $token);            !!!create-element ($el, $HTML_NS, 'p',, $token);
6714            $insert->($el);            $insert->($el);
6715            ## NOTE: Not inserted into |$self->{open_elements}|.            ## NOTE: Not inserted into |$self->{open_elements}|.
6716          }          }
6717    
6718          !!!next-token;          !!!next-token;
6719          redo B;          next B;
6720        } elsif ({        } elsif ({
6721                  a => 1,                  a => 1,
6722                  b => 1, big => 1, em => 1, font => 1, i => 1,                  b => 1, big => 1, em => 1, font => 1, i => 1,
# Line 6464  sub _tree_construction_main ($) { Line 6725  sub _tree_construction_main ($) {
6725                 }->{$token->{tag_name}}) {                 }->{$token->{tag_name}}) {
6726          !!!cp ('t427');          !!!cp ('t427');
6727          $formatting_end_tag->($token);          $formatting_end_tag->($token);
6728          redo B;          next B;
6729        } elsif ($token->{tag_name} eq 'br') {        } elsif ($token->{tag_name} eq 'br') {
6730          !!!cp ('t428');          !!!cp ('t428');
6731          !!!parse-error (type => 'unmatched end tag:br', token => $token);          !!!parse-error (type => 'unmatched end tag:br', token => $token);
# Line 6473  sub _tree_construction_main ($) { Line 6734  sub _tree_construction_main ($) {
6734          $reconstruct_active_formatting_elements->($insert_to_current);          $reconstruct_active_formatting_elements->($insert_to_current);
6735                    
6736          my $el;          my $el;
6737          !!!create-element ($el, 'br',, $token);          !!!create-element ($el, $HTML_NS, 'br',, $token);
6738          $insert->($el);          $insert->($el);
6739                    
6740          ## Ignore the token.          ## Ignore the token.
6741          !!!next-token;          !!!next-token;
6742          redo B;          next B;
6743        } elsif ({        } elsif ({
6744                  caption => 1, col => 1, colgroup => 1, frame => 1,                  caption => 1, col => 1, colgroup => 1, frame => 1,
6745                  frameset => 1, head => 1, option => 1, optgroup => 1,                  frameset => 1, head => 1, option => 1, optgroup => 1,
# Line 6495  sub _tree_construction_main ($) { Line 6756  sub _tree_construction_main ($) {
6756          !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);          !!!parse-error (type => 'unmatched end tag:'.$token->{tag_name}, token => $token);
6757          ## Ignore the token          ## Ignore the token
6758          !!!next-token;          !!!next-token;
6759          redo B;          next B;
6760                    
6761          ## ISSUE: Issue on HTML5 new elements in spec          ## ISSUE: Issue on HTML5 new elements in spec
6762                    
# Line 6556  sub _tree_construction_main ($) { Line 6817  sub _tree_construction_main ($) {
6817            ## Step 5;            ## Step 5;
6818            redo S2;            redo S2;
6819          } # S2          } # S2
6820          redo B;          next B;
6821        }        }
6822      }      }
6823      redo B;      next B;
6824      } continue { # B
6825        if ($self->{insertion_mode} & IN_FOREIGN_CONTENT_IM) {
6826          ## NOTE: The code below is executed in cases where it does not have
6827          ## to be, but it it is harmless even in those cases.
6828          ## has an element in scope
6829          INSCOPE: {
6830            for (reverse 0..$#{$self->{open_elements}}) {
6831              my $node = $self->{open_elements}->[$_];
6832              if ($node->[1] & FOREIGN_EL) {
6833                last INSCOPE;
6834              } elsif ($node->[1] & SCOPING_EL) {
6835                last;
6836              }
6837            }
6838            
6839            ## NOTE: No foreign element in scope.
6840            $self->{insertion_mode} &= ~ IN_FOREIGN_CONTENT_IM;
6841          } # INSCOPE
6842        }
6843    } # B    } # B
6844    
6845    ## Stop parsing # MUST    ## Stop parsing # MUST

Legend:
Removed from v.1.123  
changed lines
  Added in v.1.128

[email protected]
ViewVC Help
Powered by ViewVC 1.1.24