Add AVM download progress indicators#4635
Conversation
|
@jamie-osec is attempting to deploy a commit to the OtterSec Team on Vercel. A member of the Team first needs to authorize it. |
| let url = format!( | ||
| "https://github.com/otter-sec/anchor/releases/download/v{version}/\ | ||
| anchor-{version}-{target}{ext}" | ||
| ); | ||
| let res = DOWNLOAD_CLIENT.get(&url).send()?; | ||
| match res.status() { | ||
| StatusCode::NOT_FOUND => bail!( | ||
| "No prebuilt binary found for version `{version}` (HTTP 404). Try `avm install \ |
There was a problem hiding this comment.
Missing Cryptographic Signature/Checksum Verification for Stable Releases and Solana-Verify Binaries in AVM
The Anchor Version Manager (avm) downloads stable release binaries of anchor-cli and the solana-verify utility directly from GitHub releases over HTTPS, but does not perform any cryptographic signature or checksum verification on the downloaded files before writing them to the disk and marking them as executable.
In contrast, nightly builds downloaded by avm are verified against a SHA256 checksum specified in the manifest.
Without integrity verification, if the GitHub repository, the releases page, or the transport layer is compromised (e.g., via a compromised CA, DNS spoofing, or malicious release assets), an attacker can supply a backdoored binary. avm will write this binary to ~/.avm/bin/ and execute it, leading to arbitrary code execution on the developer's machine.
Trace
graph TD
subgraph SG0 ["avm/src/lib.rs"]
download_progress_bar["Creates and configures an indicatif progress bar for download tracking."]
download_response_to_writer["Downloads an HTTP response body to a writer with a progress bar."]
download_response_to_vec["Downloads an HTTP response body into a byte vector."]
current_version_file_path["current_version_file_path"]
get_bin_dir_path["get_bin_dir_path"]
get_tmp_bin_dir_path["get_tmp_bin_dir_path"]
version_binary_path["version_binary_path"]
current_version["current_version"]
use_version["use_version"]
update["update"]
fetch_raw["fetch_raw"]
append_commit["append_commit"]
get_anchor_version_from_commit["get_anchor_version_from_commit"]
install_version{{"Installs a specific version of the Anchor CLI by downloading or building from source."}}
solana_verify_installed["solana_verify_installed"]
install_solana_verify["Downloads and installs the solana-verify tool binary."]
install_solana_verify_from_source["install_solana_verify_from_source"]
read_anchorversion_file["read_anchorversion_file"]
read_installed_versions["read_installed_versions"]
end
style SG0 fill:#2a2a2a,stroke:#444,color:#aaa
install_version --> download_response_to_vec
install_version --> current_version_file_path
install_version --> get_tmp_bin_dir_path
install_version --> version_binary_path
install_version --> current_version
install_version --> use_version
install_version --> get_anchor_version_from_commit
install_version --> solana_verify_installed
install_version --> install_solana_verify
install_version --> install_solana_verify_from_source
install_version --> read_installed_versions
download_response_to_vec --> download_response_to_writer
version_binary_path --> get_bin_dir_path
current_version --> current_version_file_path
use_version --> current_version_file_path
use_version --> install_version
use_version --> read_anchorversion_file
use_version --> read_installed_versions
get_anchor_version_from_commit --> fetch_raw
get_anchor_version_from_commit --> append_commit
solana_verify_installed --> get_bin_dir_path
install_solana_verify --> download_response_to_vec
install_solana_verify --> get_bin_dir_path
read_installed_versions --> get_bin_dir_path
download_response_to_writer --> download_progress_bar
update --> install_version
Fix with AI
A security vulnerability was found by Hacktron.
File: avm/src/lib.rs
Lines: 561-580
Severity: medium
Vulnerability: Missing Cryptographic Signature/Checksum Verification for Stable Releases and Solana-Verify Binaries in AVM
Description:
The Anchor Version Manager (`avm`) downloads stable release binaries of `anchor-cli` and the `solana-verify` utility directly from GitHub releases over HTTPS, but does not perform any cryptographic signature or checksum verification on the downloaded files before writing them to the disk and marking them as executable.
In contrast, nightly builds downloaded by `avm` are verified against a SHA256 checksum specified in the manifest.
Without integrity verification, if the GitHub repository, the releases page, or the transport layer is compromised (e.g., via a compromised CA, DNS spoofing, or malicious release assets), an attacker can supply a backdoored binary. `avm` will write this binary to `~/.avm/bin/` and execute it, leading to arbitrary code execution on the developer's machine.
Affected Code:
- In [anchor/avm/src/lib.rs](./anchor/avm/src/lib.rs:561-580), `install_version` downloads stable releases without verification:
```rust
let url = format!(
"https://github.com/otter-sec/anchor/releases/download/v{version}/\
anchor-{version}-{target}{ext}"
);
let res = DOWNLOAD_CLIENT.get(&url).send()?;
...
let bin_path = version_binary_path(&version);
let bytes = download_response_to_vec(res, format!("Downloading anchor {version}"))?;
fs::write(&bin_path, bytes)?;
```
- In [anchor/avm/src/lib.rs](./anchor/avm/src/lib.rs:647-662), `install_solana_verify` downloads `solana-verify` without verification:
```rust
let url = format!(
"https://github.com/Ellipsis-Labs/solana-verifiable-build/releases/download/v{SOLANA_VERIFY_VERSION}/solana-verify-{os}"
);
let res = DOWNLOAD_CLIENT.get(&url).send()?;
...
let bin_path = get_bin_dir_path().join("solana-verify");
let bytes = download_response_to_vec(
res,
format!("Downloading solana-verify {SOLANA_VERIFY_VERSION}"),
)?;
fs::write(&bin_path, bytes)?;
```
Acceptance criteria:
- Acceptance is defined by the **actual reported behavior**, not by tests passing.
- Reproduce the issue, or narrow the exact code path that produces it, *before* changing code. State what you confirmed.
- Fix the underlying cause. Mitigations that paper over the reported behavior do not count as a fix.
- Add a regression test that fails on the unpatched code and passes on the fix. If a regression test is genuinely impractical (e.g. race condition, infra-level issue), say so and explain why.
- Existing tests passing is **not** the bar. Do not declare done on tests-pass theatre.
Only change what is necessary to fix this vulnerability. Do not refactor adjacent code or modify unrelated files.
Triage: Reply !fp <reason> (false positive), !valid (confirmed), or !accepted_risk <reason>. Any other reply is saved as a triage note.
Reason is optional but improves future scans — e.g. !fp internal endpoint, not user-facing.
No description provided.