Tornar al Blog

CVE-2026-76504: la regla comparava text, no recursos

CVE-2026-76504: la regla comparava text, no recursos

L'autenticació del Catalyst SD-WAN Manager no es va trencar. Funcionava. El que es va trencar va ser la llista que decideix quines peticions hi han de passar. La llista deia /j_security_check; la petició deia /%6a_security_check, que és la mateixa ruta amb la jota escrita en hexadecimal. Per a la llista són dues cadenes diferents. Per al servidor que hi ha darrere, el mateix recurs. En aquest forat d'un caràcter hi cap un administrador.

Operem SD-WAN multiseu i xarxa pròpia amb BGP i túnels WireGuard, de manera que un avís sobre un orquestrador ens toca de prop i el vam llegir ahir per obligació professional. Però aquest post no va de Cisco, i serveix igual encara que no tinguis ni un sol equip seu. Va d'una manera de trencar que no pertany a cap producte: existeix a qualsevol lloc on la capa que decideix si cal autenticar-se i la capa que resol el recurs llegeixen la mateixa petició de manera diferent. Nosaltres també tenim regles escrites així.

El que es va publicar ahir, i en quin ordre va passar

L'avís cisco-sa-sdwan-webauth-xr8beuuU va sortir el 30 de setembre del 2026 a les 13:00 GMT. CVE-2026-76504, CVSS base 9,8, vector CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H. Llegit en català: per xarxa, complexitat baixa, sense credencials prèvies, sense que ningú hagi de clicar res, i amb impacte alt a les tres potes. La classificació és CWE-177, tractament indegut de la codificació de la URL.

L'ordre dels fets importa més que la puntuació. Cisco escriu que el seu PSIRT va tenir coneixement d'explotació activa el setembre del 2026. És a dir: primer es va explotar, després es va publicar. I la CISA el va afegir al seu catàleg de vulnerabilitats explotades el mateix 30 de setembre, amb data límit de correcció el 3 d'octubre. Tres dies. I aquest termini no surt de la nota del CVSS: surt de l'arbre de decisió de la directiva BOD 26-04, que creua quatre variables —si l'actiu està exposat a internet, si el CVE és al catàleg, si l'explotació és automatitzable i si dona control total o parcial—. Aquest cas marca les quatre caselles dolentes, i aquesta combinació és l'única que porta aparellat tres dies i triatge forense, no només tres dies.

Branca del Manager Primera versió corregida
Anterior a 20.9No hi ha pedaç: toca migrar a una branca amb correcció
20.920.9.10.1
20.1220.12.8.2
20.1520.15.6.1
20.1820.18.4.1
26.126.1.2.1
26.226.2.1

Dos detalls d'aquella taula que convé no passar per sobre. El primer: l'error afecta el producte independentment de la configuració, de manera que no hi ha cap «nosaltres no fem servir aquesta part». El segon: Cisco diu, amb totes les lletres, que no hi ha cap workaround que ho resolgui. L'únic que hi ha és el pedaç de la teva branca — i compte amb la columna de l'esquerra, perquè la branca mana sobre l'antiguitat: ser a l'última 20.12 publicada abans d'ahir no et deixa en terreny segur si aquella última no és la 20.12.8.2.

D'on surt j_security_check, i per què aquesta ruta havia d'estar exempta

Aquell nom tan estrany no se'l va inventar Cisco. j_security_check és l'acció que l'especificació de Jakarta Servlet —l'antiga Java EE— reserva des de fa més de vint anys per al formulari d'inici de sessió: el formulari ha de fer POST contra una URL que acabi en /j_security_check, amb els camps anomenats j_username i j_password, i és el contenidor —no l'aplicació— qui recull allò i decideix. Qualsevol aplicació Java amb autenticació per formulari té aquesta ruta. No és una porta de servei ni una resta de depuració: és la porta principal, i és on la norma diu que estigui.

Aquesta ruta ha d'estar exempta de la comprovació de sessió. És el lloc on s'aconsegueix la sessió: si exigissis una sessió vàlida per arribar al formulari de login, ningú no podria iniciar sessió mai. L'excepció no hi és de més, no és una deixadesa, no és deute tècnic. És obligatòria. Tot sistema amb autenticació té almenys una ruta que s'avalua sense autenticar, i aquesta ruta és, per construcció, la més exposada que té.

L'error, per tant, no és tenir l'excepció. És un esglaó més avall: en com es comprova si una petició concreta hi cau a dins. I allà es va comparar text.

Dues lectures de la mateixa petició

%6a és la jota minúscula escrita com el seu codi hexadecimal, i això és perfectament legal en una URL: l'estàndard permet escriure qualsevol caràcter així, i els navegadors i servidors fa dècades que ho desfan sense que ningú se n'assabenti. De manera que /%6a_security_check i /j_security_check són la mateixa ruta escrita de dues maneres. La diferència és qui la mira i quan la desfà.

