سبحان الذي علم بالقلم, علم الإنسان ما لم يعلم

We all know Zero Click vulnerabilities — the attack executes without the user doing literally anything. We hear stories and go "wow, they found a Zero Click!" Or some Zero Day drops and they say it's Zero Click, then a thousand patch-your-OS warnings flood in. But how does this actually happen?

The most dangerous exploit is the one that requires zero interaction — you don't click, you don't open, you don't know.

Last year's scenario: CVE-2025–43300 — a Zero Click vulnerability on Apple systems. Through a crafted image sent to the victim, the attacker achieved an Out-of-Bounds Write in Memory. That's a Buffer Overflow, which means Malicious process hollowing, for example. By the time you figure out who sent you the image — or that there even was an image — you're already compromised.

First, we need to understand a few things

Adobe created a Raw image format (camera raw files) called DNG. Inside a DNG, there's compressed image info so you don't lose detail (unlike JPEG lossy compression). The DNG structure has two critical sections:

SectionWhat it containsKey parameterTIFF MetadataImage information and parametersSamplesPerPixel — number of channels per pixel (e.g., RGB = 3 channels)JPEG StreamContains an SOF3 marker — image info used during decompressionNumComponents — number of channels per pixel during decompression (the code reads this, not the metadata)

Important note: when the image gets decompressed, the code references the JPEG stream's NumComponents — not the TIFF metadata. These two values are supposed to match. That mismatch is exactly where things get interesting.

So where's the vulnerability?

In the library that processes and decompresses images: ImageIO. Inside it there's a sublibrary called RawCamera.bundle — exists as a file inside the dyld_shared_cache on every Apple device. Inside that, there's a class called CDNGLosslessJpegUnpacker — the class responsible for decompressing Lossless JPEG inside DNG files.

To reach the vulnerable function, you need to pass two check conditions:

Condition 1field_d8 = (null) and field_dc = 2

field_d8 and field_dc are internal fields (variables) inside the CDNGLosslessJpegUnpacker class. They hold the unpacker's state. field_d8 points to a pointer or specific flag; field_dc holds the number of channels or tile type. These correspond to TIFF tags in the image metadata — so if the image follows the right structure, the condition passes automatically.

Condition 2A check on SamplesPerPixel and NumComponents.

First it allocates buffer space in Memory normally. Then: if (NumComponents != 2) → enters the vulnerable path else → normal code runs on the same allocated space, nothing wrong

Okay, but where's the actual attack?

Now we know the attacker needs to arrange TIFF tags in the image metadata to satisfy Condition 1 — that's the easy part. For Condition 2, they need NumComponents != 2 in the decompressed data. The attacker sets it to 1 (one channel — grayscale).

Then they set SamplesPerPixel = 2 in the Metadata.

Wait — didn't we say both represent the number of channels? Shouldn't they always be the same value? Exactly. So the attacker writes in the metadata that the image is not grayscale (grayscale = 1 channel = 1 byte). By setting it to 2, they're telling the parser this is one of the medical image types — and those calculate the channel as 2 bytes.

Let's walk through the math — simplified with a 1000×1 pixel image:

// Buffer allocation — uses SamplesPerPixel from Metadata 1000 pixels × 2 samples × 2 bytes = 4,000 bytes allocated ✓

// Enter the vulnerable condition: NumComponents = 1, so (NumComponents != 2) is true // Outer for loop runs: for (i = 1; i < 1000 × 2; i += 1) → 2000 iterations // Each iteration: pointer advances by 2 samples (pixel by pixel) // Total samples written: 2000 × 2 = 4000 samples // Each sample/channel = 2 bytes

4,000 samples × 2 bytes = 8,000 bytes written Allocated: 4,000 bytes → Written: 8,000 bytes

Out-of-Bounds Write: +4,000 bytes past the buffer boundary 💀

0x0000 ████████████████████ ← allocated buffer (4000 bytes) safe zone

0x0FA0 ████████████████████ ← end of safe zone

0x0FA0 ████████████████████ ← OVERFLOW BEGINS here

0x1F40 ████████████████████ ← +4000 bytes past boundary (arbitrary write)

↑ arbitrary code execution territory

That's a Buffer Overflow → arbitrary code execution. And iMessage, which processes images automatically, is open by default on every iPhone.

And all of this happened because an image showed up in your messages. On WhatsApp. You didn't tap it. You didn't open it. You're already compromised. :)

The complete attack flow

Step 1

Craft the malicious DNG imageSet TIFF tags to satisfy field_d8 = null and field_dc = 2. Set SamplesPerPixel = 2 in TIFF metadata (signals medical image type, 2 bytes per channel). Set NumComponents = 1 in the JPEG stream (signals grayscale to the decompressor).

Step 2

Deliver via any messaging appiMessage, WhatsApp, anything that auto-processes image previews. Zero user interaction required.

Step 3

ImageIO triggers automaticallyRawCamera.bundleCDNGLosslessJpegUnpacker starts processing. Passes both conditions. Buffer allocated based on SamplesPerPixel = 2.

Step 4

Out-of-Bounds Write executesThe for loop writes 8,000 bytes into a 4,000 byte buffer. 4,000 bytes of overflow into adjacent memory regions. Arbitrary code execution achieved.

Done

Device compromised — silentlyYou never saw a prompt. You never tapped anything. You don't even know who sent it.

The patch — one line of code

Apple added a single condition check before the for loop:

if (NumComponents == SamplesPerPixel)

Before entering the vulnerable path, the parser now verifies that both values agree. If the JPEG stream says grayscale (1 channel) but the TIFF metadata says 2 samples per pixel — they don't match, the check fails, execution stops. The mismatch that enabled the entire exploit is now explicitly caught.

One comparison. That's it. That's the entire fix for a complete device takeover.

Was everyone compromised?

Yes — technically. But crafting the image or payload with all the right conditions without corrupting the image itself is genuinely difficult. That's why this vulnerability was being exploited only against targeted individuals, not in mass campaigns. The barrier to weaponization was high enough that it couldn't be sprayed at random.

Which, if you think about it, might be the scariest version: the people running this exploit were being very deliberate about who they used it on.

إن أصبت فهو من عند الله وإن أخطأت فهو من نفسي والشيطان :)