Apr 10, 2026·5 min read·2 visits
A missing authorization check in BuildKit's GRPC Gateway API allows malicious custom frontends to spawn highly privileged containers during the build process, enabling host root code execution.
Moby BuildKit versions prior to 0.12.5 contain a critical authorization bypass vulnerability (CWE-863) within the interactive containers GRPC Gateway API. A maliciously crafted Dockerfile using a custom frontend can bypass entitlement checks to launch a privileged container, resulting in a build-time escape and full host root command execution.
Moby BuildKit utilizes a modular architecture where custom frontends parse various input formats into Low-Level Builder (LLB) representations. Developers specify these frontends in Dockerfiles using the # syntax= directive. The frontends execute as ephemeral containers during the build process.
These frontend containers communicate with the primary buildkitd daemon via a GRPC-based Gateway API. This API handles operations such as resolving image metadata, executing build steps, and spawning interactive containers. The gateway exposes endpoints like Container.Start and NewContainer to facilitate dynamic build features.
CVE-2024-23653 is an incorrect authorization vulnerability (CWE-863) within this GRPC Gateway API. BuildKit versions prior to 0.12.5 fail to enforce security entitlement checks when processing dynamic container requests from custom frontends. This failure allows an unprivileged build process to spawn containers with elevated system capabilities.
The vulnerability originates from a structural disconnect between standard static build execution and the dynamic interactive container API. Standard BuildKit execution rigorously validates privileged operations. Specifically, users must supply the --allow security.insecure flag to permit containers with elevated capabilities.
However, the interactive container API bypasses this validation logic entirely. When a custom frontend interacts with the Gateway API, it constructs a GRPC request detailing the container specifications. The frontend can populate fields such as StartRequest.SecurityMode with the INSECURE enum value or set NetMode to HOST.
Because the buildkitd daemon processes these API requests without invoking the standard entitlement verification layer, it honors the frontend's specifications blindly. The daemon provisions the container according to the requested insecure parameters, granting the frontend container full Linux capabilities irrespective of the user's explicit entitlements.
The remediation strategy required architectural changes across two primary commits to enforce entitlement validation. Commit 5026d95aa3336e97cfe46e3764f52d08bac7a10e introduced privilege separation by decoupling the execution worker from the frontend Gateway. The Gateway now receives a constrained executor.Executor instance rather than a raw object with excessive internal access.
Commit 92cc595cfb12891d4b3ae476e067c74250e4b71e implemented the explicit authorization checks missing from the interactive container API. The developers introduced a validateEntitlements method within the llbBridge component. This method evaluates the requested ProcessInfo against the build's globally loaded entitlements.
func (b *llbBridge) validateEntitlements(p executor.ProcessInfo) error {
ent, err := loadEntitlements(b.builder)
if err != nil {
return err
}
v := entitlements.Values{
NetworkHost: p.Meta.NetMode == pb.NetMode_HOST,
SecurityInsecure: p.Meta.SecurityMode == pb.SecurityMode_INSECURE,
}
return ent.Check(v)
}This validation logic now executes deterministically within the Run and Exec paths of the llbBridge. By intercepting the process request before the container is spawned, the daemon ensures that any dynamic process requested via the Gateway API adheres strictly to the explicit allowlist flags provided during the build invocation.
Exploiting CVE-2024-23653 requires the attacker to construct a malicious Docker image that functions as a BuildKit frontend. This image contains custom GRPC client logic programmed to invoke the NewContainer API endpoint. The request payload explicitly sets SecurityMode to INSECURE.
The attacker then distributes a Dockerfile that references this malicious frontend using the # syntax= directive. When the victim executes a docker build command against this Dockerfile, the BuildKit daemon pulls the malicious frontend image and executes it to parse the build instructions.
During this parsing phase, the frontend image dispatches the malicious GRPC request back to the buildkitd daemon. The daemon spawns the secondary container with elevated privileges. The attacker's code inside this container inherits capabilities such as CAP_SYS_ADMIN, enabling an immediate escape to the underlying host filesystem.
The impact of this vulnerability is critical, resulting in arbitrary host root code execution. A successful exploit grants the attacker total control over the build environment. This includes complete read and write access to the host filesystem, the ability to intercept credentials stored in the build context, and pivoting capabilities into the internal network.
The CVSS v3.1 vector evaluates to 9.8 (CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H). The network attack vector is fulfilled when build systems automatically ingest and build Dockerfiles from remote repositories or pull external images as build dependencies.
Continuous Integration and Continuous Deployment (CI/CD) pipelines are primarily at risk. Build nodes frequently run with substantial IAM permissions or internal network access. A single compromised build node allows an attacker to manipulate build artifacts, access repository secrets, and establish persistent backdoors in the software supply chain.
The primary mitigation is upgrading Moby BuildKit to version 0.12.5 or later. Administrators must also deploy corresponding updates to integrated platforms, including Docker Engine, Docker Desktop, Podman, and Buildah, to ensure the patched buildkitd binary propagates throughout the environment.
Organizations unable to patch immediately should implement strict controls over Dockerfile syntax directives. Build environments must prohibit the execution of untrusted or unverified frontend images. Implementing Open Policy Agent (OPA) Gatekeeper or similar policy engines can enforce restrictions on allowed # syntax targets.
Detection engineering teams can deploy static and runtime analysis tools to identify exploitation attempts. Static analysis utilities can flag suspicious syntax directives referencing untrusted repositories. Runtime eBPF monitoring can identify anomalous GRPC requests targeting the Container.Start endpoint with insecure configurations.
CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H| Product | Affected Versions | Fixed Version |
|---|---|---|
Moby BuildKit Moby | < 0.12.5 | 0.12.5 |
| Attribute | Detail |
|---|---|
| CWE ID | CWE-863 (Incorrect Authorization) |
| Attack Vector | Network |
| CVSS Score | 9.8 |
| EPSS Score | 10.30% |
| Impact | Build-Time Container Escape / RCE |
| Exploit Status | PoC Available |
| KEV Status | Not Listed |
The software performs an authorization check when an actor attempts to access a resource or perform an action, but it does not correctly perform the check.