Wasmtime: fix stack walking across frames from different stores#4779
Merged
Conversation
Subscribe to Label Actioncc @peterhuene DetailsThis issue or pull request has been labeled: "wasmtime:api"Thus the following users have been cc'd because of the following labels:
To subscribe or unsubscribe from this label, edit the |
alexcrichton
approved these changes
Aug 30, 2022
Member
alexcrichton
left a comment
There was a problem hiding this comment.
Nice catch on this one! All makes sense and the fix here looks good to me.
I am a bit worried about how much code is being grown over time though to manage all these lists of registers going in/out of wasm. I suspect that this is becoming a growing portion of the time spent calling into wasm since there's so many branches and memory reads/writes. For now I think it's fine but I also don't know how we would improve the situation unfortunately.
We were previously implicitly assuming that all Wasm frames in a stack used the
same `VMRuntimeLimits` as the previous frame we walked, but this is not true
when Wasm in store A calls into the host which then calls into Wasm in store B:
| ... |
| Host | |
+-----------------+ | stack
| Wasm in store A | | grows
+-----------------+ | down
| Host | |
+-----------------+ |
| Wasm in store B | V
+-----------------+
Trying to walk this stack would previously result in a runtime panic.
The solution is to push the maintenance of our list of saved Wasm FP/SP/PC
registers that allow us to identify contiguous regions of Wasm frames on the
stack deeper into `CallThreadState`. The saved registers list is now maintained
whenever updating the `CallThreadState` linked list by making the
`CallThreadState::prev` field private and only accessible via a getter and
setter, where the setter always maintains our invariants.
efebd1d to
bde52b9
Compare
fitzgen
added a commit
to fitzgen/wasmtime
that referenced
this pull request
Aug 31, 2022
…codealliance#4779) We were previously implicitly assuming that all Wasm frames in a stack used the same `VMRuntimeLimits` as the previous frame we walked, but this is not true when Wasm in store A calls into the host which then calls into Wasm in store B: | ... | | Host | | +-----------------+ | stack | Wasm in store A | | grows +-----------------+ | down | Host | | +-----------------+ | | Wasm in store B | V +-----------------+ Trying to walk this stack would previously result in a runtime panic. The solution is to push the maintenance of our list of saved Wasm FP/SP/PC registers that allow us to identify contiguous regions of Wasm frames on the stack deeper into `CallThreadState`. The saved registers list is now maintained whenever updating the `CallThreadState` linked list by making the `CallThreadState::prev` field private and only accessible via a getter and setter, where the setter always maintains our invariants.
Member
Author
|
FYI this is being backported to the 0.40.X release branch in #4834 |
fitzgen
added a commit
that referenced
this pull request
Aug 31, 2022
* Wasmtime: fix stack walking across frames from different stores (#4779) We were previously implicitly assuming that all Wasm frames in a stack used the same `VMRuntimeLimits` as the previous frame we walked, but this is not true when Wasm in store A calls into the host which then calls into Wasm in store B: | ... | | Host | | +-----------------+ | stack | Wasm in store A | | grows +-----------------+ | down | Host | | +-----------------+ | | Wasm in store B | V +-----------------+ Trying to walk this stack would previously result in a runtime panic. The solution is to push the maintenance of our list of saved Wasm FP/SP/PC registers that allow us to identify contiguous regions of Wasm frames on the stack deeper into `CallThreadState`. The saved registers list is now maintained whenever updating the `CallThreadState` linked list by making the `CallThreadState::prev` field private and only accessible via a getter and setter, where the setter always maintains our invariants. * Remove unnecessary parens that cause a warning * Update release notes for 0.40.1
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 join this conversation on GitHub.
Already have an account?
Sign in to comment
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.
We were previously implicitly assuming that all Wasm frames in a stack used the same
VMRuntimeLimitsas the previous frame'sCallThreadState, but this is not true when Wasm in store A calls into the host which then calls into Wasm in store B:Trying to walk this stack would previously result in a runtime panic.
The solution is to push the maintenance of our list of saved Wasm FP/SP/PC registers that allow us to identify contiguous regions of Wasm frames on the stack deeper into
CallThreadState. The saved registers list is now maintained whenever updating theCallThreadStatelinked list by making theCallThreadState::prevfield private and only accessible via a getter and setter, where the setter always maintains our invariants.Thanks to @bnjbvr for reporting this bug!
@cfallin do you feel familiar enough with this stuff that you'd be comfortable reviewing it? If not, I can totally wait for Alex to come back from PTO.