HIP-631: Account Virtual Addresses
Author | Nana Essilfie-Conduah |
---|---|
Working Group | Danno Ferrin, Richard Bair, Michael Tinker, Ashe Oro, Greg Scullard, Luke Lee |
Discussions-To | https://github.com/hashgraph/hedera-improvement-proposal/discussions/637 |
Status | Accepted ⓘ |
Needs Council Approval | Yes ⓘ |
Review period ends ⓘ | Tue, 10 Jan 2023 07:00:00 +0000 |
Type | Standards Track ⓘ |
Category | Service ⓘ |
Created | 2022-11-28 |
Updated | 2023-02-03 |
Requires | 583 |
Table of Contents
- Abstract
- Motivation
- Rationale
- User stories
- Specification
- HAPI Changes
- Transaction signing with matching simple key
- Contract account virtual address
- Community product impacts
- Backwards Compatibility
- Security Implications
- How to Teach This
- Reference Implementation
- Rejected Ideas
- Open Issues
- References
- Copyright/license
Abstract
The Hedera Smart Contract Service (HSCS) supports the execution of EVM transactions in a fast and cheap manner, while striving for strict EVM equivalency. Hedera also supports a rich set of “native” APIs (the HAPI or Hedera API). At times, Hedera and Ethereum have made different design decisions. To support EVM equivalency on Hedera, this HIP proposes a solution to one of these design points.
In Hedera, accounts are persistent entities with keys, and those keys can rotate over time. In Ethereum, keys and accounts are synonymous, and the only way to rotate keys is to rotate accounts. This HIP proposes a new concept, that of “Virtual Addresses”, which bridge the conceptual gap between Hedera’s view of accounts, and Ethereum’s.
For easy reference new and clarifying terms are listed below.
-
ETH contracts: An EVM contract currently deployed to Ethereum or other EVM compatible ledgers in which a maintainer does not have to change code in any way before deploying to Hedera. This code may include the use of precompile contract operations such as
ECRECOVER
. -
Hedera contracts: Smart Contracts implemented with Hedera-specific extensions such as HTS integration.
-
Hedera address: Also known as the
long-zero
address (as noted in HIP 583) account identifier, this is the result of encoding the<shard>.<realm>.<num>
integer values into a 20 byte hex format to be conformant withECDSA
public addresses. -
Alias: An account alias can be an
ECDSA
/ED25519
public key (per HIP 32). Notably, in the past the alias was sometimes used to refer to anECDSA
public address, however, it should solely refer to a public key. -
Virtual Addresses: a list of ECDSA public addresses that are stored on the account entity and serve as the account identifier on the EVM for transactions.
Most of the challenges experienced to date around account interactions with smart contracts on the EVM can be summarized into 4 points.
- Account type compatibility: All Hedera accounts are not equally EVM compatible. Currently only accounts with an
ECDSA
public key and anECDSA
alias are fully EVM compatible. This is due to the underlyingECDSA
signature type which allows for EVM account address (public address - as noted in HIP 583) calculation. This negatively affects smart contract adoption for all other account types and results in EVM experience inconsistencies. - Account identifier mismatches: EVM addresses currently differ for accounts with and without an ECDSA public key alias. Accounts with an
ECDSA
public key alias will have a public address when interacting with the EVM. Accounts without anECDSA
public key alias will have their Hedera address used. In both cases the address is potentially stored in the contract state and utilized for future operation matching. - Potential feature and asset loss: An account created with a ECDSA public key that has a corresponding public key alias where the account public key (tied to a cryptographic signing key) rotates no longer conforms to the EVM signature assumptions. That is smart contracts that extract the public address from the transaction signature will not be able to confirm that the sender address matches the extracted public address - this is the
ECRECOVER
precompile flow. This may result in loss of smart contract balance and permissions as smart contracts may no longer behave as expected. - Complicated flows: Education around the current EVM address possibilities is confusing and sometimes relies on uninformed users adopting complex technical solutions. This spans from the fundamental ethos difference where Ethereum holds that
Account ⇒ ECDSA public key ⇒ evmAddress
with a focus onevmAddress
, whereas Hedera notes that Accounts contain a public key and anevmAddress
with a focus on the Account.
The above has contributed to complicated Smart Contract considerations and slow adoption.
This HIP proposes a way to rationalize a Hedera account with its features and identifiers together with standard EVM features and account identifiers. This presents a step towards EVM equivalence over EVM compatibility.
Motivation
We want all accounts to be fully Smart Contract and EVM compatible without sacrificing Hedera feature functionality.
Users familiar with EVMs should be able to maintain their standard EVM expectations (EVM equivalence) but be presented with additional possibilities unique to the Hedera network.
This should be with no little to no overhead for users, minimal efforts to devs and with no possibility of loss of assets in any migrations.
Rationale
On Hedera a complete and functioning account can be identified at a point in time by
- an account identifier
shard.realm.num
(dictated by the next available entity counter) - a modifiable cryptographic public signing key
- an optional static public key account identifier i.e. alias.
This differs from the EVM view where an account can always be identified by a single public address (as noted in HIP 583) derived from an ECDSA cryptographic public signing key. Here, it is not possible to dissociate an account from its public key as you can in Hedera.
This has made it challenging when a Hedera account needs to be represented on the EVM or when an EVM operation that relies on the public key to public address mapping is expected on the Hedera network. The alias concept from HIP 32 was modified to help alleviate this issue by providing a source for the EVM address that an account would adopt when executing EVM transactions. However, this had its limitations as it was not originally intended to encompass EVM address logic which is fundamentally based on ECDSA
keys and calculations of EVM account state.
In exploration of the challenges, the goal became to appropriately design a concept that encompassed both consistent identification but also maintained the expected cryptography requirement of ECDSA
keys that is engrained in the EVM
as defined by the Ethereum Yellow paper. For EVM equivalence, an account requires the ability to be identified in advance based on an ECDSA
public key derived public address, and the ability to sign transactions submitted with that ECDSA
key.
Notably, Hedera has provided a broader vision which allows pre-identification for both simple ED25519
and ECDSA
key types and allows for signing with simple or complex signatures natively.
It was also noted that due to Hedera’s support of key rotation and multiple keys, enterprises and security minded users would not want to give up this ability solely to gain full EVM compatibility.
Thus, the proposed solution is to allow an account to contain 1 or more evmAddress
values for ECDSA keys it owns that dictate how an account appears on the EVM. These addresses will be known as Virtual Addresses.
These evmAddress
values map to ECDSA
key pairs a user must prove ownership of. Ownership is proved by having the ECDSA private key sign the transaction that adds the ECDSA public key to the account. This dissociates the notion of account entity, public key and public address to allow for a clear separation of concern between Ethereum and Hedera styled development and user experiences.
The above diagram illustrates the sources of EVM identity and how they connect with key authorization. Initially public keys and aliases are tightly nit, changes in key values break expectations of EVM authorization checks on the alias derived address, therefore limiting an accounts key rotation options. With Virtual Addresses, keys remain the signing permission authority and can be changed but Virtual Addresses (not tied to the alias) provide the value for a transactions EVM address. This separates account identification logic allowing the preservation of EVM logic and assumptions, whiles allowing users to still capitalize on added Hedera features.
User stories
- As a user with non
ECDSA
keys invoking smart contracts I want my account to have a predictable address value when represented on theEVM
. - As a user with
ECDSA
keys invoking smart contracts regardless of alias value I want my account to have a predictable address value on the EVM as I would on Ethereum. - As an existing user with an
ECDSA
key but no alias I want to gain compatibility with smart contracts utilizingECRECOVER
as I would be on Ethereum. - As an existing user without an
ECDSA
key I want to interact with smart contracts that utilizeECRECOVER
whiles still maintaining my existing key for signing. - As an existing user I want to utilize Hedera key rotation functionality without losing compatibility with
ECRECOVER
or changing the Ethereum public address viewed by theEVM
. - As a user I want to be able to control the value of the account address the
EVM
will observe based on theECDSA
key pairs I own. - As a Hedera user, I want to add multiple EVM addresses to my existing account without needing to create a new Hedera account every time.
Specification
To resolve the issue of account EVM compatibility and identification the proposal is to add a list of Virtual Addresses to a Hedera account that are responsible for EVM
address logic.
To achieve this
- Hedera accounts can have a list of
evmAddress
values known as “Virtual Address” which govern the address the EVM observes for a given account transaction. - The Hedera network will process ownership by extracting the public key from the signature and comparing the calculated public address to the
evmAddress
passed in on addition of the virtual address and will maintain anevmAddress
→accountId
map thereafter. - Hedera Accounts can add, disable and remove virtual address entries as desired. Additionally, accounts can update their default virtual address.
- Each virtual address will have its corresponding nonce tracked and stored in state.
- The address seen by the EVM per transaction is either the default Hedera address or a verified virtual address specified.
- User accounts with a simple
ECDSA
key will be migrated to accounts with a single virtual address - Developers can utilize
HAPI
to specify EVM address overrides and retrieve account virtual address information. - Users with non-simple
ECDSA
keys can utilize anyevmAddress
matchingECDSA
key in their wallets when interacting with smart contracts to beECRECOVER
compatible. In some cases they may be able to authorize transaction submission. - Users can optionally update their simple account key structure to support signing of transactions using the matching ECDSA key pair that maps to an
evmAddress
added. - Contract accounts may utilize the
evmAddress
to store their address in accordance withCREATE
andCREATE2
EVM operations
The above diagram illustrates how an account may be created/updated to contain virtual addresses and how thesed details will be considered at transaction time when a node determines what account may be used for an EVM call.
Step 1: Alice submits a CryptoCreate or CryptoTransfer transaction specifying the public address of her ECDSA key pair and signing the transaction with her ECDSA private key. The result in both cases is that the network creates a new account with an assigned AccountId and a single virtual address.
Step 2: Alice may submit a CryptoUpdate to add or remove a virtual address. She may also perform a key update by specifying a public key (that maps to one of her virtual addresses) to be held in addition to her current key in a threshold key.
Step 3: Alice may submit a ContractCreate or ContractCall transaction for which the network will consult her account to determine the appropriate address to provide to the EVM.
HAPI Changes
Proto messages will need to be updated to represent the virtual address info in submissions and in record files exported
A VirtualAddress
message proto captures the evm address and whether it’s the default on the account
message VirtualAddress {
/**
* The 20-byte EVM address that is derived from the keccak-256 hash of a ECDSA_SECP256K1 primitive key.
*/
bytes address = 1;
/**
* Flag if this address should now be set or is the default address on the account
*/
bool is_default = 2;
}
Update AccountID
with evm_address
to separate it from alias
message AccountID {
...
oneof account {
...
/**
* The ethereum account 20-byte EVM address to be used initially in place of the public key bytes. This EVM
* address may be either the encoded form of the shard.realm.num or the keccak-256 hash of a ECDSA_SECP256K1 primitive key.
*
* If a transaction lazily-creates this account, a subsequent transaction will be required containing the public key bytes
* that map to the EVM address bytes. Lazy account creates will only support the keccak-256 hash of a ECDSA_SECP256K1 primitive key form.
*/
bytes evm_address = 5;
}
}
Expose the virtual addresses in a CryptoGetInfo
response by updating AccountInfo
message AccountInfo {
...
message VirtualAddressInfo {
/**
* A virtual address entry.
*/
VirtualAddress virtual_address = 1;
/**
* The ethereum transaction nonce associated with this virtual address.
*/
int64 nonce = 2;
}
/**
* List of virtual addresses each of which is an EVM address that maps to an ECDSA key pair a user must prove ownership of and their corresponding nonce value.
* The size will be bounded.
*/
repeated VirtualAddressInfo virtual_addresses = 24;
}
Note: Initially the number of virtual address an account can hold will be bounded first to 1, with an eventual expansion to 3 to support override scenarios and a final maximum of 10 as required. Future community use cases requiring unbounded support may update this HIP to explore and support unbounded cases.
Add the evm address to CryptoCreateTransactionBody
to support the lazy create flow and separate it from alias
message CryptoCreateTransactionBody {
...
/**
* EOA 20-byte address to create that is derived from the keccak-256 hash of a ECDSA_SECP256K1 primitive key.
*/
bytes evm_address = 20;
}
Add virtual_address_update
to CryptoUpdateTransactionBody
to support the addition and removal of virtual addresses
message CryptoUpdateTransactionBody {
...
oneof virtual_address_update {
/**
* The virtual address to be added.
*/
VirtualAddress add = 20;
/**
* The 20-byte EVM address of the virtual address that is being disabled and therefore removed from active use on the account.
*/
bytes disable = 21;
/**
* The 20-byte EVM address of the virtual address that is being removed from the account.
*/
bytes remove = 22;
/**
* The virtual address to be updated.
*/
VirtualAddress update = 20;
}
}
Update ContractCreateTransactionBody
and ContractCallTransactionBody
to support overriding the default virtual address
message ContractCreateTransactionBody {
...
/**
* The 20-byte EVM address (differs from account default) to use for the given transaction. This address must be owned by the account.
*/
bytes virtual_address_override = 21;
}
message ContractCallTransactionBody {
...
/**
* The 20-byte EVM address (differs from account default) to use for the given transaction. This address must be owned by the account.
*/
bytes virtual_address_override = 5;
}
Update ContractFunctionResult
with a map tracking all contract nonce updates during transaction execution
message ContractFunctionResult {
...
/**
* Map used to track contract nonces for all contracts that have participated in the transaction.
* The keys would have the different contract IDs and the values are the new nonce values.
*/
map<ContractID, int64> contract_nonces = 14;
}
Update the TranscationRecord
to expose a new virtual address update when not present in the transaction
message TransactionRecord {
...
/**
* The new default EVM address of the account created by this transaction.
* This field is populated only when the EVM address is not specified in the related transaction body.
*/
bytes evm_address = 21;
}
The following is a table of HAPI proto inputs and outputs to show case new/modified transaction calls and how details are exposed in record files
Transaction Type | Inputs (all keys and address map to valid ECDSA keys) | Account Exists | Record Output (VirtualAddressUpdate) | Description |
---|---|---|---|---|
ContractCreate | virtual_address_override | - | - | Contract create transaction with an override for the virtual address to be used |
ContractCall | virtual_address_override | - | - | Contract call transaction with an override for the virtual address to be used |
CryptoCreate | alias | N | evm_address = new | auto-create non-existing account with new virtual address. The provided virtual address will serve as the default virtual address for the account. |
key | N | evm_address = new | normal create non-existing account with new virtual address. The provided virtual address will serve as the default virtual address for the account. | |
evm_address | N | lazy-create non-existing account with new virtual address. The provided virtual address will serve as the default virtual address for the account. | ||
CryptoTransfer | accountId.alias | N | evm_address = new | transfer to non-existing account (auto-create with new virtual address). The provided virtual address will serve as the default virtual address for the account. |
accountId.alias | Y | - | transfer to existing | |
accountId.evmAddress | N | evm_address = new | transfer to non-existing account (lazy-create with new virtual address). The provided virtual address will serve as the default virtual address for the account. | |
accountId.evmAddress | Y | - | transfer to existing | |
CryptoUpdate | virtual_address_update.add.evmAddress = new, (optional) virtualAddress.isDefault = true | Y | - | Add virtual address to existing account. Pull details from transaction body (not populating record preserves space) |
virtual_address_update.disable = old | Y | - | Disable virtual address on existing account. Pull details from transaction body (not populating record preserves space) | |
virtual_address_update.remove = old | Y | - | Remove virtual address from existing account. Pull details from transaction body (not populating record preserves space) | |
EthereumTransaction | ethereum_data (tx.to = new) | N | evm_address = new | lazy-create non-existing account.The provided virtual address will serve as the default virtual address for the account. |
Update Account state
The HederaAccount
will need to be updated to support a list of 20-byte EVM address values and the default virtual address.
A matching set of change should be made to MerkleAccountState
public interface HederaAccount {
...
Set<ByteString> getVirtualAddresses();
void setVirtualAddresses(Set<ByteString> virtualAddresses);
ByteString getDefaultVirtualAddress;
void setDefaultVirtualAddress(ByteString virtualAddress);
void setVirtualAddressNonce(ByteString virtualAddress, long nonce);
long getVirtualAddressNonce(ByteString virtualAddress);
}
Note: To support a larger number of virtual addresses on query an additional CryptoGetAccountVirtualAddressesQuery
query type may be added to support a paid retrieval of the full list of virtual addresses.
message AccountGetVirtualAddressesQuery {
...
QueryHeader header = 1;
/**
* The account instance for which the virtual records should be retrieved
*/
AccountID accountID = 2;
}
message AccountGetVirtualAddressesResponse {
...
ResponseHeader header = 1;
message VirtualAddressInfo {
/**
* A virtual address entry.
*/
VirtualAddress virtual_address = 1;
/**
* The ethereum transaction nonce associated with this virtual address.
*/
int64 nonce = 2;
}
/**
* List of virtual addresses each of which is an EVM address that maps to an ECDSA key pair a user must prove ownership of and their corresponding nonce value.
*/
repeated VirtualAddressInfo virtual_addresses = 2;
}
Virtual address creation
The process of adding a virtual address requires authentication of the account, storage of the address and the update of a map to allow for easy searching using the address.
- Add a new
evmAddress
→accountId
map, for easy account lookups - Account creation
CryptoCreate
transactions with a simple ECDSA key will have its signature examined, the public key extracted from the signature and a corresponding Ethereum public addressevmAddress
calculated. For cases where a separate address is to be set the desired virtual address may be pulled fromCryptoCreateTransaction.evm_address
.CryptoTransfer
transactions to an Ethereum public addressevmAddress
will utilize thelazy-create
flow and create a Hollow account with a single virtual address.- In both transaction type cases the
evmAddress
→accountId
map is consulted for an existence check. Should the virtual address be absent then creation may be attempted and the map should be updated with theevmAddress
- Future transactions utilizing an
evmAddress
will verify a valid entry in the map or fail with an appropriate response code.
- Contract
ContractCall
/ContractCreate
smart contract transactions that result in new contract creation should add an Ethereum public addressevmAddress
forCREATE
&CREATE2
tocontract.account.virtualAddresses
. Contract addresses are calculated by the ledger based on internal state.- Contracts may only have 1 virtual address entry to ensure immutability in accordance with the Ethereum yellow paper. The network should prevent the update of a contracts virtual addresses.
- Export virtual address added in record for account and contract transactions
Note: Ethereum address values from know tools (such as Truffle and Hardhat) that have been exposed will be captured by a property file to prevent users from accidentally creating accounts with these breached addresses.
Note2: Account fee logic will incorporate the extra virtual address property to be stored in state.
Support virtual address list modification
The list of virtual addresses should support the ability to add, disable and remove entries.
To add a virtual address an account would submit a CryptoUpdateTransactionBody
with a virtual_address_update.add
containing the desired evmAddress. The transaction must be signed by the ECDSA private key that maps to the evm address being added.
To disable a virtual address an account would submit a CryptoUpdateTransactionBody
with a virtual_address_update.disable
containing the existing evmAddress. The transaction must be signed by the ECDSA private key that maps to the evm address being disabled.
To remove a virtual address an account would submit a CryptoUpdateTransactionBody
with a virtual_address_update.remove
containing the existing evmAddress. The transaction must be signed by the ECDSA private key that maps to the evm address being removed.
Note: Initially virtual addresses will only support addition. With maturity of the feature the ability to disable and eventually remove a virtual address will be explored.
Transaction EVM address value
The network will determine the appropriate Ethereum public address evmAddress
per transaction based on the following logic
- If no override
virtual_address_override
is provided- If a non null
defaultEvmAddress
exists it is provided to the EVM - If no
defaultEvmAddress
is present the Hedera address is provided to the EVM
- If a non null
- If an override
virtual_address_override
is provided- the
account.virtual_addresses
is verified forevmAddress
presence- If verified, transaction processing continues
- If not present the transaction fails
- The
evmAddress
→accountId
is verified for an entry- If verified, transaction processing continues
- If not present the transaction fails
- the
Alias to Virtual Account Migration
To dissociate the alias concept from EVM public addresses and to reduce the overhead on users the network should perform a state migration for accounts and contracts
Aliased accounts
Migrate accounts with ECDSA aliases or hollow accounts
First migrate accounts with an explicit alias
- An
evmAddress
→accountId
map is created to resolve future virtual address references - Traverse all alias accounts from
alias
->accountId
map - If
alias
is not an ECDSA key or 20 byte addressevmAddress
or ifaccountId
is not for typeACCOUNT
then skip - If alias is an ECDSA key calculate the 20-byte
evmAddress
public address value - Check if
evmAddress
→accountId
map contains an entry. If present skip - Perform
CryptoUpdate
withvirtual_address_update.add.evm_address = evmAddress
andvirtual_address_update.add.is_default = true
- Migrate the
ethereum_nonce
of the account to the nonce of the virtual address - Add
evmAddress
toevmAddress
→accountId
map - Check
alias
→accountId
map for an entry. If present remove theevmAddress
from thealias
→accountId
map
Post migration the account creation logic should only update the alias
→ accountId
map with public keys and no longer utilize add the 20 byte address values. Additionally, no ECDSA based account should have a account.alias
with a public address format.
Note: In the migration, the first account with a specific key will be assigned the virtual address, all other accounts with the same key will be skipped.
Contracts
Migrate contracts with valid CREATE
or CREATE2
addresses
- Traverse all contract accounts
- Check
contract.alias
- If
contract.alias
is a Hedera address or empty then skip - Migrate the
ethereum_nonce
of the contract to the nonce of the virtual address - Add
evmAddress
toevmAddress
→accountId
map - Check
alias
→accountId
map for an entry. If present remove theevmAddress
from thealias
→accountId
map
Optionally ECDSA accounts without an alias
- Traverse all accounts in ASC order of AccountID
- If
account.key
is not a simple ECDSA key skip - Calculate the 20-byte
evmAddress
public address value - Check if
evmAddress
→accountId
map contains an entry. If present skip - Perform
CryptoUpdate
withvirtual_address_update.add.evm_address = evmAddress
andvirtual_address_update.add.is_default = true
- Migrate the
ethereum_nonce
of the account to the nonce of the virtual address - Add
evmAddress
toevmAddress
→accountId
map
Note: This migration will not be performed initially and will be done at some later stage. Note 2: This migration must be done after aliases or hollow account migration above.
Connect to Hedera via Virtual Address ECDSA key
An account should be searchable by its virtual addresses fi applicable.
Search by evmAddress
will be supported by consulting the evmAddress
→ AccountId
map on queries. Similarly, if an ECDSA
public key is provided instead, the network should support extraction of the public address and subsequent search by the retrieved value. This will expand account import options in wallets and allow for account info retrieval in more scenarios.
Transaction signing with matching simple key
There will be cases where users may have a simple key (ECDSA
or ED25519
) that does not correlate to the virtual address used in a transaction that requires ECDSA
key signing. In this case users may want to utilize their virtual address key whiles maintaining the existing simple key(s) they have on their account.
To support such mobility cases, where the security implications make sense a user may update their simple key to a 1 of n threshold key. In this way users can sign transactions with their initial simple key or their desired ECDSA
simple key that maps to an evmAddress.
For example an early adopter of Hedera will most certainly have an ED25519
key on their account. In this way they would not be able to successfully call smart contract transactions that utilize ECRECOVER
. With the addition of a virtual address they are 1 step closer to being able to support this scenario but still do not match the ECDSA
key signing requirements. In this case the user may update their ED25519
key to a 1 of 2 threshold key where transactions may be signed by either the ED25519
or ECDSA
private key the user has control over.
In this scenario it can be seen as a safe security modification, however this should be up to the discretion of the user.
Note: This scenario is reserved for simple key cases only. It is strongly advised that users do not modify complex keys to be a 1 of n in which the complex key is on one of the options as this dilutes the original security architecture.
Contract account virtual address
With the addition of virtual addresses and the separation of alias, network logic allows a contract account to represent its contract address with its virtual address.
Community product impacts
SDK Impacts
To support these updates the SDK will need to update the available methods on some transactions
-
CryptoUpdate
transactions will need support to add/disable/remove and specify defaultevmAddress
.new CryptoUpdate .addVirtualAddress('0x...') // String .disableVirtualAddress('0x...') // String .removeVirtualAddress('0x...') // String .setDefaultVirtualAddress('0x...'); // String
-
ContractCreate
/ContractCall
will require the ability to specify the desiredevmAddress
per transaction. Note this may also be an accounts Hedera address to support migration cases.new ContractCreate .setVirtualAddressOverride('0x...'); // String new ContractCall .setVirtualAddressOverride('0x...'); // String
Note: This does not impact the final contract address, which will be dictated by CREATE
or CREATE2
operations.
Mirror Node Impacts
As the historic ledger of Hedera, the Mirror Node will require additional steps and updated assumptions to support Virtual Addresses.
- Aliases will be simplified in their format as post migration they will always have a simple
ECDSA
/ED25519
key value. That is the alias returned inCryptoCreate
records will no longer take the format of a public address and will always be the protobuf value of a simple key. In this way some DB or service considerations may be simplified. - Accounts will observe a new property
virtualAddressesList
. This will be a set of 20-byte hex addresses the account is associated with, with each value mapping to the same AccountId. -
To support search, the Mirror Node should support a
evmAddress
→accountId
lookup. Utilizing the current table strategy a current and history table could be employed i.e.account_virtual_addresses
andaccount_virtual_addresses_history
.create type virtual_address_status as enum ('ACTIVE', 'DISABLED', 'DELETED'); create table if not exists account_virtual_address ( evm_address bytea null, id int not null, modified_timestamp bigint not null, status virtual_address_status not null default 'ACTIVE', primary key (id, modified_timestamp, evm_address) );
- Update entity table with a
default_virtual_address
column to capture the default virtual address. -
To expose this the Mirror Node should update
api/v1/accounts/{idOrAliasOrEvmAddress}
to list both the Hedera Address (long-zero
) and its virtual addresses. This will disambiguate the potential addresses. Additionally, the endpoint should support search via Hedera or evm address.{ accounts: '0.0.1', ..., hederaAddress: '0x0...1', virtualAddresses: [ { evmAddress: '0x2...3', isDefault: false }, { evmAddress: '0x4...5', isDefault: true } ] }
Note: Should the network need to expand a larger number of virtual addresses an additional api/v1/accounts/<accountId>/virtualAddresses
endpoint may be added to encompass an endpoint that supports paging the full list of virtual addresses.
note 2: The REST API should only display active i.e. non disabled virtual addresses associated with an account.
Wallet/Exchange Impacts
Wallets and exchanges continue to serve as the entry point for account user creation. In this way they should utilize new functionality for their purposes and to allow users to transact easily
- Search accounts by virtual / Hedera address using Mirror Node or SDK.
- Import
ECDSA
private keys. In the past ED keys were the main type but with an influx of users from EVM chainsECDSA
support will be important. - Transfer to virtual / Hedera address using SDK or JSON RPC relay.
- Expose account details Hedera address and
virtualAddresses
.
Multiple personas exist for which wallets need to explore support to ensure vibrancy of the smart contract scenarios.
An additional option exists for wallets that use a seed phrase to generate keys i.e HDWalllet - the same seed phrase can create both an ED25519
and an ECDSA
key. In this way wallets may create a new account, establish a 1 of 2 threshold key in which users may utilize any key to sign. This provides users with options, namely ECRECOVER
support from creation. Additionally, users can recover both keys that may be regularly utilized.
Notably, wallets may also explore ETH native flows by supporting RLP transaction encoding and utilizing the HAPI EthereumTransaction
. This would increase their support across other chain DApps which could now be pointed to Hedera and allow for in wallet and native scenarios that are faster, cheaper and more scalable on Hedera.
Mirror Node Explorer Impacts
The Mirror Node explorers will continue to provide for many the go to source of account and ledger details. In this way the explorers should support
- Search by virtual / Hedera address - utilize the Mirror Node
- Expose account details Hedera address and
virtualAddresses
Backwards Compatibility
This HIP builds upon HIP 584 and also restores HIP 32’s consistency.
Accounts identifiers and feature applicability are unrestrained to apply in more scenarios with less crossover.
Security Implications
The addition and removal of virtual addresses relies on the current Hedera methodology of signing transactions with the account private key. As such the network is able to confirm ownership of the evmAddress. Additionally, the ledger will ensure uniqueness of evmAddress and will ensure only 1 account will have the address.
Additionally, the use of an evmAddress provides no authorization for Hedera transaction functionality.
As such the ledger and the EVM maintain their authorization capabilities.
As always users and developers are responsible for key hygiene and proper storage of keys.
How to Teach This
- Additional documentation on protobufs
- SDK examples should be written to highlight
Crypto
Update to add and remove virtual addresses
- Mirror Node
- Open API spec should be updated for
/api/v1/accounts/{accountIdOrEVmAddress}
- DB documentation should be updated to highlight new table(s)
- Open API spec should be updated for
- Doc site tutorials utilizing SDKs should be written to highlight alias setting and the lazy account creation flow.
Reference Implementation
Rejected Ideas
The continuous conflict of pure Ethereum account matra vs Hedera Account layout resulted in multiple ideas being considered but ultimately rejected. These included
- A special reserved
ECDSA
basedaliasKey
on all accounts. This would have ensured only a single key was used on contract interactions. - A special reserved
ECDSA
basedaliasKey
and an additionalevmAlias
. This would have provided complete separation of all EVM interactions with Hedera account keys. - Requiring nested signing similar tot he relay in which an out HAPI transaction has the Hedera signatures and an inner EVM transaction has the appropriate transaction with the EC public address
Open Issues
- Should virtual address transfer between accounts be supported? In this way an account could remove an address and on a separate account add the same virtual address?
- Should
ETH contracts
be better phrased asEVM contracts
?
References
Copyright/license
This document is licensed under the Apache License, Version 2.0 – see LICENSE or (https://www.apache.org/licenses/LICENSE-2.0)
Citation
Please cite this document as: