package TokeniserImpl;
use strict;
use warnings;

my ($machineState, $contentModel, $Char_EOF, $currentCharacter, $escapeFlag);

our $entityNameMatch = qr/^(thetasym;|Epsilon;|Omicron;|Upsilon;|alefsym;|epsilon;|omicron;|upsilon;|Aacute;|Agrave;|Atilde;|Ccedil;|Dagger;|Eacute;|Egrave;|Iacute;|Igrave;|Lambda;|Ntilde;|Oacute;|Ograve;|Oslash;|Otilde;|Scaron;|Uacute;|Ugrave;|Yacute;|aacute;|agrave;|atilde;|brvbar;|ccedil;|curren;|dagger;|divide;|eacute;|egrave;|forall;|frac12;|frac14;|frac34;|hearts;|hellip;|iacute;|igrave;|iquest;|lambda;|lfloor;|lowast;|lsaquo;|middot;|ntilde;|oacute;|ograve;|oslash;|otilde;|otimes;|permil;|plusmn;|rfloor;|rsaquo;|scaron;|sigmaf;|spades;|there4;|thinsp;|uacute;|ugrave;|weierp;|yacute;|AElig;|Aacute|Acirc;|Agrave|Alpha;|Aring;|Atilde|Ccedil|Delta;|Eacute|Ecirc;|Egrave|Gamma;|Iacute|Icirc;|Igrave|Kappa;|Ntilde|OElig;|Oacute|Ocirc;|Ograve|Omega;|Oslash|Otilde|Prime;|Sigma;|THORN;|TRADE;|Theta;|Uacute|Ucirc;|Ugrave|Yacute|aacute|acirc;|acute;|aelig;|agrave|alpha;|aring;|asymp;|atilde|bdquo;|brvbar|ccedil|cedil;|clubs;|crarr;|curren|delta;|diams;|divide|eacute|ecirc;|egrave|empty;|equiv;|exist;|frac12|frac14|frac34|frasl;|gamma;|iacute|icirc;|iexcl;|igrave|image;|infin;|iquest|kappa;|laquo;|lceil;|ldquo;|lsquo;|mdash;|micro;|middot|minus;|nabla;|ndash;|notin;|ntilde|oacute|ocirc;|oelig;|ograve|oline;|omega;|oplus;|oslash|otilde|plusmn|pound;|prime;|radic;|raquo;|rceil;|rdquo;|rsquo;|sbquo;|sigma;|szlig;|theta;|thorn;|tilde;|times;|trade;|uacute|ucirc;|ugrave|upsih;|yacute|AElig|Acirc|Aring|Auml;|Beta;|COPY;|Ecirc|Euml;|Icirc|Iota;|Iuml;|Ocirc|Ouml;|QUOT;|THORN|Ucirc|Uuml;|Yuml;|Zeta;|acirc|acute|aelig|apos;|aring|auml;|beta;|bull;|cedil|cent;|circ;|cong;|copy;|dArr;|darr;|ecirc|emsp;|ensp;|euml;|euro;|fnof;|hArr;|harr;|icirc|iexcl|iota;|isin;|iuml;|lArr;|lang;|laquo|larr;|macr;|micro|nbsp;|nsub;|ocirc|ordf;|ordm;|ouml;|para;|part;|perp;|pound|prod;|prop;|quot;|rArr;|rang;|raquo|rarr;|real;|sdot;|sect;|sube;|sup1;|sup2;|sup3;|supe;|szlig|thorn|times|uArr;|uarr;|ucirc|uuml;|yuml;|zeta;|zwnj;|AMP;|Auml|COPY|Chi;|ETH;|Eta;|Euml|Iuml|Ouml|Phi;|Psi;|QUOT|REG;|Rho;|Tau;|Uuml|amp;|and;|ang;|auml|cap;|cent|chi;|copy|cup;|deg;|eta;|eth;|euml|int;|iuml|loz;|lrm;|macr|nbsp|not;|ordf|ordm|ouml|para|phi;|piv;|psi;|quot|reg;|rho;|rlm;|sect|shy;|sim;|sub;|sum;|sup1|sup2|sup3|sup;|tau;|uml;|uuml|yen;|yuml|zwj;|AMP|ETH|GT;|LT;|Mu;|Nu;|Pi;|REG|Xi;|amp|deg|eth|ge;|gt;|le;|lt;|mu;|ne;|ni;|not|nu;|or;|pi;|reg|shy|uml|xi;|yen|GT|LT|gt|lt)/;

