CVEReports
CVEReports

Automated vulnerability intelligence platform. Comprehensive reports for high-severity CVEs generated by AI.

Product

  • Home
  • Sitemap
  • RSS Feed

Company

  • About
  • Contact
  • Privacy Policy
  • Terms of Service

© 2026 CVEReports. All rights reserved.

Made with love by Amit Schendel & Alon Barad



CVE-2026-48853

CVE-2026-48853: Remote Code Execution and Denial of Service in elixir-grpc via Erlpack Deserialization

Amit Schendel
Amit Schendel
Senior Security Researcher

Aug 26, 2026·8 min read·1 visit

Executive Summary (TL;DR)

Unauthenticated remote attackers can crash the BEAM VM or execute arbitrary code via crafted gRPC payloads containing unsafe Erlang External Term Format (ETF) structures when using the Erlpack codec.

A critical vulnerability exists in the elixir-grpc library's Erlpack codec, where the unsafe deserialization of Erlang External Term Format (ETF) payloads allows unauthenticated remote attackers to cause a Denial of Service through atom table exhaustion or execute arbitrary code on the host server.

Vulnerability Overview

The grpc package for Elixir (specifically elixir-grpc) provides support for the gRPC protocol over HTTP/2 inside the Erlang VM (BEAM). A core component of this implementation is its codec architecture, which enables decoding incoming payloads of different formats depending on the request headers. When the Erlpack codec is configured, the server decodes incoming payloads using Erlang External Term Format (ETF).

By sending a crafted request with the Content-Type: application/grpc+erlpack header, an unauthenticated remote attacker can trigger deserialization of untrusted ETF payloads. This processing exposes the server to both Denial of Service (DoS) and Remote Code Execution (RCE) vectors. The flaw stems from the library invoking Erlang's deserialization primitive without adequate safeguards, failing to restrict resource allocation or prevent the materialization of executable code objects.

The vulnerability is tracked under CVE-2026-48853 and GHSA-grp7-v8xh-rj7h. It represents a critical threat because the affected endpoint requires no authentication and is exposed directly to the network. The CVSS 4.0 base score is evaluated at 9.2, reflecting high confidentiality, integrity, and availability impacts on the affected host. System administrators and developers must take immediate action to either upgrade their dependencies or disable the affected codec.

Root Cause Analysis

The root cause of this vulnerability lies in the implementation of the decode/2 function in lib/grpc/codec/erlpack.ex. The grpc framework permits multiple content-types for payload serialization, with application/grpc+erlpack mapping to the GRPC.Codec.Erlpack module. Prior to the fix, the decoder parsed raw incoming binary data directly by invoking :erlang.binary_to_term/1 without the :safe option and without verifying the structured type of the decoded payload.

Erlang's :erlang.binary_to_term/1 reconstructs Erlang External Term Format (ETF) streams back into in-memory BEAM terms. This behavior presents a significant security risk when exposed to untrusted input. Under ETF specification, terms can represent primitive types, composite structures, or complex control structures like compiled anonymous functions (funs) and global identifier references. Parsing unvalidated ETF payloads triggers two distinct security failures, namely atom table exhaustion and dynamic executable term injection.

First, the BEAM virtual machine utilizes a global, shared table to store atoms, which are immutable symbolic constants. Crucially, the virtual machine does not garbage-collect atoms. The atom table is bounded by a hard-coded limit of 1,048,576 entries by default. An attacker sending serialized ETF structures containing unique, randomized atom identifiers forces the parser to allocate new atoms inside the table. This rapidly consumes all available slots, throwing a terminal SystemLimitError and instantly crashing the entire BEAM node.

Second, ETF supports the serialization of compiled anonymous functions (funs). When the VM deserializes an ETF payload containing a compiled fun, it instantiates the function object directly into memory. If the decoded term flows into a downstream execution context—such as passing the term to list-processing utilities, logging functions, mapping routines, or database drivers—the VM executes the arbitrary code embedded in the fun. Because elixir-grpc did not filter out executable types post-deserialization, this path provides a reliable mechanism for remote code execution.

