CVE-2026-48772
Full vulnerability record from the local CVENow database.
Description
ProxySQL is a proxy for MySQL and its forks, as well as PostgreSQL. In versions 2.0.0 through 3.0.8, the ProxySQL MySQL frontend accepts the `PROXY UNKNOWN <addr> <addr> <port> <port>\r\n` PP1 frame as a well-formed PROXY protocol header. The HAProxy PROXY protocol v1 specification says that when the protocol token is `UNKNOWN`, the receiver MUST ignore any address fields that follow it, because the proxy has declared it cannot determine the client identity. ProxySQL parses those address fields anyway via `sscanf` and writes the spoofed source address into the session's `addr.addr` field. From there it flows directly into the query-rule matcher, where the `client_addr` predicate decides routing and ACL. When `mysql-proxy_protocol_networks = '*'` (the default), any TCP peer can send a PP1 frame and choose any source IP claim. With that, any `mysql_query_rules` row pinned to a `client_addr` value is forgeable: the attacker writes the address they want to match into the PP1 line, and ProxySQL routes their query as if it came from that address. In practice this is a routing and ACL bypass. Real deployments use `client_addr` for read-write splitting (internal apps go to the primary, public traffic to read replicas), per-app schema pinning, and query-filter rules (DDL allowed only from admin CIDR, public queries blocked from dangerous patterns). An attacker that can reach the frontend port can forge their way into any of those routes. Version 3.0.9 patches this issue.
View original CVE JSON
{
"id": "CVE-2026-48772",
"sourceIdentifier": "[email protected]",
"published": "2026-06-19T20:16:17.803",
"lastModified": "2026-10-25T23:10:00.167",
"vulnStatus": "Analyzed",
"cveTags": [],
"descriptions": [
{
"lang": "en",
"value": "ProxySQL is a proxy for MySQL and its forks, as well as PostgreSQL. In versions 2.0.0 through 3.0.8, the ProxySQL MySQL frontend accepts the `PROXY UNKNOWN <addr> <addr> <port> <port>\\r\\n` PP1 frame as a well-formed PROXY protocol header. The HAProxy PROXY protocol v1 specification says that when the protocol token is `UNKNOWN`, the receiver MUST ignore any address fields that follow it, because the proxy has declared it cannot determine the client identity. ProxySQL parses those address fields anyway via `sscanf` and writes the spoofed source address into the session's `addr.addr` field. From there it flows directly into the query-rule matcher, where the `client_addr` predicate decides routing and ACL. When `mysql-proxy_protocol_networks = '*'` (the default), any TCP peer can send a PP1 frame and choose any source IP claim. With that, any `mysql_query_rules` row pinned to a `client_addr` value is forgeable: the attacker writes the address they want to match into the PP1 line, and ProxySQL routes their query as if it came from that address. In practice this is a routing and ACL bypass. Real deployments use `client_addr` for read-write splitting (internal apps go to the primary, public traffic to read replicas), per-app schema pinning, and query-filter rules (DDL allowed only from admin CIDR, public queries blocked from dangerous patterns). An attacker that can reach the frontend port can forge their way into any of those routes. Version 3.0.9 patches this issue."
},
{
"lang": "es",
"value": "ProxySQL es un proxy para MySQL y sus bifurcaciones, así como para PostgreSQL. En las versiones 2.0.0 a 3.0.8, el frontend MySQL de ProxySQL acepta la trama PP1 ’PROXY UNKNOWN [addr] [addr] [port] [port]\\r\\n’ como una cabecera de protocolo PROXY bien formada. La especificación del protocolo PROXY v1 de HAProxy establece que cuando el token del protocolo es ’UNKNOWN’, el receptor DEBE ignorar cualquier campo de dirección que le siga, porque el proxy ha declarado que no puede determinar la identidad del cliente. ProxySQL analiza esos campos de dirección de todos modos a través de ’sscanf’ y escribe la dirección de origen falsificada en el campo ’addr.addr’ de la sesión. Desde allí fluye directamente al comparador de reglas de consulta, donde el predicado ’client_addr’ decide el enrutamiento y la ACL. Cuando ’mysql-proxy_protocol_networks = ’*’’ (el valor predeterminado), cualquier par TCP puede enviar una trama PP1 y elegir cualquier declaración de IP de origen. Con eso, cualquier fila de ’mysql_query_rules’ fijada a un valor de ’client_addr’ es falsificable: el atacante escribe la dirección que quiere que coincida en la línea PP1, y ProxySQL enruta su consulta como si viniera de esa dirección. En la práctica, esto es un bypass de enrutamiento y ACL. Las implementaciones reales usan ’client_addr’ para la división de lectura-escritura (las aplicaciones internas van al primario, el tráfico público a las réplicas de lectura), la fijación de esquema por aplicación y las reglas de filtro de consulta (DDL permitido solo desde CIDR de administrador, consultas públicas bloqueadas de patrones peligrosos). Un atacante que puede alcanzar el puerto del frontend puede falsificar su camino hacia cualquiera de esas rutas. La versión 3.0.9 parchea este problema."
}
],
"affected": [
{
"source": "[email protected]",
"affectedData": [
{
"vendor": "sysown",
"product": "proxysql",
"versions": [
{
"version": ">= 2.0.0, < 3.0.9",
"status": "affected"
}
]
}
]
}
],
"metrics": {
"cvssMetricV31": [
{
"source": "[email protected]",
"type": "Secondary",
"cvssData": {
"version": "3.1",
"vectorString": "CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:C/C:H/I:H/A:N",
"baseScore": 10.0,
"baseSeverity": "CRITICAL",
"attackVector": "NETWORK",
"attackComplexity": "LOW",
"privilegesRequired": "NONE",
"userInteraction": "NONE",
"scope": "CHANGED",
"confidentialityImpact": "HIGH",
"integrityImpact": "HIGH",
"availabilityImpact": "NONE"
},
"exploitabilityScore": 3.9,
"impactScore": 5.8
}
],
"ssvcV203": [
{
"source": "134c704f-9b21-4f2e-91b3-4a467353bcc0",
"ssvcData": {
"timestamp": "2026-06-22T15:15:18.320420Z",
"id": "CVE-2026-48772",
"options": [
{
"exploitation": "poc"
},
{
"automatable": "yes"
},
{
"technicalImpact": "partial"
}
],
"role": "CISA Coordinator",
"version": "2.0.3"
}
}
]
},
"weaknesses": [
{
"source": "[email protected]",
"type": "Secondary",
"description": [
{
"lang": "en",
"value": "CWE-348"
},
{
"lang": "en",
"value": "CWE-863"
}
]
}
],
"configurations": [
{
"nodes": [
{
"operator": "OR",
"negate": false,
"cpeMatch": [
{
"vulnerable": true,
"criteria": "cpe:2.3:a:proxysql:proxysql:*:*:*:*:*:*:*:*",
"versionStartIncluding": "2.0.0",
"versionEndExcluding": "3.0.9",
"matchCriteriaId": "B4CAF149-E318-46D2-AFFB-E9D9A57B081E"
}
]
}
]
}
],
"references": [
{
"url": "https://github.com/sysown/proxysql/releases/tag/v3.0.9",
"source": "[email protected]",
"tags": [
"Release Notes"
]
},
{
"url": "https://github.com/sysown/proxysql/security/advisories/GHSA-gw94-85m2-x8v2",
"source": "[email protected]",
"tags": [
"Vendor Advisory",
"Exploit"
]
},
{
"url": "https://github.com/sysown/proxysql/security/advisories/GHSA-gw94-85m2-x8v2",
"source": "134c704f-9b21-4f2e-91b3-4a467353bcc0",
"tags": [
"Vendor Advisory",
"Exploit"
]
}
]
}