groundy
Security

libheif AVIF RCE: What Next.js, sharp, and WordPress Teams Must Patch

Vercel reports a libheif AVIF RCE affecting Next.js, sharp, and WordPress. Teams must patch libheif to v1.23.4, as platform mitigations do not cover self-hosted or direct use.

Published 4 references
Two forest-green ceramic funnels cast hard shadows on ivory. One has a black stopper; the other has a gap in its stem beside a copper-colored replacement segment.
On this page10 sections

If your application decodes user-supplied AVIF images anywhere outside Vercel’s hosted Image Optimization Service, you are carrying the patch burden for the libheif remote code execution vulnerability reported in August 2026. The vulnerable code sits in libheif, an upstream C library, not in Next.js, sharp, or WordPress themselves. The concrete action is to inventory every surface that decodes untrusted AVIF and upgrade libheif to v1.23.4, a drop-in security release whose maintainers advise all users to install.

The bug is upstream: how an AVIF upload reaches libheif

The first misconception to clear away is that this is a Next.js vulnerability. It is not, according to Vercel’s disclosure post, which describes how security firm Hacktron reported what looked like an RCE in Next.js image optimization in August 2026. The investigation found the vulnerable code was upstream in libheif, “an AVIF image decoder used by Next.js, ImageMagick, WordPress, sharp, and much of the web.”

That distinction matters because it determines who has to act. A framework CVE gets fixed by bumping an npm package. An upstream C library CVE gets fixed by everyone who ships that library, in every language binding, container image, and server package that embeds it. The Vercel post lays out the dependency chain for AVIF in a Next.js application: the <Image> component invokes the /_next/image optimization endpoint, which calls sharp, which calls libvips, which uses libheif to decode the image. The /_next/image endpoint, sharp, and libvips all sit between the developer’s JSX and the vulnerable decoder, and none of them is where the bug lives.

libheif itself is an HEIF and AVIF file format decoder and encoder implementing ISO/IEC 23008-12, per the project’s GitHub repository. Because AVIF decoding is a memory-unsafe parsing problem applied to attacker-controlled bytes, and because libheif sits at the bottom of so many image pipelines, a single decoder bug propagates into products whose maintainers may not even know they depend on it. That is the supply-chain shape of this incident: the patch obligation arrives not from the framework you chose but from a transitive native dependency you inherited.

What Vercel’s mitigation covers, and who it leaves exposed

Vercel’s response is the second place where scope gets misread. Per the disclosure post, Vercel disabled AVIF optimization and resizing in its central Image Optimization Service, so “any incoming AVIF images were not passed to libheif for decoding and RCE was not possible on Vercel.” The post states this platform mitigation was applied on August 13.

Read that sentence carefully and it protects exactly one population: applications whose images are optimized by Vercel’s hosted service. It does nothing for:

  • Self-hosted Next.js deployments running /_next/image on their own infrastructure, which route AVIF through sharp, libvips, and libheif on the team’s own servers until they apply the August 25 Next.js security release, which disabled AVIF optimization and resizing in Next.js.
  • Any application that calls sharp or libvips directly, outside the Next.js image pipeline entirely.
  • ImageMagick installations that process AVIF among their supported formats.
  • WordPress sites and plugins whose media pipelines decode AVIF.

Self-hosted Next.js users did get a framework-level fix, but it arrived separately and later. Per the disclosure post, “Protecting self-hosted applications required a Next.js release. On August 25, Next.js published a security release” whose effect was that it “disabled AVIF optimization and resizing in Next.js,” chosen because “the patched libheif release was still propagating downstream.” That is twelve days after Vercel’s platform mitigation, and deployments that have not applied the release are still on the exposed path.

This split between managed-platform mitigation and self-managed patch burden is becoming a recurring pattern in Vercel-adjacent security events; we saw a similar divide when the s1ngularity supply-chain attack on Nx left self-hosted runners outside the platform’s scanning coverage. The rule is not that frameworks never help; Next.js shipped its own AVIF-disabling release the same day the upstream fix landed. It is that a platform mitigation covers only what runs on the platform. Code you deploy anywhere else depends on upstream and framework releases you have to notice and apply yourself.

