Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion nix/overlay.nix
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ rev: final: prev: {
# ourselves instead.
mantis-extvm-pb = builtins.fetchGit {
url = "https://github.com/input-output-hk/mantis-extvm-pb";
rev = "8f52caba70afc95ce669e9d61f773468db54557e";
rev = "ae19e1fd9d3c0deba63c894be128d67e9519fe1f";
};

writeBashChecked = final.writers.makeScriptWriter {
Expand Down
2 changes: 1 addition & 1 deletion src/main/protobuf/extvm
Submodule extvm updated 2 files
+1 −1 VERSION
+25 −3 msg.proto
38 changes: 34 additions & 4 deletions src/main/scala/io/iohk/ethereum/extvm/VMClient.scala
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,17 @@ class VMClient(externalVmConfig: VmConfig.ExternalConfig, messageHandler: Messag
resultMsg: msg.CallResult
): ProgramResult[W, S] = {
val updatedWorld = applyAccountChanges[W, S](world, resultMsg)

val accessedResultTuple = resultMsg.accessList
.map { accessList =>
val addresses: Set[Address] = accessList.addresses.map(a => a: Address).toSet
val locations: Set[(Address, BigInt)] = accessList.storageLocations.map { loc =>
(loc.address: Address, loc.storageLocation: BigInt)
}.toSet
(addresses, locations)
}
.getOrElse((Set.empty[Address], Set.empty[(Address, BigInt)]))

ProgramResult(
resultMsg.returnData,
resultMsg.gasRemaining,
Expand All @@ -114,9 +125,8 @@ class VMClient(externalVmConfig: VmConfig.ExternalConfig, messageHandler: Messag
Nil,
resultMsg.gasRefund,
if (resultMsg.error) Some(OutOfGas) else None,
// FIXME handle accessed addresses and storage in extVM
Set.empty,
Set.empty
accessedResultTuple._1,
accessedResultTuple._2
)
}

Expand Down Expand Up @@ -155,6 +165,23 @@ class VMClient(externalVmConfig: VmConfig.ExternalConfig, messageHandler: Messag
case _ => Config.Empty
}

val txType =
if (ctx.warmAddresses.isEmpty && ctx.warmStorage.isEmpty) msg.CallContext.TxType.LEGACY
else msg.CallContext.TxType.ACCESSLIST

val extraData = txType match {
case msg.CallContext.TxType.LEGACY => msg.CallContext.ExtraData.Empty
case msg.CallContext.TxType.ACCESSLIST =>
msg.CallContext.ExtraData.AccessList(
msg
.AccessListData()
.withAddresses(ctx.warmAddresses.toSeq.map(_.bytes))
.withStorageLocations(
ctx.warmStorage.toSeq.map(x => msg.StorageEntry(address = x._1, storageLocation = x._2))
)
)
}

msg.CallContext(
callerAddr = ctx.callerAddr,
recipientAddr = ctx.recipientAddr.map(_.bytes).getOrElse(ByteString.empty): ByteString,
Expand All @@ -163,7 +190,9 @@ class VMClient(externalVmConfig: VmConfig.ExternalConfig, messageHandler: Messag
gasPrice = ctx.gasPrice,
gasProvided = ctx.startGas,
blockHeader = Some(blockHeader),
config = config
config = config,
txType = txType,
extraData = extraData
)
}

Expand All @@ -178,6 +207,7 @@ class VMClient(externalVmConfig: VmConfig.ExternalConfig, messageHandler: Messag
constantinopleBlockNumber = blockchainConfig.constantinopleBlockNumber,
petersburgBlockNumber = blockchainConfig.petersburgBlockNumber,
istanbulBlockNumber = blockchainConfig.istanbulBlockNumber,
berlinBlockNumber = blockchainConfig.berlinBlockNumber,
maxCodeSize = blockchainConfig.maxCodeSize.map(bigintToGByteString).getOrElse(ByteString()),
accountStartNonce = blockchainConfig.accountStartNonce,
chainId = ByteString(blockchainConfig.chainId)
Expand Down
21 changes: 18 additions & 3 deletions src/main/scala/io/iohk/ethereum/extvm/VMServer.scala
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@ import com.typesafe.config.ConfigFactory
import io.iohk.ethereum.domain.Address
import io.iohk.ethereum.domain.BlockHeader
import io.iohk.ethereum.extvm.Implicits._
import io.iohk.ethereum.extvm.msg.AccessListData
import io.iohk.ethereum.extvm.msg.StorageEntry
import io.iohk.ethereum.utils._
import io.iohk.ethereum.vm.BlockchainConfigForEvm
import io.iohk.ethereum.vm.EvmConfig
Expand Down Expand Up @@ -106,6 +108,7 @@ class VMServer(messageHandler: MessageHandler) extends Logger {
messageHandler.close()
}

// scalastyle:off method.length
private def constructContextFromMsg(contextMsg: msg.CallContext): ProgramContext[World, Storage] = {
import ByteString.{empty => irrelevant} // used for irrelevant BlockHeader fields

Expand Down Expand Up @@ -136,6 +139,10 @@ class VMServer(messageHandler: MessageHandler) extends Logger {
val recipientAddr: Option[Address] =
Option(contextMsg.recipientAddr).filterNot(_.isEmpty).map(bytes => Address(bytes: ByteString))

val (warmAddresses: Set[Address], warmStorage: Set[(Address, BigInt)]) = contextMsg.extraData.accessList
.map(extractWarmAccessList)
.getOrElse((Set.empty[Address], Set.empty[(Address, BigInt)]))

ProgramContext(
callerAddr = contextMsg.callerAddr,
originAddr = contextMsg.callerAddr,
Expand All @@ -152,11 +159,19 @@ class VMServer(messageHandler: MessageHandler) extends Logger {
initialAddressesToDelete = Set(),
evmConfig = vmConfig,
originalWorld = world,
// TODO ETCM-1202 use access list from CallContext
warmAddresses = Set.empty,
warmStorage = Set.empty
warmAddresses = warmAddresses,
warmStorage = warmStorage
)
}
// scalastyle:on method.length

private def extractWarmAccessList(ald: AccessListData): (Set[Address], Set[(Address, BigInt)]) = {
val warmAddresses: Set[Address] = ald.addresses.toSet.map((bs: GByteString) => Address(bs: ByteString))
val warmStorage: Set[(Address, BigInt)] = ald.storageLocations.toSet.map { (se: StorageEntry) =>
(Address(se.address: ByteString), se.storageLocation: BigInt)
}
(warmAddresses, warmStorage)
}

private def buildResultMsg(result: ProgramResult[World, Storage]): msg.CallResult = {

Expand Down
1 change: 1 addition & 0 deletions src/test/scala/io/iohk/ethereum/extvm/VMClientSpec.scala
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,7 @@ class VMClientSpec extends AnyFlatSpec with Matchers with MockFactory {
constantinopleBlockNumber = forkBlockNumbers.constantinopleBlockNumber,
petersburgBlockNumber = forkBlockNumbers.petersburgBlockNumber,
istanbulBlockNumber = forkBlockNumbers.istanbulBlockNumber,
berlinBlockNumber = forkBlockNumbers.berlinBlockNumber,
maxCodeSize = blockchainConfig.maxCodeSize.get,
accountStartNonce = blockchainConfig.accountStartNonce,
chainId = ByteString(blockchainConfig.chainId)
Expand Down
2 changes: 1 addition & 1 deletion src/test/scala/io/iohk/ethereum/extvm/VMServerSpec.scala
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ class VMServerSpec extends AnyFlatSpec with Matchers with MockFactory {
chainId = ByteString(blockchainConfig.chainId)
)
val ethereumConfigMsg: Hello.Config.EthereumConfig = msg.Hello.Config.EthereumConfig(ethereumConfig)
val helloMsg: Hello = msg.Hello(version = "2.1", config = ethereumConfigMsg)
val helloMsg: Hello = msg.Hello(version = "2.2", config = ethereumConfigMsg)

val messageHandler: MessageHandler = mock[MessageHandler]
val vmServer = new VMServer(messageHandler)
Expand Down