golang / go

The Go programming language
https://go.dev
BSD 3-Clause "New" or "Revised" License
123.03k stars 17.54k forks source link

net/http: do not decode multipart form parts containing Content-Transfer-Encoding headers #63855

Open neild opened 10 months ago

neild commented 10 months ago

A multipart/form-data form consists of a series of parts, separated by a boundary. As originally specified in RFC 2388, each part may contain a Content-Transfer-Encoding header as defined in RFC 2045 Section 6.

RFC 7578, Section 4.7, which updates and obsoletes RFC 2388, deprecates the use of Content-Transfer-Encoding in contexts which support binary data, specifically including HTTP.

http.Request.ParseMultipartForm will parse form parts containing a Content-Transfer-Encoding header. To use an example from RFC 7578, ParseMultipartForm will parse this form part as containing the body "Joe owes €100.":

--AaB03x
content-disposition: form-data; name="field1"
content-type: text/plain;charset=UTF-8
content-transfer-encoding: quoted-printable

Joe owes =E2=82=AC100.
--AaB03x

This can act as a content smuggling vector, since other implementations generally do not decode quoted-printable form parts in HTTP multipart/form-data responses. As a hardening measure, we should consider not decoding encoded parts in ParseMultipartForm. RFC 7578 indicates that implementations that send such bodies are uncommon to nonexistent.

neild commented 10 months ago

Addendum:

Thanks to Qi Wang and Jianjun Chen for reporting this issue.

gopherbot commented 6 months ago

Change https://go.dev/cl/573195 mentions this issue: mime/multipart: add Reader.SetRejectContentTransferEncoding

gopherbot commented 6 months ago

Change https://go.dev/cl/573196 mentions this issue: net/http: reject multipart requests containing a "Content-Transfer-Encoding" header

ianlancetaylor commented 6 months ago

See also #66434.