Which surfaces in your stack actually decode untrusted AVIF

The triage question is narrower than “do we use Next.js” or “do we have ImageMagick installed.” It is: does an attacker-controlled AVIF file ever reach a libheif decode path on infrastructure we operate? The table below maps the surfaces named in the Vercel account to their exposure logic. Two caveats apply to the whole table: the per-stack rows describe the dependency relationship established in the vendor account, and whether a given WordPress or ImageMagick configuration decodes untrusted AVIF by default is not established in the available evidence and needs confirmation against upstream advisories.

SurfaceHow AVIF reaches libheifCovered by Vercel’s mitigation?Your action
Next.js on Vercel (<Image> / /_next/image)Handled by the managed Image Optimization ServiceYes, AVIF decoding disabled in the central serviceConfirm you are not also decoding AVIF elsewhere (API routes, background jobs)
Self-hosted Next.js image optimization/_next/image → sharp → libvips → libheif on your serversNoApply the August 25 Next.js security release, which disabled AVIF optimization and resizing; upgrade libheif to v1.23.4 across every environment running the optimizer
Direct sharp / libvips uselibvips calls libheif for AVIF decodeNoUpgrade libheif; audit whether untrusted uploads reach the pipeline
ImageMagickAVIF among 200+ supported formats, decoding via libheifNoUpgrade libheif
WordPress media handlinglibheif used by WordPress per the vendor account; default AVIF decode behavior unverifiedNoConfirm whether your configuration decodes uploaded AVIF, then upgrade libheif

The checklist version of this, for a team doing the inventory:

  1. Search your codebase and infrastructure for AVIF inputs: accept headers, upload handlers, MIME allowlists, next.config image settings, and any pipeline that converts or resizes user media.
  2. For each hit, trace whether decoding happens on Vercel’s managed service or on infrastructure you control.
  3. For everything you control, find where libheif actually comes from: a system package, a libvips build, a container base image, or a bundled binary. The upgrade path differs in each case, and container images often pin their own copy.
  4. Confirm the upgrade landed by checking the libheif version in the running environment, not just in the lockfile or Dockerfile.

The patch: v1.23.2 remediated the RCE, v1.23.4 is the latest drop-in

Unlike most of this article’s open questions, the remediation target is stated plainly in the sources. Per the Vercel disclosure post, “On August 25, six days after the August 19 meeting, the libheif maintainer released v1.23.2, which remediated the RCE.” The v1.23.2 release notes line up with that account: @hacktronai-research appears among the credited reporters, and one of the two critical issues in that release, GHSA-2jg2-4ch7-h545, covers out-of-bounds read and write in derived-item and pixel-plane handling, where “A working code-execution exploit was confirmed.” The release notes never mention Next.js or Vercel; the connection runs through the reporter credit and the vendor’s timeline. On the vendor account, versions before v1.23.2 are the affected range.

Two further security releases followed. v1.23.3 fixed another critical issue, and v1.23.4 is the latest: per its notes, it “is ABI- and API-compatible with v1.23.3 and is a drop-in replacement. Three of the fixed issues are rated high, so all users are advised to upgrade.” Patch to v1.23.4 unless you have a reason to pin an older v1.23.x; v1.23.2 is the floor that remediates the reported RCE.

ABI compatibility means you can swap the shared library without recompiling the things that link against it, which matters enormously for the sharp-libvips chain and for distribution packages. The friction in this patch is not engineering risk; it is discovery risk. Teams that do not know libheif is in their image cannot patch it, and the dependency chain is long enough that many will not know.

Defense in depth, and its limits

Two configuration-level mitigations are worth understanding, and neither substitutes for the patch.

ImageMagick has a relevant precedent. Per Wikipedia’s ImageMagick entry, the 2016 vulnerability that allowed arbitrary code execution on servers processing user-uploaded images “did not affect ImageMagick distributions that included a properly configured security policy”, a claim that carries a [citation needed] flag, so treat it as suggestive rather than established. What “properly configured” meant in that incident, and whether any policy configuration changes what AVIF input ImageMagick will decode today, is not established in the available sources. ImageMagick publishes security-policy guidance and encourages configuring a policy suited to your environment, so if you run it against untrusted uploads, that documentation is where to check what your build can be made to refuse.