our $entityNameMatchAttr = qr/^(?:Aacute|Agrave|Atilde|Ccedil|Eacute|Egrave|Iacute|Igrave|Ntilde|Oacute|Ograve|Oslash|Otilde|Uacute|Ugrave|Yacute|aacute|agrave|atilde|brvbar|ccedil|curren|divide|eacute|egrave|frac12|frac14|frac34|iacute|igrave|iquest|middot|ntilde|oacute|ograve|oslash|otilde|plusmn|uacute|ugrave|yacute|AElig|Acirc|Aring|Ecirc|Icirc|Ocirc|THORN|Ucirc|acirc|acute|aelig|aring|cedil|ecirc|icirc|iexcl|laquo|micro|ocirc|pound|raquo|szlig|thorn|times|ucirc|Auml|COPY|Euml|Iuml|Ouml|QUOT|Uuml|auml|cent|copy|euml|iuml|macr|nbsp|ordf|ordm|ouml|para|quot|sect|sup1|sup2|sup3|uuml|yuml|AMP|ETH|REG|amp|deg|eth|not|reg|shy|uml|yen|GT|LT|gt|lt)(?:[^0-9A-Za-z]|$)/;

our $entityNameValues = { "AElig" => 0x00C6, "AElig;" => 0x00C6, "AMP" => 0x0026, "AMP;" => 0x0026, "Aacute" => 0x00C1, "Aacute;" => 0x00C1, "Acirc" => 0x00C2, "Acirc;" => 0x00C2, "Agrave" => 0x00C0, "Agrave;" => 0x00C0, "Alpha;" => 0x0391, "Aring" => 0x00C5, "Aring;" => 0x00C5, "Atilde" => 0x00C3, "Atilde;" => 0x00C3, "Auml" => 0x00C4, "Auml;" => 0x00C4, "Beta;" => 0x0392, "COPY" => 0x00A9, "COPY;" => 0x00A9, "Ccedil" => 0x00C7, "Ccedil;" => 0x00C7, "Chi;" => 0x03A7, "Dagger;" => 0x2021, "Delta;" => 0x0394, "ETH" => 0x00D0, "ETH;" => 0x00D0, "Eacute" => 0x00C9, "Eacute;" => 0x00C9, "Ecirc" => 0x00CA, "Ecirc;" => 0x00CA, "Egrave" => 0x00C8, "Egrave;" => 0x00C8, "Epsilon;" => 0x0395, "Eta;" => 0x0397, "Euml" => 0x00CB, "Euml;" => 0x00CB, "GT" => 0x003E, "GT;" => 0x003E, "Gamma;" => 0x0393, "Iacute" => 0x00CD, "Iacute;" => 0x00CD, "Icirc" => 0x00CE, "Icirc;" => 0x00CE, "Igrave" => 0x00CC, "Igrave;" => 0x00CC, "Iota;" => 0x0399, "Iuml" => 0x00CF, "Iuml;" => 0x00CF, "Kappa;" => 0x039A, "LT" => 0x003C, "LT;" => 0x003C, "Lambda;" => 0x039B, "Mu;" => 0x039C, "Ntilde" => 0x00D1, "Ntilde;" => 0x00D1, "Nu;" => 0x039D, "OElig;" => 0x0152, "Oacute" => 0x00D3, "Oacute;" => 0x00D3, "Ocirc" => 0x00D4, "Ocirc;" => 0x00D4, "Ograve" => 0x00D2, "Ograve;" => 0x00D2, "Omega;" => 0x03A9, "Omicron;" => 0x039F, "Oslash" => 0x00D8, "Oslash;" => 0x00D8, "Otilde" => 0x00D5, "Otilde;" => 0x00D5, "Ouml" => 0x00D6, "Ouml;" => 0x00D6, "Phi;" => 0x03A6, "Pi;" => 0x03A0, "Prime;" => 0x2033, "Psi;" => 0x03A8, "QUOT" => 0x0022, "QUOT;" => 0x0022, "REG" => 0x00AE, "REG;" => 0x00AE, "Rho;" => 0x03A1, "Scaron;" => 0x0160, "Sigma;" => 0x03A3, "THORN" => 0x00DE, "THORN;" => 0x00DE, "TRADE;" => 0x2122, "Tau;" => 0x03A4, "Theta;" => 0x0398, "Uacute" => 0x00DA, "Uacute;" => 0x00DA, "Ucirc" => 0x00DB, "Ucirc;" => 0x00DB, "Ugrave" => 0x00D9, "Ugrave;" => 0x00D9, "Upsilon;" => 0x03A5, "Uuml" => 0x00DC, "Uuml;" => 0x00DC, "Xi;" => 0x039E, "Yacute" => 0x00DD, "Yacute;" => 0x00DD, "Yuml;" => 0x0178, "Zeta;" => 0x0396, "aacute" => 0x00E1, "aacute;" => 0x00E1, "acirc" => 0x00E2, "acirc;" => 0x00E2, "acute" => 0x00B4, "acute;" => 0x00B4, "aelig" => 0x00E6, "aelig;" => 0x00E6, "agrave" => 0x00E0, "agrave;" => 0x00E0, "alefsym;" => 0x2135, "alpha;" => 0x03B1, "amp" => 0x0026, "amp;" => 0x0026, "and;" => 0x2227, "ang;" => 0x2220, "apos;" => 0x0027, "aring" => 0x00E5, "aring;" => 0x00E5, "asymp;" => 0x2248, "atilde" => 0x00E3, "atilde;" => 0x00E3, "auml" => 0x00E4, "auml;" => 0x00E4, "bdquo;" => 0x201E, "beta;" => 0x03B2, "brvbar" => 0x00A6, "brvbar;" => 0x00A6, "bull;" => 0x2022, "cap;" => 0x2229, "ccedil" => 0x00E7, "ccedil;" => 0x00E7, "cedil" => 0x00B8, "cedil;" => 0x00B8, "cent" => 0x00A2, "cent;" => 0x00A2, "chi;" => 0x03C7, "circ;" => 0x02C6, "clubs;" => 0x2663, "cong;" => 0x2245, "copy" => 0x00A9, "copy;" => 0x00A9, "crarr;" => 0x21B5, "cup;" => 0x222A, "curren" => 0x00A4, "curren;" => 0x00A4, "dArr;" => 0x21D3, "dagger;" => 0x2020, "darr;" => 0x2193, "deg" => 0x00B0, "deg;" => 0x00B0, "delta;" => 0x03B4, "diams;" => 0x2666, "divide" => 0x00F7, "divide;" => 0x00F7, "eacute" => 0x00E9, "eacute;" => 0x00E9, "ecirc" => 0x00EA, "ecirc;" => 0x00EA, "egrave" => 0x00E8, "egrave;" => 0x00E8, "empty;" => 0x2205, "emsp;" => 0x2003, "ensp;" => 0x2002, "epsilon;" => 0x03B5, "equiv;" => 0x2261, "eta;" => 0x03B7, "eth" => 0x00F0, "eth;" => 0x00F0, "euml" => 0x00EB, "euml;" => 0x00EB, "euro;" => 0x20AC, "exist;" => 0x2203, "fnof;" => 0x0192, "forall;" => 0x2200, "frac12" => 0x00BD, "frac12;" => 0x00BD, "frac14" => 0x00BC, "frac14;" => 0x00BC, "frac34" => 0x00BE, "frac34;" => 0x00BE, "frasl;" => 0x2044, "gamma;" => 0x03B3, "ge;" => 0x2265, "gt" => 0x003E, "gt;" => 0x003E, "hArr;" => 0x21D4, "harr;" => 0x2194, "hearts;" => 0x2665, "hellip;" => 0x2026, "iacute" => 0x00ED, "iacute;" => 0x00ED, "icirc" => 0x00EE, "icirc;" => 0x00EE, "iexcl" => 0x00A1, "iexcl;" => 0x00A1, "igrave" => 0x00EC, "igrave;" => 0x00EC, "image;" => 0x2111, "infin;" => 0x221E, "int;" => 0x222B, "iota;" => 0x03B9, "iquest" => 0x00BF, "iquest;" => 0x00BF, "isin;" => 0x2208, "iuml" => 0x00EF, "iuml;" => 0x00EF, "kappa;" => 0x03BA, "lArr;" => 0x21D0, "lambda;" => 0x03BB, "lang;" => 0x3008, "laquo" => 0x00AB, "laquo;" => 0x00AB, "larr;" => 0x2190, "lceil;" => 0x2308, "ldquo;" => 0x201C, "le;" => 0x2264, "lfloor;" => 0x230A, "lowast;" => 0x2217, "loz;" => 0x25CA, "lrm;" => 0x200E, "lsaquo;" => 0x2039, "lsquo;" => 0x2018, "lt" => 0x003C, "lt;" => 0x003C, "macr" => 0x00AF, "macr;" => 0x00AF, "mdash;" => 0x2014, "micro" => 0x00B5, "micro;" => 0x00B5, "middot" => 0x00B7, "middot;" => 0x00B7, "minus;" => 0x2212, "mu;" => 0x03BC, "nabla;" => 0x2207, "nbsp" => 0x00A0, "nbsp;" => 0x00A0, "ndash;" => 0x2013, "ne;" => 0x2260, "ni;" => 0x220B, "not" => 0x00AC, "not;" => 0x00AC, "notin;" => 0x2209, "nsub;" => 0x2284, "ntilde" => 0x00F1, "ntilde;" => 0x00F1, "nu;" => 0x03BD, "oacute" => 0x00F3, "oacute;" => 0x00F3, "ocirc" => 0x00F4, "ocirc;" => 0x00F4, "oelig;" => 0x0153, "ograve" => 0x00F2, "ograve;" => 0x00F2, "oline;" => 0x203E, "omega;" => 0x03C9, "omicron;" => 0x03BF, "oplus;" => 0x2295, "or;" => 0x2228, "ordf" => 0x00AA, "ordf;" => 0x00AA, "ordm" => 0x00BA, "ordm;" => 0x00BA, "oslash" => 0x00F8, "oslash;" => 0x00F8, "otilde" => 0x00F5, "otilde;" => 0x00F5, "otimes;" => 0x2297, "ouml" => 0x00F6, "ouml;" => 0x00F6, "para" => 0x00B6, "para;" => 0x00B6, "part;" => 0x2202, "permil;" => 0x2030, "perp;" => 0x22A5, "phi;" => 0x03C6, "pi;" => 0x03C0, "piv;" => 0x03D6, "plusmn" => 0x00B1, "plusmn;" => 0x00B1, "pound" => 0x00A3, "pound;" => 0x00A3, "prime;" => 0x2032, "prod;" => 0x220F, "prop;" => 0x221D, "psi;" => 0x03C8, "quot" => 0x0022, "quot;" => 0x0022, "rArr;" => 0x21D2, "radic;" => 0x221A, "rang;" => 0x3009, "raquo" => 0x00BB, "raquo;" => 0x00BB, "rarr;" => 0x2192, "rceil;" => 0x2309, "rdquo;" => 0x201D, "real;" => 0x211C, "reg" => 0x00AE, "reg;" => 0x00AE, "rfloor;" => 0x230B, "rho;" => 0x03C1, "rlm;" => 0x200F, "rsaquo;" => 0x203A, "rsquo;" => 0x2019, "sbquo;" => 0x201A, "scaron;" => 0x0161, "sdot;" => 0x22C5, "sect" => 0x00A7, "sect;" => 0x00A7, "shy" => 0x00AD, "shy;" => 0x00AD, "sigma;" => 0x03C3, "sigmaf;" => 0x03C2, "sim;" => 0x223C, "spades;" => 0x2660, "sub;" => 0x2282, "sube;" => 0x2286, "sum;" => 0x2211, "sup1" => 0x00B9, "sup1;" => 0x00B9, "sup2" => 0x00B2, "sup2;" => 0x00B2, "sup3" => 0x00B3, "sup3;" => 0x00B3, "sup;" => 0x2283, "supe;" => 0x2287, "szlig" => 0x00DF, "szlig;" => 0x00DF, "tau;" => 0x03C4, "there4;" => 0x2234, "theta;" => 0x03B8, "thetasym;" => 0x03D1, "thinsp;" => 0x2009, "thorn" => 0x00FE, "thorn;" => 0x00FE, "tilde;" => 0x02DC, "times" => 0x00D7, "times;" => 0x00D7, "trade;" => 0x2122, "uArr;" => 0x21D1, "uacute" => 0x00FA, "uacute;" => 0x00FA, "uarr;" => 0x2191, "ucirc" => 0x00FB, "ucirc;" => 0x00FB, "ugrave" => 0x00F9, "ugrave;" => 0x00F9, "uml" => 0x00A8, "uml;" => 0x00A8, "upsih;" => 0x03D2, "upsilon;" => 0x03C5, "uuml" => 0x00FC, "uuml;" => 0x00FC, "weierp;" => 0x2118, "xi;" => 0x03BE, "yacute" => 0x00FD, "yacute;" => 0x00FD, "yen" => 0x00A5, "yen;" => 0x00A5, "yuml" => 0x00FF, "yuml;" => 0x00FF, "zeta;" => 0x03B6, "zwj;" => 0x200D, "zwnj;" => 0x200C };

