Back to skill

Security audit

IQDB

Security checks for vulnerabilities and agentic risk

Overview

The skill is purpose-aligned for Solana on-chain storage, but it gives high-impact wallet, payment, and installer guidance with insufficient guardrails.

Review carefully before installing. Use a dedicated low-value devnet wallet first, protect any Solana keypair JSON as a private key, avoid storing secrets or personal data on-chain, pin and verify dependencies/installers where possible, and manually confirm payment recipient, amount, token, network, and service identity before signing any transaction.

Vulnerability Patterns
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Insecure DependenciesIntroduces malicious components through unsafe dependency sources
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
Findings (4)

T03 · Remote Payload Retrieval and Execution

Error
Location
references/setup.md:10
Finding
Remote Installer Is Downloaded and Executed Without Integrity Verification<![CDATA[ ## Vulnerability Details **File Location**: `references/setup.md:10` **Vulnerability Type**: Remote payload retrieval and immediate shell execution **Risk Level**: Critical ### Vulnerable Code ```bash # macOS/Linux sh -c "$(curl -sSfL https://release.anza.xyz/stable/install)" ``` ### Technical Analysis The setup instructions download content from a remote URL and pass the response directly to `sh`. The effective code executed on the user's system is therefore not contained in, pinned by, or reviewable from this Skill package. No release version, cryptographic checksum, or publisher signature is specified. HTTPS protects the connection in transit under normal circumstances, but it does not protect users if the distribution endpoint, publisher account, DNS infrastructure, certificate authority, or hosted installer is compromised. Executing a mutable remote response is not the minimum privilege necessary to install the Solana CLI. A release artifact can instead be downloaded, authenticated, inspected, and then executed separately. ### Attack Path 1. An attacker compromises the remote distribution endpoint or redirects requests to it. 2. The attacker replaces the legitimate installer response with a malicious shell payload. 3. A user follows the documented setup command. 4. `curl` downloads the attacker's current payload. 5. Command substitution supplies that payload directly to `sh`. 6. The payload executes with all permissions available to the user running the command. 7. It may read wallet files, environment variables, credentials, project files, or install additional persistence. ### Impact Assessment Successful exploitation provides arbitrary command execution with the invoking user's privileges. In the documented environment, this may expose Solana wallet keypair files and other credentials and may permit unauthorized transaction signing if the relevant keys are accessible. The payload could also alter local source code, install persisten ...[truncated 53 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Remove the command that executes a network response directly. 2. Pin installation instructions to a specific, reviewed Solana CLI release. 3. Download the release artifact to a local file without executing it. 4. Verify a hardcoded SHA-256 or stronger checksum obtained through an authenticated release channel. 5. Verify the publisher's cryptographic signature where supported. 6. Instruct users to inspect the downloaded installer before running it. 7. Run installation with ordinary user privileges and avoid `sudo` unless a specific step demonstrably requires it. 8. Document the expected artifact name, version, checksum, and signature-verification procedure. A safer workflow should follow this pattern: ```bash curl -fL -o solana-installer '<version-pinned-release-URL>' echo '<reviewed-sha256> solana-installer' | sha256sum --check - # Verify the publisher signature as well, if available. less solana-installer sh solana-installer ``` ]]>

T08 · Insecure Dependencies

Warning
Location
references/setup.md:36
Finding
Security-Sensitive npm Dependencies Are Installed Without Version Pinning<![CDATA[ ## Vulnerability Details **File Locations**: `skill.md:39`, `skill.md:44`, `references/setup.md:36`, `references/setup.md:44`, `references/hanlock.md:26` **Vulnerability Type**: Unpinned third-party dependencies and mutable supply-chain resolution **Risk Level**: Medium ### Vulnerable Code ```bash npm install @iqlabs-official/solana-sdk @solana/web3.js ``` ```bash npm install @iqlabsteam/iqdb @coral-xyz/anchor @solana/web3.js ``` ```bash npm install @iqlabsteam/iqdb @coral-xyz/anchor @solana/web3.js hanlock ``` ```bash npm install hanlock ``` ### Technical Analysis The installation commands omit exact package versions and the project contains no documented lockfile or integrity-pinned installation procedure. Consequently, installation resolves whatever package versions satisfy npm's current defaults at execution time rather than the releases reviewed when the Skill was authored. These packages are security-sensitive because the resulting code participates in wallet-backed Solana transactions, communicates with RPC services, and processes data intended for on-chain storage. npm packages may also execute lifecycle scripts during installation. A compromised publisher account, package release, transitive dependency, or registry response could therefore introduce executable code into the user's environment. This does not establish that the named packages are currently malicious. The vulnerability is the mutable and insufficiently authenticated dependency-resolution process. ### Attack Path 1. An attacker compromises a package publisher, registry account, or transitive dependency. 2. The attacker publishes a malicious release under one of the package names used by the instructions. 3. A user runs an unpinned `npm install` command. 4. npm resolves the malicious release because no exact reviewed version or lockfile constrains resolution. 5. Malicious lifecycle or runtime code executes locally. 6. The code may inspect wallet configuration, read acc ...[truncated 565 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Pin every direct dependency to an exact, reviewed version rather than a range or implicit latest release. 2. Generate and commit `package-lock.json`. 3. Use `npm ci` for reproducible installation instead of unconstrained `npm install`. 4. Review and retain lockfile integrity hashes. 5. Audit transitive dependencies and package ownership before upgrades. 6. Review package lifecycle scripts; use `npm ci --ignore-scripts` where package functionality permits. 7. Perform dependency upgrades through an explicit review process rather than resolving new versions during routine setup. 8. Run package installation and applications without administrative privileges. 9. Isolate wallet signing from general dependency code, preferably using a hardware wallet or an external signer that displays transaction details. Example: ```bash npm install --save-exact @iqlabs-official/solana-sdk@<reviewed-version> \ @solana/web3.js@<reviewed-version> npm ci ``` ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
skill.md:130
Finding
Weak XOR-Based Obfuscation Is Demonstrated for Permanent On-Chain Secrets<![CDATA[ ## Vulnerability Details **File Locations**: `skill.md:130-144`, `references/hanlock.md:47-51`, `references/hanlock.md:72-75` **Vulnerability Type**: Insecure protection of sensitive on-chain data **Risk Level**: Medium ### Vulnerable Code ```javascript const { encodeWithPassword, decodeWithPassword } = require('hanlock'); const encoded = encodeWithPassword('short secret', 'mypassword'); // → Korean syllable string like "깁닣뭡..." // Write encoded data on-chain await iqdb.writeRow('secrets', JSON.stringify({ owner: 'Alice', data: encoded })); // Later — decode const decoded = decodeWithPassword(encoded, 'mypassword'); // → 'short secret' ``` The documented transformation is: ```text 1. Password → deterministic byte sequence via simple hash 2. Plaintext → byte array 3. XOR plaintext bytes with password-derived bytes (repeating) 4. Map resulting values to Hangul syllable block range (11,172 possible syllables) 5. Output: string of Korean characters ``` ### Technical Analysis The documented protection mechanism derives a deterministic byte sequence through a simple hash and applies repeating XOR to plaintext. This is obfuscation rather than cryptographically secure encryption. It has no authenticated-encryption tag, robust password-based key derivation, random salt, or nonce. Repeating XOR is vulnerable to known-plaintext analysis, password guessing, repeated-key analysis, and structural inference. Because the encoded value is written to Solana, an attacker can obtain it permanently and perform unlimited offline analysis without triggering rate limits or account lockouts. The detailed reference does warn that hanLock is not suitable for passwords, keys, or personally identifiable information. However, the primary example labels the plaintext as a “secret,” writes it to a table named `secrets`, and describes the mechanism as lightweight on-chain privacy. That presentation can lead users to rely on it for confidentiality despite its stated limita ...[truncated 1145 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Remove examples that call hanLock-protected values “secrets” or present the mechanism as privacy protection. 2. State prominently in the primary Skill file—not only the detailed reference—that hanLock must not protect confidential data. 3. Prohibit storing passwords, private keys, credentials, authentication tokens, personal information, or regulated data with this encoding. 4. For confidentiality, use authenticated encryption such as XChaCha20-Poly1305 or AES-256-GCM. 5. If a password is used, derive the key with a memory-hard KDF such as Argon2id using a unique random salt and appropriate cost parameters. 6. Generate a unique random nonce for each encryption operation and store the salt, nonce, ciphertext, and authentication tag. 7. Keep high-value plaintext off-chain whenever possible; store only hashes, commitments, or encrypted references. 8. Explain that encryption does not eliminate the risks of permanent ciphertext publication or future cryptographic weakening. 9. Ensure decryption fails closed when authentication verification fails. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
references/x402-payments.md:35
Finding
Payment Transaction Trusts an Unauthenticated Quote Destination and Amount<![CDATA[ ## Vulnerability Details **File Location**: `references/x402-payments.md:35-50` **Vulnerability Type**: Insufficient validation of irreversible payment parameters **Risk Level**: Medium ### Vulnerable Code ```typescript import { Connection, PublicKey, Transaction, SystemProgram } from '@solana/web3.js'; // For SOL payment const tx = new Transaction().add( SystemProgram.transfer({ fromPubkey: wallet.publicKey, toPubkey: new PublicKey(quote.paymentAddress), lamports: Math.ceil(parseFloat(quote.price) * 1e9) }) ); const sig = await connection.sendTransaction(tx, [wallet]); ``` ### Technical Analysis The example constructs an irreversible SOL transfer using `quote.paymentAddress` and `quote.price` directly. The documentation does not identify a pinned trusted service origin or require cryptographic authentication of the quote. It also does not validate the recipient against an allowlist, confirm the Solana network, enforce an amount ceiling, bind the quote to the expected token or mint, verify expiration, or require an explicit human confirmation of the final transaction. `PublicKey` construction only checks whether the value can be represented as a Solana public key; it does not establish that the recipient belongs to the legitimate x402 service. Similarly, parsing the quoted price does not prove that the amount is authorized or reasonable. Network transmission is necessary for the declared quote and inscription functionality, but allowing a remote response to control an irreversible payment destination and amount without authentication exceeds the minimum trust needed for that workflow. ### Attack Path 1. A user configures or is directed to a malicious or compromised quote endpoint. 2. The endpoint returns a syntactically valid quote containing an attacker-controlled `paymentAddress`. 3. The endpoint supplies a plausible or inflated `price`. 4. The application converts these fields directly into a `SystemProgram.transfer`. 5. ...[truncated 746 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Specify and pin the expected x402 HTTPS service origin. 2. Require quotes to be cryptographically signed by a known service key. 3. Verify the signature before using any quote field. 4. Bind the signed quote to the recipient address, network, token or mint, amount, quote identifier, file metadata, payer, and expiration time. 5. Validate that the selected Solana cluster matches the quote. 6. Enforce configurable maximum payment amounts and reject non-finite, negative, malformed, or unexpectedly precise values. 7. Avoid floating-point arithmetic for currency; parse decimal values into integer lamports or token base units using strict decimal logic. 8. Display the final recipient, amount, token, network, and service identity to the user before requesting a signature. 9. Prefer a hardware or external wallet that independently displays transaction details. 10. Verify payment and inscription status on-chain and document refund or failure handling before allowing further payments. ]]>
Vulnerability Patterns
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
Findings (6)

Missing User Warnings

Medium
Confidence
87% confidence
Finding
The documentation instructs users to set `ANCHOR_WALLET=/path/to/solana/keypair.json` without warning that this file points to highly sensitive signing credentials. In a skill focused on on-chain writes and paid inscription, normalizing direct use of a local keypair path increases the risk of accidental exposure through misconfiguration, insecure file permissions, logs, screenshots, or unsafe automation environments.

Missing User Warnings

Medium
Confidence
90% confidence
Finding
This markdown file describes `pushInstruction` being used to delete existing rows by passing an empty string, but it does not provide a user-facing warning about the potential impact on stored data. Under the markdown criteria for missing user warnings, destructive or data-affecting behavior should be disclosed clearly.

Missing User Warnings

Medium
Confidence
93% confidence
Finding
The setup instructions tell users to generate a Solana keypair file on disk and configure it as the active wallet, but they do not warn that this file contains the private key and must be protected like a secret. In the context of a skill that later recommends mainnet use with real SOL, a user may reuse this wallet or mishandle the keypair, leading to fund loss or unauthorized signing if the file is exposed.

Missing User Warnings

Medium
Confidence
90% confidence
Finding
The document’s primary workflow explains how to pay for and permanently inscribe files on-chain, but does not prominently warn users before the workflow that uploaded data becomes public, immutable, and effectively undeletable. In this skill context, that omission is materially dangerous because users may upload sensitive, regulated, or proprietary data under the mistaken assumption it can later be removed or kept private.

Missing User Warnings

Medium
Confidence
93% confidence
Finding
The skill presents hanLock as a privacy mechanism for writing data on-chain, but it does not clearly warn that the resulting data is still permanently public and that password-based encoding is not equivalent to strong cryptographic encryption. This can mislead users into storing secrets, credentials, or regulated data on an immutable public ledger under a false sense of confidentiality.

Natural-Language Policy Violations

Low
Confidence
81% confidence
Finding
The file describes converting arbitrary data into Korean Hangul syllables and frames that output as useful for privacy. Because this imposes a specific language/script on encoded content without mentioning user choice or opt-in, it may violate a language/locale policy that discourages forcing a locale-specific representation.

Static analysis

No suspicious patterns detected.