From 38651e997128d71bf2891759d63e1923c6c8bf6d Mon Sep 17 00:00:00 2001 From: Eric Wong Date: Fri, 23 Sep 2022 11:28:50 -0500 Subject: [PATCH] evm: line edits --- src/technical/evm/bestPractices.md | 2 +- src/technical/evm/coreLayer.md | 15 ++++++++------- src/technical/evm/nftLayer.md | 2 +- src/technical/evm/overview.md | 2 +- src/technical/evm/tokenLayer.md | 28 ++++++++++++++-------------- 5 files changed, 25 insertions(+), 24 deletions(-) diff --git a/src/technical/evm/bestPractices.md b/src/technical/evm/bestPractices.md index d5d4f4b..5f88053 100644 --- a/src/technical/evm/bestPractices.md +++ b/src/technical/evm/bestPractices.md @@ -27,7 +27,7 @@ function emitMyMessage(address intendedRecipient, uint32 nonce) // that the correct contract is submitting this VAA. // 1 is the consistency level, - // this message will be emitted after only 1 confirmation + // this message will be emitted after only 1 block sequence = core_bridge.publishMessage(nonce, "My Message to " + intendedRecipient, 1); // The sequence is passed back to the caller, which can be useful relay information. diff --git a/src/technical/evm/coreLayer.md b/src/technical/evm/coreLayer.md index e39ad3d..7eda7b3 100644 --- a/src/technical/evm/coreLayer.md +++ b/src/technical/evm/coreLayer.md @@ -19,11 +19,11 @@ IWormhole core_bridge = IWormhole(wormhole_core_bridge_address); ## Primary functions -The Wormhole Core Layer effectively only has two important interactions -- (1) emit VAAs, and (2) parse and verify VAAs that originated from other chains. +The Wormhole Core Layer has two important interactions -- (1) emit VAAs, and (2) parse and verify VAAs that originated from other chains. ### Emitting a VAA -There are two forms that VAAs can be emitted within Wormhole: +There are two forms of VAAs that can be emitted: - Single VAA: all messages will be emitted in this format - Batch VAA: messages that are generated from the same transaction will be emitted in this format. This feature was developed to provide an easier paradigm for composability and better gas efficiency for more involved cross-chain activity. @@ -31,11 +31,9 @@ There are two forms that VAAs can be emitted within Wormhole: To emit a VAA, always use `publishMessage` which takes in the following arguments: 1. `nonce` (uint32): a number assigned to each message - - The `nonce` provides a mechanism by which to group messages together within a Batch VAA. - - How Batch VAAs are generated based on a message's `nonce` is described below. + - The `nonce` provides a mechanism by which to group messages together within a Batch VAA. How the `nonce` is used is described below. 2. `Consistency` (uint8): the number of blocks that Guardians will wait before signing a message - - Each blockchain has different finality periods. In general, higher consistencies mean more security against blockchain reorgs. - - [Here](../../reference/contracts.md) are the consistency levels by blockchain that are used by the xAsset layer to have a high level of guarantee against reorgs. + - Each blockchain has different finality periods based on the consensus mechanism. In general, higher consistency values provides more security against blockchain reorgs. [Here](../../reference/contracts.md) are the consistency levels by blockchain that are used by the xAsset layer to have a high level of guarantee against reorgs. 3. `Payload` (bytes[]): raw bytes to emit - It is up to the emitting contract to properly define this arbitrary set of bytes. @@ -83,8 +81,11 @@ To properly parse and verify a single VAA, always use `parseAndVerifyVM` which t 3. `reason` (string): Explanatory error message if a VAA is invalid, or an empty string if it is valid. **Batch VAA** + To properly parse and verify a batch VAA, always use `parseAndVerifyBatchVM` which takes in two arguments: `encodedVM` (bytes) and `cache` (bool). In most scenarios, you'll want to set `cache` equal to true. -This will return a VM2 object, containing all the 'headless' VAAs contained inside the batch VAA. These headless VAAs can be verified by `parseAndVerifyVM`, which means that modules which verify messages can be agnostic as to if the message was original part of a batch VAA or a single VAA. This is gone into in more depth in the [Best Practices](./bestPractices.md) section. +This will return a VM2 object, containing all the 'headless' VAAs contained inside the batch VAA. These headless VAAs can be verified by `parseAndVerifyVM`, which means that modules which verify messages in an xDapp can be agnostic as to whether a message came from a batch VAA or a single VAA. + +The [Best Practices](./bestPractices.md) section goes into more depth of how to interact with the coreLayer. diff --git a/src/technical/evm/nftLayer.md b/src/technical/evm/nftLayer.md index 5dc8c9b..5af25ce 100644 --- a/src/technical/evm/nftLayer.md +++ b/src/technical/evm/nftLayer.md @@ -36,7 +36,7 @@ transferNFT(tokenAddress, tokenID, recipientChain, recipient, nonce); ``` 2. Retrieve the emitted VAA from the Guardian Network. (Usually done by a relayer) - - _Note: NFT Transfer VAAs are retrieved from the Guardian Network by the `emitterChainID`, `emitterAddress`, and `sequence`_ + - NFT Transfer VAAs are retrieved from the Guardian Network by the `emitterChainID`, `emitterAddress`, and `sequence`. ```js const emitterAddr = getEmitterAddressEth(network.NFTBridgeAddress); diff --git a/src/technical/evm/overview.md b/src/technical/evm/overview.md index e5f1ebc..02f302f 100644 --- a/src/technical/evm/overview.md +++ b/src/technical/evm/overview.md @@ -2,7 +2,7 @@ **Disclaimer**: This section is written as a guide for how to use Wormhole for experienced EVM developers. If you are new to using the EVM ecosystem, it's recommended for you to get started with a tutorial like [this](https://ethereum.org/en/developers/docs/intro-to-ethereum/). -For our purposes, EVM refers to any blockchain in the Wormhole ecosystem that utilizes EVM contracts of Wormhole -- this includes blockchains beyond Ethereum such as Polygon or Avalanche, as well as EVM+ environments such as Acala. +Within the Wormhole ecosystem, EVM refers to any blockchain that utilizes EVM contracts of Wormhole -- this includes blockchains beyond Ethereum such as Polygon or Avalanche, as well as EVM+ environments such as Acala. At certain points, it may be easiest to integrate simply by referencing the implementation of the Wormhole contracts. The official implementation for the Wormhole contracts can be found [here](https://github.com/wormhole-foundation/wormhole/tree/dev.v2/ethereum). diff --git a/src/technical/evm/tokenLayer.md b/src/technical/evm/tokenLayer.md index 77ab6cd..3e0f52b 100644 --- a/src/technical/evm/tokenLayer.md +++ b/src/technical/evm/tokenLayer.md @@ -17,7 +17,7 @@ ITokenBridge token_bridge = ITokenBridge(wormhole_token_bridge_address); ## Registering New Tokens -Attesting a token from EVM needs to happen once per token. If a token is not attested, it will not be claimable until so. However, there are no restrictions to reattesting a token; doing so will update the metadata. +Attesting a token from EVM needs to happen once per token as it will not be claimable until so. However, there are no restrictions to reattesting a token; repeat attestations will update the metadata. It is not advised to attest tokens on-chain for most usecases. To attest a token by an off-chain process, you can either do it by hand through one of the Token Bridge UIs (for example [Portal](https://www.portalbridge.com/#/register)) or using the [Typescript SDK](https://www.npmjs.com/package/@certusone/wormhole-sdk). @@ -25,9 +25,9 @@ _[Here](../../development/portal/evm/attestingToken.md) is an example of how to ## Basic Transfer -Basic transfer should only be used if you are transferring messages to an end user wallet. If the end destination is a contract, you should only use Contract Controlled Transfers (described below). +Basic transfer should only be used if you are transferring tokens to an end user wallet. If the end destination is a contract, you should only use Contract Controlled Transfers (described below). -It is important to note the transferring native currency is a special case of the Basic Transfer. As such, a different function call is provided as a QoL improvement when initiating and completing the transfer messaging when unwrapping the ETH is desired. +It is important to note the transferring native currency is a special case of the Basic Transfer. As such, a different function call for initiating and completing a transfer is provided as a QoL improvement that will handle the wrapping and unwrapping of ETH. To transfer a token, there are four steps: @@ -40,7 +40,7 @@ contractAddress.approve(token_bridge_address, amt); 2. Transfer the token to create the transfer VAA. - This function call will return a `sequence` (uint64) that is used in the VAA retrieval step. - - _Note: Wormhole addresses are 32 bytes for standardization across the different blockchains within the Wormhole ecosystem._ + - _Note: For the recipient address, Wormhole addresses are 32 bytes for standardization across the different blockchains within the Wormhole ecosystem._ ``` // To initiate transfer of normal ERC-20s @@ -51,9 +51,9 @@ token_bridge.wrapAndTransferETH(recipientChain, recipient, arbiterFee, nonce); ``` 3. Retrieve the emitted VAA. - - _Note: Basic Transfer VAAs are retrieved from the Guardian Network by the `emitterChainID`, `emitterAddress`, and `sequence`_ + - Basic Transfer VAAs are retrieved from the Guardian Network by the `emitterChainID`, `emitterAddress`, and `sequence`. -``` +```js const emitterAddr = getEmitterAddressEth(network.tokenBridgeAddress); const seq = parseSequenceFromLogEth(tx, network.bridgeAddress); const vaaURL = `${config.wormhole.restAddress}/v1/signed_vaa/${network.wormholeChainId}/${emitterAddr}/${seq}`; @@ -77,15 +77,15 @@ completeTransferAndUnwrapETH(VAA); ## Contract Controlled Transfer -For any message transfers where the destination is a contract, you should always used Contract Controlled Transfers. +For any token transfers where the destination is a contract, you should always use Contract Controlled Transfers. There are a few main differences between Contract Controlled Transfers and Basic Transfers: -- message contains both tokens and an arbitrary payload -- can only be redeemed by a specified contract address -- does not have a relayer fee field because of the redemption restriction above. +- messages contains both tokens and an arbitrary payload +- messages can only be redeemed by a specified contract address +- messages do not have a relayer fee field because of the redemption restriction above -As was the case with Basic Transfers, transferring native currency is a special case for Contract Controlled Transfers as well. As such, a different function call is provided as a QoL improvement when initiating and completing the transfer messaging when unwrapping the ETH is desired. +As was the case with Basic Transfers, transferring native currency is a special case for Contract Controlled Transfers as well. As such, similar QoL improvement functions are provided that handle the wrapping and unwrapping of ETH. The process of sending a Contract Controlled Transfer is very similar to that of a Basic Transfer: @@ -98,7 +98,7 @@ contractAddress.approve(token_bridge_address, amt); 2. Transfer the token to create the transfer VAA. - This function call will return a `sequence` (uint64) that is used in the VAA retrieval step. - - _Note: Wormhole addresses are 32 bytes for standardization across the different blockchains within the Wormhole ecosystem._ + - _Note: For the recipient addres, Wormhole addresses are 32 bytes for standardization across the different blockchains within the Wormhole ecosystem._ ``` // To initiate transfer of normal ERC-20s @@ -109,9 +109,9 @@ token_bridge.wrapAndTransferETHWithPayload(recipientChain, recipient, nonce, pay ``` 3. Retrieve the emitted VAA. - - _Note: Basic Transfer VAAs are retrieved from the Guardian Network by the `emitterChainID`, `emitterAddress`, and `sequence`_ + - Contract Controlled Transfer VAAs are retrieved from the Guardian Network by the `emitterChainID`, `emitterAddress`, and `sequence`. -``` +```js const emitterAddr = getEmitterAddressEth(network.tokenBridgeAddress); const seq = parseSequenceFromLogEth(tx, network.bridgeAddress); const vaaURL = `${config.wormhole.restAddress}/v1/signed_vaa/${network.wormholeChainId}/${emitterAddr}/${seq}`;