our $entityMap = { 0x000D => 0x000A, 0x0080 => 0x20AC, 0x0081 => 0xFFFD, 0x0082 => 0x201A, 0x0083 => 0x0192, 0x0084 => 0x201E, 0x0085 => 0x2026, 0x0086 => 0x2020, 0x0087 => 0x2021, 0x0088 => 0x02C6, 0x0089 => 0x2030, 0x008A => 0x0160, 0x008B => 0x2039, 0x008C => 0x0152, 0x008D => 0xFFFD, 0x008E => 0x017D, 0x008F => 0xFFFD, 0x0090 => 0xFFFD, 0x0091 => 0x2018, 0x0092 => 0x2019, 0x0093 => 0x201C, 0x0094 => 0x201D, 0x0095 => 0x2022, 0x0096 => 0x2013, 0x0097 => 0x2014, 0x0098 => 0x02DC, 0x0099 => 0x2122, 0x009A => 0x0161, 0x009B => 0x203A, 0x009C => 0x0153, 0x009D => 0xFFFD, 0x009E => 0x017E, 0x009F => 0x0178 };

my $PCDATA = 0;
my $RCDATA = 1;
my $CDATA = 2;
my $PLAINTEXT = 3;

my $DataState;
my $EntityDataState;
my $TagOpenState;
my $CloseTagOpenState;
my $TagNameState;
my $BeforeAttributeNameState;
my $AttributeNameState;
my $AfterAttributeNameState;
my $BeforeAttributeValueState;
my $AttributeValueDoubleQuotedState;
my $AttributeValueSingleQuotedState;
my $AttributeValueUnquotedState;
my $EntityInAttributeValueState_DoubleQuoted;
my $EntityInAttributeValueState_SingleQuoted;
my $EntityInAttributeValueState_Unquoted;
my $BogusCommentState;
my $BogusCommentState_Continue;
my $MarkupDeclarationOpenState;
my $CommentStartState;
my $CommentStartDashState;
my $CommentState;
my $CommentEndDashState;
my $CommentEndState;
my $DoctypeState;
my $BeforeDoctypeNameState;
my $DoctypeNameState;
my $AfterDoctypeNameState;
my $BeforeDoctypePublicIdentifierState;
my $DoctypePublicIdentifierDoubleQuotedState;
my $DoctypePublicIdentifierSingleQuotedState;
my $AfterDoctypePublicIdentifierState;
my $BeforeDoctypeSystemIdentifierState;
my $DoctypeSystemIdentifierDoubleQuotedState;
my $DoctypeSystemIdentifierSingleQuotedState;
my $AfterDoctypeSystemIdentifierState;
my $BogusDoctypeState;

