← Paper hub Chapter 5 / 6 Discussion
Section V

Discussion

Why mitigations failed, sandbox escape, structural alternatives.

The 2025 WhatsApp–ImageIO chain and its 2021 FORCEDENTRY predecessor demonstrate a consistent architectural pattern: a delivery primitive (messaging protocol bypass) composes with an exploitation primitive (image parser memory corruption) to achieve zero-click code execution. This section examines why the current mitigation stack did not prevent the 2025 chain, what lies beyond the initial RCE, what structural alternatives exist, and the limitations of this study.

Why the Mitigation Stack Did Not Prevent This Chain

Section II-D introduced three mitigations deployed on iOS: ASLR, stack canaries, and application sandboxing. None of them target the root cause of CVE-2025-43300.

ASLR randomizes memory layout but does not prevent the out-of-bounds write itself. The write occurs regardless of where the buffer is placed; ASLR only makes it harder to know where to redirect control flow afterward. In practice, a second, milder bug in the same process (an information leak) suffices to defeat ASLR by revealing a code or data address, after which the attacker can construct a valid target for the hijacked pointer. Information leaks in image parsers are common: the same complexity that produces out-of-bounds writes routinely produces out-of-bounds reads [19].

Stack canaries are entirely irrelevant: the overflow occurs on the heap, not the stack. Canaries protect saved return addresses; they do not monitor heap metadata or function pointers stored in heap-allocated objects.

Application sandboxing limits what the attacker can do after RCE but does not prevent the RCE itself. The sandbox around WhatsApp restricts file-system and IPC access, but the attacker’s initial foothold (code execution inside the process) is already sufficient to exfiltrate data accessible to that process (contacts, messages, media, location) and to attempt a sandbox escape via a separate vulnerability.

Pointer Authentication Codes (PAC), deployed on ARMv8.3+ Apple silicon [29], sign pointers with a process-specific secret so that corrupted pointers fail verification before use. PAC raises the cost of control-flow hijacking significantly but has been bypassed in academic and in-the-wild settings, typically by reusing legitimately signed pointers or by targeting code paths that do not enforce PAC on every indirect call.

The pattern is consistent: each mitigation addresses a symptom (where code lives, whether the return address is intact, what permissions the process has, whether a pointer is signed) rather than the root cause (the program wrote past the end of a buffer because no bounds check existed). So long as the parser is written in a language that permits unchecked memory access, the vulnerability class persists and mitigations can only raise the cost of exploitation, not eliminate it.

This failure is not confined to iOS. Table I in Section II-F documents nine write-primitive chains from 2016 to 2026 spanning five distinct CWE classes across the Linux kernel and the iOS media pipeline. The Linux entries cover kernel memory management, pipe page cache, the cryptographic API, and IPsec networking - entirely different subsystems, yet all bypass identical mitigation sets (SMAP, SMEP, KASLR) and reach the same local root primitive. Two of those entries arrived during the final week of preparation of this manuscript. Copy Fail (CVE-2026-31431, disclosed April 29, 2026) [15] exploits an incorrect resource transfer in the AF_ALG crypto interface to write four bytes into arbitrary kernel page-cache frames, achieving deterministic root on a fully patched Ubuntu 24.04. Nine days later, DirtyFrag (CVE-2026-43284, disclosed May 7, 2026) [16, 26] repeats the same page-cache-write primitive through the xfrm-ESP IPsec subsystem. Both exploit the same SMAP/SMEP/KASLR-bypassing technique as DirtyPipe [23] four years earlier. The cadence - at least one high-profile root or RCE exploit per year since 2016, across Linux and iOS - indicates that the deployed mitigation approach has not reduced the annual production rate of exploitable write primitives.

Beyond RCE: Sandbox Escape and Persistence

A zero-click RCE inside a sandboxed process is not, by itself, full device compromise. The reported FORCEDENTRY and 2025 chains both achieved persistent, cross-application surveillance (call recording, message exfiltration, camera/microphone access), implying that additional stages followed the initial RCE: at minimum, a sandbox escape and a privilege-escalation step. These stages are outside the scope of this paper: they involve kernel vulnerabilities and system-daemon bugs unrelated to the two CVEs studied, but their existence must be acknowledged: the image-parser RCE is the entry point, not the endpoint, of the full attack.

Structural Alternatives

If mitigations cannot close the vulnerability class, what can? Two categories of structural change address the root cause.

