Skip to content

[Firmware] image: PNG accepted at load but decode/save fail ("PNG decoder/encoder is not enabled") #23

Open

Description

@leeebo

Issue draft (espressif/esp-vision — "Firmware" template)

Title: [Firmware] image: PNG accepted at load but decode/save fail ("PNG decoder/encoder is not enabled")

Problem summary

image.Image(path) silently accepts PNG files (header metadata such as width/height
is readable, no error at load), but the first operation that needs pixel decoding
fails with RuntimeError: PNG decoder is not enabled, and saving to a .png path
fails with RuntimeError: PNG encoder is not enabled. This contradicts the
documentation, which lists PNG as a supported format (image.Image.to_png in the
image-model concept page) and states that Image.save() infers the format from the
file extension.

The delayed failure is the harmful part: an app can load a PNG asset at boot without
error and only crash later, mid-stream, when the asset is first used. In our
privacy-camera application, a PNG emoji overlay loaded fine at startup and crashed
the running app (after ~34,000 frames) the moment a face was detected and the
overlay had to be drawn. A load-time rejection (like BMP's) would have caught this
immediately.

Environment

  • Board model and hardware revision: ESP32-P4X Function EV Board (ESP32-P4)
  • Chip, camera, display, and peripherals: ESP32-P4; camera is not involved in this
    repro; no display connected
  • Firmware version/commit and download source or CI job: esp-vision catalog
    firmware, commit 3d84b2d (reported by the device firmware check); ESP-IDF
    v5.5.6. Latest catalog release 2026.11.06 not yet tested.
  • ESP-IDF version/commit (custom builds): not applicable (catalog firmware)
  • Build command and configuration changes (custom builds): not applicable
  • Power supply and connection: USB to host (serial + UVC)

Steps to reproduce

  1. Flash or boot the firmware above.
  2. Upload a PNG image to flash (e.g. /emoji.png, 128x128) and open the REPL.
  3. Run the minimal script:
import image
p = image.Image('/emoji.png')            # accepted, no error
p.width()                                 # 128 -> header is read fine
img = image.Image(320, 240, image.RGB565)
img.draw_image(p, 10, 10)                 # RuntimeError: PNG decoder is not enabled
p.save('/tmp_emoji.png')                  # RuntimeError: PNG encoder is not enabled
p.save('/tmp_emoji.jpg', quality=80)      # OK
j = image.Image('/emoji.jpg')             # OK
img.draw_image(j, 10, 10)                 # OK

Reproduction frequency: 100% across REPL and running-application contexts, on cold
boot and after soft reset.

Expected behavior

Either of the following:

  • PNG assets load, decode, and save as documented ("format inferred from the
    extension"; to_png listed as a supported output), or
  • image.Image(path) rejects a PNG immediately at load with a clear error, like it
    does for unsupported BMP data (OSError: Unsupported format!).

Actual behavior

  • PNG loads silently (metadata readable), then decode fails later:
    RuntimeError: PNG decoder is not enabled.
  • PNG save fails: RuntimeError: PNG encoder is not enabled.
  • JPEG load/decode/save works end to end on the same firmware.

Logs and attachments

  • emoji.png — PNG asset that loads but fails to decode (any valid PNG reproduces
    this; the exact asset is available on request)
  • emoji.jpg — JPEG version of the same asset that works (control case)
  • No crash log: the failure surfaces as a Python RuntimeError in the REPL and in the
    running application.

Workaround and regression

Workaround: convert assets to JPEG before uploading. Unknown whether this worked on
an earlier firmware; first failing version observed is catalog firmware 3d84b2d
(not yet re-tested on 2026.11.06).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions