Firmware for the M5Stack UnitCam S3 (5MP) that saves one JPEG per second to the microSD card while power is on. Includes chip overheating protection.
Where files go: simple_picsaver/ on the FAT volume (full path on device: /sdcard/simple_picsaver/). Use a FAT32 card. You can optionally encrypt each JPEG (see below); files are then named *.ucam.
Names: uptime since power-on, HHHH_MM_SS.jpg (or .ucam): hours, minutes within that hour, seconds. Resets after each reboot.
Feedback: the LED toggles each time a frame is written successfully.
Pins: platforms/unitcam_s3_5mp/main/board_pins.hpp
- ESP-IDF 5.1.x installed and environment set (
idf.pyworks in a terminal).
-
Clone this repository.
-
Install the Arduino core into the project (required for the build):
python fetch_repos.py
That clones the revision listed in
repos.jsonintoplatforms/unitcam_s3_5mp/components/arduino-esp32. -
The esp32-camera component is already under
platforms/unitcam_s3_5mp/components/esp32-camera.
cd platforms/unitcam_s3_5mp
idf.py set-target esp32s3
idf.py build
idf.py -p PORT flash monitorReplace PORT with your serial port (for example COM9 on Windows or /dev/ttyUSB0 on Linux).
If you change partitions or hit odd CMake cache issues:
idf.py fullclean
idf.py build-
Set the passphrase in menuconfig (same value you will use on the PC):
cd platforms/unitcam_s3_5mp idf.py menuconfigOpen Picsaver (SD JPEG) and set Passphrase for AES-256-GCM file encryption to a non-empty string. Leave it empty to save normal
.jpgfiles. -
Rebuild and flash (
idf.py buildthenidf.py -p PORT flash). -
On the SD card you will see
*.ucamfiles (see Names above for the uptime pattern). -
Decrypt on your computer (Python 3):
pip install pycryptodome python tools/decrypt_ucam.py path/to/file.ucam -p "YOUR_PASSPHRASE"One
.jpgis written next to each.ucam(orpython tools/decrypt_ucam.py path/to/folder -p "..."for every*.ucam; optional-o other_folderfor outputs).
The firmware uses PBKDF2-HMAC-SHA256 (10000 iterations) and AES-256-GCM. The passphrase is stored in flash and sdkconfig; anyone with the firmware image or full flash dump could recover it. For stronger protection, use Espressif flash encryption / secure boot and treat this as protection against casual SD access only.
Keeps only frames that differ enough from the previous frame (good for motion detection highlight):
pip install pycryptodome pillow
python tools/ucam_keyframes.py path/to/folder_with_ucam -p "YOUR_PASSPHRASE" -o path/to/output_keyframesAdjust sensitivity with -t (default mean absolute difference 8.0 on a 0–255 grayscale scale; lower = more frames kept). Use --dry-run to see decisions without writing files.
With --debug, the script also writes plots tools/ucam_diff_histogram.png (histogram with the mean absolute differences, useful to establish a reasonable threshold; install matplotlib for the PNG).