Memory-safe languages (Rust, Swift, Go, Java) enforce bounds checking, type safety, and lifetime management at compile time or runtime, making out-of-bounds writes impossible in safe code by construction [12]. Rewriting media parsers in a memory-safe language would eliminate CWE-787 from the attack surface entirely. The industry is already moving in this direction. Apple has begun shipping Swift-based replacements for some system components. Google’s Android team has documented that the share of memory-safety vulnerabilities in new Android code fell to near zero in modules rewritten in Rust [12]. Most significantly, the Linux kernel (the canonical example of a safety-critical C codebase) merged initial Rust infrastructure in Linux 6.1 (December 2022) and shipped its first production Rust-written driver (a network PHY driver for the Asix ax88796b chipset) in Linux 6.8 (March 2024) [30]; Rust was declared a permanent, non-experimental part of the kernel at the 2025 Kernel Maintainer Summit in Tokyo [31]. At the distribution level, Ubuntu 25.10 (October 2025) became the first major distribution release to ship uutils, a Rust reimplementation of the GNU core utilities, as the default [32]. Ubuntu 26.04 LTS (April 2026) extended this to the long-term-support release and additionally shipped sudo-rs, a memory-safe Rust reimplementation of sudo, as the default privilege-escalation binary [33], replacing two C codebases that have long been high-value targets for local privilege escalation. The challenge for media frameworks is scale: ImageIO is a large, performance-critical C/Objective-C codebase with decades of accumulated optimisation, and incremental rewriting is slow, but uutils, sudo-rs, and the Linux Rust drivers demonstrate that production-grade, security-critical C code can be incrementally replaced.

Hardware-enforced memory safety, specifically ARM Memory Tagging Extension (MTE) on ARMv8.5+, assigns a 4-bit tag to every 16-byte memory granule and checks the tag on every access. A heap overflow that crosses a granule boundary with the wrong tag traps immediately, preventing the corruption from reaching adjacent objects. MTE is deployed on some Android devices but is not yet enabled on iOS. If deployed, MTE would make the CVE-2025-43300 overflow detectable at the hardware level regardless of the implementation language. In synchronous checking mode, a tag mismatch faults precisely on the violating instruction and yields defender-usable telemetry; asynchronous mode defers the trap to the next context switch for substantially lower overhead, trading temporal precision for deployability and making it the mode Android ships by default.

Copy Fail: A Concrete Kernel Walk-Through

Copy Fail (CVE-2026-31431) provides a concrete illustration of how the write-primitive pattern in Table I manifests at the Linux kernel level [34]. Its mechanism is instructive precisely because it has no structural connection to iOS or to image parsing - yet its exploitation outcome and the reason current mitigations did not stop it are identical to those of CVE-2025-43300.

The vulnerable optimization.

Linux exposes its in-kernel cryptographic algorithms to unprivileged userspace via AF_ALG sockets. A 2017 kernel commit to algif_aead.c introduced an in-place AEAD (Authenticated Encryption with Associated Data) optimization: instead of maintaining separate input and output scatterlists, the kernel chains both into one combined scatterlist using sg_chain(). The optimization is correct so long as the source data resides in kernel-managed bounce buffers - but the splice() system call can insert raw page-cache page references directly into that scatterlist, bypassing the buffer abstraction entirely.

The write.

The authencesn AEAD template performs a byte-rearrangement step during IPsec ESP decryption: it writes four bytes of the Extended Sequence Number (seqno_lo, taken from attacker-controlled AAD bytes 4–7) to the offset assoclen + cryptlen in the destination scatterlist via scatterwalk_map_and_copy(). In the in-place configuration this offset lands in the chained page-cache pages, producing an attacker-controlled 4-byte write to any page-cache page the attacker can name via splice(). Listing 3 contrasts the vulnerable and fixed kernel paths.

/* Vulnerable: in-place -- src and dst share
   the same scatterlist, which may contain
   page-cache pages inserted via splice().  */
req->src = req->dst;
scatterwalk_map_and_copy(       /* OOBW:   */
    &seqno_lo, req->dst,        /* writes  */
    assoclen + cryptlen, 4, 1); /* into PC */

/* Fixed: out-of-place -- TX and RX SGL
   are kept separate; page-cache pages
   never enter the writable dst path.     */
req->src = tsgl_src; /* TX: user-supplied  */
req->dst = rsgl_dst; /* RX: kernel buffer  */
Listing 3. Vulnerable (in-place) vs. fixed (out-of-place) path in algif_aead.c. The single-line change that keeps req->src != req->dst eliminates the OOBW.
Figure 6: fig:copyfail-sgl
Fig. 6. Scatterlist layout in algif_aead.c before and after the CVE-2026-31431 patch. Left (vulnerable): req->src = req->dst; page-cache pages arrive via splice() in the combined SGL, so the authencesn 4-byte write crosses into page-cache memory (OOBW). Right (fixed): TX and RX SGLs are kept separate; the write is confined to the kernel output buffer.

