contract creation code

pull/7/head
yann300 9 years ago
parent 006dc9b32a
commit 6518e8a54e
  1. 35
      src/asmCode.js
  2. 9
      src/codeResolver.js
  3. 18
      src/stepManager.js
  4. 39
      src/traceAnalyser.js
  5. 13
      src/traceCache.js
  6. 25
      src/traceManager.js
  7. 2
      src/txBrowser.js

@ -67,22 +67,37 @@ module.exports = React.createClass({
code: ['loading...']
})
var self = this
codeResolver.resolveCode(address, currentStep, this.context.tx, function (address, code) {
if (window.ethDebuggerSelectedItem !== currentStep) {
console.log(currentStep + ' discarded. current is ' + window.ethDebuggerSelectedItem)
return
}
self.setState({
code: code,
address: address
if (address.indexOf('(Contract Creation Code)') !== -1) {
this.context.traceManager.getContractCreationCode(address, function (error, hexCode) {
if (error) {
console.log(error)
} else {
var codes = codeResolver.cacheExecutingCode(address, hexCode)
self.updateCode(codes.code, address, currentStep)
}
})
self.setInstructionIndex(address, currentStep)
})
} else {
codeResolver.resolveCode(address, currentStep, this.context.tx, function (address, code) {
if (window.ethDebuggerSelectedItem !== currentStep) {
console.log(currentStep + ' discarded. current is ' + window.ethDebuggerSelectedItem)
return
}
self.updateCode(code, address, currentStep)
})
}
} else {
this.setInstructionIndex(this.state.address, currentStep)
}
},
updateCode: function (code, address, currentStep) {
this.setState({
code: code,
address: address
})
this.setInstructionIndex(address, currentStep)
},
setInstructionIndex: function (address, step) {
var self = this
this.context.traceManager.getCurrentPC(step, function (error, instIndex) {

@ -18,11 +18,6 @@ module.exports = {
return
}
if (address === '(Contract Creation Code)') { // start of the trace
callBack(address, this.cacheExecutingCode(address, transaction.input).code)
return
}
var self = this
this.loadCode(address, function (code) {
callBack(address, self.cacheExecutingCode(address, code).code)
@ -42,8 +37,8 @@ module.exports = {
cacheExecutingCode: function (address, hexCode) {
var codes = this.formatCode(hexCode)
this.codes[address] = codes[0]
this.instructionsIndexByBytesOffset[address] = codes[1]
this.codes[address] = codes.code
this.instructionsIndexByBytesOffset[address] = codes.instructionsIndexByBytesOffset
return codes
},

@ -64,18 +64,27 @@ module.exports = React.createClass({
},
sliderMoved: function (step) {
if (step >= this.state.traceLength || step < 0) {
return
}
this.props.onStepChanged(step)
this.changeState(step)
},
stepIntoForward: function () {
var step = this.state.currentStepIndex + 1
if (step >= this.state.traceLength || step < 0) {
return
}
this.props.onStepChanged(step)
this.changeState(step)
},
stepIntoBack: function () {
var step = this.state.currentStepIndex - 1
if (step >= this.state.traceLength || step < 0) {
return
}
this.props.onStepChanged(step)
this.refs.slider.setValue(step)
this.changeState(step)
@ -83,6 +92,9 @@ module.exports = React.createClass({
stepOverForward: function () {
var step = this.context.traceManager.findStepOverForward(this.state.currentStepIndex)
if (step >= this.state.traceLength || step < 0) {
return
}
this.props.onStepChanged(step)
this.refs.slider.setValue(step)
this.changeState(step)
@ -90,6 +102,9 @@ module.exports = React.createClass({
stepOverBack: function () {
var step = this.context.traceManager.findStepOverBack(this.state.currentStepIndex)
if (step >= this.state.traceLength || step < 0) {
return
}
this.props.onStepChanged(step)
this.refs.slider.setValue(step)
this.changeState(step)
@ -97,6 +112,9 @@ module.exports = React.createClass({
jumpToNextCall: function () {
var step = this.context.traceManager.findNextCall(this.state.currentStepIndex)
if (step >= this.state.traceLength || step < 0) {
return
}
this.props.onStepChanged(step)
this.refs.slider.setValue(step)
this.changeState(step)

@ -6,19 +6,22 @@ function TraceAnalyser (_cache) {
this.trace = null
}
TraceAnalyser.prototype.analyse = function (trace, root, callback) {
TraceAnalyser.prototype.analyse = function (trace, tx, callback) {
this.trace = trace
this.traceCache.pushStoreChanges(0, root)
this.traceCache.pushStoreChanges(0, tx.to)
var context = {
currentStorageAddress: root,
previousStorageAddress: root
currentStorageAddress: tx.to,
previousStorageAddress: tx.to
}
var callStack = [root]
var callStack = [tx.to]
this.traceCache.pushCallStack(0, {
callStack: callStack.slice(0)
})
if (tx.to === '(Contract Creation Code)') {
this.traceCache.pushContractCreation(tx.to, tx.input)
}
for (var k = 0; k < this.trace.length; k++) {
var step = this.trace[k]
this.buildCalldata(k, step)
@ -61,26 +64,30 @@ TraceAnalyser.prototype.buildStorage = function (index, step, context) {
TraceAnalyser.prototype.buildDepth = function (index, step, callStack) {
if (traceManagerUtil.isCallInstruction(step) && !traceManagerUtil.isCallToPrecompiledContract(index, this.trace)) {
var newAddress = traceManagerUtil.resolveCalledAddress(index, this.trace)
if (newAddress) {
callStack.push(newAddress)
if (traceManagerUtil.isCreateInstruction(step)) {
var contractToken = '(Contract Creation Code) ' + index
callStack.push(contractToken)
var lastMemoryChange = this.traceCache.memoryChanges[this.traceCache.memoryChanges.length - 1]
this.traceCache.pushContractCreationFromMemory(index, contractToken, this.trace, lastMemoryChange)
} else {
console.log('unable to build depth changes. ' + index + ' does not match with a CALL. depth changes will be corrupted')
var newAddress = traceManagerUtil.resolveCalledAddress(index, this.trace)
if (newAddress) {
callStack.push(newAddress)
} else {
console.log('unable to build depth changes. ' + index + ' does not match with a CALL. depth changes will be corrupted')
}
}
this.traceCache.pushCallChanges(step, index + 1)
this.traceCache.pushCallStack(index + 1, {
callStack: callStack.slice(0)
})
} else if (traceManagerUtil.isReturnInstruction(step)) {
this.traceCache.pushCallChanges(step, index)
this.traceCache.pushCallStack(index, {
callStack.pop()
this.traceCache.pushCallChanges(step, index + 1)
this.traceCache.pushCallStack(index + 1, {
callStack: callStack.slice(0)
})
callStack.pop()
}
}
// 0x90a99e9dbfc38ce0fd6330f97a192a9ef27b8329b57309e8b2abe47a6fe74574
// 0xc0e95f27e1482ba09dea8162c4b4090e3d89e214416df2ce9d5517ff2107de19
module.exports = TraceAnalyser

@ -9,6 +9,7 @@ TraceCache.prototype.init = function () {
this.callChanges = []
this.returnChanges = []
this.calls = {}
this.contractCreation = {}
this.callDataChanges = []
this.memoryChanges = []
@ -32,6 +33,18 @@ TraceCache.prototype.pushCallChanges = function (step, value) {
}
}
TraceCache.prototype.pushContractCreationFromMemory = function (index, token, trace, lastMemoryChange) {
var memory = trace[lastMemoryChange].memory
var stack = trace[index].stack
var offset = 2 * parseInt(stack[stack.length - 2], 16)
var size = 2 * parseInt(stack[stack.length - 3], 16)
this.contractCreation[token] = '0x' + memory.substr(offset, size)
}
TraceCache.prototype.pushContractCreation = function (token, code) {
this.contractCreation[token] = code
}
TraceCache.prototype.pushReturnChanges = function (value) {
this.returnChanges.push(value)
}

@ -30,7 +30,7 @@ TraceManager.prototype.resolveTrace = function (tx, callback) {
} else {
if (result.structLogs.length > 0) {
self.trace = result.structLogs
self.traceAnalyser.analyse(result.structLogs, tx.to, function (error, result) {
self.traceAnalyser.analyse(result.structLogs, tx, function (error, result) {
if (error) {
console.log(error)
callback(false)
@ -146,23 +146,26 @@ TraceManager.prototype.getCurrentCalledAddressAt = function (stepIndex, callback
if (addressIndex === 0) {
callback(null, self.tx.to)
} else {
var step = this.trace[addressIndex]
if (traceManagerUtil.isCreateInstruction(step)) {
callback(null, '(Contract Creation Code)')
var callStack = self.traceCache.callStack[addressIndex].callStack
var calledAddress = callStack[callStack.length - 1]
if (calledAddress) {
callback(null, calledAddress)
} else {
var callStack = self.traceCache.callStack[addressIndex].callStack
var calledAddress = callStack[callStack.length - 1]
if (calledAddress) {
callback(null, calledAddress)
} else {
callback('unable to get current called address. ' + stepIndex + ' does not match with a CALL', null)
}
callback('unable to get current called address. ' + stepIndex + ' does not match with a CALL', null)
}
}
}
})
}
TraceManager.prototype.getContractCreationCode = function (token, callback) {
if (this.traceCache.contractCreation[token]) {
callback(null, this.traceCache.contractCreation[token])
} else {
callback('no contract creation named ' + token, null)
}
}
TraceManager.prototype.getMemoryAt = function (stepIndex, callback) {
if (stepIndex >= this.trace.length) {
callback('trace smaller than requested', null)

@ -12,7 +12,7 @@ module.exports = React.createClass({
},
getInitialState: function () {
return {blockNumber: '1000110', txNumber: '0x71a6d583d16d142c5c3e8903060e8a4ee5a5016348a9448df6c3e63b68076ec4', from: '', to: '', hash: ''}
return {blockNumber: '1000110', txNumber: '0x50a420e75151e7f04a014019598764102675e0c6c8979f1089690c594cbe871c', from: '', to: '', hash: ''}
},
// creation 0xa9619e1d0a35b2c1d686f5b661b3abd87f998d2844e8e9cc905edb57fc9ce349

Loading…
Cancel
Save