@@ -177,6 +177,8 @@ class AsmParser : public MCAsmParser {
177177
178178 // / Are we parsing ms-style inline assembly?
179179 bool ParsingMSInlineAsm = false ;
180+ bool NeedParseFromRdata = false ;
181+ int ParseRdataCnt = 0 ;
180182
181183 // / Did we already inform the user about inconsistent MD5 usage?
182184 bool ReportedInconsistentMD5 = false ;
@@ -996,11 +998,65 @@ bool AsmParser::Run(bool NoInitialTextSection, bool NoFinalize) {
996998
997999 getTargetParser ().onBeginOfFile ();
9981000
1001+ // Save begin location, check if have .rdata section, confirm where to begin
1002+ // parse. If have it and .rdata after .text, begin parse from .rdata, when go
1003+ // to Eof, jump to begin location and then continue parse.
1004+ SMLoc IDLoc_start = getTok ().getLoc ();
1005+ SMLoc IDLoc_rdata = getTok ().getLoc ();
1006+ StringRef IDVal;
1007+ bool HasParseText = false ;
1008+ bool HasParseRdata = false ;
1009+ while (Lexer.isNot (AsmToken::Eof)) {
1010+ while (Lexer.is (AsmToken::Space)) {
1011+ IDLoc_rdata = getTok ().getLoc ();
1012+ Lex ();
1013+ }
1014+ if (Lexer.is (AsmToken::EndOfStatement) || Lexer.is (AsmToken::Integer) ||
1015+ Lexer.is (AsmToken::Dot) || Lexer.is (AsmToken::LCurly) ||
1016+ Lexer.is (AsmToken::RCurly) ||
1017+ (Lexer.is (AsmToken::Star) &&
1018+ getTargetParser ().starIsStartOfStatement ())) {
1019+ IDLoc_rdata = getTok ().getLoc ();
1020+ Lex ();
1021+ } else if (!parseIdentifier (IDVal)) {
1022+ if (IDVal == " .rdata" )
1023+ HasParseRdata = true ;
1024+ if (IDVal == " .text" )
1025+ HasParseText = true ;
1026+ // .text section before .rdata section.
1027+ if (IDVal == " .rdata" && HasParseText == true ) {
1028+ NeedParseFromRdata = true ;
1029+ jumpToLoc (IDLoc_rdata);
1030+ Lex ();
1031+ break ;
1032+ }
1033+ if (IDVal == " .text" && HasParseRdata == true ) {
1034+ break ;
1035+ }
1036+ IDLoc_rdata = getTok ().getLoc ();
1037+ Lex ();
1038+ } else {
1039+ IDLoc_rdata = getTok ().getLoc ();
1040+ Lex ();
1041+ }
1042+ }
1043+
1044+ // If did not have .rdata section or .rdata before .text, jump to begin
1045+ // location and then parse.
1046+ if (NeedParseFromRdata == false ) {
1047+ jumpToLoc (IDLoc_start);
1048+ Lex ();
1049+ }
1050+
1051+ BeginParse:
9991052 // While we have input, parse each statement.
10001053 while (Lexer.isNot (AsmToken::Eof)) {
10011054 ParseStatementInfo Info (&AsmStrRewrites);
10021055 bool Parsed = parseStatement (Info, nullptr );
10031056
1057+ if (!Parsed && (ParseRdataCnt == 2 )) {
1058+ break ;
1059+ }
10041060 // If we have a Lexer Error we are on an Error Token. Load in Lexer Error
10051061 // for printing ErrMsg via Lex() only if no (presumably better) parser error
10061062 // exists.
@@ -1016,6 +1072,15 @@ bool AsmParser::Run(bool NoInitialTextSection, bool NoFinalize) {
10161072 eatToEndOfStatement ();
10171073 }
10181074
1075+ // Because when we parse from .rdata, what before .rdata would be skipped and
1076+ // not be parsed, so need to go to begin location until once again parse
1077+ // .rdata section.
1078+ if (NeedParseFromRdata == true ) {
1079+ jumpToLoc (IDLoc_start);
1080+ Lex ();
1081+ goto BeginParse;
1082+ }
1083+
10191084 getTargetParser ().onEndOfFile ();
10201085 printPendingErrors ();
10211086
@@ -2003,6 +2068,15 @@ bool AsmParser::parseStatement(ParseStatementInfo &Info,
20032068 // manner, or at least have a default behavior that's shared between
20042069 // all targets and platforms.
20052070
2071+ // Prevent parsing .rdata section twice.
2072+ if (IDVal == " .rdata" ) {
2073+ ParseRdataCnt++;
2074+ }
2075+ if (NeedParseFromRdata == true && ParseRdataCnt == 2 ) {
2076+ NeedParseFromRdata = false ;
2077+ return false ;
2078+ }
2079+
20062080 getTargetParser ().flushPendingInstructions (getStreamer ());
20072081
20082082 ParseStatus TPDirectiveReturn = getTargetParser ().parseDirective (ID);
0 commit comments