Code Analysis

The original, vulnerable implementation of the codec in lib/grpc/codec/erlpack.ex was minimal and assumed all incoming data was well-formed and safe. It executed the following block of code:

defmodule GRPC.Codec.Erlpack do
  @behaviour GRPC.Codec
 
  def name() do
    "erlpack"
  end
 
  def decode(binary, _module) do
    :erlang.binary_to_term(binary)
  end
end

This simple implementation passed the raw payload binary directly to the unsafe :erlang.binary_to_term/1 function. The lack of options and post-processing left the VM fully exposed to arbitrary term instantiation.

To resolve this vulnerability, the developers modified the decoding routine to use the :safe option and introduced a strict, recursive validation function called ensure_safe_term!/1. The updated implementation is shown below:

defmodule GRPC.Codec.Erlpack do
  @behaviour GRPC.Codec
 
  def name() do
    "erlpack"
  end
 
  def decode(binary, _module) do
    # The :safe option prevents the parser from creating new atoms.
    term = :erlang.binary_to_term(binary, [:safe])
    # Recursively check the term for forbidden data types.
    ensure_safe_term!(term)
    term
  end
 
  # Raise an error if the term contains forbidden execution elements
  defp ensure_safe_term!(term)
       when is_function(term) or is_pid(term) or is_port(term) or is_reference(term) do
    raise ArgumentError,
          "refusing to decode unsafe erlpack payload containing a #{term_type(term)}"
  end
 
  defp ensure_safe_term!(term) when is_list(term) do
    Enum.each(term, &ensure_safe_term!/1)
  end
 
  defp ensure_safe_term!(term) when is_tuple(term) do
    term |> Tuple.to_list() |> Enum.each(&ensure_safe_term!/1)
  end
 
  defp ensure_safe_term!(term) when is_map(term) do
    # Map.to_list/1 is used to iterate over plain maps and structs safely
    Enum.each(Map.to_list(term), fn {key, value} ->
      ensure_safe_term!(key)
      ensure_safe_term!(value)
    end)
  end
 
  defp ensure_safe_term!(_term), do: :ok
 
  defp term_type(term) when is_function(term), do: "function"
  defp term_type(term) when is_pid(term), do: "pid"
  defp term_type(term) when is_port(term), do: "port"
  defp term_type(term) when is_reference(term), do: "reference"
end

The fix is complete because it addresses both vulnerability vectors. The :safe flag prevents the generation of novel atoms, neutralizing the atom-table exhaustion vector. Concurrently, the recursive ensure_safe_term!/1 traversal blocks the materialization of function, pid, port, and reference types. These are types that do not belong in a legitimate gRPC payload and are often abused to bypass sandbox constraints or achieve code execution across different Erlang releases.

Exploitation Methodology

To exploit this vulnerability, an attacker targets the gRPC listener port (typically 50051) over HTTP/2. The exploit relies on initiating a standard gRPC call but modifying the metadata headers and the body payload. The headers must specify Content-Type: application/grpc+erlpack to route the incoming binary payload to the vulnerable codec.

The attack flow is visualized in the following diagram:

For a Denial of Service attack, the payload consists of an ETF array populated with unique small UTF-8 atoms. An attacker can generate these systematically. When the BEAM parser encounters each new atom definition, it registers it globally. Sending a stream of distinct atoms across multiple concurrent HTTP/2 streams quickly exhausts the remaining allocation slots in the atom table, forcing the VM to execute an unrecoverable shut down.

For Remote Code Execution, the attacker serializes an anonymous function. For example, an attacker can compile a fun executing an OS system command using System.cmd/2. The compiled function bytecode is serialized into ETF using native Erlang functions. When the server processes the payload, the fun is reconstructed in memory. If any downstream application logic maps over the deserialized structure or invokes a callback on the payload elements, the embedded function executes within the context of the running application, granting the attacker shell access.

