CVE-2025-47736
Executive Summary
CVE-2025-47736 is a denial-of-service (DoS) vulnerability in the libsql-sqlite3-parser crate (Rust), specifically in the dialect/mod.rs file. The parser crashes when processing input that is not valid UTF-8. This vulnerability has a low CVSS score of 2.9 due to its local attack vector and requirement for user interaction. The EPSS score is 0.0%, indicating no active exploitation in the wild. No public proof-of-concept (PoC) or exploit code is available. The vendor has provided a fix in commit 14f422a, but no patched version has been officially released.
This record — and 170,000+ others — are available via the ValtersIT API. One endpoint replaces five: NVD + GitHub CVE + CISA KEV + EPSS + Nuclei + Exploit-DB, unified.
No signup required
Supply Chain & Package Security
This vulnerability affects the Rust crate libsql-sqlite3-parser, which is a dependency for applications using the LibSQL database engine. The crate is distributed via crates.io. Users of this crate should update to the latest commit or apply the patch manually. The lack of a versioned release increases supply chain risk, as automated dependency managers may not detect the vulnerability.
CVSS Breakdown & Threat Level
- Attack Vector (AV): Local (L) – The attacker must have local access to the system.
- Attack Complexity (AC): Low (L) – No special conditions required.
- Privileges Required (PR): None (N) – No authentication needed.
- User Interaction (UI): Required (R) – The victim must parse malicious input.
- Scope (S): Unchanged (U) – The vulnerability does not affect other components.
- Confidentiality (C): None (N) – No data exposure.
- Integrity (I): None (N) – No data modification.
- Availability (A): Low (L) – The crash causes a temporary denial of service.
Threat Level: Low. The vulnerability requires local access and user interaction, and only results in a crash. No remote exploitation or data compromise is possible.
Deep Dive & Mechanics
The vulnerability resides in the dialect/mod.rs file of the libsql-sqlite3-parser crate. The parser assumes that all input is valid UTF-8. When it encounters non-UTF-8 bytes, it attempts to process them as UTF-8, leading to a panic (crash) in Rust. This is a classic encoding error (CWE-172).
The crash occurs because the parser uses functions like str::from_utf8 or similar without proper error handling. When the input contains invalid UTF-8 sequences, the function returns an error, which is unwrapped or otherwise mishandled, causing the program to abort.
Root Cause: Lack of input validation for UTF-8 encoding before parsing.
Impact: An attacker can craft a malicious SQL query or database file containing non-UTF-8 bytes. When the parser processes this input, it crashes, causing a denial of service for the application using the crate.
Vulnerable vs. Patched Code
Vulnerable Code (before commit 14f422a):
// dialect/mod.rs (simplified)
fn parse_dialect(input: &str) -> Result<Dialect, Error> {
// Assume input is valid UTF-8
let bytes = input.as_bytes();
// ... parsing logic that may panic on invalid UTF-8
}
Patched Code (after commit 14f422a):
// dialect/mod.rs (simplified)
fn parse_dialect(input: &[u8]) -> Result<Dialect, Error> {
// Handle non-UTF-8 input gracefully
let s = std::str::from_utf8(input).map_err(|_| Error::InvalidEncoding)?;
// ... parsing logic
}
The patch changes the function signature to accept &[u8] instead of &str, and explicitly checks for valid UTF-8, returning an error instead of panicking.
Exploitation & Lab Setup
Red Team (Attacker)
No public exploit code exists. To reproduce the crash:
- Create a file or input stream containing non-UTF-8 bytes (e.g.,
0xFF 0xFE 0x00). - Feed this input to an application using the vulnerable
libsql-sqlite3-parsercrate. - The application will crash with a panic.
Example (Python):
import socket
# Connect to a vulnerable service (if exposed)
s = socket.socket()
s.connect(("target", 8080))
# Send non-UTF-8 bytes
s.send(b"\xff\xfe\x00")
s.close()
Blue Team (Defender)
- Monitor for crashes in applications using
libsql-sqlite3-parser. - Look for logs containing "panicked at" or "thread 'main' panicked" related to UTF-8 parsing.
- Use the detection rules below to identify malicious input.
Indicators of Compromise (IOCs)
- Network: Inbound connections containing non-UTF-8 bytes in SQL queries.
- File: Database files with invalid UTF-8 sequences.
- Logs: Application crash logs with "panicked at 'called
Result::unwrap()on anErrvalue: Utf8Error'". - Process: Application process terminating unexpectedly.
Detection Engineering
YARA Rule
rule CVE_2025_47736_NonUTF8_Input {
meta:
description = "Detects non-UTF-8 bytes that could trigger CVE-2025-47736"
author = "Valters IT"
date = "2025-04-10"
reference = "CVE-2025-47736"
strings:
$non_utf8 = /[\x80-\xFF]/ // Non-ASCII bytes
condition:
$non_utf8 and filesize < 10KB
}
Sigma Rule
title: CVE-2025-47736 - libsql-sqlite3-parser Crash on Non-UTF-8 Input
id: 8a4b3c2d-1e5f-4a7b-9c8d-0e1f2a3b4c5d
status: experimental
description: Detects application crashes caused by non-UTF-8 input to libsql-sqlite3-parser
logsource:
category: application
product: libsql
detection:
selection:
EventID: 1000 # Application Error (Windows)
Message|contains: "panicked at"
condition: selection
falsepositives:
- Legitimate non-UTF-8 data in other contexts
level: low
Suricata Rule
alert tcp any any -> any any (msg:"CVE-2025-47736 - Non-UTF-8 SQL Input"; content:"|ff fe 00|"; sid:1000001; rev:1;)
Remediation & Mitigation
- Immediate: Apply the patch from commit
14f422amanually to thelibsql-sqlite3-parsercrate. - Short-term: Update to the latest version of the crate once a patched release is published.
- Long-term: Implement input validation for UTF-8 encoding at the application level before passing data to the parser.
- Workaround: Use a reverse proxy or WAF to filter out non-UTF-8 bytes from incoming SQL queries.
Valters IT
Senior DevSecOps & Cyber Threat Intelligence Expert