This repository was archived by the owner on Jan 22, 2025. It is now read-only.
Refactoring: Move KeyedAccounts to InvokeContext#15410
Merged
Lichtso merged 33 commits intosolana-labs:masterfrom Apr 19, 2021
Merged
Refactoring: Move KeyedAccounts to InvokeContext#15410Lichtso merged 33 commits intosolana-labs:masterfrom
Lichtso merged 33 commits intosolana-labs:masterfrom
Conversation
c9e3da2 to
84fbeb5
Compare
Codecov Report
@@ Coverage Diff @@
## master #15410 +/- ##
=========================================
- Coverage 83.0% 83.0% -0.1%
=========================================
Files 415 415
Lines 114701 114852 +151
=========================================
+ Hits 95265 95375 +110
- Misses 19436 19477 +41 |
Contributor
|
(I'm mailed Travis CI support about the missing status here, no need to block this PR on them) |
dde5ee0 to
9e6812d
Compare
47625d8 to
4f27d01
Compare
0f8ac54 to
0f9652c
Compare
0f9652c to
2571c4f
Compare
…ader_upgradeable_instruction().
…ader_instruction() and in bpf_loader::Executor::execute().
…struction(), bpf_loader::process_instruction_jit() and bpf_loader::process_instruction_common().
…al to the keyed_accounts parameter.
…:create_pre_accounts() in InvokeContext::new().
…ccounts() into create_keyed_accounts_unified(). Throws instead CallDepth of GenericError at invoke_stack.last().ok_or(). Renames program => executable.
41aec06 to
0689763
Compare
This was referenced Jun 2, 2021
Closed
This file contains hidden or 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
Sign up for free
to subscribe to this conversation on GitHub.
Already have an account?
Sign in.
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.
Problem
keyed_accountsare currently passed as a parameter everywhere, but they need to be managed in one place so that their allocation scheme can be changed.Summary of Changes
Collects all parametric occurrences and the construction of
keyed_accountsand puts them intoInvokeContext.Progress and Open Issues
next_keyed_account()vs.keyed_account_at_index()The replacement of
next_keyed_accountbykeyed_account_at_indexis necessary in order to drop references ofkeyed_accountsand retrieve them after function calls which involve passinginvoke_context. The reference inside the iterator ofkeyed_accountswould lead to a collision of borrows otherwise. Ideas of alternative approaches are welcome!Pro
Indices are better because they:
.next().Contra
Quoting @garious:
Neutral
Quoting @jackcmay:
The tale of MessageProcessor::process_cross_program_instruction
The main problem is getting the
KeyedAccounts into theInvokeContextthrough the stack push. This is hard as there are two references inside theKeyedAccountstruct:key: &'a Pubkeyaccount: &'a RefCell<AccountSharedData>Both give the
KeyedAccountstruct the lifetime'a. Now, in oder to push the newKeyedAccounts into theInvokeContextwe need to prove to the borrow checker that the newKeyedAccounts will live as long asInvokeContextdoes. We can't just recycle the existingKeyedAccounts, as they also have two other fieldsis_signerandis_writablewhich can be different at every invocation level.Lifetime of KeyedAccounts
Because the
InvokeContextis a trait we can not alias the lifetime of its implementation with thepushmethod directly. Instead the constructor of theKeyedAccounts has to be called from inside the specific implementations of the trait so that the two lifetimes correctly alias.Lifetime of Account keys
The
keys can not be borrowed fromVec<PreAccount>as theVecis owned byselfinside ofThisInvokeContext. Instead they must be borrowed frommessage.account_keyslike it is done in create_keyed_accounts.Lifetime of Account RefCells
While the
keys of theKeyedAccounts can be borrowed from the existing ones, theAccounts are created on the Rust stack at these three locations:So we have to
unsafe { transmute }the lifetime to get them into theInvokeContext. This is possible as we know that the stack frame will be popped again before the original reference goes out of scope.Otherwise, if we instead correctly bind the existing
Accounts to the newKeyedAccounts verify_and_update will sound alarm as the inner instruction supposedly changed theAccounts of the outer one.Future Work (for subsequent PRs)
Accounts into the BPF VM usingMemoryRegionsKeyedAccountsis_writableflag to make some readonlyPreAccounts from theInvokeContextas theAccounts are readonly anywaysunsafe { transmute }which was introduced in this PR