La capa de davant compara la cadena que ha arribat contra la seva llista de rutes i no hi troba coincidència, de manera que la petició no rep el tractament que li tocava. La capa de darrere desfà el percentatge i serveix el mateix recurs de sempre. Cap de les dues no fa res il·legal per separat; el que no existeix és un acord entre elles sobre quan es desfà la codificació. La recomanació de MITRE per a CWE-177 cap en una línia i és exactament la que s'incompleix: descodifica i canonicalitza a la teva representació interna abans de validar, i no descodifiquis dues vegades.

Dit així sona a problema de qui escriu productes. No ho és. El patró és protegir una ruta pel seu nom des d'una capa diferent de la que la resol, i aquesta frase descriu molta infraestructura corrent: el location d'un nginx que exigeix auth_basic sobre /admin, una regla de WAF escrita com a expressió regular sobre el camí, un balancejador a qui vas dir «publica només /api», la cadena de filtres d'un framework que protegeix per prefix. Cadascuna d'aquestes peces normalitza, i ho fa bé i documentat. El forat no apareix dins d'una peça: apareix entre dues, quan les seves normalitzacions no són idèntiques i ningú no ho ha comprovat mai perquè, amb la ruta escrita en clar, totes dues donen el mateix resultat.

La prova de trenta segons, al teu stack

Agafa una ruta que el teu proxy protegeixi i demana-la dues vegades: una tal qual i una altra amb la primera lletra en hexadecimal. %61 és la «a».

curl -s -o /dev/null -w '%{http_code}\n' https://tu.dominio/admin/
curl -s -o /dev/null -w '%{http_code}\n' https://tu.dominio/%61dmin/

Variants que valen la pena a la segona volta: la ruta en majúscules, amb barra final i sense, amb la codificació doble (%2561dmin, que és el percentatge escrit al seu torn en hexadecimal), amb un punt i coma pel mig. I ara la part que fa útil la prova: el que busques no és un 200. Un 200 pot voler dir simplement que aquest recurs era públic i no passava res. El que busques és una diferència de criteri entre les dues capes, i això no ho diu el codi de resposta: ho diuen els dos registres posats l'un al costat de l'altre. Si el proxy va anotar que no va aplicar la regla i l'aplicació va anotar que va servir /admin/, ja tens la resposta i no cal seguir.

Avancem el resultat més probable, perquè és el que confon: contra un nginx a seques no hi veuràs cap diferència, i això és bon senyal —desfà el percentatge abans de decidir quin location aplica, de manera que les dues peticions són la mateixa per a ell—. El forat surt quan hi ha dues peces i la segona torna a tocar la ruta. Per això la prova que interessa no és contra el teu proxy tot sol, sinó contra la cadena sencera tal com està muntada en producció. I l'obvi, dit en veu alta perquè costa poc: això es fa contra sistemes propis, amb permís i avisant qui estigui mirant els panells. Llançat contra un tercer no és una prova, és una altra cosa amb un altre nom.

Els dos grep que el pedaç no substitueix

Si s'explotava abans de l'avís, pedaçar tanca la porta però no contesta la pregunta que importa, que és si algú hi va passar mentre era oberta. Aquí Cisco va fer una cosa que no sempre fa i que s'agraeix: va publicar on mirar, amb la ruta sencera i amb línies d'exemple reals. A /var/log/nms/containers/service-proxy/serviceproxy-access.log, peticions a j_security_check des d'adreces desconegudes o no autoritzades; la línia que publica l'avís comença així: [2026-09-29T23:11:13.948-05:00] "POST /%6a_security_check HTTP/1.1" 200 - 48 0 4. I a /var/log/nms/vmanage-server.log, l'altra cara de la mateixa petició, amb l'usuari a la vista: Request Stored in Map is (/%6a_security_check) for user (viptela-reserved-..).

grep -F '_security_check' /var/log/nms/containers/service-proxy/serviceproxy-access.log | grep -F '%'

grep -F 'viptela-reserved-' /var/log/nms/vmanage-server.log

El primer no busca %6a en concret a propòsit: qualsevol signe de percentatge en una línia de _security_check mereix una mirada, perquè el formulari legítim no codifica res en aquesta ruta. Dit amb precisió, perquè importa: el grep és de línia i no de ruta, així que també et traurà percentatges que vinguin de l'agent d'usuari o de la cadena de consulta. Són falsos positius i es descarten d'una ullada, però convé saber-ho abans de comptar. I el nom del segon fitxer explica tot sol una part de la història: es diu vmanage-server.log perquè el producte es va dir vManage. El nom comercial va canviar; el del fitxer no, i per això al grep cal escriure el nom vell.