$DataState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 38 && ($contentModel == $PCDATA || $contentModel == $RCDATA))
    {
        $machineState = $EntityDataState;
    }
    elsif ($currentCharacter == 45)
    {
        if (($contentModel == $RCDATA || $contentModel == $CDATA) && !$escapeFlag && getOldCharacter(1) == 45 && getOldCharacter(2) == 33 && getOldCharacter(3) == 60)
        {
            $escapeFlag = 1;
            emitCharacterToken($currentCharacter);
        }
        else
        {
            emitCharacterToken($currentCharacter);
        }
    }
    elsif ($currentCharacter == 60 && $contentModel == $PCDATA)
    {
        $machineState = $TagOpenState;
    }
    elsif ($currentCharacter == 60 && ($contentModel == $RCDATA || $contentModel == $CDATA) && !$escapeFlag)
    {
        $machineState = $TagOpenState;
    }
    elsif ($currentCharacter == 62)
    {
        if (($contentModel == $RCDATA || $contentModel == $CDATA) && $escapeFlag && getOldCharacter(1) == 45 && getOldCharacter(2) == 45)
        {
            $escapeFlag = 0;
            emitCharacterToken($currentCharacter);
        }
        else
        {
            emitCharacterToken($currentCharacter);
        }
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        emitEOFToken();
        return;
    }
    elsif (1)
    {
        emitCharacterToken($currentCharacter);
    }
    return;
};
$EntityDataState = sub {
    my $hasConsumableEntity_ = hasConsumableEntity(0);
    if (!$hasConsumableEntity_)
    {
        emitCharacterToken(38);
        $machineState = $DataState;
    }
    elsif (1)
    {
        consumeAndEmitEntity();
        $machineState = $DataState;
    }
    return;
};
$TagOpenState = sub {
    $currentCharacter = consumeCharacter();
    if ($contentModel == $RCDATA || $contentModel == $CDATA)
    {
        if ($currentCharacter == 47)
        {
            $machineState = $CloseTagOpenState;
        }
        else
        {
            emitCharacterToken(60);
            reconsumeCharacter($currentCharacter);
            $machineState = $DataState;
        }
    }
    elsif ($contentModel == $PCDATA && $currentCharacter == 33)
    {
        $machineState = $MarkupDeclarationOpenState;
    }
    elsif ($contentModel == $PCDATA && $currentCharacter == 47)
    {
        $machineState = $CloseTagOpenState;
    }
    elsif ($contentModel == $PCDATA && ($currentCharacter >= 65 && $currentCharacter <= 90))
    {
        createStartTagToken();
        appendToTagTokenName($currentCharacter + 32);
        $machineState = $TagNameState;
    }
    elsif ($contentModel == $PCDATA && ($currentCharacter >= 97 && $currentCharacter <= 122))
    {
        createStartTagToken();
        appendToTagTokenName($currentCharacter);
        $machineState = $TagNameState;
    }
    elsif ($contentModel == $PCDATA && $currentCharacter == 62)
    {
        parseError("Character '>' in TagOpenState");
        emitCharacterToken(60);
        emitCharacterToken(62);
        $machineState = $DataState;
    }
    elsif ($contentModel == $PCDATA && $currentCharacter == 63)
    {
        parseError("Character '?' in TagOpenState");
        $machineState = $BogusCommentState;
    }
    elsif ($contentModel == $PCDATA && 1)
    {
        parseError("Unexpected character in TagOpenState");
        emitCharacterToken(60);
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    return;
};
$CloseTagOpenState = sub {
    $currentCharacter = consumeCharacter();
    my $isEndOfCData_ = isEndOfCData();
    if (($contentModel == $RCDATA || $contentModel == $CDATA) && !$isEndOfCData_)
    {
        emitCharacterToken(60);
        emitCharacterToken(47);
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (($contentModel == $PCDATA || $isEndOfCData_) && ($currentCharacter >= 65 && $currentCharacter <= 90))
    {
        createEndTagToken();
        appendToTagTokenName($currentCharacter + 32);
        $machineState = $TagNameState;
    }
    elsif (($contentModel == $PCDATA || $isEndOfCData_) && ($currentCharacter >= 97 && $currentCharacter <= 122))
    {
        createEndTagToken();
        appendToTagTokenName($currentCharacter);
        $machineState = $TagNameState;
    }
    elsif (($contentModel == $PCDATA || $isEndOfCData_) && $currentCharacter == 62)
    {
        parseError("Character '>' in CloseTagOpenState");
        $machineState = $DataState;
    }
    elsif (($contentModel == $PCDATA || $isEndOfCData_) && $currentCharacter == $Char_EOF)
    {
        parseError("EOF in CloseTagOpenState");
        emitCharacterToken(60);
        emitCharacterToken(47);
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (($contentModel == $PCDATA || $isEndOfCData_) && 1)
    {
        parseError("Unexpected character in CloseTagOpenState");
        $machineState = $BogusCommentState;
    }
    return;
};
$TagNameState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
        $machineState = $BeforeAttributeNameState;
    }
    elsif ($currentCharacter == 62)
    {
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter >= 65 && $currentCharacter <= 90)
    {
        appendToTagTokenName($currentCharacter + 32);
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in TagNameState");
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif ($currentCharacter == 47)
    {
        parseErrorIfNonpermittedSlash();
        $machineState = $BeforeAttributeNameState;
    }
    elsif (1)
    {
        appendToTagTokenName($currentCharacter);
    }
    return;
};
$BeforeAttributeNameState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 62)
    {
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter >= 65 && $currentCharacter <= 90)
    {
        createTagTokenAttribute();
        appendToTagTokenAttributeName($currentCharacter + 32);
        $machineState = $AttributeNameState;
    }
    elsif ($currentCharacter == 47)
    {
        parseErrorIfNonpermittedSlash();
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in BeforeAttributeNameState");
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        createTagTokenAttribute();
        appendToTagTokenAttributeName($currentCharacter);
        $machineState = $AttributeNameState;
    }
    return;
};
$AttributeNameState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
        handleDuplicateAttributes();
        $machineState = $AfterAttributeNameState;
    }
    elsif ($currentCharacter == 61)
    {
        handleDuplicateAttributes();
        $machineState = $BeforeAttributeValueState;
    }
    elsif ($currentCharacter == 62)
    {
        handleDuplicateAttributes();
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter >= 65 && $currentCharacter <= 90)
    {
        appendToTagTokenAttributeName($currentCharacter + 32);
    }
    elsif ($currentCharacter == 47)
    {
        parseErrorIfNonpermittedSlash();
        handleDuplicateAttributes();
        $machineState = $BeforeAttributeNameState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AttributeNameState");
        handleDuplicateAttributes();
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToTagTokenAttributeName($currentCharacter);
    }
    return;
};
$AfterAttributeNameState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 61)
    {
        $machineState = $BeforeAttributeValueState;
    }
    elsif ($currentCharacter == 62)
    {
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter >= 65 && $currentCharacter <= 90)
    {
        createTagTokenAttribute();
        appendToTagTokenAttributeName($currentCharacter + 32);
        $machineState = $AttributeNameState;
    }
    elsif ($currentCharacter == 47)
    {
        parseErrorIfNonpermittedSlash();
        $machineState = $BeforeAttributeNameState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AfterAttributeNameState");
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        createTagTokenAttribute();
        appendToTagTokenAttributeName($currentCharacter);
        $machineState = $AttributeNameState;
    }
    return;
};
$BeforeAttributeValueState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 34)
    {
        $machineState = $AttributeValueDoubleQuotedState;
    }
    elsif ($currentCharacter == 38)
    {
        reconsumeCharacter($currentCharacter);
        $machineState = $AttributeValueUnquotedState;
    }
    elsif ($currentCharacter == 39)
    {
        $machineState = $AttributeValueSingleQuotedState;
    }
    elsif ($currentCharacter == 62)
    {
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in BeforeAttributeValueState");
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToTagTokenAttributeValue($currentCharacter);
        $machineState = $AttributeValueUnquotedState;
    }
    return;
};
$AttributeValueDoubleQuotedState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 34)
    {
        $machineState = $BeforeAttributeNameState;
    }
    elsif ($currentCharacter == 38)
    {
        $machineState = $EntityInAttributeValueState_DoubleQuoted;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AttributeValueDoubleQuotedState");
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToTagTokenAttributeValue($currentCharacter);
    }
    return;
};
$AttributeValueSingleQuotedState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 39)
    {
        $machineState = $BeforeAttributeNameState;
    }
    elsif ($currentCharacter == 38)
    {
        $machineState = $EntityInAttributeValueState_SingleQuoted;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AttributeValueSingleQuotedState");
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToTagTokenAttributeValue($currentCharacter);
    }
    return;
};
$AttributeValueUnquotedState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
        $machineState = $BeforeAttributeNameState;
    }
    elsif ($currentCharacter == 38)
    {
        $machineState = $EntityInAttributeValueState_Unquoted;
    }
    elsif ($currentCharacter == 62)
    {
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AttributeValueUnquotedState");
        parseErrorIfEndTagWithAttributes();
        emitCurrentTagToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToTagTokenAttributeValue($currentCharacter);
    }
    return;
};
$EntityInAttributeValueState_DoubleQuoted = sub {
    my $hasConsumableEntity_ = hasConsumableEntity(1);
    if (!$hasConsumableEntity_)
    {
        appendToTagTokenAttributeValue(38);
        $machineState = $AttributeValueDoubleQuotedState;
    }
    elsif (1)
    {
        consumeAndAppendEntity();
        $machineState = $AttributeValueDoubleQuotedState;
    }
    return;
};
$EntityInAttributeValueState_SingleQuoted = sub {
    my $hasConsumableEntity_ = hasConsumableEntity(1);
    if (!$hasConsumableEntity_)
    {
        appendToTagTokenAttributeValue(38);
        $machineState = $AttributeValueSingleQuotedState;
    }
    elsif (1)
    {
        consumeAndAppendEntity();
        $machineState = $AttributeValueSingleQuotedState;
    }
    return;
};
$EntityInAttributeValueState_Unquoted = sub {
    my $hasConsumableEntity_ = hasConsumableEntity(1);
    if (!$hasConsumableEntity_)
    {
        appendToTagTokenAttributeValue(38);
        $machineState = $AttributeValueUnquotedState;
    }
    elsif (1)
    {
        consumeAndAppendEntity();
        $machineState = $AttributeValueUnquotedState;
    }
    return;
};
$BogusCommentState = sub {
    if ($currentCharacter == $Char_EOF)
    {
        createCommentToken();
        emitCurrentCommentToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif ($currentCharacter == 62)
    {
        createCommentToken();
        emitCurrentCommentToken();
        $machineState = $DataState;
    }
    elsif (1)
    {
        createCommentToken();
        appendToCommentToken($currentCharacter);
        $machineState = $BogusCommentState_Continue;
    }
    return;
};
$BogusCommentState_Continue = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == $Char_EOF)
    {
        emitCurrentCommentToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif ($currentCharacter == 62)
    {
        emitCurrentCommentToken();
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToCommentToken($currentCharacter);
    }
    return;
};
$MarkupDeclarationOpenState = sub {
    $currentCharacter = consumeCharacter();
    if (isFollowedBy("--"))
    {
        $currentCharacter = consumeCharacter();
        createCommentToken();
        $machineState = $CommentStartState;
    }
    elsif (!(isFollowedBy("--")) && isFollowedBy("doctype"))
    {
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $machineState = $DoctypeState;
    }
    elsif (1)
    {
        parseError("Unexpected character in MarkupDeclarationOpenState");
        $machineState = $BogusCommentState;
    }
    return;
};
$CommentStartState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 45)
    {
        $machineState = $CommentStartDashState;
    }
    elsif ($currentCharacter == 62)
    {
        parseError("Character '>' in CommentStartState");
        emitCurrentCommentToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in CommentStartState");
        emitCurrentCommentToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToCommentToken($currentCharacter);
        $machineState = $CommentState;
    }
    return;
};
$CommentStartDashState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 45)
    {
        $machineState = $CommentEndState;
    }
    elsif ($currentCharacter == 62)
    {
        parseError("Character '>' in CommentStartDashState");
        emitCurrentCommentToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in CommentStartDashState");
        emitCurrentCommentToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToCommentToken(45);
        appendToCommentToken($currentCharacter);
        $machineState = $CommentState;
    }
    return;
};
$CommentState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 45)
    {
        $machineState = $CommentEndDashState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in CommentState");
        emitCurrentCommentToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToCommentToken($currentCharacter);
    }
    return;
};
$CommentEndDashState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 45)
    {
        $machineState = $CommentEndState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in CommentEndDashState");
        emitCurrentCommentToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToCommentToken(45);
        appendToCommentToken($currentCharacter);
        $machineState = $CommentState;
    }
    return;
};
$CommentEndState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 62)
    {
        emitCurrentCommentToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == 45)
    {
        parseError("Character '-' in CommentEndState");
        appendToCommentToken(45);
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in CommentEndState");
        emitCurrentCommentToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        parseError("Unexpected character in CommentEndState");
        appendToCommentToken(45);
        appendToCommentToken(45);
        appendToCommentToken($currentCharacter);
        $machineState = $CommentState;
    }
    return;
};
$DoctypeState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
        $machineState = $BeforeDoctypeNameState;
    }
    elsif (1)
    {
        parseError("Unexpected character in DoctypeState");
        reconsumeCharacter($currentCharacter);
        $machineState = $BeforeDoctypeNameState;
    }
    return;
};
$BeforeDoctypeNameState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 62)
    {
        parseError("Character '>' in BeforeDoctypeNameState");
        createDoctypeToken();
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in BeforeDoctypeNameState");
        createDoctypeToken();
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        createDoctypeToken();
        appendToDoctypeTokenName($currentCharacter);
        $machineState = $DoctypeNameState;
    }
    return;
};
$DoctypeNameState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
        $machineState = $AfterDoctypeNameState;
    }
    elsif ($currentCharacter == 62)
    {
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in DoctypeNameState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToDoctypeTokenName($currentCharacter);
    }
    return;
};
$AfterDoctypeNameState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 62)
    {
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AfterDoctypeNameState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (isFollowedBy("public"))
    {
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $machineState = $BeforeDoctypePublicIdentifierState;
    }
    elsif (isFollowedBy("system"))
    {
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $currentCharacter = consumeCharacter();
        $machineState = $BeforeDoctypeSystemIdentifierState;
    }
    elsif (1)
    {
        parseError("Unexpected character in AfterDoctypeNameState");
        $machineState = $BogusDoctypeState;
    }
    return;
};
$BeforeDoctypePublicIdentifierState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 34)
    {
        setDoctypeTokenPubIdEmpty();
        $machineState = $DoctypePublicIdentifierDoubleQuotedState;
    }
    elsif ($currentCharacter == 39)
    {
        setDoctypeTokenPubIdEmpty();
        $machineState = $DoctypePublicIdentifierSingleQuotedState;
    }
    elsif ($currentCharacter == 62)
    {
        parseError("Character '>' in BeforeDoctypePublicIdentifierState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in BeforeDoctypePublicIdentifierState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        parseError("Unexpected character in BeforeDoctypePublicIdentifierState");
        $machineState = $BogusDoctypeState;
    }
    return;
};
$DoctypePublicIdentifierDoubleQuotedState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 34)
    {
        $machineState = $AfterDoctypePublicIdentifierState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in DoctypePublicIdentifierDoubleQuotedState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToDoctypeTokenPubId($currentCharacter);
    }
    return;
};
$DoctypePublicIdentifierSingleQuotedState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 39)
    {
        $machineState = $AfterDoctypePublicIdentifierState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in DoctypePublicIdentifierSingleQuotedState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToDoctypeTokenPubId($currentCharacter);
    }
    return;
};
$AfterDoctypePublicIdentifierState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 34)
    {
        setDoctypeTokenSysIdEmpty();
        $machineState = $DoctypeSystemIdentifierDoubleQuotedState;
    }
    elsif ($currentCharacter == 39)
    {
        setDoctypeTokenSysIdEmpty();
        $machineState = $DoctypeSystemIdentifierSingleQuotedState;
    }
    elsif ($currentCharacter == 62)
    {
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AfterDoctypePublicIdentifierState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        parseError("Unexpected character in AfterDoctypePublicIdentifierState");
        $machineState = $BogusDoctypeState;
    }
    return;
};
$BeforeDoctypeSystemIdentifierState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 34)
    {
        setDoctypeTokenSysIdEmpty();
        $machineState = $DoctypeSystemIdentifierDoubleQuotedState;
    }
    elsif ($currentCharacter == 39)
    {
        setDoctypeTokenSysIdEmpty();
        $machineState = $DoctypeSystemIdentifierSingleQuotedState;
    }
    elsif ($currentCharacter == 62)
    {
        parseError("Character '>' in BeforeDoctypeSystemIdentifierState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in BeforeDoctypeSystemIdentifierState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        parseError("Unexpected character in BeforeDoctypeSystemIdentifierState");
        $machineState = $BogusDoctypeState;
    }
    return;
};
$DoctypeSystemIdentifierDoubleQuotedState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 34)
    {
        $machineState = $AfterDoctypeSystemIdentifierState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in DoctypeSystemIdentifierDoubleQuotedState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToDoctypeTokenSysId($currentCharacter);
    }
    return;
};
$DoctypeSystemIdentifierSingleQuotedState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 39)
    {
        $machineState = $AfterDoctypeSystemIdentifierState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in DoctypeSystemIdentifierSingleQuotedState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        appendToDoctypeTokenSysId($currentCharacter);
    }
    return;
};
$AfterDoctypeSystemIdentifierState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 9 || $currentCharacter == 10 || $currentCharacter == 11 || $currentCharacter == 12 || $currentCharacter == 32)
    {
    }
    elsif ($currentCharacter == 62)
    {
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in AfterDoctypeSystemIdentifierState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
        parseError("Unexpected character in AfterDoctypeSystemIdentifierState");
        $machineState = $BogusDoctypeState;
    }
    return;
};
$BogusDoctypeState = sub {
    $currentCharacter = consumeCharacter();
    if ($currentCharacter == 62)
    {
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        $machineState = $DataState;
    }
    elsif ($currentCharacter == $Char_EOF)
    {
        parseError("EOF in BogusDoctypeState");
        setDoctypeTokenIncorrect();
        emitCurrentDoctypeToken();
        reconsumeCharacter($currentCharacter);
        $machineState = $DataState;
    }
    elsif (1)
    {
    }
    return;
};
sub init { $machineState = $DataState; $contentModel = $PCDATA; $Char_EOF = 0; $escapeFlag = 0 }
sub step { $machineState->(); return $machineState; }
