-
Notifications
You must be signed in to change notification settings - Fork 717
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
LDC support in predicates #612
Merged
Merged
Changes from all commits
Commits
Show all changes
11 commits
Select commit
Hold shift + click to select a range
7df4517
Add LDC mode 2, which allows code from memory
Dentosal 9c122c8
Fix link to LDC
Dentosal fd5de5e
Rewrite predicate section
Dentosal d8d3910
Update headers
Dentosal 9270a2e
Fix formatting
Dentosal 5ddaee5
fmt
Dentosal 6aa02ac
Clarify padding behavior
Dentosal 697d0eb
Update src/fuel-vm/instruction-set.md
Dentosal e4ee95b
Update src/fuel-vm/instruction-set.md
Dentosal b1bacaf
Merge branch 'dento/ldc-mode-2' into dento/predicate-relax-limits
Dentosal edd52bf
Merge branch 'master' into dento/predicate-relax-limits
Dentosal File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change | ||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
@@ -7,9 +7,9 @@ | |||||||||||||||||||||
- [Instruction Set](#instruction-set) | ||||||||||||||||||||||
- [VM Initialization](#vm-initialization) | ||||||||||||||||||||||
- [Contexts](#contexts) | ||||||||||||||||||||||
- [Predicate Estimation](#predicate-estimation) | ||||||||||||||||||||||
- [Predicate Verification](#predicate-verification) | ||||||||||||||||||||||
- [Script Execution](#script-execution) | ||||||||||||||||||||||
- [Predicate Estimation and Verification](#predicate-estimation-and-verification) | ||||||||||||||||||||||
- [Script Execution](#script-execution) | ||||||||||||||||||||||
- [Call](#call) | ||||||||||||||||||||||
- [Call Frames](#call-frames) | ||||||||||||||||||||||
- [Ownership](#ownership) | ||||||||||||||||||||||
|
||||||||||||||||||||||
|
@@ -82,7 +82,7 @@ To initialize the VM, the following is pushed on the stack sequentially: | |||||||||||||||||||||
1. Transaction hash (`byte[32]`, word-aligned), computed as defined [here](../identifiers/transaction-id.md). | ||||||||||||||||||||||
1. Base asset ID (`byte[32]`, word-aligned) | ||||||||||||||||||||||
1. [`MAX_INPUTS`](../tx-format/consensus_parameters.md) pairs of `(asset_id: byte[32], balance: uint64)`, of: | ||||||||||||||||||||||
1. For [predicate estimation](#predicate-estimation) and [predicate verification](#predicate-verification), zeroes. | ||||||||||||||||||||||
1. For [predicate estimation and verification](#predicate-estimation-and-verification), zeroes. | ||||||||||||||||||||||
1. For [script execution](#script-execution), the free balance for each asset ID seen in the transaction's inputs, ordered in ascending order. If there are fewer than `MAX_INPUTS` asset IDs, the pair has a value of zero. | ||||||||||||||||||||||
1. Transaction length, in bytes (`uint64`, word-aligned). | ||||||||||||||||||||||
1. The [transaction, serialized](../tx-format/index.md). | ||||||||||||||||||||||
|
@@ -95,54 +95,39 @@ Then the following registers are initialized (without explicit initialization, a | |||||||||||||||||||||
|
||||||||||||||||||||||
## Contexts | ||||||||||||||||||||||
|
||||||||||||||||||||||
There are 4 _contexts_ in the FuelVM: [predicate estimation](#predicate-estimation), [predicate verification](#predicate-verification), [scripts](#script-execution), and [calls](./instruction-set.md#call-call-contract). A context is an isolated execution environment with defined [memory ownership](#ownership) and can be _external_ or _internal_: | ||||||||||||||||||||||
There are 4 _contexts_ in the FuelVM: [predicate estimation and verification](#predicate-estimation-and-verification), [scripts](#script-execution), and [calls](#call). A context is an isolated execution environment with defined [memory ownership](#ownership) and can be _external_ or _internal_: | ||||||||||||||||||||||
|
||||||||||||||||||||||
- External: predicate and script. `$fp` will be zero. | ||||||||||||||||||||||
- Internal: call. `$fp` will be non-zero. | ||||||||||||||||||||||
|
||||||||||||||||||||||
[Returning](./instruction-set.md#return-return-from-call) from a context behaves differently depending on whether the context is external or internal. | ||||||||||||||||||||||
|
||||||||||||||||||||||
## Predicate Estimation | ||||||||||||||||||||||
### Predicate Estimation and Verification | ||||||||||||||||||||||
|
||||||||||||||||||||||
For any input of type [`InputType.Coin`](../tx-format/index.md) or [`InputType.Message`](../tx-format/index.md), a non-zero `predicateLength` field means the UTXO being spent is a [`P2SH`](https://en.bitcoin.it/wiki/P2SH) rather than a [`P2PKH`](https://en.bitcoin.it/P2PKH) output. | ||||||||||||||||||||||
There are two ways to run predicates on the VM: | ||||||||||||||||||||||
|
||||||||||||||||||||||
For each such input in the transaction, the VM is [initialized](#vm-initialization), then: | ||||||||||||||||||||||
|
||||||||||||||||||||||
1. `$pc` and `$is` are set to the start of the input's `predicate` field. | ||||||||||||||||||||||
1. `$ggas` and `$cgas` are set to `MAX_GAS_PER_PREDICATE`. | ||||||||||||||||||||||
|
||||||||||||||||||||||
Predicate estimation will fail if gas is exhausted during execution. | ||||||||||||||||||||||
|
||||||||||||||||||||||
During predicate mode, hitting any of the following instructions causes predicate estimation to halt, returning Boolean `false`: | ||||||||||||||||||||||
|
||||||||||||||||||||||
1. Any [contract instruction](./instruction-set.md#contract-instructions). | ||||||||||||||||||||||
|
||||||||||||||||||||||
In addition, during predicate mode if `$pc` is set to a value greater than the end of predicate bytecode (this would allow bytecode outside the actual predicate), predicate estimation halts returning Boolean `false`. | ||||||||||||||||||||||
|
||||||||||||||||||||||
A predicate that halts without returning Boolean `true` would not pass verification, making the entire transaction invalid. Note that predicate validity is monotonic with respect to time (i.e. if a predicate evaluates to `true` then it will always evaluate to `true` in the future). | ||||||||||||||||||||||
|
||||||||||||||||||||||
After successful execution, `predicateGasUsed` is set to `MAX_GAS_PER_PREDICATE - $ggas`. | ||||||||||||||||||||||
|
||||||||||||||||||||||
## Predicate Verification | ||||||||||||||||||||||
1. Estimation: runs the predicate and updates the amount of gas used | ||||||||||||||||||||||
1. Verification: runs the predicate and verifies the amount of gas used matches the input | ||||||||||||||||||||||
|
||||||||||||||||||||||
For any input of type [`InputType.Coin`](../tx-format/input.md#inputcoin) or [`InputType.Message`](../tx-format/input.md#inputmessage), a non-zero `predicateLength` field means the UTXO being spent is a [`P2SH`](https://en.bitcoin.it/P2SH) rather than a [`P2PKH`](https://en.bitcoin.it/P2PKH) output. | ||||||||||||||||||||||
|
||||||||||||||||||||||
For each such input in the transaction, the VM is [initialized](#vm-initialization), then: | ||||||||||||||||||||||
|
||||||||||||||||||||||
1. `$pc` and `$is` are set to the start of the input's `predicate` field. | ||||||||||||||||||||||
1. `$ggas` and `$cgas` are set to `predicateGasUsed`. | ||||||||||||||||||||||
1. `$ggas` and `$cgas` are set to `MAX_GAS_PER_PREDICATE` for estimation, and `predicateGasUsed` for verification. | ||||||||||||||||||||||
|
||||||||||||||||||||||
Predicate verification will fail if gas is exhausted during execution. | ||||||||||||||||||||||
Predicate execution will fail if gas is exhausted during execution. | ||||||||||||||||||||||
|
||||||||||||||||||||||
During predicate mode, hitting any [contract instruction](./instruction-set.md#contract-instructions) causes predicate verification to halt, returning Boolean `false`. | ||||||||||||||||||||||
During predicate mode, hitting any [contract instruction](./instruction-set.md#contract-instructions) (except `ldc` with non-contract target) causes predicate verification to halt, returning Boolean `false`. | ||||||||||||||||||||||
|
||||||||||||||||||||||
In addition, during predicate mode if `$pc` is set to a value greater than the end of predicate bytecode (this would allow bytecode outside the actual predicate), predicate verification halts returning Boolean `false`. | ||||||||||||||||||||||
A predicate that halts without returning Boolean `true` would not pass verification, making the entire transaction invalid. Note that predicate return value is monotonic with respect to time (i.e. if a predicate evaluates to `true` then it will always evaluate to `true` in the future). | ||||||||||||||||||||||
|
||||||||||||||||||||||
A predicate that halts without returning Boolean `true` does not pass verification, making the entire transaction invalid. Note that predicate validity is monotonic with respect to time (i.e. if a predicate evaluates to `true` then it will always evaluate to `true` in the future). | ||||||||||||||||||||||
After successful execution, the run mode is determines the final step: | ||||||||||||||||||||||
|
||||||||||||||||||||||
After execution, if `$ggas` is non-zero, predicate verification fails. | ||||||||||||||||||||||
1. Estimation: `predicateGasUsed` is set to `MAX_GAS_PER_PREDICATE - $ggas`. | ||||||||||||||||||||||
1. Verification: if `$ggas` is non-zero, predicate verification fails. | ||||||||||||||||||||||
|
||||||||||||||||||||||
## Script Execution | ||||||||||||||||||||||
### Script Execution | ||||||||||||||||||||||
|
||||||||||||||||||||||
If script bytecode is present, transaction validation requires execution. | ||||||||||||||||||||||
|
||||||||||||||||||||||
|
@@ -157,6 +142,10 @@ For each instruction, its gas cost `gc` is first computed. If `gc > $cgas`, dedu | |||||||||||||||||||||
|
||||||||||||||||||||||
After the script has been executed, `tx.receiptsRoot` is updated to contain the Merkle root of the receipts, [as described in the `TransactionScript` spec](../tx-format/transaction.md#`TransactionScript`). | ||||||||||||||||||||||
|
||||||||||||||||||||||
### Call | ||||||||||||||||||||||
|
||||||||||||||||||||||
Call context is entered via [`CALL` instruction](./instruction-set.md#call-call-contract). It's also called _internal context_, or _contract context_. Call context is used to access state of a contract. | ||||||||||||||||||||||
|
||||||||||||||||||||||
## Call Frames | ||||||||||||||||||||||
Comment on lines
+145
to
149
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Maybe it is better to do like this?
Suggested change
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. No. |
||||||||||||||||||||||
|
||||||||||||||||||||||
Cross-contract calls push a _call frame_ onto the stack, similar to a stack frame used in regular languages for function calls (which may be used by a high-level language that targets the FuelVM). The distinction is as follows: | ||||||||||||||||||||||
|
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, it looks like before we should allow usage of blob instructions in the VM as well(because they are not contract instruction)=D So now it works as expected