libheif itself ships security limits, documented in the project README, that prevent oversized images from exhausting memory and guard against denial-of-service from malicious inputs. Third-party integrations can disable these globally via LIBHEIF_SECURITY_LIMITS=off. Two things follow. First, check that nothing in your environment sets that variable; if it does, you have voluntarily removed a safety rail. Second, do not mistake these limits for RCE protection. They address memory exhaustion and DoS, not arbitrary code execution during decode. They are a second layer, not the fix.

Why this class of bug will keep arriving

The maintenance context turns this from an incident into a forecast. Per the libheif repository, as of August 2026 “libheif and libde265 are maintained by a single independent developer with almost no recurring funding, while 37 security advisories had to be investigated, fixed and released in 2026 alone.” Between January and August 2026, those 37 advisories, most found with automated tools by organizations shipping libheif in their products, drove six releases made mainly to ship security fixes.

Vercel’s disclosure post draws the same conclusion from the demand side: as LLMs accelerate vulnerability research, it expects more upstream vulnerabilities like this one to surface across the open-source ecosystem. Both signals point the same direction. Automated and LLM-assisted research is getting better at finding bugs in exactly the kind of code libheif represents: memory-unsafe parsers of complex binary formats, maintained by one person, embedded transitively in thousands of products. The rate of discovery is now set by the researchers’ tools, while the rate of remediation is still set by one maintainer’s capacity and by how quickly downstream consumers can find and patch a library they did not know they shipped.

For platform teams, the durable takeaway is operational rather than philosophical: you need a bill of materials that includes native transitive dependencies, and you need it before the next advisory, because the triage checklist above is much faster to run when the answer to “where does libheif come from in our images” is already written down.

What remains unverified

This article’s timeline and blast radius rest on a single vendor account, Vercel’s own disclosure post, corroborated on the patch side by the upstream release notes. Before you treat any of the following as settled, confirm against primary advisories:

  • A CVE number for the code-execution issue. The advisory matching the reported RCE, GHSA-2jg2-4ch7-h545, is listed on the releases page without a CVE number, under the note that “CVE numbers will be added when assigned.” Until one is published, tracking this issue in a vulnerability scanner or exception process is awkward, and any article or ticket citing a specific CVE id for it is ahead of the evidence.
  • Per-stack default exposure. Whether common WordPress configurations or default ImageMagick installs decode untrusted AVIF out of the box is not established in the available evidence. The Wikipedia policy-mitigation precedent also carries an explicit [citation needed] flag.

None of these gaps changes the decision. If Vercel hosts your Next.js image optimization, the vendor states its central service no longer passes AVIF to libheif, and your residual task is checking for decode paths outside that service. Self-hosted Next.js teams should confirm the August 25 security release is applied, then run the same check. Everyone else should treat libheif v1.23.2 as the minimum patch and v1.23.4 as the target: the first is the release the vendor names as remediating the RCE, the second is a drop-in replacement whose maintainers advise all users to install it, and the cost of applying either is far below the cost of discovering your exposure during an incident. The verification steps above are about writing accurate records, not about whether to patch.

Frequently Asked Questions

Which libheif version should teams upgrade to for the AVIF RCE fix?

v1.23.4 is the latest: per its notes, it “is ABI- and API-compatible with v1.23.3 and is a drop-in replacement. Three of the fixed issues are rated high, so all users are advised to upgrade.” Patch to v1.23.4 unless you have a reason to pin an older v1.23.x; v1.23.2 is the floor that remediates the reported RCE.

How can teams verify the libheif patch is active in their environment?

  1. Confirm the upgrade landed by checking the libheif version in the running environment, not just in the lockfile or Dockerfile.

References

Follow the links in the article for context. The supporting material is collected here for further reading.

  1. libheif GitHub repositorygithub.comAccessed
  2. libheif releasesgithub.comAccessed
  3. ImageMagicken.wikipedia.orgAccessed

Join the discussion

Share a useful perspective or ask a question about this article.

Discussion guidelinesComments privacy