Tetrak
GitHub ↗
Security · Pillow

Encoding a TIFF to memory uses a freed buffer when libtiff rejects a tag

Pillow: Heap use-after-free when encoding TIFF to an in-memory buffer

Advisory
CVE-2026-112396
Library
Pillow, pillow on PyPI
Published
Severity
5.9 out of 10, as published
Affected
< 12.3.0
Fixed in
12.3.0
Reaches you
on a save path

What triggers it

Image.save(format="TIFF") to an in-memory buffer with a tag libtiff rejects.

What sillybos does

Refused by default

sillybos refuses the triggering file under its default policy, through the allow_inconsistent_tiff_tags check.

The rejected tag, a floating-point Predictor on integer samples in the report's example, rides into the save when the program keeps the opened file's tag table. The reader reads the Predictor and the SampleFormat and reports the contradiction, and a policy that refuses inconsistent tags refuses the file before Pillow sees it (allow_inconsistent_tiff_tags). The default refuses it since 5.0.0; before that the setting had to be chosen.

Proposed from the advisory's text on 2026-11-01, as part of folding the backfill into the record; confirmed by a person on 2026-11-03. Re-read on 2026-11-03 against the question of what rides from an opened file into a save: the file is the input. Bucket and finding confirmed by a person on 2026-11-03; waits for the policy on a TIFF's tags and its test before it can be promoted. The policy was built on 2026-11-03 (sillybos 4.2.0). Refused by default from 5.0.0 (3 November 2026).

Proved by this test in the sillybos suite, which builds the triggering file from bytes and checks that it is refused:

How to protect yourself

In general. Upgrade to Pillow 12.3.0.

Specifically. Keep allow_inconsistent_tiff_tags off, as it is by default, and save to a file rather than memory; upgrade to Pillow 12.3.0.

The general advice applies to every row here.

Sources