mirror of
https://github.com/ethereum/solidity
synced 2023-10-03 13:03:40 +00:00
Parsing for inline assembly.
This commit is contained in:
@@ -45,6 +45,7 @@
|
||||
#include <libsolidity/interface/CompilerStack.h>
|
||||
#include <libsolidity/interface/SourceReferenceFormatter.h>
|
||||
#include <libsolidity/interface/GasEstimator.h>
|
||||
#include <libsolidity/inlineasm/AsmParser.h>
|
||||
#include <libsolidity/formal/Why3Translator.h>
|
||||
|
||||
using namespace std;
|
||||
@@ -430,6 +431,10 @@ Allowed options)",
|
||||
"Output a single json document containing the specified information."
|
||||
)
|
||||
(g_argGas.c_str(), "Print an estimate of the maximal gas usage for each function.")
|
||||
(
|
||||
"assemble",
|
||||
"Switch to assembly mode, ignoring all options and assumes input is assembly."
|
||||
)
|
||||
(
|
||||
"link",
|
||||
"Switch to linker mode, ignoring all options apart from --libraries "
|
||||
@@ -509,6 +514,12 @@ bool CommandLineInterface::processInput()
|
||||
if (!parseLibraryOption(library))
|
||||
return false;
|
||||
|
||||
if (m_args.count("assemble"))
|
||||
{
|
||||
// switch to assembly mode
|
||||
m_onlyAssemble = true;
|
||||
return assemble();
|
||||
}
|
||||
if (m_args.count("link"))
|
||||
{
|
||||
// switch to linker mode
|
||||
@@ -574,6 +585,7 @@ bool CommandLineInterface::processInput()
|
||||
};
|
||||
|
||||
m_compiler.reset(new CompilerStack(m_args.count(g_argAddStandard) > 0, fileReader));
|
||||
auto scannerFromSourceName = [&](string const& _sourceName) -> solidity::Scanner const& { return m_compiler->scanner(_sourceName); };
|
||||
try
|
||||
{
|
||||
for (auto const& sourceCode: m_sourceCodes)
|
||||
@@ -593,7 +605,8 @@ bool CommandLineInterface::processInput()
|
||||
SourceReferenceFormatter::printExceptionInformation(
|
||||
cerr,
|
||||
*error,
|
||||
(error->type() == Error::Type::Warning) ? "Warning" : "Error", *m_compiler
|
||||
(error->type() == Error::Type::Warning) ? "Warning" : "Error",
|
||||
scannerFromSourceName
|
||||
);
|
||||
|
||||
if (!successful)
|
||||
@@ -601,7 +614,7 @@ bool CommandLineInterface::processInput()
|
||||
}
|
||||
catch (CompilerError const& _exception)
|
||||
{
|
||||
SourceReferenceFormatter::printExceptionInformation(cerr, _exception, "Compiler error", *m_compiler);
|
||||
SourceReferenceFormatter::printExceptionInformation(cerr, _exception, "Compiler error", scannerFromSourceName);
|
||||
return false;
|
||||
}
|
||||
catch (InternalCompilerError const& _exception)
|
||||
@@ -615,7 +628,7 @@ bool CommandLineInterface::processInput()
|
||||
if (_error.type() == Error::Type::DocstringParsingError)
|
||||
cerr << "Documentation parsing error: " << *boost::get_error_info<errinfo_comment>(_error) << endl;
|
||||
else
|
||||
SourceReferenceFormatter::printExceptionInformation(cerr, _error, _error.typeName(), *m_compiler);
|
||||
SourceReferenceFormatter::printExceptionInformation(cerr, _error, _error.typeName(), scannerFromSourceName);
|
||||
|
||||
return false;
|
||||
}
|
||||
@@ -759,7 +772,9 @@ void CommandLineInterface::handleAst(string const& _argStr)
|
||||
|
||||
void CommandLineInterface::actOnInput()
|
||||
{
|
||||
if (m_onlyLink)
|
||||
if (m_onlyAssemble)
|
||||
return; //@TODO
|
||||
else if (m_onlyLink)
|
||||
writeLinkedFiles();
|
||||
else
|
||||
outputCompilationResults();
|
||||
@@ -812,6 +827,31 @@ void CommandLineInterface::writeLinkedFiles()
|
||||
writeFile(src.first, src.second);
|
||||
}
|
||||
|
||||
bool CommandLineInterface::assemble()
|
||||
{
|
||||
//@TODO later, we will use the convenience interface and should also remove the include above
|
||||
bool successful = true;
|
||||
ErrorList errors;
|
||||
map<string, shared_ptr<Scanner>> scanners;
|
||||
for (auto const& src: m_sourceCodes)
|
||||
{
|
||||
auto scanner = make_shared<Scanner>(CharStream(src.second), src.first);
|
||||
scanners[src.first] = scanner;
|
||||
InlineAssemblyParser parser(errors);
|
||||
if (!parser.parse(scanner))
|
||||
successful = false;
|
||||
}
|
||||
for (auto const& error: errors)
|
||||
SourceReferenceFormatter::printExceptionInformation(
|
||||
cerr,
|
||||
*error,
|
||||
(error->type() == Error::Type::Warning) ? "Warning" : "Error",
|
||||
[&](string const& _source) -> Scanner const& { return *scanners.at(_source); }
|
||||
);
|
||||
|
||||
return successful;
|
||||
}
|
||||
|
||||
void CommandLineInterface::outputCompilationResults()
|
||||
{
|
||||
handleCombinedJSON();
|
||||
|
||||
@@ -50,6 +50,9 @@ private:
|
||||
bool link();
|
||||
void writeLinkedFiles();
|
||||
|
||||
/// Parse assembly input.
|
||||
bool assemble();
|
||||
|
||||
void outputCompilationResults();
|
||||
|
||||
void handleCombinedJSON();
|
||||
@@ -73,6 +76,7 @@ private:
|
||||
/// @arg _data to be written
|
||||
void createFile(std::string const& _fileName, std::string const& _data);
|
||||
|
||||
bool m_onlyAssemble = false;
|
||||
bool m_onlyLink = false;
|
||||
|
||||
/// Compiler arguments variable map
|
||||
|
||||
+12
-6
@@ -21,6 +21,7 @@
|
||||
*/
|
||||
|
||||
#include <string>
|
||||
#include <functional>
|
||||
#include <iostream>
|
||||
#include <json/json.h>
|
||||
#include <libdevcore/Common.h>
|
||||
@@ -47,10 +48,14 @@ extern "C" {
|
||||
typedef void (*CStyleReadFileCallback)(char const* _path, char** o_contents, char** o_error);
|
||||
}
|
||||
|
||||
string formatError(Exception const& _exception, string const& _name, CompilerStack const& _compiler)
|
||||
string formatError(
|
||||
Exception const& _exception,
|
||||
string const& _name,
|
||||
function<Scanner const&(string const&)> const& _scannerFromSourceName
|
||||
)
|
||||
{
|
||||
ostringstream errorOutput;
|
||||
SourceReferenceFormatter::printExceptionInformation(errorOutput, _exception, _name, _compiler);
|
||||
SourceReferenceFormatter::printExceptionInformation(errorOutput, _exception, _name, _scannerFromSourceName);
|
||||
return errorOutput.str();
|
||||
}
|
||||
|
||||
@@ -150,6 +155,7 @@ string compile(StringMap const& _sources, bool _optimize, CStyleReadFileCallback
|
||||
};
|
||||
}
|
||||
CompilerStack compiler(true, readCallback);
|
||||
auto scannerFromSourceName = [&](string const& _sourceName) -> solidity::Scanner const& { return compiler.scanner(_sourceName); };
|
||||
bool success = false;
|
||||
try
|
||||
{
|
||||
@@ -161,22 +167,22 @@ string compile(StringMap const& _sources, bool _optimize, CStyleReadFileCallback
|
||||
errors.append(formatError(
|
||||
*error,
|
||||
(err->type() == Error::Type::Warning) ? "Warning" : "Error",
|
||||
compiler
|
||||
scannerFromSourceName
|
||||
));
|
||||
}
|
||||
success = succ; // keep success false on exception
|
||||
}
|
||||
catch (Error const& error)
|
||||
{
|
||||
errors.append(formatError(error, error.typeName(), compiler));
|
||||
errors.append(formatError(error, error.typeName(), scannerFromSourceName));
|
||||
}
|
||||
catch (CompilerError const& exception)
|
||||
{
|
||||
errors.append(formatError(exception, "Compiler error", compiler));
|
||||
errors.append(formatError(exception, "Compiler error", scannerFromSourceName));
|
||||
}
|
||||
catch (InternalCompilerError const& exception)
|
||||
{
|
||||
errors.append(formatError(exception, "Internal compiler error", compiler));
|
||||
errors.append(formatError(exception, "Internal compiler error", scannerFromSourceName));
|
||||
}
|
||||
catch (Exception const& exception)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user