diff --git a/lib/registrar.js b/lib/registrar.js index 608fe28..8187584 100644 --- a/lib/registrar.js +++ b/lib/registrar.js @@ -94,14 +94,28 @@ class Registrar { * @param {Object} expression AST node */ functionDeclaration(contract, expression) { - const startContract = contract.instrumented.slice(0, expression.range[0]); + let start = 0; + + // It's possible functions will have modifiers that take string args + // which contains an open curly brace. Skip ahead... + if (expression.modifiers && expression.modifiers.length){ + for (let modifier of expression.modifiers ){ + if (modifier.range[1] > start){ + start = modifier.range[1]; + } + } + } else { + start = expression.range[0]; + } + + const startContract = contract.instrumented.slice(0, start); const startline = ( startContract.match(/\n/g) || [] ).length + 1; - const startcol = expression.range[0] - startContract.lastIndexOf('\n') - 1; + const startcol = start - startContract.lastIndexOf('\n') - 1; - const endlineDelta = contract.instrumented.slice(expression.range[0]).indexOf('{'); + const endlineDelta = contract.instrumented.slice(start).indexOf('{'); const functionDefinition = contract.instrumented.slice( - expression.range[0], - expression.range[0] + endlineDelta + start, + start + endlineDelta ); const endline = startline + (functionDefinition.match(/\n/g) || []).length; const endcol = functionDefinition.length - functionDefinition.lastIndexOf('\n'); @@ -118,7 +132,7 @@ class Registrar { this._createInjectionPoint( contract, - expression.range[0] + endlineDelta + 1, + start + endlineDelta + 1, { type: 'injectFunction', fnId: contract.fnId, diff --git a/test/sources/solidity/contracts/statements/interpolation.sol b/test/sources/solidity/contracts/statements/interpolation.sol index c0d4a08..d922a25 100644 --- a/test/sources/solidity/contracts/statements/interpolation.sol +++ b/test/sources/solidity/contracts/statements/interpolation.sol @@ -6,8 +6,14 @@ contract Interpolated { } } -contract Test is Interpolated("abc{defg}"){ +contract TestA is Interpolated("abc{defg}"){ function a(uint x) public { uint y = x; } } + +contract TestB is Interpolated { + constructor(uint x) public Interpolated("abc{defg}") { + uint y = x; + } +} diff --git a/test/units/statements.js b/test/units/statements.js index 808ec32..69d10bf 100644 --- a/test/units/statements.js +++ b/test/units/statements.js @@ -23,7 +23,7 @@ describe('generic statements', () => { util.report(info.solcOutput.errors); }) - it('should compile a base contract contructor with a string arg containing "{"', ()=> { + it('should compile base contract contructors with string args containing "{"', ()=> { const info = util.instrumentAndCompile('statements/interpolation'); util.report(info.solcOutput.errors); })