Affected versions

Symfony Serializer versions <5.4.56, >=6, <6.4.50, >=7, <7.4.23, >=8, <8.1.11 are affected by this security issue.

The issue has been fixed in Symfony Serializer 5.4.56, 6.4.50, 7.4.23, 8.1.11.

Description

DataUriNormalizer::denormalize() checks its input with a case-insensitive regular expression, so it accepts a URI that starts with DATA: or Data:. But PHP uses its data: stream wrapper only when the scheme is lowercase. With any other case, PHP opens the string as a relative local path. It also resolves .. in that path, even through directories that don't exist. The regular expression allows / and . in the payload.

As a result, DATA:,/../../../../../../../../../../etc/hostname denormalized to \SplFileObject gives the content of /etc/hostname. Denormalized to \SplFileInfo or to File, the same URI gives the file as soon as the application calls openFile() or getContent().

Any deserialize() of client data into these types is affected. On Symfony 6.4 and later, this includes #[MapRequestPayload] DTOs with such a property. FrameworkBundle registers DataUriNormalizer by default.

Resolution

Once the regular expression accepts the URI, DataUriNormalizer lowercases its scheme before opening it. URI schemes are case-insensitive, so DATA:,Hello is still accepted and now reads Hello.

The patch for this issue is available here for branch 5.4 (and forward-ported to 6.4, 7.4, 8.1 and 8.2).

Credits

We would like to thank Nicolas Grekas for reporting the issue and providing the fix.