Impact & Technical Consequences

The impact of CVE-2026-48853 is critical. Successful exploitation yields remote code execution or complete service denial. Because the vulnerable code path executes immediately upon receiving and parsing the HTTP/2 gRPC frame headers and body, the attacker does not need to bypass authentication checks or possess valid credentials. Any network-exposed gRPC endpoint supporting Erlpack serialization is vulnerable.

If the attacker pursues Denial of Service, the consequence is a persistent and total crash of the hosting BEAM node. Recovering from this state requires an external orchestration service (such as Kubernetes or systemd) to restart the container or daemon. This creates a highly reliable attack vector for disrupting critical communications, particularly in distributed microservice architectures that rely heavily on gRPC for internal coordination.

If the attacker pursues Remote Code Execution, the compromise is absolute. The executed commands run with the privileges of the OS user running the BEAM VM. The attacker can read configuration environment variables, extract secrets, access localized databases, and pivot deeper into the internal network. In containerized environments, this execution can serve as a stepping stone to cluster-wide compromise if the container possesses elevated capabilities or holds service account tokens.

Remediation & Defensive Strategies

The primary and most effective remediation strategy is to upgrade elixir-grpc to version 1.0.0 or higher. This version implements the safe deserialization workflow and eliminates the vulnerability entirely. Users should update their project dependencies and redeploy the affected applications.

If upgrading is not immediately feasible, teams can apply defensive configurations to mitigate the risk. The first temporary measure is to restrict the supported codecs on the gRPC servers. By default, applications should only declare GRPC.Codec.Proto in their server module configuration. Removing GRPC.Codec.Erlpack from the codecs key prevents the server from routing requests to the vulnerable decoding logic, rejecting application/grpc+erlpack requests at the frame-routing level.

Additionally, network-level mitigations can be implemented at the ingress controller, reverse proxy, or Web Application Firewall (WAF) layer. Since the exploit depends on the Content-Type header, administrators can configure NGINX, Envoy, or HAProxy to inspect the Content-Type header of incoming gRPC traffic. Any HTTP/2 request with a Content-Type matching application/grpc+erlpack should be blocked and logged as an intrusion attempt before reaching the backend BEAM nodes.

Official Patches

elixir-grpcFix commit implementing safe deserialization check in Erlpack codec

Fix Analysis (1)

Technical Appendix

CVSS Score
9.2/ 10
CVSS:4.0/AV:N/AC:L/AT:P/PR:N/UI:N/VC:H/VI:H/VA:H/SC:N/SI:N/SA:N
EPSS Probability
0.57%
Top 55% most exploited

Affected Systems

elixir-grpc/grpc

Affected Versions Detail

Product
Affected Versions
Fixed Version
grpc
elixir-grpc
>= 0.4.0, < 1.0.0v1.0.0
AttributeDetail
CWE IDCWE-502, CWE-770
Attack VectorNetwork (AV:N/AC:L/AT:P/PR:N/UI:N)
CVSS Score9.2 (Critical)
EPSS Score0.00573 (44.79th percentile)
ImpactRemote Code Execution (RCE) / Denial of Service (DoS)
Exploit StatusPoC / Analysis
CISA KEV StatusNot Listed

MITRE ATT&CK Mapping

T1190Exploit Public-Facing Application
Initial Access
T1059Command and Scripting Interpreter
Execution
T1499Endpoint Denial of Service
Impact
CWE-502
Deserialization of Untrusted Data

The product deserializes untrusted data without sufficiently verifying that the resulting data will be safe, and allocates resources without limits.

Known Exploits & Detection

GitHub Security AdvisoryAnalysis of the Erlpack deserialization vectors (atom table exhaustion and function execution).

Vulnerability Timeline

Vulnerability published on NVD and GHSA advisory created
2026-06-15
Official fix commit merged and released in version 1.0.0
2026-06-15
CVE records updated with CVSS 4.0 score of 9.2
2026-06-17

