Salvo's form data parsing implementations (form_data() method and Extractible macro) do not enforce payload size limits before reading request bodies into memory. This allows attackers to cause Out-of-Memory (OOM) conditions by sending extremely large payloads, leading to service crashes and denial of service.
Three attack vectors exist in Salvo's form handling:
URL-encoded form data (application/x-www-form-urlencoded)
Request::form_data() calls BodyExt::collect(body) which reads the entire body into memory without size checkingreq.form_data().await directlyMultipart form data (multipart/form-data)
Extractible macro
#[derive(Extractible)] with #[salvo(extract(default_source(from = "body")))] internally calls form_data()The FormData::read() implementation prioritizes convenience over safety by reading entire request bodies before validation. Even when Request::payload_with_max_size() is available, it's not automatically applied in the form parsing path.
Extract data from request example in readme.md in docker file with limited memory say 100mb.application/x-www-form-urlencoded OR multipart/form-data payload to the endpoint.#[derive(Extractible)] with body sourcesCurrently, Salvo's multipart form data parsing automatically handles file uploads without explicit developer intent. This creates several security and usability concerns:
{
"cwe_ids": [
"CWE-770"
],
"github_reviewed": true,
"github_reviewed_at": "2026-03-19T12:44:56Z",
"nvd_published_at": "2026-03-24T00:16:29Z",
"severity": "HIGH"
}