Exploitation.

The exploit requires no privileges [34]:

  1. Open an AF_ALG socket bound to authencesn(hmac(sha256),cbc(aes)).

  2. Encode the desired 4-byte payload in AAD bytes 4–7 of a sendmsg() call.

  3. Use splice() to feed the target file’s page-cache pages (e.g., the /usr/bin/su setuid binary) as the ciphertext/tag input.

  4. Call recv(): the kernel decrypts in-place and authencesn writes the 4 controlled bytes into the in-memory copy of the target binary.

  5. Execute the corrupted binary; su is setuid root, so the injected stub runs with root privileges.

A critical stealth property: the corrupted page is never marked dirty, so the on-disk binary is unchanged and disk-based integrity mechanisms (IMA, dm-verity) do not trigger. The exploit is portable - a single 732-byte Python script achieves deterministic root on Ubuntu, Amazon Linux, RHEL, and SUSE - and requires no race condition or timing window [34].

Structural parallel.

SMAP, SMEP, and KASLR were all active on the test systems and none of them stopped Copy Fail, for exactly the same reason that ASLR, stack canaries, and PAC did not stop CVE-2025-43300: the write itself is never intercepted. The attacker does not need to redirect control flow - the kernel’s own AEAD routine performs the write on the attacker’s behalf. This is the same “legitimate-code-does-the-write” pattern as the ImageIO DNG parser: in both cases the memory safety violation is internal to a trusted subsystem, invisible to any mitigation that only monitors control-flow integrity or address-layout randomness.

Limitations

Three limitations must be acknowledged. First, our analysis of CVE-2025-43300 is second-hand: we rely on Quarkslab’s reconstruction from patch diffing [17], not on independent reverse engineering. Certain exploitation details (heap-spraying strategy, PAC bypass technique) are inferred, not observed. Second, the Phoenix heap-two exercise deliberately omits real-world complications (ASLR, PAC, heap randomization, concurrent allocation); it illustrates the core mechanic, not the full exploitation engineering. Third, Section II-F extends comparison to nine chains spanning 2016–2026; further generalization of the “same primitive, different subsystem” thesis remains limited to publicly disclosed cases, and our analysis of several entries (BLASTPASS, Operation Triangulation, Copy Fail, DirtyFrag) relies on vendor advisories and third-party writeups rather than independent reverse engineering.

References

  1. [12] CISA, “The Urgent Need for Memory Safety in Software Products”, Policy document, 2023.
  2. [15] Microsoft Threat Intelligence, “CVE-2026-31431: Copy Fail Vulnerability Enables Linux Root Privilege Escalation”, Microsoft Security Blog, 2026.
  3. [16] Wiz Research, “DirtyFrag: Linux Kernel Local Privilege Escalation via ESP and RxRPC (CVE-2026-43284)”, Wiz security blog, 2026.
  4. [17] Quarkslab, “Reverse Engineering of Apple's iOS 0-click CVE-2025-43300: 2 Bytes That Make Size Matter”, Research blog, 2025.
  5. [19] Szekeres, L. and Payer, M. and Wei, T. and Song, D., “SoK: Eternal War in Memory”, IEEE Symposium on Security and Privacy (S\&P), 2013.
  6. [23] Kellermann, Max, “The Dirty Pipe Vulnerability (CVE-2022-0847)”, Technical writeup, CM4All, 2022.
  7. [26] Red Hat Customer Portal, “DirtyFrag Linux Kernel Local Privilege Escalation -- CVE-2026-43284”, Red Hat Security Bulletin RHSB-2026-003, 2026.
  8. [29] Qualcomm Technologies, Inc., “Pointer Authentication on ARMv8.3”, Whitepaper, 2017.
  9. [30] Phoronix, “The First Rust-Written Network PHY Driver Set To Land In Linux~6.8”, Online news, 2024.
  10. [31] LWN.net, “The (successful) end of the kernel Rust experiment”, Online news, 2025.
  11. [32] LWN.net, “Oxidizing Ubuntu: Adopting Rust Utilities by Default”, Online news, 2025.
  12. [33] Canonical, “What's new in security for Ubuntu~26.04~LTS?”, Engineering blog, 2026.
  13. [34] Xint Security Research, “Copy Fail (CVE-2026-31431): Technical Walkthrough for Linux Distributions”, Security research blog, 2026.