From 296b3d6311186c7444d9d6763f8ee2d3c373dc14 Mon Sep 17 00:00:00 2001 From: Remco Bloemen Date: Thu, 20 Dec 2018 15:27:12 -0800 Subject: Throw error when source location is missing --- packages/sol-tracing-utils/src/source_maps.ts | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/source_maps.ts b/packages/sol-tracing-utils/src/source_maps.ts index af0fb4035..ceb20d843 100644 --- a/packages/sol-tracing-utils/src/source_maps.ts +++ b/packages/sol-tracing-utils/src/source_maps.ts @@ -67,13 +67,17 @@ export function parseSourceMap( fileIndex, }; if (parsedEntry.fileIndex !== -1 && !_.isUndefined(locationByOffsetByFileIndex[parsedEntry.fileIndex])) { + const locationByOffset = locationByOffsetByFileIndex[parsedEntry.fileIndex]; const sourceRange = { location: { - start: locationByOffsetByFileIndex[parsedEntry.fileIndex][parsedEntry.offset], - end: locationByOffsetByFileIndex[parsedEntry.fileIndex][parsedEntry.offset + parsedEntry.length], + start: locationByOffset[parsedEntry.offset], + end: locationByOffset[parsedEntry.offset + parsedEntry.length], }, fileName: sources[parsedEntry.fileIndex], }; + if (sourceRange.location.start === undefined || sourceRange.location.end === undefined) { + throw new Error(`Error while processing sourcemap: location out of range in ${sourceRange.fileName}`); + } instructionIndexToSourceRange[i] = sourceRange; } else { // Some assembly code generated by Solidity can't be mapped back to a line of source code. -- cgit v1.2.3 From 7af0818dffe67483491f99062071b582fba456cb Mon Sep 17 00:00:00 2001 From: Remco Bloemen Date: Thu, 20 Dec 2018 15:31:13 -0800 Subject: Capture errors in next callbacks --- .../src/trace_collection_subprovider.ts | 24 +++++++++++++++++++--- 1 file changed, 21 insertions(+), 3 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index 25e38768d..8b4ea82f5 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -20,6 +20,24 @@ export interface TraceCollectionSubproviderConfig { shouldCollectGasEstimateTraces: boolean; } +type AsyncFunc = (...args: any[]) => Promise; + +// This wrapper outputs errors to console even if the promise gets ignored +// we need this because web3-provider-engine does not handler promises in +// the after function of next(after). +function logErrors(fn: AsyncFunc): AsyncFunc { + async function wrapped(...args: any[]): Promise { + try { + await fn(...args); + } catch (e) { + // tslint:disable-next-line no-console + console.error(e); + throw e; + } + } + return wrapped; +} + // Because there is no notion of a call trace in the Ethereum rpc - we collect them in a rather non-obvious/hacky way. // On each call - we create a snapshot, execute the call as a transaction, get the trace, revert the snapshot. // That allows us to avoid influencing test behaviour. @@ -74,7 +92,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const txData = payload.params[0]; - next(this._onTransactionSentAsync.bind(this, txData)); + next(logErrors(this._onTransactionSentAsync.bind(this, txData))); } return; @@ -83,7 +101,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const callData = payload.params[0]; - next(this._onCallOrGasEstimateExecutedAsync.bind(this, callData)); + next(logErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, callData))); } return; @@ -92,7 +110,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const estimateGasData = payload.params[0]; - next(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData)); + next(logErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData))); } return; -- cgit v1.2.3 From e1b99b5e2f0098d97a0d73d60889f0ef7d14b6f7 Mon Sep 17 00:00:00 2001 From: Remco Bloemen Date: Thu, 20 Dec 2018 15:31:25 -0800 Subject: Use tracer for debug traces --- .../src/trace_info_subprovider.ts | 26 +++++++++++++++++----- 1 file changed, 21 insertions(+), 5 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_info_subprovider.ts b/packages/sol-tracing-utils/src/trace_info_subprovider.ts index 635a68f58..8713ccb5e 100644 --- a/packages/sol-tracing-utils/src/trace_info_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_info_subprovider.ts @@ -1,3 +1,4 @@ +import { StructLog } from 'ethereum-types'; import * as _ from 'lodash'; import { constants } from './constants'; @@ -12,11 +13,26 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { protected abstract _handleTraceInfoAsync(traceInfo: TraceInfo): Promise; protected async _recordTxTraceAsync(address: string, data: string | undefined, txHash: string): Promise { await this._web3Wrapper.awaitTransactionMinedAsync(txHash, 0); - const trace = await this._web3Wrapper.getTransactionTraceAsync(txHash, { - disableMemory: true, - disableStack: false, - disableStorage: true, - }); + // For very large traces we use a custom tracer that outputs a format compatible with a + // regular trace. We only need the 2nd item on the stack when the instruction is a call. + // By not including othe stack values, we severly limit the amount of data to be collectd. + const tracer = + '{' + + ' data: [],' + + ' step: function(log) {' + + ' const op = log.op.toString();' + + ' const opn = 0 | log.op.toNumber();' + + ' const pc = 0 | log.getPC();' + + ' const depth = 0 | log.getDepth();' + + ' const gas = 0 | log.getGas();' + + ' const isCall = opn == 0xf1 || opn == 0xf2 || opn == 0xf4 || opn == 0xf5;' + + " const stack = isCall ? ['0x'+log.stack.peek(1).toString(16), null] : null;" + + ' this.data.push({ pc, gas, depth, op, stack}); ' + + ' },' + + ' fault: function() { },' + + ' result: function() { return {structLogs: this.data}; }' + + '}'; + const trace = await this._web3Wrapper.getTransactionTraceAsync(txHash, { tracer, timeout: '600s' }); const tracesByContractAddress = getTracesByContractAddress(trace.structLogs, address); const subcallAddresses = _.keys(tracesByContractAddress); if (address === constants.NEW_CONTRACT) { -- cgit v1.2.3 From 89429c54a7424eb6aa233047fa83fe595faa44d5 Mon Sep 17 00:00:00 2001 From: Fabio Berger Date: Fri, 11 Jan 2019 18:04:33 +0100 Subject: Updated CHANGELOGS --- packages/sol-tracing-utils/CHANGELOG.json | 3 ++- packages/sol-tracing-utils/CHANGELOG.md | 4 ++++ 2 files changed, 6 insertions(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/CHANGELOG.json b/packages/sol-tracing-utils/CHANGELOG.json index 9c0b73169..1b11011d3 100644 --- a/packages/sol-tracing-utils/CHANGELOG.json +++ b/packages/sol-tracing-utils/CHANGELOG.json @@ -6,7 +6,8 @@ "note": "Move out specific tools and leave just the shared parts of the codebase", "pr": 1492 } - ] + ], + "timestamp": 1547225310 }, { "timestamp": 1547040760, diff --git a/packages/sol-tracing-utils/CHANGELOG.md b/packages/sol-tracing-utils/CHANGELOG.md index c2bc3cd01..da998f905 100644 --- a/packages/sol-tracing-utils/CHANGELOG.md +++ b/packages/sol-tracing-utils/CHANGELOG.md @@ -5,6 +5,10 @@ Edit the package's CHANGELOG.json file only. CHANGELOG +## v3.0.0 - _January 11, 2019_ + + * Move out specific tools and leave just the shared parts of the codebase (#1492) + ## v2.1.17 - _January 9, 2019_ * Dependencies updated -- cgit v1.2.3 From cf3787edbb9e8acf7160ab93b903b54c63bdffda Mon Sep 17 00:00:00 2001 From: Fabio Berger Date: Fri, 11 Jan 2019 18:04:43 +0100 Subject: Publish - 0x.js@3.0.1 - @0x/abi-gen@1.0.21 - @0x/abi-gen-wrappers@2.1.1 - @0x/assert@1.0.22 - @0x/asset-buyer@4.0.0 - @0x/base-contract@3.0.12 - @0x/connect@3.0.12 - @0x/contract-wrappers@4.2.1 - @0x/dev-tools-pages@0.0.12 - @0x/dev-utils@1.0.23 - ethereum-types@1.1.5 - @0x/fill-scenarios@1.1.1 - @0x/instant@1.0.6 - @0x/json-schemas@2.1.6 - @0x/metacoin@0.0.34 - @0x/migrations@2.3.1 - @0x/monorepo-scripts@1.0.17 - @0x/order-utils@3.1.1 - @0x/order-watcher@2.4.1 - @0x/pipeline@1.0.4 - @0x/react-docs@1.0.24 - @0x/react-shared@1.1.1 - @0x/sol-compiler@2.0.1 - @0x/sol-coverage@1.0.1 - @0x/sol-doc@1.0.13 - @0x/sol-profiler@1.0.1 - @0x/sol-resolver@1.2.2 - @0x/sol-trace@1.0.1 - @0x/sol-tracing-utils@3.0.0 - @0x/sra-spec@1.0.15 - @0x/subproviders@2.1.10 - @0x/testnet-faucets@1.0.62 - @0x/tslint-config@2.0.1 - @0x/types@1.5.1 - @0x/typescript-typings@3.0.7 - @0x/utils@3.0.0 - @0x/web3-wrapper@3.2.3 - @0x/website@0.0.65 - @0x/contracts-examples@1.0.4 - @0x/contracts-extensions@1.2.1 - @0x/contracts-interfaces@1.0.4 - @0x/contracts-libs@1.0.4 - @0x/contracts-multisig@1.0.4 - @0x/contracts-protocol@2.2.1 - @0x/contracts-test-utils@1.0.4 - @0x/contracts-tokens@1.0.4 - @0x/contracts-utils@1.0.4 --- packages/sol-tracing-utils/package.json | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/package.json b/packages/sol-tracing-utils/package.json index 9486ab541..5021342fa 100644 --- a/packages/sol-tracing-utils/package.json +++ b/packages/sol-tracing-utils/package.json @@ -1,6 +1,6 @@ { "name": "@0x/sol-tracing-utils", - "version": "2.1.17", + "version": "3.0.0", "engines": { "node": ">=6.12" }, @@ -42,14 +42,14 @@ }, "homepage": "https://github.com/0xProject/0x-monorepo/packages/sol-tracing-utils/README.md", "dependencies": { - "@0x/dev-utils": "^1.0.22", - "@0x/sol-compiler": "^2.0.0", - "@0x/subproviders": "^2.1.9", - "@0x/typescript-typings": "^3.0.6", - "@0x/utils": "^2.1.1", - "@0x/web3-wrapper": "^3.2.2", + "@0x/dev-utils": "^1.0.23", + "@0x/sol-compiler": "^2.0.1", + "@0x/subproviders": "^2.1.10", + "@0x/typescript-typings": "^3.0.7", + "@0x/utils": "^3.0.0", + "@0x/web3-wrapper": "^3.2.3", "@types/solidity-parser-antlr": "^0.2.0", - "ethereum-types": "^1.1.4", + "ethereum-types": "^1.1.5", "ethereumjs-util": "^5.1.1", "glob": "^7.1.2", "istanbul": "^0.4.5", @@ -61,7 +61,7 @@ "solidity-parser-antlr": "^0.2.12" }, "devDependencies": { - "@0x/tslint-config": "^2.0.0", + "@0x/tslint-config": "^2.0.1", "@types/istanbul": "^0.4.30", "@types/loglevel": "^1.5.3", "@types/mkdirp": "^0.5.1", -- cgit v1.2.3 From ab5cd8f9387e601677de697c7573c6c13383e932 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 11:38:36 +0100 Subject: Use a custom JS tracer --- .../src/trace_info_subprovider.ts | 35 +++++++++++----------- 1 file changed, 18 insertions(+), 17 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_info_subprovider.ts b/packages/sol-tracing-utils/src/trace_info_subprovider.ts index 8713ccb5e..43853e152 100644 --- a/packages/sol-tracing-utils/src/trace_info_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_info_subprovider.ts @@ -1,4 +1,3 @@ -import { StructLog } from 'ethereum-types'; import * as _ from 'lodash'; import { constants } from './constants'; @@ -16,22 +15,24 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { // For very large traces we use a custom tracer that outputs a format compatible with a // regular trace. We only need the 2nd item on the stack when the instruction is a call. // By not including othe stack values, we severly limit the amount of data to be collectd. - const tracer = - '{' + - ' data: [],' + - ' step: function(log) {' + - ' const op = log.op.toString();' + - ' const opn = 0 | log.op.toNumber();' + - ' const pc = 0 | log.getPC();' + - ' const depth = 0 | log.getDepth();' + - ' const gas = 0 | log.getGas();' + - ' const isCall = opn == 0xf1 || opn == 0xf2 || opn == 0xf4 || opn == 0xf5;' + - " const stack = isCall ? ['0x'+log.stack.peek(1).toString(16), null] : null;" + - ' this.data.push({ pc, gas, depth, op, stack}); ' + - ' },' + - ' fault: function() { },' + - ' result: function() { return {structLogs: this.data}; }' + - '}'; + const tracer = ` + { + data: [], + step: function(log) { + const op = log.op.toString(); + const opn = 0 | log.op.toNumber(); + const pc = 0 | log.getPC(); + const depth = 0 | log.getDepth(); + const gasCost = 0 | log.getCost(); + const gas = 0 | log.getGas(); + const isCall = opn == 0xf1 || opn == 0xf2 || opn == 0xf4 || opn == 0xf5; + const stack = isCall ? ['0x'+log.stack.peek(1).toString(16), null] : null; + this.data.push({ pc, gasCost, depth, op, stack, gas }); + }, + fault: function() { }, + result: function() { return {structLogs: this.data}; } + } + `; const trace = await this._web3Wrapper.getTransactionTraceAsync(txHash, { tracer, timeout: '600s' }); const tracesByContractAddress = getTracesByContractAddress(trace.structLogs, address); const subcallAddresses = _.keys(tracesByContractAddress); -- cgit v1.2.3 From 2345a3bdfe5be9ea2d13ed98b889e01286ddaab2 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 11:40:05 +0100 Subject: Add assembly statements to AST Visitor --- packages/sol-tracing-utils/src/ast_visitor.ts | 33 +++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/ast_visitor.ts b/packages/sol-tracing-utils/src/ast_visitor.ts index e55cdf6ec..fe71c974b 100644 --- a/packages/sol-tracing-utils/src/ast_visitor.ts +++ b/packages/sol-tracing-utils/src/ast_visitor.ts @@ -94,6 +94,39 @@ export class ASTVisitor { public InlineAssemblyStatement(ast: Parser.InlineAssemblyStatement): void { this._visitStatement(ast); } + public AssemblyLocalDefinition(ast: Parser.AssemblyLocalDefinition): void { + this._visitStatement(ast); + } + public AssemblyCall(ast: Parser.AssemblyCall): void { + this._visitStatement(ast); + } + public AssemblyIf(ast: Parser.AssemblyIf): void { + this._visitStatement(ast); + } + public AssemblyBlock(ast: Parser.AssemblyBlock): void { + this._visitStatement(ast); + } + public AssemblyExpression(ast: Parser.AssemblyExpression): void { + this._visitStatement(ast); + } + public AssemblyAssignment(ast: Parser.AssemblyAssignment): void { + this._visitStatement(ast); + } + public LabelDefinition(ast: Parser.LabelDefinition): void { + this._visitStatement(ast); + } + public AssemblySwitch(ast: Parser.AssemblySwitch): void { + this._visitStatement(ast); + } + public AssemblyFunctionDefinition(ast: Parser.AssemblyFunctionDefinition): void { + this._visitStatement(ast); + } + public AssemblyFor(ast: Parser.AssemblyFor): void { + this._visitStatement(ast); + } + public SubAssembly(ast: Parser.SubAssembly): void { + this._visitStatement(ast); + } public BinaryOperation(ast: Parser.BinaryOperation): void { const BRANCHING_BIN_OPS = ['&&', '||']; if (_.includes(BRANCHING_BIN_OPS, ast.operator)) { -- cgit v1.2.3 From 8b62783f4876594ad350175b12a85321e9d1a3fc Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 11:50:05 +0100 Subject: Add utils.isRangeEqual to sol-profiler --- packages/sol-tracing-utils/src/utils.ts | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/utils.ts b/packages/sol-tracing-utils/src/utils.ts index d8bc65e73..644321f32 100644 --- a/packages/sol-tracing-utils/src/utils.ts +++ b/packages/sol-tracing-utils/src/utils.ts @@ -23,6 +23,12 @@ export const utils = { utils.compareLineColumn(childRange.end, parentRange.end) <= 0 ); }, + isRangeEqual(childRange: SingleFileSourceRange, parentRange: SingleFileSourceRange): boolean { + return ( + utils.compareLineColumn(parentRange.start, childRange.start) === 0 && + utils.compareLineColumn(childRange.end, parentRange.end) === 0 + ); + }, bytecodeToBytecodeRegex(bytecode: string): string { const bytecodeRegex = bytecode // Library linking placeholder: __ConvertLib____________________________ -- cgit v1.2.3 From 2581bc93e5893d43642b240d290c141f0d9419bf Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 12:02:32 +0100 Subject: Fix the bug with incorrect source maps parsing by changing contract data from an array to a mapping --- .../src/artifact_adapters/sol_compiler_artifact_adapter.ts | 11 ++++++++--- packages/sol-tracing-utils/src/source_maps.ts | 13 ++++++++----- packages/sol-tracing-utils/src/trace_collector.ts | 8 ++++---- packages/sol-tracing-utils/src/types.ts | 4 ++-- 4 files changed, 22 insertions(+), 14 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts b/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts index 57391abbe..7d85f6c68 100644 --- a/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts +++ b/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts @@ -43,9 +43,14 @@ export class SolCompilerArtifactAdapter extends AbstractArtifactAdapter { logUtils.warn(`${artifactFileName} doesn't contain bytecode. Skipping...`); continue; } - let sources = _.keys(artifact.sources); - sources = _.map(sources, relativeFilePath => path.resolve(this._sourcesPath, relativeFilePath)); - const sourceCodes = _.map(sources, (source: string) => fs.readFileSync(source).toString()); + const sources: { [sourceId: number]: string } = {}; + const sourceCodes: { [sourceId: number]: string } = {}; + _.map(artifact.sources, (value: { id: number }, relativeFilePath: string) => { + const filePath = path.resolve(this._sourcesPath, relativeFilePath); + const fileContent = fs.readFileSync(filePath).toString(); + sources[value.id] = filePath; + sourceCodes[value.id] = fileContent; + }); const contractData = { sourceCodes, sources, diff --git a/packages/sol-tracing-utils/src/source_maps.ts b/packages/sol-tracing-utils/src/source_maps.ts index ceb20d843..c674d32a3 100644 --- a/packages/sol-tracing-utils/src/source_maps.ts +++ b/packages/sol-tracing-utils/src/source_maps.ts @@ -33,20 +33,23 @@ export function getLocationByOffset(str: string): LocationByOffset { /** * Parses a sourcemap string. * The solidity sourcemap format is documented here: https://github.com/ethereum/solidity/blob/develop/docs/miscellaneous.rst#source-mappings - * @param sourceCodes sources contents + * @param sourceCodes sources contents by index * @param srcMap source map string * @param bytecodeHex contract bytecode - * @param sources sources file names + * @param sources sources file names by index */ export function parseSourceMap( - sourceCodes: string[], + sourceCodes: { [fileIndex: number]: string }, srcMap: string, bytecodeHex: string, - sources: string[], + sources: { [fileIndex: number]: string }, ): { [programCounter: number]: SourceRange } { const bytecode = Uint8Array.from(Buffer.from(bytecodeHex, 'hex')); const pcToInstructionIndex: { [programCounter: number]: number } = getPcToInstructionIndexMapping(bytecode); - const locationByOffsetByFileIndex = _.map(sourceCodes, s => (_.isUndefined(s) ? {} : getLocationByOffset(s))); + const locationByOffsetByFileIndex: { [fileIndex: number]: LocationByOffset } = {}; + _.map(sourceCodes, (sourceCode: string, fileIndex: number) => { + locationByOffsetByFileIndex[fileIndex] = _.isUndefined(sourceCode) ? {} : getLocationByOffset(sourceCode); + }); const entries = srcMap.split(';'); let lastParsedEntry: SourceLocation = {} as any; const instructionIndexToSourceRange: { [instructionIndex: number]: SourceRange } = {}; diff --git a/packages/sol-tracing-utils/src/trace_collector.ts b/packages/sol-tracing-utils/src/trace_collector.ts index 943e208cf..f5dde8762 100644 --- a/packages/sol-tracing-utils/src/trace_collector.ts +++ b/packages/sol-tracing-utils/src/trace_collector.ts @@ -56,7 +56,7 @@ export class TraceCollector { this._singleFileSubtraceHandler = singleFileSubtraceHandler; } public async writeOutputAsync(): Promise { - const finalCoverage = this._collector.getFinalCoverage(); + const finalCoverage: Coverage = this._collector.getFinalCoverage(); const stringifiedCoverage = JSON.stringify(finalCoverage, null, '\t'); await mkdirpAsync('coverage'); fs.writeFileSync('coverage/coverage.json', stringifiedCoverage); @@ -80,14 +80,14 @@ export class TraceCollector { const bytecodeHex = stripHexPrefix(bytecode); const sourceMap = isContractCreation ? contractData.sourceMap : contractData.sourceMapRuntime; const pcToSourceRange = parseSourceMap(contractData.sourceCodes, sourceMap, bytecodeHex, contractData.sources); - for (let fileIndex = 0; fileIndex < contractData.sources.length; fileIndex++) { + _.map(contractData.sources, (_sourcePath: string, fileIndex: string) => { const singleFileCoverageForTrace = this._singleFileSubtraceHandler( contractData, traceInfo.subtrace, pcToSourceRange, - fileIndex, + _.parseInt(fileIndex), ); this._collector.add(singleFileCoverageForTrace); - } + }); } } diff --git a/packages/sol-tracing-utils/src/types.ts b/packages/sol-tracing-utils/src/types.ts index 54ade0400..fa10a93d6 100644 --- a/packages/sol-tracing-utils/src/types.ts +++ b/packages/sol-tracing-utils/src/types.ts @@ -81,8 +81,8 @@ export interface ContractData { sourceMap: string; runtimeBytecode: string; sourceMapRuntime: string; - sourceCodes: string[]; - sources: string[]; + sourceCodes: { [sourceId: number]: string }; + sources: { [sourceId: number]: string }; } // Part of the trace executed within the same context -- cgit v1.2.3 From 2b8f0d887ad529bb0557a55c67cc162977c7b270 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 12:16:00 +0100 Subject: Fix linter --- packages/sol-tracing-utils/src/trace_collection_subprovider.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index 8b4ea82f5..3ae8566f9 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -26,7 +26,7 @@ type AsyncFunc = (...args: any[]) => Promise; // we need this because web3-provider-engine does not handler promises in // the after function of next(after). function logErrors(fn: AsyncFunc): AsyncFunc { - async function wrapped(...args: any[]): Promise { + async function wrappedAsync(...args: any[]): Promise { try { await fn(...args); } catch (e) { @@ -35,7 +35,7 @@ function logErrors(fn: AsyncFunc): AsyncFunc { throw e; } } - return wrapped; + return wrappedAsync; } // Because there is no notion of a call trace in the Ethereum rpc - we collect them in a rather non-obvious/hacky way. -- cgit v1.2.3 From bd71f4a4807cf1221444362ce983c44f0531f494 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 12:46:37 +0100 Subject: Add CHANGELOG entries --- packages/sol-tracing-utils/CHANGELOG.json | 44 ++++++++++++++++++++++++++----- 1 file changed, 38 insertions(+), 6 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/CHANGELOG.json b/packages/sol-tracing-utils/CHANGELOG.json index 1b11011d3..7ca8bfced 100644 --- a/packages/sol-tracing-utils/CHANGELOG.json +++ b/packages/sol-tracing-utils/CHANGELOG.json @@ -1,4 +1,30 @@ [ + { + "version": "4.0.0", + "changes": [ + { + "note": "Fix the bug with incorrect parsing of `sourceMaps`", + "pr": 1498 + }, + { + "note": + "Change the types of `ContractData.sources` and `ContractData.sourceCodes` to be objects instead of arrays", + "pr": 1498 + }, + { + "note": "Use custom JS tracer to speed up tracing on clients that support it (Geth)", + "pr": 1498 + }, + { + "note": "Log the errors in `TraceCollectionSubprovider`", + "pr": 1498 + }, + { + "note": "Add support for assembly statements", + "pr": 1498 + } + ] + }, { "version": "3.0.0", "changes": [ @@ -167,7 +193,8 @@ "version": "2.1.0", "changes": [ { - "note": "Export types: `JSONRPCRequestPayload`, `Provider`, `JSONRPCErrorCallback`, `JSONRPCResponsePayload`, `JSONRPCRequestPayloadWithMethod`, `NextCallback`, `ErrorCallback`, `OnNextCompleted` and `Callback`", + "note": + "Export types: `JSONRPCRequestPayload`, `Provider`, `JSONRPCErrorCallback`, `JSONRPCResponsePayload`, `JSONRPCRequestPayloadWithMethod`, `NextCallback`, `ErrorCallback`, `OnNextCompleted` and `Callback`", "pr": 924 } ], @@ -177,7 +204,8 @@ "version": "2.0.0", "changes": [ { - "note": "Fix a bug when eth_call coverage was not computed because of silent schema validation failures", + "note": + "Fix a bug when eth_call coverage was not computed because of silent schema validation failures", "pr": 938 }, { @@ -185,11 +213,13 @@ "pr": 938 }, { - "note": "Change the first param of `TruffleArtifactAdapter` to be the `projectRoot` instead of `sourcesDir`", + "note": + "Change the first param of `TruffleArtifactAdapter` to be the `projectRoot` instead of `sourcesDir`", "pr": 938 }, { - "note": "Throw a helpful error message if truffle artifacts were generated with a different solc version than the one passed in", + "note": + "Throw a helpful error message if truffle artifacts were generated with a different solc version than the one passed in", "pr": 938 } ], @@ -227,7 +257,8 @@ "version": "1.0.0", "changes": [ { - "note": "Add artifact adapter as a parameter for `CoverageSubprovider`. Export `AbstractArtifactAdapter`", + "note": + "Add artifact adapter as a parameter for `CoverageSubprovider`. Export `AbstractArtifactAdapter`", "pr": 589 }, { @@ -283,7 +314,8 @@ "pr": 690 }, { - "note": "Fix a bug when in `TruffleArtifactsAdapter` causing it to throw if `compiler.json` is not there", + "note": + "Fix a bug when in `TruffleArtifactsAdapter` causing it to throw if `compiler.json` is not there", "pr": 690 }, { -- cgit v1.2.3 From 092a851bb3c54a6bc37c9b2456e890c75e8f6739 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 12:53:14 +0100 Subject: Use custom JS tracer only if the node is geth --- .../src/trace_info_subprovider.ts | 58 ++++++++++++++-------- 1 file changed, 36 insertions(+), 22 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_info_subprovider.ts b/packages/sol-tracing-utils/src/trace_info_subprovider.ts index 43853e152..698867056 100644 --- a/packages/sol-tracing-utils/src/trace_info_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_info_subprovider.ts @@ -1,3 +1,4 @@ +import { NodeType } from '@0x/web3-wrapper'; import * as _ from 'lodash'; import { constants } from './constants'; @@ -12,28 +13,41 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { protected abstract _handleTraceInfoAsync(traceInfo: TraceInfo): Promise; protected async _recordTxTraceAsync(address: string, data: string | undefined, txHash: string): Promise { await this._web3Wrapper.awaitTransactionMinedAsync(txHash, 0); - // For very large traces we use a custom tracer that outputs a format compatible with a - // regular trace. We only need the 2nd item on the stack when the instruction is a call. - // By not including othe stack values, we severly limit the amount of data to be collectd. - const tracer = ` - { - data: [], - step: function(log) { - const op = log.op.toString(); - const opn = 0 | log.op.toNumber(); - const pc = 0 | log.getPC(); - const depth = 0 | log.getDepth(); - const gasCost = 0 | log.getCost(); - const gas = 0 | log.getGas(); - const isCall = opn == 0xf1 || opn == 0xf2 || opn == 0xf4 || opn == 0xf5; - const stack = isCall ? ['0x'+log.stack.peek(1).toString(16), null] : null; - this.data.push({ pc, gasCost, depth, op, stack, gas }); - }, - fault: function() { }, - result: function() { return {structLogs: this.data}; } - } - `; - const trace = await this._web3Wrapper.getTransactionTraceAsync(txHash, { tracer, timeout: '600s' }); + const nodeType = await this._web3Wrapper.getNodeTypeAsync(); + let trace; + if (nodeType === NodeType.Geth) { + // For very large traces we use a custom tracer that outputs a format compatible with a + // regular trace. We only need the 2nd item on the stack when the instruction is a call. + // By not including othe stack values, we severly limit the amount of data to be collectd. + const tracer = ` + { + data: [], + step: function(log) { + const op = log.op.toString(); + const opn = 0 | log.op.toNumber(); + const pc = 0 | log.getPC(); + const depth = 0 | log.getDepth(); + const gasCost = 0 | log.getCost(); + const gas = 0 | log.getGas(); + const isCall = opn == 0xf1 || opn == 0xf2 || opn == 0xf4 || opn == 0xf5; + const stack = isCall ? ['0x'+log.stack.peek(1).toString(16), null] : null; + this.data.push({ pc, gasCost, depth, op, stack, gas }); + }, + fault: function() { }, + result: function() { return {structLogs: this.data}; } + } + `; + trace = await this._web3Wrapper.getTransactionTraceAsync(txHash, { tracer, timeout: '600s' }); + } else { + /** + * Ganache doesn't support custom tracers yet. + */ + trace = await this._web3Wrapper.getTransactionTraceAsync(txHash, { + disableMemory: true, + disableStack: false, + disableStorage: true, + }); + } const tracesByContractAddress = getTracesByContractAddress(trace.structLogs, address); const subcallAddresses = _.keys(tracesByContractAddress); if (address === constants.NEW_CONTRACT) { -- cgit v1.2.3 From 4b9648c7c9f5e39c8220013f6001315ee9840a8a Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 13:13:45 +0100 Subject: Apply prettier --- packages/sol-tracing-utils/CHANGELOG.json | 21 +++++++-------------- 1 file changed, 7 insertions(+), 14 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/CHANGELOG.json b/packages/sol-tracing-utils/CHANGELOG.json index 7ca8bfced..2c7f102c1 100644 --- a/packages/sol-tracing-utils/CHANGELOG.json +++ b/packages/sol-tracing-utils/CHANGELOG.json @@ -7,8 +7,7 @@ "pr": 1498 }, { - "note": - "Change the types of `ContractData.sources` and `ContractData.sourceCodes` to be objects instead of arrays", + "note": "Change the types of `ContractData.sources` and `ContractData.sourceCodes` to be objects instead of arrays", "pr": 1498 }, { @@ -193,8 +192,7 @@ "version": "2.1.0", "changes": [ { - "note": - "Export types: `JSONRPCRequestPayload`, `Provider`, `JSONRPCErrorCallback`, `JSONRPCResponsePayload`, `JSONRPCRequestPayloadWithMethod`, `NextCallback`, `ErrorCallback`, `OnNextCompleted` and `Callback`", + "note": "Export types: `JSONRPCRequestPayload`, `Provider`, `JSONRPCErrorCallback`, `JSONRPCResponsePayload`, `JSONRPCRequestPayloadWithMethod`, `NextCallback`, `ErrorCallback`, `OnNextCompleted` and `Callback`", "pr": 924 } ], @@ -204,8 +202,7 @@ "version": "2.0.0", "changes": [ { - "note": - "Fix a bug when eth_call coverage was not computed because of silent schema validation failures", + "note": "Fix a bug when eth_call coverage was not computed because of silent schema validation failures", "pr": 938 }, { @@ -213,13 +210,11 @@ "pr": 938 }, { - "note": - "Change the first param of `TruffleArtifactAdapter` to be the `projectRoot` instead of `sourcesDir`", + "note": "Change the first param of `TruffleArtifactAdapter` to be the `projectRoot` instead of `sourcesDir`", "pr": 938 }, { - "note": - "Throw a helpful error message if truffle artifacts were generated with a different solc version than the one passed in", + "note": "Throw a helpful error message if truffle artifacts were generated with a different solc version than the one passed in", "pr": 938 } ], @@ -257,8 +252,7 @@ "version": "1.0.0", "changes": [ { - "note": - "Add artifact adapter as a parameter for `CoverageSubprovider`. Export `AbstractArtifactAdapter`", + "note": "Add artifact adapter as a parameter for `CoverageSubprovider`. Export `AbstractArtifactAdapter`", "pr": 589 }, { @@ -314,8 +308,7 @@ "pr": 690 }, { - "note": - "Fix a bug when in `TruffleArtifactsAdapter` causing it to throw if `compiler.json` is not there", + "note": "Fix a bug when in `TruffleArtifactsAdapter` causing it to throw if `compiler.json` is not there", "pr": 690 }, { -- cgit v1.2.3 From 45d70dd30b215120b122b77252d243d8f6120eea Mon Sep 17 00:00:00 2001 From: Fabio B Date: Mon, 14 Jan 2019 13:50:45 +0100 Subject: Update packages/sol-tracing-utils/CHANGELOG.json Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/CHANGELOG.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/CHANGELOG.json b/packages/sol-tracing-utils/CHANGELOG.json index 2c7f102c1..3630ea9b5 100644 --- a/packages/sol-tracing-utils/CHANGELOG.json +++ b/packages/sol-tracing-utils/CHANGELOG.json @@ -3,7 +3,7 @@ "version": "4.0.0", "changes": [ { - "note": "Fix the bug with incorrect parsing of `sourceMaps`", + "note": "Fix a bug with incorrect parsing of `sourceMaps` due to sources being in an array instead of a map", "pr": 1498 }, { -- cgit v1.2.3 From b41bcd80eff30d5144627a60bfe0a8ed7c09f48a Mon Sep 17 00:00:00 2001 From: Fabio B Date: Mon, 14 Jan 2019 13:50:53 +0100 Subject: Update packages/sol-tracing-utils/CHANGELOG.json Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/CHANGELOG.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/CHANGELOG.json b/packages/sol-tracing-utils/CHANGELOG.json index 3630ea9b5..077facf40 100644 --- a/packages/sol-tracing-utils/CHANGELOG.json +++ b/packages/sol-tracing-utils/CHANGELOG.json @@ -15,7 +15,7 @@ "pr": 1498 }, { - "note": "Log the errors in `TraceCollectionSubprovider`", + "note": "Log errors encountered in `TraceCollectionSubprovider`", "pr": 1498 }, { -- cgit v1.2.3 From 1c279f97ce9fc0025c554fd7bb58f3941a9fc77c Mon Sep 17 00:00:00 2001 From: Fabio B Date: Mon, 14 Jan 2019 13:51:01 +0100 Subject: Update packages/sol-tracing-utils/src/source_maps.ts Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/src/source_maps.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/source_maps.ts b/packages/sol-tracing-utils/src/source_maps.ts index c674d32a3..9f7f6547f 100644 --- a/packages/sol-tracing-utils/src/source_maps.ts +++ b/packages/sol-tracing-utils/src/source_maps.ts @@ -36,7 +36,7 @@ export function getLocationByOffset(str: string): LocationByOffset { * @param sourceCodes sources contents by index * @param srcMap source map string * @param bytecodeHex contract bytecode - * @param sources sources file names by index + * @param indexToSource index to source file path */ export function parseSourceMap( sourceCodes: { [fileIndex: number]: string }, -- cgit v1.2.3 From ed3b89f0054677025e42483df720d59abce133b4 Mon Sep 17 00:00:00 2001 From: Fabio B Date: Mon, 14 Jan 2019 13:51:10 +0100 Subject: Update packages/sol-tracing-utils/src/trace_collection_subprovider.ts Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/src/trace_collection_subprovider.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index 3ae8566f9..e3f5561aa 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -23,7 +23,7 @@ export interface TraceCollectionSubproviderConfig { type AsyncFunc = (...args: any[]) => Promise; // This wrapper outputs errors to console even if the promise gets ignored -// we need this because web3-provider-engine does not handler promises in +// we need this because web3-provider-engine does not handle promises in // the after function of next(after). function logErrors(fn: AsyncFunc): AsyncFunc { async function wrappedAsync(...args: any[]): Promise { -- cgit v1.2.3 From caba2faa927f8b130d6a21de2f0e892d24370ffc Mon Sep 17 00:00:00 2001 From: Fabio B Date: Mon, 14 Jan 2019 13:52:26 +0100 Subject: Update packages/sol-tracing-utils/src/trace_info_subprovider.ts Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/src/trace_info_subprovider.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_info_subprovider.ts b/packages/sol-tracing-utils/src/trace_info_subprovider.ts index 698867056..dc42ce25e 100644 --- a/packages/sol-tracing-utils/src/trace_info_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_info_subprovider.ts @@ -18,7 +18,7 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { if (nodeType === NodeType.Geth) { // For very large traces we use a custom tracer that outputs a format compatible with a // regular trace. We only need the 2nd item on the stack when the instruction is a call. - // By not including othe stack values, we severly limit the amount of data to be collectd. + // By not including other stack values, we drastically limit the amount of data to be collected. const tracer = ` { data: [], -- cgit v1.2.3 From e14f1646d6ff0a3389f4087da642b3c121228f20 Mon Sep 17 00:00:00 2001 From: Fabio B Date: Mon, 14 Jan 2019 13:54:50 +0100 Subject: Update packages/sol-tracing-utils/CHANGELOG.json Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/CHANGELOG.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/CHANGELOG.json b/packages/sol-tracing-utils/CHANGELOG.json index 077facf40..5992016b1 100644 --- a/packages/sol-tracing-utils/CHANGELOG.json +++ b/packages/sol-tracing-utils/CHANGELOG.json @@ -11,7 +11,7 @@ "pr": 1498 }, { - "note": "Use custom JS tracer to speed up tracing on clients that support it (Geth)", + "note": "Use custom JS tracer to speed up tracing on clients that support it (e.g., Geth)", "pr": 1498 }, { -- cgit v1.2.3 From 1f7179b1788d3e05163e8e5244a31470b01f8ca7 Mon Sep 17 00:00:00 2001 From: Fabio B Date: Mon, 14 Jan 2019 14:29:01 +0100 Subject: Update packages/sol-tracing-utils/src/source_maps.ts Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/src/source_maps.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/source_maps.ts b/packages/sol-tracing-utils/src/source_maps.ts index 9f7f6547f..ae004c2ec 100644 --- a/packages/sol-tracing-utils/src/source_maps.ts +++ b/packages/sol-tracing-utils/src/source_maps.ts @@ -33,7 +33,7 @@ export function getLocationByOffset(str: string): LocationByOffset { /** * Parses a sourcemap string. * The solidity sourcemap format is documented here: https://github.com/ethereum/solidity/blob/develop/docs/miscellaneous.rst#source-mappings - * @param sourceCodes sources contents by index + * @param indexToSourceCode index to source code * @param srcMap source map string * @param bytecodeHex contract bytecode * @param indexToSource index to source file path -- cgit v1.2.3 From 02543fdd0c393dfd36a8734ba804babd1584d3d7 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 14:42:45 +0100 Subject: Add a link to tracing examples --- packages/sol-tracing-utils/src/trace_info_subprovider.ts | 2 ++ 1 file changed, 2 insertions(+) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_info_subprovider.ts b/packages/sol-tracing-utils/src/trace_info_subprovider.ts index dc42ce25e..38a55646d 100644 --- a/packages/sol-tracing-utils/src/trace_info_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_info_subprovider.ts @@ -19,6 +19,8 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { // For very large traces we use a custom tracer that outputs a format compatible with a // regular trace. We only need the 2nd item on the stack when the instruction is a call. // By not including other stack values, we drastically limit the amount of data to be collected. + // There are no good docs about how to write those tracers, but you can find some example ones here: + // https://github.com/ethereum/go-ethereum/tree/master/eth/tracers/internal/tracers const tracer = ` { data: [], -- cgit v1.2.3 From 4689309857126669563dc9ea0e912ec9cec74157 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 14:43:03 +0100 Subject: Add SourceCodes and Sources types --- packages/sol-tracing-utils/src/types.ts | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/types.ts b/packages/sol-tracing-utils/src/types.ts index fa10a93d6..2b305c16e 100644 --- a/packages/sol-tracing-utils/src/types.ts +++ b/packages/sol-tracing-utils/src/types.ts @@ -76,13 +76,20 @@ export interface Coverage { }; } +export interface SourceCodes { + [sourceId: number]: string; +} +export interface Sources { + [sourceId: number]: string; +} + export interface ContractData { bytecode: string; sourceMap: string; runtimeBytecode: string; sourceMapRuntime: string; - sourceCodes: { [sourceId: number]: string }; - sources: { [sourceId: number]: string }; + sourceCodes: SourceCodes; + sources: Sources; } // Part of the trace executed within the same context -- cgit v1.2.3 From 83b46cbf71abd897b434ff510035171297a51255 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Mon, 14 Jan 2019 14:48:59 +0100 Subject: Rename mappins to have a direct naming scheme instead of a reverse one --- packages/sol-tracing-utils/src/ast_visitor.ts | 12 +++++------ .../src/collect_coverage_entries.ts | 6 +++--- packages/sol-tracing-utils/src/index.ts | 2 +- packages/sol-tracing-utils/src/source_maps.ts | 24 +++++++++++----------- packages/sol-tracing-utils/src/types.ts | 2 +- .../sol-tracing-utils/test/source_maps_test.ts | 6 +++--- 6 files changed, 26 insertions(+), 26 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/ast_visitor.ts b/packages/sol-tracing-utils/src/ast_visitor.ts index fe71c974b..1ac9cd1de 100644 --- a/packages/sol-tracing-utils/src/ast_visitor.ts +++ b/packages/sol-tracing-utils/src/ast_visitor.ts @@ -1,7 +1,7 @@ import * as _ from 'lodash'; import * as Parser from 'solidity-parser-antlr'; -import { BranchMap, FnMap, LocationByOffset, SingleFileSourceRange, StatementMap } from './types'; +import { BranchMap, FnMap, OffsetToLocation, SingleFileSourceRange, StatementMap } from './types'; export interface CoverageEntriesDescription { fnMap: FnMap; @@ -22,13 +22,13 @@ export class ASTVisitor { private readonly _branchMap: BranchMap = {}; private readonly _modifiersStatementIds: number[] = []; private readonly _statementMap: StatementMap = {}; - private readonly _locationByOffset: LocationByOffset; + private readonly _offsetToLocation: OffsetToLocation; private readonly _ignoreRangesBeginningAt: number[]; // keep track of contract/function ranges that are to be ignored // so we can also ignore any children nodes within the contract/function private readonly _ignoreRangesWithin: Array<[number, number]> = []; - constructor(locationByOffset: LocationByOffset, ignoreRangesBeginningAt: number[] = []) { - this._locationByOffset = locationByOffset; + constructor(offsetToLocation: OffsetToLocation, ignoreRangesBeginningAt: number[] = []) { + this._offsetToLocation = offsetToLocation; this._ignoreRangesBeginningAt = ignoreRangesBeginningAt; } public getCollectedCoverageEntries(): CoverageEntriesDescription { @@ -169,8 +169,8 @@ export class ASTVisitor { } private _getExpressionRange(ast: Parser.ASTNode): SingleFileSourceRange { const astRange = ast.range as [number, number]; - const start = this._locationByOffset[astRange[0]]; - const end = this._locationByOffset[astRange[1] + 1]; + const start = this._offsetToLocation[astRange[0]]; + const end = this._offsetToLocation[astRange[1] + 1]; const range = { start, end, diff --git a/packages/sol-tracing-utils/src/collect_coverage_entries.ts b/packages/sol-tracing-utils/src/collect_coverage_entries.ts index bdbcd613e..3ca794f8e 100644 --- a/packages/sol-tracing-utils/src/collect_coverage_entries.ts +++ b/packages/sol-tracing-utils/src/collect_coverage_entries.ts @@ -3,7 +3,7 @@ import * as _ from 'lodash'; import * as parser from 'solidity-parser-antlr'; import { ASTVisitor, CoverageEntriesDescription } from './ast_visitor'; -import { getLocationByOffset } from './source_maps'; +import { getOffsetToLocation } from './source_maps'; const IGNORE_RE = /\/\*\s*solcov\s+ignore\s+next\s*\*\/\s*/gm; @@ -14,9 +14,9 @@ export const collectCoverageEntries = (contractSource: string) => { const sourceHash = ethUtil.sha3(contractSource).toString('hex'); if (_.isUndefined(coverageEntriesBySourceHash[sourceHash]) && !_.isUndefined(contractSource)) { const ast = parser.parse(contractSource, { range: true }); - const locationByOffset = getLocationByOffset(contractSource); + const offsetToLocation = getOffsetToLocation(contractSource); const ignoreRangesBegingingAt = gatherRangesToIgnore(contractSource); - const visitor = new ASTVisitor(locationByOffset, ignoreRangesBegingingAt); + const visitor = new ASTVisitor(offsetToLocation, ignoreRangesBegingingAt); parser.visit(ast, visitor); coverageEntriesBySourceHash[sourceHash] = visitor.getCollectedCoverageEntries(); } diff --git a/packages/sol-tracing-utils/src/index.ts b/packages/sol-tracing-utils/src/index.ts index 413e5305e..8e3136046 100644 --- a/packages/sol-tracing-utils/src/index.ts +++ b/packages/sol-tracing-utils/src/index.ts @@ -22,7 +22,7 @@ export { BranchMap, EvmCallStackEntry, FnMap, - LocationByOffset, + OffsetToLocation, StatementMap, TraceInfoBase, TraceInfoExistingContract, diff --git a/packages/sol-tracing-utils/src/source_maps.ts b/packages/sol-tracing-utils/src/source_maps.ts index ae004c2ec..0a2d3c88a 100644 --- a/packages/sol-tracing-utils/src/source_maps.ts +++ b/packages/sol-tracing-utils/src/source_maps.ts @@ -1,7 +1,7 @@ import * as _ from 'lodash'; import { getPcToInstructionIndexMapping } from './instructions'; -import { LocationByOffset, SourceRange } from './types'; +import { OffsetToLocation, SourceRange } from './types'; const RADIX = 10; @@ -15,19 +15,19 @@ export interface SourceLocation { * Receives a string with newlines and returns a map of byte offset to LineColumn * @param str A string to process */ -export function getLocationByOffset(str: string): LocationByOffset { - const locationByOffset: LocationByOffset = { 0: { line: 1, column: 0 } }; +export function getOffsetToLocation(str: string): OffsetToLocation { + const offsetToLocation: OffsetToLocation = { 0: { line: 1, column: 0 } }; let currentOffset = 0; for (const char of str.split('')) { - const location = locationByOffset[currentOffset]; + const location = offsetToLocation[currentOffset]; const isNewline = char === '\n'; - locationByOffset[currentOffset + 1] = { + offsetToLocation[currentOffset + 1] = { line: location.line + (isNewline ? 1 : 0), column: isNewline ? 0 : location.column + 1, }; currentOffset++; } - return locationByOffset; + return offsetToLocation; } /** @@ -46,9 +46,9 @@ export function parseSourceMap( ): { [programCounter: number]: SourceRange } { const bytecode = Uint8Array.from(Buffer.from(bytecodeHex, 'hex')); const pcToInstructionIndex: { [programCounter: number]: number } = getPcToInstructionIndexMapping(bytecode); - const locationByOffsetByFileIndex: { [fileIndex: number]: LocationByOffset } = {}; + const fileIndexToOffsetToLocation: { [fileIndex: number]: OffsetToLocation } = {}; _.map(sourceCodes, (sourceCode: string, fileIndex: number) => { - locationByOffsetByFileIndex[fileIndex] = _.isUndefined(sourceCode) ? {} : getLocationByOffset(sourceCode); + fileIndexToOffsetToLocation[fileIndex] = _.isUndefined(sourceCode) ? {} : getOffsetToLocation(sourceCode); }); const entries = srcMap.split(';'); let lastParsedEntry: SourceLocation = {} as any; @@ -69,12 +69,12 @@ export function parseSourceMap( length, fileIndex, }; - if (parsedEntry.fileIndex !== -1 && !_.isUndefined(locationByOffsetByFileIndex[parsedEntry.fileIndex])) { - const locationByOffset = locationByOffsetByFileIndex[parsedEntry.fileIndex]; + if (parsedEntry.fileIndex !== -1 && !_.isUndefined(fileIndexToOffsetToLocation[parsedEntry.fileIndex])) { + const offsetToLocation = fileIndexToOffsetToLocation[parsedEntry.fileIndex]; const sourceRange = { location: { - start: locationByOffset[parsedEntry.offset], - end: locationByOffset[parsedEntry.offset + parsedEntry.length], + start: offsetToLocation[parsedEntry.offset], + end: offsetToLocation[parsedEntry.offset + parsedEntry.length], }, fileName: sources[parsedEntry.fileIndex], }; diff --git a/packages/sol-tracing-utils/src/types.ts b/packages/sol-tracing-utils/src/types.ts index 2b305c16e..27568ae03 100644 --- a/packages/sol-tracing-utils/src/types.ts +++ b/packages/sol-tracing-utils/src/types.ts @@ -16,7 +16,7 @@ export interface SingleFileSourceRange { end: LineColumn; } -export interface LocationByOffset { +export interface OffsetToLocation { [offset: number]: LineColumn; } diff --git a/packages/sol-tracing-utils/test/source_maps_test.ts b/packages/sol-tracing-utils/test/source_maps_test.ts index 5820bedd7..330a6a3e1 100644 --- a/packages/sol-tracing-utils/test/source_maps_test.ts +++ b/packages/sol-tracing-utils/test/source_maps_test.ts @@ -4,7 +4,7 @@ import * as _ from 'lodash'; import 'mocha'; import * as path from 'path'; -import { getLocationByOffset, parseSourceMap } from '../src/source_maps'; +import { getOffsetToLocation, parseSourceMap } from '../src/source_maps'; const expect = chai.expect; @@ -15,7 +15,7 @@ const simplestContract = fs.readFileSync(simplestContractFileName).toString(); describe('source maps', () => { describe('#getLocationByOffset', () => { it('correctly computes location by offset', () => { - const locationByOffset = getLocationByOffset(simplestContract); + const offsetToLocation = getOffsetToLocation(simplestContract); const expectedLocationByOffset = { '0': { line: 1, column: 0 }, '1': { line: 1, column: 1 }, @@ -41,7 +41,7 @@ describe('source maps', () => { '21': { line: 2, column: 1 }, '22': { line: 3, column: 0 }, }; - expect(locationByOffset).to.be.deep.equal(expectedLocationByOffset); + expect(offsetToLocation).to.be.deep.equal(expectedLocationByOffset); }); }); describe('#parseSourceMap', () => { -- cgit v1.2.3 From a8e32d8c87bd2bcf846f124f2d153fd92658dd1e Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Tue, 15 Jan 2019 11:18:29 +0100 Subject: Export Sources and SourceCodes out of tracing utils --- packages/sol-tracing-utils/src/index.ts | 2 ++ 1 file changed, 2 insertions(+) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/index.ts b/packages/sol-tracing-utils/src/index.ts index 8e3136046..fdf024ae0 100644 --- a/packages/sol-tracing-utils/src/index.ts +++ b/packages/sol-tracing-utils/src/index.ts @@ -27,6 +27,8 @@ export { TraceInfoBase, TraceInfoExistingContract, TraceInfoNewContract, + Sources, + SourceCodes, } from './types'; export { collectCoverageEntries } from './collect_coverage_entries'; export { TraceCollector, SingleFileSubtraceHandler } from './trace_collector'; -- cgit v1.2.3 From d9675ad6d3ca5e1c124c91d182cfbec9c912fb15 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Tue, 15 Jan 2019 11:48:04 +0100 Subject: Refactor logAsyncErrors to follow our conventions --- .../sol-tracing-utils/src/trace_collection_subprovider.ts | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index e3f5561aa..d79c5ca22 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -1,4 +1,5 @@ import { BlockchainLifecycle } from '@0x/dev-utils'; +import { logUtils } from '@0x/utils'; import { Callback, ErrorCallback, NextCallback, Subprovider } from '@0x/subproviders'; import { CallDataRPC, marshaller, Web3Wrapper } from '@0x/web3-wrapper'; import { JSONRPCRequestPayload, Provider, TxData } from 'ethereum-types'; @@ -25,14 +26,14 @@ type AsyncFunc = (...args: any[]) => Promise; // This wrapper outputs errors to console even if the promise gets ignored // we need this because web3-provider-engine does not handle promises in // the after function of next(after). -function logErrors(fn: AsyncFunc): AsyncFunc { +function logAsyncErrors(fn: AsyncFunc): AsyncFunc { async function wrappedAsync(...args: any[]): Promise { try { await fn(...args); - } catch (e) { + } catch (err) { // tslint:disable-next-line no-console - console.error(e); - throw e; + logUtils.error(err); + throw err; } } return wrappedAsync; @@ -92,7 +93,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const txData = payload.params[0]; - next(logErrors(this._onTransactionSentAsync.bind(this, txData))); + next(logAsyncErrors(this._onTransactionSentAsync.bind(this, txData))); } return; @@ -101,7 +102,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const callData = payload.params[0]; - next(logErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, callData))); + next(logAsyncErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, callData))); } return; @@ -110,7 +111,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const estimateGasData = payload.params[0]; - next(logErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData))); + next(logAsyncErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData))); } return; -- cgit v1.2.3 From 7ea274b7316ddc40298a66278a14a735cfd314de Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Tue, 15 Jan 2019 11:55:06 +0100 Subject: Remove logAsyncErrors hack --- .../src/trace_collection_subprovider.ts | 78 ++++++++++------------ 1 file changed, 34 insertions(+), 44 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index d79c5ca22..a57ecaad3 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -21,24 +21,6 @@ export interface TraceCollectionSubproviderConfig { shouldCollectGasEstimateTraces: boolean; } -type AsyncFunc = (...args: any[]) => Promise; - -// This wrapper outputs errors to console even if the promise gets ignored -// we need this because web3-provider-engine does not handle promises in -// the after function of next(after). -function logAsyncErrors(fn: AsyncFunc): AsyncFunc { - async function wrappedAsync(...args: any[]): Promise { - try { - await fn(...args); - } catch (err) { - // tslint:disable-next-line no-console - logUtils.error(err); - throw err; - } - } - return wrappedAsync; -} - // Because there is no notion of a call trace in the Ethereum rpc - we collect them in a rather non-obvious/hacky way. // On each call - we create a snapshot, execute the call as a transaction, get the trace, revert the snapshot. // That allows us to avoid influencing test behaviour. @@ -93,7 +75,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const txData = payload.params[0]; - next(logAsyncErrors(this._onTransactionSentAsync.bind(this, txData))); + next(this._onTransactionSentAsync.bind(this, txData)); } return; @@ -102,7 +84,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const callData = payload.params[0]; - next(logAsyncErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, callData))); + next(this._onCallOrGasEstimateExecutedAsync.bind(this, callData)); } return; @@ -111,7 +93,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const estimateGasData = payload.params[0]; - next(logAsyncErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData))); + next(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData)); } return; @@ -145,31 +127,35 @@ export abstract class TraceCollectionSubprovider extends Subprovider { txHash: string | undefined, cb: Callback, ): Promise { - if (!txData.isFakeTransaction) { - // This transaction is a usual transaction. Not a call executed as one. - // And we don't want it to be executed within a snapshotting period - await this._lock.acquire(); - } - const NULL_ADDRESS = '0x0'; - if (_.isNull(err)) { - const toAddress = - _.isUndefined(txData.to) || txData.to === NULL_ADDRESS ? constants.NEW_CONTRACT : txData.to; - await this._recordTxTraceAsync(toAddress, txData.data, txHash as string); - } else { - const latestBlock = await this._web3Wrapper.getBlockWithTransactionDataAsync(BlockParamLiteral.Latest); - const transactions = latestBlock.transactions; - for (const transaction of transactions) { + try { + if (!txData.isFakeTransaction) { + // This transaction is a usual transaction. Not a call executed as one. + // And we don't want it to be executed within a snapshotting period + await this._lock.acquire(); + } + const NULL_ADDRESS = '0x0'; + if (_.isNull(err)) { const toAddress = _.isUndefined(txData.to) || txData.to === NULL_ADDRESS ? constants.NEW_CONTRACT : txData.to; - await this._recordTxTraceAsync(toAddress, transaction.input, transaction.hash); + await this._recordTxTraceAsync(toAddress, txData.data, txHash as string); + } else { + const latestBlock = await this._web3Wrapper.getBlockWithTransactionDataAsync(BlockParamLiteral.Latest); + const transactions = latestBlock.transactions; + for (const transaction of transactions) { + const toAddress = + _.isUndefined(txData.to) || txData.to === NULL_ADDRESS ? constants.NEW_CONTRACT : txData.to; + await this._recordTxTraceAsync(toAddress, transaction.input, transaction.hash); + } } + if (!txData.isFakeTransaction) { + // This transaction is a usual transaction. Not a call executed as one. + // And we don't want it to be executed within a snapshotting period + this._lock.release(); + } + cb(); + } catch (err) { + cb(err); } - if (!txData.isFakeTransaction) { - // This transaction is a usual transaction. Not a call executed as one. - // And we don't want it to be executed within a snapshotting period - this._lock.release(); - } - cb(); } private async _onCallOrGasEstimateExecutedAsync( callData: Partial, @@ -177,8 +163,12 @@ export abstract class TraceCollectionSubprovider extends Subprovider { _callResult: string, cb: Callback, ): Promise { - await this._recordCallOrGasEstimateTraceAsync(callData); - cb(); + try { + await this._recordCallOrGasEstimateTraceAsync(callData); + cb(); + } catch (err) { + cb(err); + } } private async _recordCallOrGasEstimateTraceAsync(callData: Partial): Promise { // We don't want other transactions to be exeucted during snashotting period, that's why we lock the -- cgit v1.2.3 From c2ec4174b765d2f3352dd0fd8b04e4d2c1955d64 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Tue, 15 Jan 2019 12:09:17 +0100 Subject: Revert "Remove logAsyncErrors hack" This reverts commit 7ea274b7316ddc40298a66278a14a735cfd314de. --- .../src/trace_collection_subprovider.ts | 78 ++++++++++++---------- 1 file changed, 44 insertions(+), 34 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index a57ecaad3..d79c5ca22 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -21,6 +21,24 @@ export interface TraceCollectionSubproviderConfig { shouldCollectGasEstimateTraces: boolean; } +type AsyncFunc = (...args: any[]) => Promise; + +// This wrapper outputs errors to console even if the promise gets ignored +// we need this because web3-provider-engine does not handle promises in +// the after function of next(after). +function logAsyncErrors(fn: AsyncFunc): AsyncFunc { + async function wrappedAsync(...args: any[]): Promise { + try { + await fn(...args); + } catch (err) { + // tslint:disable-next-line no-console + logUtils.error(err); + throw err; + } + } + return wrappedAsync; +} + // Because there is no notion of a call trace in the Ethereum rpc - we collect them in a rather non-obvious/hacky way. // On each call - we create a snapshot, execute the call as a transaction, get the trace, revert the snapshot. // That allows us to avoid influencing test behaviour. @@ -75,7 +93,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const txData = payload.params[0]; - next(this._onTransactionSentAsync.bind(this, txData)); + next(logAsyncErrors(this._onTransactionSentAsync.bind(this, txData))); } return; @@ -84,7 +102,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const callData = payload.params[0]; - next(this._onCallOrGasEstimateExecutedAsync.bind(this, callData)); + next(logAsyncErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, callData))); } return; @@ -93,7 +111,7 @@ export abstract class TraceCollectionSubprovider extends Subprovider { next(); } else { const estimateGasData = payload.params[0]; - next(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData)); + next(logAsyncErrors(this._onCallOrGasEstimateExecutedAsync.bind(this, estimateGasData))); } return; @@ -127,35 +145,31 @@ export abstract class TraceCollectionSubprovider extends Subprovider { txHash: string | undefined, cb: Callback, ): Promise { - try { - if (!txData.isFakeTransaction) { - // This transaction is a usual transaction. Not a call executed as one. - // And we don't want it to be executed within a snapshotting period - await this._lock.acquire(); - } - const NULL_ADDRESS = '0x0'; - if (_.isNull(err)) { + if (!txData.isFakeTransaction) { + // This transaction is a usual transaction. Not a call executed as one. + // And we don't want it to be executed within a snapshotting period + await this._lock.acquire(); + } + const NULL_ADDRESS = '0x0'; + if (_.isNull(err)) { + const toAddress = + _.isUndefined(txData.to) || txData.to === NULL_ADDRESS ? constants.NEW_CONTRACT : txData.to; + await this._recordTxTraceAsync(toAddress, txData.data, txHash as string); + } else { + const latestBlock = await this._web3Wrapper.getBlockWithTransactionDataAsync(BlockParamLiteral.Latest); + const transactions = latestBlock.transactions; + for (const transaction of transactions) { const toAddress = _.isUndefined(txData.to) || txData.to === NULL_ADDRESS ? constants.NEW_CONTRACT : txData.to; - await this._recordTxTraceAsync(toAddress, txData.data, txHash as string); - } else { - const latestBlock = await this._web3Wrapper.getBlockWithTransactionDataAsync(BlockParamLiteral.Latest); - const transactions = latestBlock.transactions; - for (const transaction of transactions) { - const toAddress = - _.isUndefined(txData.to) || txData.to === NULL_ADDRESS ? constants.NEW_CONTRACT : txData.to; - await this._recordTxTraceAsync(toAddress, transaction.input, transaction.hash); - } + await this._recordTxTraceAsync(toAddress, transaction.input, transaction.hash); } - if (!txData.isFakeTransaction) { - // This transaction is a usual transaction. Not a call executed as one. - // And we don't want it to be executed within a snapshotting period - this._lock.release(); - } - cb(); - } catch (err) { - cb(err); } + if (!txData.isFakeTransaction) { + // This transaction is a usual transaction. Not a call executed as one. + // And we don't want it to be executed within a snapshotting period + this._lock.release(); + } + cb(); } private async _onCallOrGasEstimateExecutedAsync( callData: Partial, @@ -163,12 +177,8 @@ export abstract class TraceCollectionSubprovider extends Subprovider { _callResult: string, cb: Callback, ): Promise { - try { - await this._recordCallOrGasEstimateTraceAsync(callData); - cb(); - } catch (err) { - cb(err); - } + await this._recordCallOrGasEstimateTraceAsync(callData); + cb(); } private async _recordCallOrGasEstimateTraceAsync(callData: Partial): Promise { // We don't want other transactions to be exeucted during snashotting period, that's why we lock the -- cgit v1.2.3 From 75a4bbc5f2bf38c2ea8c18f21dc9b54eaf5bb422 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Tue, 15 Jan 2019 12:09:48 +0100 Subject: Remove unused tslint disable --- packages/sol-tracing-utils/src/trace_collection_subprovider.ts | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index d79c5ca22..2bbb4c62b 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -1,6 +1,6 @@ import { BlockchainLifecycle } from '@0x/dev-utils'; -import { logUtils } from '@0x/utils'; import { Callback, ErrorCallback, NextCallback, Subprovider } from '@0x/subproviders'; +import { logUtils } from '@0x/utils'; import { CallDataRPC, marshaller, Web3Wrapper } from '@0x/web3-wrapper'; import { JSONRPCRequestPayload, Provider, TxData } from 'ethereum-types'; import * as _ from 'lodash'; @@ -31,8 +31,7 @@ function logAsyncErrors(fn: AsyncFunc): AsyncFunc { try { await fn(...args); } catch (err) { - // tslint:disable-next-line no-console - logUtils.error(err); + logUtils.log(err); throw err; } } -- cgit v1.2.3 From 63a63543be74d9e8822b7b111aa46350a5f524d8 Mon Sep 17 00:00:00 2001 From: Leonid Logvinov Date: Tue, 15 Jan 2019 13:33:24 +0100 Subject: Make mapping namings direct --- .../sol_compiler_artifact_adapter.ts | 6 +++--- .../src/collect_coverage_entries.ts | 8 ++++---- .../src/get_source_range_snippet.ts | 8 ++++---- packages/sol-tracing-utils/src/source_maps.ts | 6 +++--- packages/sol-tracing-utils/src/trace.ts | 22 +++++++++++----------- .../src/trace_info_subprovider.ts | 12 ++++++------ packages/sol-tracing-utils/test/trace_test.ts | 4 ++-- 7 files changed, 33 insertions(+), 33 deletions(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts b/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts index 7d85f6c68..d52587f2c 100644 --- a/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts +++ b/packages/sol-tracing-utils/src/artifact_adapters/sol_compiler_artifact_adapter.ts @@ -5,7 +5,7 @@ import * as glob from 'glob'; import * as _ from 'lodash'; import * as path from 'path'; -import { ContractData } from '../types'; +import { ContractData, SourceCodes, Sources } from '../types'; import { AbstractArtifactAdapter } from './abstract_artifact_adapter'; @@ -43,8 +43,8 @@ export class SolCompilerArtifactAdapter extends AbstractArtifactAdapter { logUtils.warn(`${artifactFileName} doesn't contain bytecode. Skipping...`); continue; } - const sources: { [sourceId: number]: string } = {}; - const sourceCodes: { [sourceId: number]: string } = {}; + const sources: Sources = {}; + const sourceCodes: SourceCodes = {}; _.map(artifact.sources, (value: { id: number }, relativeFilePath: string) => { const filePath = path.resolve(this._sourcesPath, relativeFilePath); const fileContent = fs.readFileSync(filePath).toString(); diff --git a/packages/sol-tracing-utils/src/collect_coverage_entries.ts b/packages/sol-tracing-utils/src/collect_coverage_entries.ts index 3ca794f8e..9e3591d74 100644 --- a/packages/sol-tracing-utils/src/collect_coverage_entries.ts +++ b/packages/sol-tracing-utils/src/collect_coverage_entries.ts @@ -8,19 +8,19 @@ import { getOffsetToLocation } from './source_maps'; const IGNORE_RE = /\/\*\s*solcov\s+ignore\s+next\s*\*\/\s*/gm; // Parsing source code for each transaction/code is slow and therefore we cache it -const coverageEntriesBySourceHash: { [sourceHash: string]: CoverageEntriesDescription } = {}; +const sourceHashToCoverageEntries: { [sourceHash: string]: CoverageEntriesDescription } = {}; export const collectCoverageEntries = (contractSource: string) => { const sourceHash = ethUtil.sha3(contractSource).toString('hex'); - if (_.isUndefined(coverageEntriesBySourceHash[sourceHash]) && !_.isUndefined(contractSource)) { + if (_.isUndefined(sourceHashToCoverageEntries[sourceHash]) && !_.isUndefined(contractSource)) { const ast = parser.parse(contractSource, { range: true }); const offsetToLocation = getOffsetToLocation(contractSource); const ignoreRangesBegingingAt = gatherRangesToIgnore(contractSource); const visitor = new ASTVisitor(offsetToLocation, ignoreRangesBegingingAt); parser.visit(ast, visitor); - coverageEntriesBySourceHash[sourceHash] = visitor.getCollectedCoverageEntries(); + sourceHashToCoverageEntries[sourceHash] = visitor.getCollectedCoverageEntries(); } - const coverageEntriesDescription = coverageEntriesBySourceHash[sourceHash]; + const coverageEntriesDescription = sourceHashToCoverageEntries[sourceHash]; return coverageEntriesDescription; }; diff --git a/packages/sol-tracing-utils/src/get_source_range_snippet.ts b/packages/sol-tracing-utils/src/get_source_range_snippet.ts index f578675d3..7aef00fee 100644 --- a/packages/sol-tracing-utils/src/get_source_range_snippet.ts +++ b/packages/sol-tracing-utils/src/get_source_range_snippet.ts @@ -13,7 +13,7 @@ interface ASTInfo { } // Parsing source code for each transaction/code is slow and therefore we cache it -const parsedSourceByHash: { [sourceHash: string]: Parser.ASTNode } = {}; +const hashToParsedSource: { [sourceHash: string]: Parser.ASTNode } = {}; /** * Gets the source range snippet by source range to be used by revert trace. @@ -22,10 +22,10 @@ const parsedSourceByHash: { [sourceHash: string]: Parser.ASTNode } = {}; */ export function getSourceRangeSnippet(sourceRange: SourceRange, sourceCode: string): SourceSnippet | null { const sourceHash = ethUtil.sha3(sourceCode).toString('hex'); - if (_.isUndefined(parsedSourceByHash[sourceHash])) { - parsedSourceByHash[sourceHash] = Parser.parse(sourceCode, { loc: true }); + if (_.isUndefined(hashToParsedSource[sourceHash])) { + hashToParsedSource[sourceHash] = Parser.parse(sourceCode, { loc: true }); } - const astNode = parsedSourceByHash[sourceHash]; + const astNode = hashToParsedSource[sourceHash]; const visitor = new ASTInfoVisitor(); Parser.visit(astNode, visitor); const astInfo = visitor.getASTInfoForRange(sourceRange); diff --git a/packages/sol-tracing-utils/src/source_maps.ts b/packages/sol-tracing-utils/src/source_maps.ts index 0a2d3c88a..8c17652d9 100644 --- a/packages/sol-tracing-utils/src/source_maps.ts +++ b/packages/sol-tracing-utils/src/source_maps.ts @@ -1,7 +1,7 @@ import * as _ from 'lodash'; import { getPcToInstructionIndexMapping } from './instructions'; -import { OffsetToLocation, SourceRange } from './types'; +import { OffsetToLocation, SourceCodes, SourceRange, Sources } from './types'; const RADIX = 10; @@ -39,10 +39,10 @@ export function getOffsetToLocation(str: string): OffsetToLocation { * @param indexToSource index to source file path */ export function parseSourceMap( - sourceCodes: { [fileIndex: number]: string }, + sourceCodes: SourceCodes, srcMap: string, bytecodeHex: string, - sources: { [fileIndex: number]: string }, + sources: Sources, ): { [programCounter: number]: SourceRange } { const bytecode = Uint8Array.from(Buffer.from(bytecodeHex, 'hex')); const pcToInstructionIndex: { [programCounter: number]: number } = getPcToInstructionIndexMapping(bytecode); diff --git a/packages/sol-tracing-utils/src/trace.ts b/packages/sol-tracing-utils/src/trace.ts index 770080af3..973452b24 100644 --- a/packages/sol-tracing-utils/src/trace.ts +++ b/packages/sol-tracing-utils/src/trace.ts @@ -4,21 +4,21 @@ import * as _ from 'lodash'; import { utils } from './utils'; -export interface TraceByContractAddress { +export interface ContractAddressToTraces { [contractAddress: string]: StructLog[]; } /** - * Converts linear stack trace to `TraceByContractAddress`. + * Converts linear stack trace to `ContractAddressToTraces`. * @param structLogs stack trace * @param startAddress initial context address */ -export function getTracesByContractAddress(structLogs: StructLog[], startAddress: string): TraceByContractAddress { - const traceByContractAddress: TraceByContractAddress = {}; +export function getContractAddressToTraces(structLogs: StructLog[], startAddress: string): ContractAddressToTraces { + const contractAddressToTraces: ContractAddressToTraces = {}; let currentTraceSegment = []; const addressStack = [startAddress]; if (_.isEmpty(structLogs)) { - return traceByContractAddress; + return contractAddressToTraces; } const normalizedStructLogs = utils.normalizeStructLogs(structLogs); // tslint:disable-next-line:prefer-for-of @@ -45,14 +45,14 @@ export function getTracesByContractAddress(structLogs: StructLog[], startAddress const nextStructLog = normalizedStructLogs[i + 1]; if (nextStructLog.depth !== structLog.depth) { addressStack.push(newAddress); - traceByContractAddress[currentAddress] = (traceByContractAddress[currentAddress] || []).concat( + contractAddressToTraces[currentAddress] = (contractAddressToTraces[currentAddress] || []).concat( currentTraceSegment, ); currentTraceSegment = []; } } else if (utils.isEndOpcode(structLog.op)) { const currentAddress = addressStack.pop() as string; - traceByContractAddress[currentAddress] = (traceByContractAddress[currentAddress] || []).concat( + contractAddressToTraces[currentAddress] = (contractAddressToTraces[currentAddress] || []).concat( currentTraceSegment, ); currentTraceSegment = []; @@ -71,7 +71,7 @@ export function getTracesByContractAddress(structLogs: StructLog[], startAddress logUtils.warn( "Detected a contract created from within another contract. We currently do not support that scenario. We'll just skip that trace", ); - return traceByContractAddress; + return contractAddressToTraces; } else { if (structLog !== _.last(normalizedStructLogs)) { const nextStructLog = normalizedStructLogs[i + 1]; @@ -79,7 +79,7 @@ export function getTracesByContractAddress(structLogs: StructLog[], startAddress continue; } else if (nextStructLog.depth === structLog.depth - 1) { const currentAddress = addressStack.pop() as string; - traceByContractAddress[currentAddress] = (traceByContractAddress[currentAddress] || []).concat( + contractAddressToTraces[currentAddress] = (contractAddressToTraces[currentAddress] || []).concat( currentTraceSegment, ); currentTraceSegment = []; @@ -94,11 +94,11 @@ export function getTracesByContractAddress(structLogs: StructLog[], startAddress } if (currentTraceSegment.length !== 0) { const currentAddress = addressStack.pop() as string; - traceByContractAddress[currentAddress] = (traceByContractAddress[currentAddress] || []).concat( + contractAddressToTraces[currentAddress] = (contractAddressToTraces[currentAddress] || []).concat( currentTraceSegment, ); currentTraceSegment = []; logUtils.warn('Malformed trace. Current trace segment non empty at the end'); } - return traceByContractAddress; + return contractAddressToTraces; } diff --git a/packages/sol-tracing-utils/src/trace_info_subprovider.ts b/packages/sol-tracing-utils/src/trace_info_subprovider.ts index 38a55646d..b75fc7bf7 100644 --- a/packages/sol-tracing-utils/src/trace_info_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_info_subprovider.ts @@ -2,7 +2,7 @@ import { NodeType } from '@0x/web3-wrapper'; import * as _ from 'lodash'; import { constants } from './constants'; -import { getTracesByContractAddress } from './trace'; +import { getContractAddressToTraces } from './trace'; import { TraceCollectionSubprovider } from './trace_collection_subprovider'; import { TraceInfo, TraceInfoExistingContract, TraceInfoNewContract } from './types'; @@ -50,13 +50,13 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { disableStorage: true, }); } - const tracesByContractAddress = getTracesByContractAddress(trace.structLogs, address); - const subcallAddresses = _.keys(tracesByContractAddress); + const contractAddressToTraces = getContractAddressToTraces(trace.structLogs, address); + const subcallAddresses = _.keys(contractAddressToTraces); if (address === constants.NEW_CONTRACT) { for (const subcallAddress of subcallAddresses) { let traceInfo: TraceInfoNewContract | TraceInfoExistingContract; if (subcallAddress === 'NEW_CONTRACT') { - const traceForThatSubcall = tracesByContractAddress[subcallAddress]; + const traceForThatSubcall = contractAddressToTraces[subcallAddress]; traceInfo = { subtrace: traceForThatSubcall, txHash, @@ -65,7 +65,7 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { }; } else { const runtimeBytecode = await this._web3Wrapper.getContractCodeAsync(subcallAddress); - const traceForThatSubcall = tracesByContractAddress[subcallAddress]; + const traceForThatSubcall = contractAddressToTraces[subcallAddress]; traceInfo = { subtrace: traceForThatSubcall, txHash, @@ -78,7 +78,7 @@ export abstract class TraceInfoSubprovider extends TraceCollectionSubprovider { } else { for (const subcallAddress of subcallAddresses) { const runtimeBytecode = await this._web3Wrapper.getContractCodeAsync(subcallAddress); - const traceForThatSubcall = tracesByContractAddress[subcallAddress]; + const traceForThatSubcall = contractAddressToTraces[subcallAddress]; const traceInfo: TraceInfoExistingContract = { subtrace: traceForThatSubcall, txHash, diff --git a/packages/sol-tracing-utils/test/trace_test.ts b/packages/sol-tracing-utils/test/trace_test.ts index 7a034362c..c9ed93e63 100644 --- a/packages/sol-tracing-utils/test/trace_test.ts +++ b/packages/sol-tracing-utils/test/trace_test.ts @@ -3,7 +3,7 @@ import { OpCode, StructLog } from 'ethereum-types'; import * as _ from 'lodash'; import 'mocha'; -import { getTracesByContractAddress } from '../src/trace'; +import { getContractAddressToTraces } from '../src/trace'; const expect = chai.expect; @@ -44,7 +44,7 @@ describe('Trace', () => { ]; const fullTrace = _.map(trace, compactStructLog => addDefaultStructLogFields(compactStructLog)); const startAddress = '0x0000000000000000000000000000000000000001'; - const traceByContractAddress = getTracesByContractAddress(fullTrace, startAddress); + const traceByContractAddress = getContractAddressToTraces(fullTrace, startAddress); const expectedTraceByContractAddress = { [startAddress]: [fullTrace[0], fullTrace[2]], [delegateCallAddress]: [fullTrace[1]], -- cgit v1.2.3 From 64d99dc07cc82c7cc2917871596b46985f1d709f Mon Sep 17 00:00:00 2001 From: Fabio B Date: Tue, 15 Jan 2019 14:44:52 +0100 Subject: Update packages/sol-tracing-utils/src/trace_collection_subprovider.ts Co-Authored-By: LogvinovLeon --- packages/sol-tracing-utils/src/trace_collection_subprovider.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/sol-tracing-utils') diff --git a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts index 2bbb4c62b..323e1523c 100644 --- a/packages/sol-tracing-utils/src/trace_collection_subprovider.ts +++ b/packages/sol-tracing-utils/src/trace_collection_subprovider.ts @@ -23,7 +23,7 @@ export interface TraceCollectionSubproviderConfig { type AsyncFunc = (...args: any[]) => Promise; -// This wrapper outputs errors to console even if the promise gets ignored +// HACK: This wrapper outputs errors to console even if the promise gets ignored // we need this because web3-provider-engine does not handle promises in // the after function of next(after). function logAsyncErrors(fn: AsyncFunc): AsyncFunc { -- cgit v1.2.3