References & Sources

  • [1]Fix Commit in GitHub Repository
  • [2]GitHub Security Advisory (GHSA-grp7-v8xh-rj7h)
  • [3]Official Erlef CNA Record
  • [4]Open Source Vulnerabilities (OSV) Record
  • [5]NVD CVE-2026-48853 Detail

Attack Flow Diagram

Press enter or space to select a node. You can then use the arrow keys to move the node around. Press delete to remove it and escape to cancel.
Press enter or space to select an edge. You can then press delete to remove it or escape to cancel.

More Reports

•19 minutes ago•CVE-2026-55637
8.8

CVE-2026-55637: Remote Administrative Command Execution in genieacs-mcp via DNS Rebinding

CVE-2026-55637 is a high-severity DNS rebinding vulnerability affecting the genieacs-mcp Model Context Protocol server. Prior to version 0.3.2, the application's Streamable HTTP transport lacks adequate Host and Origin header validation. This omission allows external attackers to bypass the Same-Origin Policy through a victim's browser and issue unauthenticated commands to loopback listeners.

Alon Barad
Alon Barad
0 views•5 min read
•about 2 hours ago•CVE-2026-48599
7.6

CVE-2026-48599: Authorization Bypass in elixir-grpc/grpc Transcoding Layer

An authorization bypass vulnerability exists in the elixir-grpc/grpc library version 0.8.0 up to 1.0.0. Due to insecure map merging precedence inside the HTTP-to-gRPC transcoding engine, query-string parameters and request bodies can override routing path variables, allowing attackers to execute unauthorized actions on other accounts.

Alon Barad
Alon Barad
4 views•6 min read
•about 3 hours ago•CVE-2026-48854
8.7

CVE-2026-48854: Unauthenticated Denial of Service via Resource Exhaustion in elixir-grpc Server

An allocation of resources without limits or throttling vulnerability exists in the Elixir grpc server component when processing unary requests. Unauthenticated remote attackers can stream unbounded data payloads, bypassing standard timeout mechanisms and exhausting host BEAM VM memory, resulting in an immediate crash of the server node.

Alon Barad
Alon Barad
3 views•7 min read
•about 4 hours ago•CVE-2026-53430
8.7

CVE-2026-53430: Unauthenticated Remote Denial of Service via Gzip Decompression Bomb in elixir-grpc/grpc

CVE-2026-53430 is a critical uncontrolled resource consumption vulnerability in the elixir-grpc/grpc library. An unauthenticated remote attacker can cause immediate memory exhaustion and system crashes by sending crafted gRPC frames compressed with Gzip, leading to a complete Denial of Service.

Alon Barad
Alon Barad
5 views•7 min read
•about 5 hours ago•CVE-2026-55663
5.6

CVE-2026-55663: unauthenticated state cookie forgery in mediasoup SCTP stack

A cryptographic validation flaw (CWE-345) exists in the built-in SCTP implementation of mediasoup (NPM package < 3.20.6, Rust crate < 0.22.5). Due to missing cryptographic signature verification of State Cookies, an on-path attacker targeting PlainTransport or PipeTransport without DTLS can forge state cookies containing static magic bytes. This allows the attacker to establish arbitrary SCTP associations and inject malicious DataChannel messages.

Amit Schendel
Amit Schendel
4 views•8 min read
•about 6 hours ago•CVE-2026-49757
9.2

CVE-2026-49757: Authentication Bypass and Account Takeover in ash_authentication OAuth2/OIDC

An authentication bypass and account takeover vulnerability in the AshAuthentication Elixir library (developed by team-alembic) allows unauthenticated remote attackers to compromise local accounts. By relying on mutable and unverified email claims instead of stable cryptographic issuer and subject pairings during OAuth2 and OIDC federated login flows, the application fails to validate the trust boundary of the incoming session.

Alon Barad
Alon Barad
3 views•6 min read