28
28
29
29
#include < fmt/format.h>
30
30
31
- #include < sstream>
32
-
33
31
using namespace std ::string_literals;
34
32
using namespace solidity ;
35
33
using namespace solidity ::test;
@@ -39,15 +37,21 @@ using namespace solidity::langutil;
39
37
40
38
Json PlainAssemblyParser::parse (std::string _sourceName, std::string const & _source)
41
39
{
40
+ m_sourceStream = std::istringstream (_source);
42
41
m_sourceName = std::move (_sourceName);
43
42
Json codeJSON = Json::array ();
44
- std::istringstream sourceStream (_source);
45
- while (getline (sourceStream, m_line))
43
+ m_lineNumber = 0 ;
44
+
45
+ if (!m_line.has_value ())
46
+ advanceLine ();
47
+
48
+ while (m_line.has_value ())
46
49
{
47
- advanceLine (m_line);
48
50
if (m_lineTokens.empty ())
51
+ {
52
+ advanceLine ();
49
53
continue ;
50
-
54
+ }
51
55
if (c_instructions.contains (currentToken ().value ))
52
56
{
53
57
expectNoMoreArguments ();
@@ -84,6 +88,8 @@ Json PlainAssemblyParser::parse(std::string _sourceName, std::string const& _sou
84
88
}
85
89
else
86
90
BOOST_THROW_EXCEPTION (std::runtime_error (formatError (" Unknown instruction." )));
91
+
92
+ advanceLine ();
87
93
}
88
94
return {{" .code" , codeJSON}};
89
95
}
@@ -125,12 +131,20 @@ void PlainAssemblyParser::expectNoMoreArguments()
125
131
BOOST_THROW_EXCEPTION (std::runtime_error (formatError (" Too many arguments." )));
126
132
}
127
133
128
- void PlainAssemblyParser::advanceLine (std::string_view _line )
134
+ bool PlainAssemblyParser::advanceLine ()
129
135
{
136
+ std::string line;
137
+ if (!getline (m_sourceStream, line))
138
+ {
139
+ m_line = std::nullopt;
140
+ return false ;
141
+ }
142
+
130
143
++m_lineNumber;
131
- m_line = _line ;
132
- m_lineTokens = tokenizeLine (m_line);
144
+ m_line = std::move (line) ;
145
+ m_lineTokens = tokenizeLine (* m_line);
133
146
m_tokenIndex = 0 ;
147
+ return true ;
134
148
}
135
149
136
150
std::vector<PlainAssemblyParser::Token> PlainAssemblyParser::tokenizeLine (std::string_view _line)
@@ -162,6 +176,9 @@ std::vector<PlainAssemblyParser::Token> PlainAssemblyParser::tokenizeLine(std::s
162
176
163
177
std::string PlainAssemblyParser::formatError (std::string_view _message) const
164
178
{
179
+ soltestAssert (m_line.has_value ());
180
+ soltestAssert (!m_lineTokens.empty ());
181
+
165
182
std::string lineNumberString = std::to_string (m_lineNumber);
166
183
std::string padding (lineNumberString.size (), ' ' );
167
184
std::string underline = std::string (currentToken ().position , ' ' ) + std::string (currentToken ().value .size (), ' ^' );
@@ -174,7 +191,7 @@ std::string PlainAssemblyParser::formatError(std::string_view _message) const
174
191
_message,
175
192
padding, m_sourceName,
176
193
padding,
177
- m_lineNumber, m_line,
194
+ m_lineNumber, * m_line,
178
195
padding, underline
179
196
);
180
197
}
0 commit comments