Les dues preguntes operatives que vénen darrere d'aquests dos comandaments no són de seguretat, són d'operació, i solen tenir pitjor resposta. La primera: aquests fitxers surten de l'aparell? Si només viuen al disc de l'equip que estàs investigant, l'estàs investigant amb les seves pròpies notes, i l'acció que exigeix la CISA per a aquest CVE no diu únicament «pedaça»: remet a la seva directiva BOD 26-04 i als seus requisits de triatge forense. És difícil fer triatge sobre un registre que el mateix sospitós podria haver editat. La segona: des de quina data els tens? Si la rotació se'n porta trenta dies, la finestra del setembre de què parla l'avís potser ja no existeix. Vam escriure justament sobre això quan li va tocar al Firewall Management Center: pedaçar tanca la porta, però no esborra el que algú ja es va endur.

No hi havia workaround, però sí que hi havia diferència

Les dues coses són certes alhora i convé no barrejar-les. No hi ha workaround per a l'error: res del que toquis a la configuració del Manager no ho arregla. Però la recomanació que Cisco repeteix per als desplegaments a casa és la de sempre —impedir l'accés des de xarxes no segures i limitar-lo amb un filtratge a hosts coneguts i de confiança—, i aquesta sí que decideix quanta gent ho podia intentar. Un 9,8 sense autenticació per xarxa és devastador quan el port és on qualsevol hi arriba, i és una tasca de manteniment quan al 443 de l'orquestrador només hi arriba una xarxa de gestió amb origen filtrat.

Que no es llegeixi al revés: això no substitueix el pedaç, i el termini de la CISA són tres dies que es compleixen. El que canvia és si aquesta setmana has tingut un incident o una finestra de manteniment. Ja vam escriure sobre per què l'orquestrador del teu SD-WAN és la clau de totes les teves seus, i sobre el repartiment de responsabilitats quan surt un error d'un fabricant de xarxa: la vulnerabilitat és seva, l'excepció del tallafocs és teva. Aquest cas és la mateixa frase amb un altre producte; si ja la vas llegir allà, aquest paràgraf et sobra.

Els límits del que acabem de dir

No hem vist l'exploit ni l'hem reproduït, i no tenim cap Manager afectat per explicar: la mecànica que hem descrit és la que publica l'avís de Cisco i recull la fitxa de la CISA, i fins aquí arribem. Els dos grep surten de la descripció d'indicadors d'aquest avís, però el format exacte de cada línia depèn de la teva versió, així que mira una línia real abans de fiar-te del recompte. La prova del %61 és il·lustrativa i no és un escàner: una diferència entre les dues capes no és automàticament un forat, és un lloc on cal mirar. I les versions corregides són les que figuraven a l'avís del 30 de setembre del 2026: Cisco revisa els seus avisos, i el que mana és el document, no aquest post.

El conflicte d'interès, per davant: no som revenedors de Cisco ni de cap plataforma SD-WAN, però operar orquestradors aliens, decidir des d'on s'abasten i aplicar pedaços amb termini és feina que facturem.

Fonts (verificades l'1 d'octubre del 2026): l'identificador de l'avís, la seva data i hora de publicació (30-09-2026, 13:00 GMT), el CVSS base 9,8 amb el seu vector, la classificació CWE-177, la frase sobre que afecta el producte amb independència de la configuració, la taula de branques i primeres versions corregides, la declaració que no existeix workaround, la recomanació de restringir l'accés a hosts coneguts, la menció que el PSIRT va conèixer explotació activa el setembre del 2026 i els indicadors de compromís amb els noms de fitxer serviceproxy-access.log i vmanage-server.log — avís de seguretat de Cisco cisco-sa-sdwan-webauth-xr8beuuU; la data d'alta al catàleg (30-09-2026), el termini de correcció del 3 d'octubre del 2026 i l'acció requerida amb referència a la BOD 26-04 i als requisits de triatge forense — catàleg de vulnerabilitats explotades conegudes de la CISA; la definició de CWE-177 i la recomanació de descodificar i canonicalitzar abans de validar — CWE-177, MITRE; que j_security_check, j_username i j_password són els noms que l'especificació reserva per a l'autenticació per formulari — documentació de Jakarta EE; el detall del caràcter codificat a la ruta i la lectura dels indicadors — anàlisi de Rapid7. La lectura que el patró «protegir pel nom de ruta des d'una altra capa» és el problema de fons, els dos grep i la prova del %61 són nostres, no de cap d'aquelles fonts.

Des de quants llocs s'abasta el teu orquestrador?

Si la resposta és «és a la DMZ» i no una llista d'orígens, aquesta dada la decideix avui un avís de fabricant i no pas tu. Dissenyem i operem SD-WAN multiseu i el perímetre de seguretat que l'envolta, inclòs l'avorriment de portar la llista de qui abasta el pla de gestió i que els registres surtin de l'aparell abans de necessitar-los. Si vols, ho mirem sobre la teva xarxa i et diem què hi ha publicat que no hi hauria de ser.

Parlar amb everyWAN

Etiquetes:

Compartir:

Subscriu-te al nostre butlletí

Per rebre històries del món IT, novetats d'everyWAN i ofertes exclusives per a subscriptors, dona't d'alta a la nostra llista de correu

everyWAN
everyWAN