Tested on a MacBook Pro 14" (M1 Pro), macOS 27.0.1.
for k in EnableAppleISPEmulator EnableVEIRL EnableMCTF; do
sudo -u _cmiodalassistants defaults write com.apple.coremedia $k -bool NO
done
sudo killall appleh13camerad
To undo, run the same loop with defaults delete com.apple.coremedia $k instead of write,
then restart the daemon the same way.
The setting is system-wide, so every app using the built-in camera is affected. Expect more visible noise in low light.
About 3 seconds after the camera opens, the image becomes noticeably smoother and loses detail. A detail metric on the luma plane drops from about 2.0 to 1.1 within one frame. The drop happens at every resolution, and the frame metadata does not show it.
appleh13camerad is the daemon that owns the camera ISP. After the ISP, it passes frames
through a software stage called AppleISPEmulator. That stage runs MLVNR, a temporal neural
denoiser on the Neural Engine. Its rate limiter keeps it off while the model warms up, then
turns it on. You can see this in the daemon's log:
/usr/bin/log stream --level info --predicate 'process == "appleh13camerad"'
ProcessFrames_MLVNR_IIR_1: Suppressing algorithm to achieve target frame-rate
ProcessFrames_MLVNR_IIR_1: Algorithm rate-limit released.
The image changes at the second message.
The daemon reads its settings with CFPreferencesCopyValue from the com.apple.coremedia
domain of its own user, _cmiodalassistants. Disassembling /usr/sbin/appleh13camerad
shows which keys it reads:
EnableAppleISPEmulatorcontrols the whole emulator stage, including MLVNR. When it is off, the stream starts without that stage.EnableVEIRLcontrols a GPU enhancement in the same stage.EnableMCTFcontrols the multi-frame temporal filter.RadialGainEnablecontrols lens-shading correction. It is left on.
The daemon reads these keys when it starts, so it needs a restart after the change. Killing it is safe because launchd relaunches it when an app next uses the camera.
After the change, a 15-second stream shows no MLVNR, emulator or Neural Engine activity in the daemon log. The detail metric stays at 4 to 5.5 throughout. It is higher than the original 2.0 because the temporal filter is also off.