0xMiden / 0xMiden/protocol

Smart Contract Diff Audit L-32: Assetless Notes Produce Transaction Scripts That Fail With Stack-Depth Errors

未关闭
#3,690 1 条评论 0 个 reaction 已指派 0 人 在 GitHub 查看
主要语言
Rust
星标
132
派生
167
平均合并
1 天 23 小时
30 天内合并 PR
110

描述

[`NoteAssets`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-protocol/src/note/assets.rs#L21-L28) allows a note to carry between zero and 64 assets, and several first-party standard notes, such as [`MintNote`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-standards/src/note/mint.rs#L191-L205), are built with an empty asset set. When a send-notes script is generated for an account exposing the basic wallet interface, [`move_asset_to_note_body`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-standards/src/tx_script/send_notes_script.rs#L155-L197) emits the sequence that restores the operand stack only inside the per-asset loop. The call to [`create_note`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-standards/asm/standards/note/note_creator.masm#L16-L30) leaves the stack deeper than the frame the script started with, [`push_attachments`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-standards/src/tx_script/send_notes_script.rs#L263-L279) is stack neutral, and [`finalize_note`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-standards/src/tx_script/send_notes_script.rs#L281-L289) removes a single element. A note that carries no assets therefore skips the loop entirely and ends five elements too deep, and every additional assetless note adds five more.

The transaction script is entered from the kernel with [`dyncall`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-protocol/asm/kernels/transaction/bin/main.masm#L153), and the virtual machine requires the body of a call to return at a stack depth of 16. A script generated for an assetless note consequently aborts on return with a stack-depth error instead of executing. The faucet branch of the generator rejects notes that do not carry exactly one asset through [`FaucetNoteWithoutAsset`](https://github.com/0xMiden/protocol/blob/8411bf093bde25285708faac152b6d7269009617/crates/miden-standards/src/tx_script/send_notes_script.rs#L207-L209), but the wallet branch applies no equivalent check, so an explicitly supported note shape is accepted at build time and fails at execution or proving time with an error that does not point at its cause. No adversary is involved and no state change occurs, since the failure surfaces locally before the transaction is applied.

Consider emitting the stack normalization unconditionally after note creation, outside the per-asset loop, so that the frame is restored regardless of how many assets the note carries. If assetless notes are not intended to be supported by this generator, consider rejecting them at build time with a dedicated error instead. In either case, consider extending the transaction script tests to cover notes with zero assets, including several such notes in a single script.

---

_Copied verbatim from finding [L-32](https://audits.openzeppelin.com/miden/miden-01-07-smart-contract-diff-audit-nfts/issues/assetless-notes-produce-transaction-scripts-that-fail-with-stack-depth-errors-353a7b31) (low severity) of the OpenZeppelin [smart contract diff audit (NFTs)](https://audits.openzeppelin.com/miden/miden-01-07-smart-contract-diff-audit-nfts). The audit was performed against commit `8411bf093bde25285708faac152b6d7269009617`._

贡献指南

打开贡献指南

评估

这个 Issue 还没有评估数据。

把新 issue 发到你的邮箱

精选适合新手参与的 GitHub issue 摘要。