diff --git a/Changelog.md b/Changelog.md index acad1a3fa..faab15472 100644 --- a/Changelog.md +++ b/Changelog.md @@ -17,6 +17,7 @@ Compiler Features: Bugfixes: * AST: Do not output value of Yul literal if it is not a valid UTF-8 string. * SMTChecker: Fix internal error on struct constructor with fixed bytes member initialized with string literal. + * Source Locations: Properly set source location of scoped blocks. * Standard JSON: Properly allow the ``inliner`` setting under ``settings.optimizer.details``. * Type Checker: Fix internal compiler error related to having mapping types in constructor parameter for abstract contracts. diff --git a/libsolidity/codegen/ContractCompiler.cpp b/libsolidity/codegen/ContractCompiler.cpp index e010b8efe..5afa4d26f 100644 --- a/libsolidity/codegen/ContractCompiler.cpp +++ b/libsolidity/codegen/ContractCompiler.cpp @@ -1354,6 +1354,7 @@ bool ContractCompiler::visit(PlaceholderStatement const& _placeholderStatement) bool ContractCompiler::visit(Block const& _block) { + m_context.pushVisitedNodes(&_block); if (_block.unchecked()) { solAssert(m_context.arithmetic() == Arithmetic::Checked, ""); @@ -1372,6 +1373,7 @@ void ContractCompiler::endVisit(Block const& _block) } // Frees local variables declared in the scope of this block. popScopedVariables(&_block); + m_context.popVisitedNodes(); } void ContractCompiler::appendMissingFunctions() diff --git a/test/libsolidity/StandardCompiler.cpp b/test/libsolidity/StandardCompiler.cpp index cf21ebab6..6f72026bb 100644 --- a/test/libsolidity/StandardCompiler.cpp +++ b/test/libsolidity/StandardCompiler.cpp @@ -1758,6 +1758,43 @@ BOOST_AUTO_TEST_CASE(dependency_tracking_of_abstract_contract_yul) BOOST_REQUIRE(result["sources"].size() == 1); } +BOOST_AUTO_TEST_CASE(source_location_of_bare_block) +{ + char const* input = R"( + { + "language": "Solidity", + "sources": { + "A.sol": { + "content": "contract A { constructor() { uint x = 2; { uint y = 3; } } }" + } + }, + "settings": { + "outputSelection": { + "A.sol": { + "A": ["evm.bytecode.sourceMap"] + } + } + } + } + )"; + + Json::Value parsedInput; + BOOST_REQUIRE(util::jsonParseStrict(input, parsedInput)); + + solidity::frontend::StandardCompiler compiler; + Json::Value result = compiler.compile(parsedInput); + + string sourceMap = result["contracts"]["A.sol"]["A"]["evm"]["bytecode"]["sourceMap"].asString(); + + // Check that the bare block's source location is referenced. + string sourceRef = + ";" + + to_string(string{"contract A { constructor() { uint x = 2; "}.size()) + + ":" + + to_string(string{"{ uint y = 3; }"}.size()); + BOOST_REQUIRE(sourceMap.find(sourceRef) != string::npos); +} + BOOST_AUTO_TEST_SUITE_END() } // end namespaces