Skip to content

Backslash-escaped LF in a quoted parameter value bypasses validation #30

Description

@hey-jj

MediaType::parse accepts a quoted parameter value that contains a backslash-escaped LF. The LF survives into Display and as_str, so re-serializing the media type emits a raw line break inside a header value.

Version: mediatype 0.22.0, default features.

Reproducer

use mediatype::{MediaType, MediaTypeBuf};

fn main() {
    let input = "text/plain; x=\"a\\\nInjected: yes\"";

    let mt = MediaType::parse(input);
    println!("{:?}", mt);
    println!("{:?}", mt.unwrap().to_string());

    let buf: Result<MediaTypeBuf, _> = input.parse();
    println!("{:?}", buf);
}

Observed

MediaType::parse returns Ok. Parsing the same string into MediaTypeBuf also returns Ok. Display and as_str preserve the raw LF before Injected: yes.

Expected

Err(MediaTypeError::InvalidParamValue). RFC 7230 section 3.2.6 does not permit LF in either qdtext or quoted-pair.

Root cause

PR #28 landed in 0.22.0 and added this arm to the quoted-value match:

'\n' | '\r' => return Err(MediaTypeError::InvalidParamValue),

An earlier arm at src/parse.rs:207 claims the character first:

_ if escaped => { escaped = false; }

A backslash sets escaped, so the parser consumes the following character without checking it and the LF reaches the value. The tests PR #28 added cover raw CR, raw LF and raw CRLF. None covers the escaped form.

Scope

Quoted parameter values holding a backslash that the parser treats as an escape, immediately followed by LF. Both MediaType and MediaTypeBuf accept such input.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions