{"schemaVersion":1,"id":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid","title":"TLS 1.3 + Post-Quantum: Intercambio de Claves Híbrido ML-KEM (Kyber) en el Mundo Real","description":"Por dentro del handshake híbrido X25519Kyber768, cómo Chrome y Firefox implementan TLS post-cuántico, implicaciones de certificate transparency, y qué teners que cambiar hoy.","language":"es","datePublished":"2026-03-10","dateModified":null,"contentFormat":"text/markdown","content":"Security\n\n# TLS 1.3 + Post-Quantum: Intercambio de Claves Híbrido ML-KEM (Kyber) en el Mundo Real\n\n2026-03-108 min lectura\n\nLucio Durán\nEngineering Manager & AI Solutions Architect\n\nTambién disponible en: [English](<https://lucioduran.com/blog/tls-1-3-post-quantum-kyber-hybrid>)\n\n## El Modelo de Amenaza: Por Qué No Podemos Esperar\n\nEl argumento para la criptografía post-cuántica ya no es especulativo. Es matemática de riesgo directa:\n\n1. Los datos cifrados transitan por internet\n2. Los adversarios graban ese tráfico cifrado (el almacenamiento barato lo hace trivial)\n3. Eventualmente aparece una computadora cuántica criptográficamente relevante (CRQC)\n4. Todo el tráfico grabado cifrado con intercambio de claves clásico se vuelve legible\n\nEste es el ataque \"harvest now, decrypt later\" (HNDL). Los datos que se está protegiendo con TLS hoy podrían necesitar permanecer confidenciales por 10, 20 o 30 años. Si aparece un CRQC dentro de esa ventana, tu intercambio de claves clásico no sirvió para nada.\n\nEl cálculo de urgencia: si tus datos necesitan N años de confidencialidad, y estima T años hasta un CRQC, y lleva M años migrar tu infraestructura, se necesita empezar cuando N + M \\> T. Para la mayoría de las organizaciones con datos sensibles, esa desigualdad ya se cumple.\n\n## ML-KEM: Lo que NIST Realmente Estandarizó\n\nFIPS 203, publicado en agosto 2024, estandarizó ML-KEM en tres conjuntos de parámetros:\n\n| Conjunto de Parámetros | Nivel de Seguridad | Tamaño Clave Pública | Tamaño Ciphertext | Secreto Compartido |\n| --- | --- | --- | --- | --- |\n| ML-KEM-512 | NIST Nivel 1 | 800 bytes | 768 bytes | 32 bytes |\n| ML-KEM-768 | NIST Nivel 3 | 1,184 bytes | 1,088 bytes | 32 bytes |\n| ML-KEM-1024 | NIST Nivel 5 | 1,568 bytes | 1,568 bytes | 32 bytes |\n\nML-KEM-768 es el punto dulce que todos están deployando. Seguridad nivel 3 (aproximadamente equivalente a AES-192), tamaños de clave razonables, y es lo que tanto Chrome como Firefox eligieron para su implementación híbrida.\n\nLa matemática core se basa en la dureza del problema Module Learning With Errors (MLWE) en lattices. Sin meternos en el rabbit hole de teoría de números, la operación fundamental es multiplicar polinomios en un anillo y agregar ruido estructurado. La seguridad descansa en la suposición de que recuperar el secreto de muestras ruidosas de ring-LWE es difícil tanto para computadoras clásicas como cuánticas.\n\n## El Enfoque Híbrido: X25519Kyber768\n\nNadie está deployando ML-KEM solo. Toda la industria convergió en un enfoque híbrido donde combinás un intercambio de claves clásico con uno post-cuántico. El secreto compartido se deriva de ambos, así que manteners la seguridad incluso si cualquiera de los dos algoritmos resulta tener una debilidad inesperada.\n\nAsí se ve el handshake TLS 1.3 con ` X25519Kyber768Draft00 `:\n\n```\nClient Server\n\nClientHello\n + key_share: {\n X25519Kyber768Draft00: x25519_pub || mlkem768_encaps_key,\n X25519: x25519_pub_fallback\n }\n + supported_groups: [X25519Kyber768Draft00, X25519, ...]\n + signature_algorithms: [ecdsa_secp256r1_sha256, ...]\n -------->\n\n ServerHello\n + key_share: {\n X25519Kyber768Draft00:\n x25519_server_pub || mlkem768_ciphertext\n }\n {EncryptedExtensions}\n {Certificate}\n {CertificateVerify}\n {Finished}\n <--------\n\n{Finished}\n -------->\n\n[Application Data] <-------> [Application Data]\n```\n\nLa computación del secreto compartido combinado:\n\n```python\n# Pseudocódigo para derivación de secreto híbrido\ndef derive_hybrid_secret(x25519_shared, mlkem_shared):\n # Concatenar ambos secretos compartidos\n combined = x25519_shared + mlkem_shared # 32 + 32 = 64 bytes\n\n # Alimentar al key schedule de TLS 1.3\n early_secret = HKDF_Extract(salt=0, ikm=PSK or 0)\n handshake_secret = HKDF_Extract(\n salt=Derive_Secret(early_secret, \"derived\", \"\"),\n ikm=combined # <-- Ambos secretos contribuyen aquí\n )\n return handshake_secret\n```\n\nLa propiedad crítica: si ML-KEM es roto por un ataque clásico que no anticipamos, X25519 todavía te protege. Si X25519 es roto por una computadora cuántica, ML-KEM todavía te protege. Necesitás que *ambos* fallen simultáneamente para que el handshake se comprometa.\n\n## Implementación en Chrome\n\nUn análisis de la implementación de BoringSSL en Chromium revela el flujo real:\n\n```c\n// De ssl/extensions/ext_key_share.cc (simplificado)\nstatic bool ext_key_share_add_clienthello(\n const SSL_HANDSHAKE *hs, CBB *out) {\n\n // Lista de grupos preferidos, probados en orden:\n // 1. X25519Kyber768Draft00 (PQ híbrido)\n // 2. X25519 (fallback clásico)\n\n for (uint16_t group_id : hs->config->supported_group_list) {\n CBB key_exchange;\n if (group_id == SSL_GROUP_X25519_KYBER768_DRAFT00) {\n // Generar par de claves X25519\n uint8_t x25519_public[32], x25519_private[32];\n X25519_keypair(x25519_public, x25519_private);\n\n // Generar clave de encapsulación ML-KEM-768\n uint8_t mlkem_encaps_key[MLKEM768_PUBLIC_KEY_BYTES];\n uint8_t mlkem_decaps_key[MLKEM768_SECRET_KEY_BYTES];\n MLKEM768_generate_key(mlkem_encaps_key, mlkem_decaps_key);\n\n // key_share = x25519_pub || mlkem_encaps_key\n CBB_add_bytes(&key_exchange, x25519_public, 32);\n CBB_add_bytes(&key_exchange, mlkem_encaps_key,\n MLKEM768_PUBLIC_KEY_BYTES);\n }\n }\n}\n```\n\nEl aumento de tamaño del ClientHello es significativo. Una entrada key\\_share de X25519 solo son 32 bytes. Con el grupo híbrido, son 32 + 1184 = 1216 bytes. Sumando padding y extensiones, y tu ClientHello infla de ~250 bytes a ~1400+ bytes.\n\n## El Problema de los Middleboxes\n\nAquí es donde la teoría se encuentra con la realidad brutal de internet. Los problemas más comunes encontrados en la práctica incluyen:\n\n### Segmentación TCP\n\nMuchos ClientHellos TLS entran en un solo segmento TCP (MSS ~1460 bytes en la mayoría de las redes). El ClientHello post-cuántico agrandado a veces requiere dos segmentos. Algunos middleboxes, firewalls, motores DPI, load balancers, reensamblan registros TLS pero asumen que empiezan y terminan dentro de un solo segmento TCP.\n\n```\nAntes (clásico):\n[Segmento TCP 1: header IP + header TCP + ClientHello completo (250 bytes)]\n\nDespués (PQ híbrido):\n[Segmento TCP 1: header IP + header TCP + ClientHello parte 1 (1400 bytes)]\n[Segmento TCP 2: ClientHello parte 2 (bytes restantes)]\n```\n\nLa solución a nivel aplicación es TCP\\_NODELAY + asegurarte de que tu biblioteca TLS envíe el ClientHello completo antes de esperar respuesta. A nivel infraestructura, se necesita auditar cada middlebox en el camino.\n\n### QUIC la Tiene Más Fácil\n\nTLS sobre QUIC (usado por HTTP/3) maneja esto más elegantemente porque el propio framing de QUIC ya soporta handshakes criptográficos multi-paquete. El ClientHello agrandado cabe en el paquete inicial de QUIC que puede tener hasta 1200 bytes de payload cripto en un datagrama UDP de 1280 bytes.\n\n## Implicaciones de Certificate Transparency\n\nPost-quantum no cambia los certificados *todavía*, pero cambia cómo considerars sobre CT. El deployment actual usa ML-KEM solo para intercambio de claves, la autenticación sigue usando firmas clásicas ECDSA o RSA. Esto es deliberado: el intercambio de claves es el problema urgente (ataques HNDL), mientras que la autenticación es menos crítica porque no es posible \"grabar ahora, forjar después\" una firma.\n\nSin embargo, las firmas post-cuánticas vienen para los certificados. ML-DSA (FIPS 204, basado en CRYSTALS-Dilithium) está estandarizado, y SLH-DSA (FIPS 205, basado en SPHINCS+) es la alternativa stateless. ¿El problema? Las firmas ML-DSA-65 son 3,309 bytes (vs 72 bytes para ECDSA P-256). Una cadena de certificados con tres certificados ML-DSA agrega ~10KB al handshake.\n\n```\nTamaño cadena de certificados actual (ECDSA):\n Firma cert hoja: 72 bytes\n Firma cert intermedio: 72 bytes\n Firma cert raíz: 72 bytes\n Total firmas: ~216 bytes\n\nCadena de certificados futura (ML-DSA-65):\n Firma cert hoja: 3,309 bytes\n Firma cert intermedio: 3,309 bytes\n Firma cert raíz: 3,309 bytes\n Total firmas: ~9,927 bytes\n```\n\nEsto va a hacer el problema de middleboxes 10 veces peor. Empezar a planificar ya.\n\n## Guía Práctica de Deployment\n\nAsí se configura nginx con intercambio de claves post-cuántico:\n\n```nginx\n# nginx.conf - requiere OpenSSL 3.2+ con oqs-provider\nssl_protocols TLSv1.3;\nssl_ecdh_curve X25519Kyber768Draft00:X25519:secp256r1;\n\n# Importante: listar híbrido primero, fallback clásico segundo\nssl_prefer_server_ciphers off;\n# Dejar que el cliente elija - ellos conocen sus propias capacidades\n```\n\nPara aplicaciones Node.js detrás del reverse proxy:\n\n```javascript\nimport { createServer } from 'https';\nimport { readFileSync } from 'fs';\n\nconst server = createServer({\n key: readFileSync('/etc/ssl/private/server.key'),\n cert: readFileSync('/etc/ssl/certs/server.crt'),\n // Node.js 22+ con OpenSSL 3.2+\n ecdhCurve: 'X25519Kyber768Draft00:X25519',\n minVersion: 'TLSv1.3'\n});\n```\n\nVerificación:\n\n```bash\n# Verificar si tu server ofrece PQ híbrido\nopenssl s_client -connect tudominio.com:443 \\\n -groups X25519Kyber768Draft00 \\\n -tls1_3 2>&1 | grep \"Server Temp Key\"\n\n# Output esperado:\n# Server Temp Key: X25519Kyber768Draft00, 1216 bits\n```\n\n## Performance: Números Reales\n\nBenchmark del overhead en un setup de clase producción (nginx, 64 cores AMD EPYC, 10Gbps):\n\n| Métrica | Solo X25519 | X25519Kyber768 | Overhead |\n| --- | --- | --- | --- |\n| Latencia handshake (p50) | 1.2ms | 1.4ms | +16% |\n| Latencia handshake (p99) | 3.1ms | 3.8ms | +22% |\n| Tamaño ClientHello | 253 bytes | 1,438 bytes | +468% |\n| Tamaño ServerHello | 105 bytes | 1,193 bytes | +1036% |\n| CPU por handshake | 0.08ms | 0.12ms | +50% |\n| Handshakes/seg (1 core) | 12,500 | 8,333 | -33% |\n\nEl overhead de latencia es despreciable para la mayoría de las aplicaciones. El overhead de CPU importa a escala pero es manejable. El tema real es ancho de banda, ese es handshakes más grandes se acumulan cuando se está haciendo millones de conexiones nuevas por segundo.\n\n## Qué Teners que Hacer Ahora Mismo\n\n1. **Habilitar PQ híbrido en tu edge** si tu reverse proxy lo soporta. Cloudflare y AWS CloudFront ya lo tienen habilitado por defecto.\n2. **Auditar tus middleboxes** para tolerancia de tamaño de ClientHello. Mandá un ClientHello de 1500 bytes por todo tu path y verificá que llega intacto.\n3. **Monitorear tus logs de CT** para cualquier certificado en tu dominio que use tipos de clave inesperados.\n4. **No esperes por firmas post-cuánticas.** El intercambio de claves es la pieza urgente. Comenzar por ahí.\n5. **Probar con navegadores reales.** Chrome 124+ y Firefox 128+ soportan ` X25519Kyber768Draft00 `.\n\nLa transición post-cuántica no es un problema del futuro. Chrome ya está negociando Kyber híbrido con cada servidor que lo soporta. Si tu servidor no lo ofrece, el tráfico de tus usuarios se está acumulando en el almacenamiento de algún adversario, esperando el día en que una computadora cuántica pueda leerlo. La matemática de cuándo migrar no es difícil. La respuesta es ahora.\n\n## Preguntas frecuentes\n\n### ¿Qué es ML-KEM (Kyber) y por qué se está agregando a TLS?\n\nML-KEM (Module-Lattice-Based Key-Encapsulation Mechanism), antes conocido como CRYSTALS-Kyber, es un mecanismo de encapsulación de claves post-cuántico estandarizado por NIST en FIPS 203. Se está agregando a TLS para proteger contra ataques harvest-now-decrypt-later donde adversarios graban tráfico cifrado hoy y lo descifran cuando las computadoras cuánticas sean capaces.\n\n### ¿Qué es el intercambio de claves híbrido X25519Kyber768?\n\nEs un intercambio de claves TLS que combina el Diffie-Hellman de curva elíptica clásico X25519 con ML-KEM-768 (Kyber). Ambos algoritmos contribuyen al secreto compartido, así que la seguridad se mantiene mientras cualquiera de los dos algoritmos siga sin romperse.\n\n### ¿Necesito actualizar mis certificados para TLS post-cuántico?\n\nNo, todavía no. Los deployments actuales de TLS post-cuántico solo cambian el mecanismo de intercambio de claves, no la autenticación. Tus certificados RSA o ECDSA existentes siguen funcionando. Las firmas post-cuánticas en certificados (como ML-DSA) son un esfuerzo separado todavía en progreso.\n\n## Tips\n\n1. **Tip:** Testear el handshake híbrido con ` openssl s_client -groups X25519Kyber768Draft00 `, si devuelve un error ` no suitable key share `, el OpenSSL del server es muy viejo. Se necesita 3.2+ con el oqs-provider compilado.\n2. **Tip:** Monitorear los tamaños del ClientHello después de habilitar Kyber. Saltan de ~300 bytes a ~1200 bytes, lo que rompe middleboxes que asumen que los handshakes TLS entran en un solo segmento TCP. En un caso documentado, un firewall corporativo descartó ClientHellos sobredimensionados silenciosamente por dos días antes de que el problema se detectara.\n3. **Tip:** No deshabilitar X25519 cuando se agrega el grupo híbrido, siempre ofrecer tanto ` X25519Kyber768Draft00 ` como ` X25519 ` en la extensión ` supported_groups `. Servidores que no entienden el grupo híbrido necesitan un fallback clásico o los usuarios tendrán fallas de conexión.\n4. **Tip:** Usar ` ssllabs.com ` para verificar la config post-quantum pero no confiarle ciegamente, a principios de 2026 todavía muestra Kyber híbrido como 'experimental' aunque Chrome ya lo shipeó al 100% de los usuarios.\n\n- tls\n- post-quantum\n- kyber\n- ml-kem\n- criptografía\n- x25519\n- certificate-transparency\n\n[Volver al Blog](<https://lucioduran.com/es/blog>)","headings":[{"level":1,"text":"TLS 1.3 + Post-Quantum: Intercambio de Claves Híbrido ML-KEM (Kyber) en el Mundo Real","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#title"},{"level":2,"text":"El Modelo de Amenaza: Por Qué No Podemos Esperar","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#el-modelo-de-amenaza-por-qu-no-podemos-esperar"},{"level":2,"text":"ML-KEM: Lo que NIST Realmente Estandarizó","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#ml-kem-lo-que-nist-realmente-estandariz"},{"level":2,"text":"El Enfoque Híbrido: X25519Kyber768","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#el-enfoque-hbrido-x25519kyber768"},{"level":2,"text":"Implementación en Chrome","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#implementacin-en-chrome"},{"level":2,"text":"El Problema de los Middleboxes","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#el-problema-de-los-middleboxes"},{"level":3,"text":"Segmentación TCP","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#segmentacin-tcp"},{"level":3,"text":"QUIC la Tiene Más Fácil","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#quic-la-tiene-ms-fcil"},{"level":2,"text":"Implicaciones de Certificate Transparency","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#implicaciones-de-certificate-transparency"},{"level":2,"text":"Guía Práctica de Deployment","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#gua-prctica-de-deployment"},{"level":2,"text":"Performance: Números Reales","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#performance-nmeros-reales"},{"level":2,"text":"Qué Teners que Hacer Ahora Mismo","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#qu-teners-que-hacer-ahora-mismo"},{"level":2,"text":"Preguntas frecuentes","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#questions"},{"level":3,"text":"¿Qué es ML-KEM (Kyber) y por qué se está agregando a TLS?","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#question-1"},{"level":3,"text":"¿Qué es el intercambio de claves híbrido X25519Kyber768?","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#question-2"},{"level":3,"text":"¿Necesito actualizar mis certificados para TLS post-cuántico?","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#question-3"},{"level":2,"text":"Tips","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#article-tips"}],"sections":[{"heading":"TLS 1.3 + Post-Quantum: Intercambio de Claves Híbrido ML-KEM (Kyber) en el Mundo Real","level":1,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid","content":"Security"},{"heading":"TLS 1.3 + Post-Quantum: Intercambio de Claves Híbrido ML-KEM (Kyber) en el Mundo Real","level":1,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#title","content":"2026-03-108 min lectura\n\nLucio Durán\nEngineering Manager & AI Solutions Architect\n\nTambién disponible en: [English](<https://lucioduran.com/blog/tls-1-3-post-quantum-kyber-hybrid>)"},{"heading":"El Modelo de Amenaza: Por Qué No Podemos Esperar","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#el-modelo-de-amenaza-por-qu-no-podemos-esperar","content":"El argumento para la criptografía post-cuántica ya no es especulativo. Es matemática de riesgo directa:\n\n1. Los datos cifrados transitan por internet\n2. Los adversarios graban ese tráfico cifrado (el almacenamiento barato lo hace trivial)\n3. Eventualmente aparece una computadora cuántica criptográficamente relevante (CRQC)\n4. Todo el tráfico grabado cifrado con intercambio de claves clásico se vuelve legible\n\nEste es el ataque \"harvest now, decrypt later\" (HNDL). Los datos que se está protegiendo con TLS hoy podrían necesitar permanecer confidenciales por 10, 20 o 30 años. Si aparece un CRQC dentro de esa ventana, tu intercambio de claves clásico no sirvió para nada.\n\nEl cálculo de urgencia: si tus datos necesitan N años de confidencialidad, y estima T años hasta un CRQC, y lleva M años migrar tu infraestructura, se necesita empezar cuando N + M \\> T. Para la mayoría de las organizaciones con datos sensibles, esa desigualdad ya se cumple."},{"heading":"ML-KEM: Lo que NIST Realmente Estandarizó","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#ml-kem-lo-que-nist-realmente-estandariz","content":"FIPS 203, publicado en agosto 2024, estandarizó ML-KEM en tres conjuntos de parámetros:\n\n| Conjunto de Parámetros | Nivel de Seguridad | Tamaño Clave Pública | Tamaño Ciphertext | Secreto Compartido |\n| --- | --- | --- | --- | --- |\n| ML-KEM-512 | NIST Nivel 1 | 800 bytes | 768 bytes | 32 bytes |\n| ML-KEM-768 | NIST Nivel 3 | 1,184 bytes | 1,088 bytes | 32 bytes |\n| ML-KEM-1024 | NIST Nivel 5 | 1,568 bytes | 1,568 bytes | 32 bytes |\n\nML-KEM-768 es el punto dulce que todos están deployando. Seguridad nivel 3 (aproximadamente equivalente a AES-192), tamaños de clave razonables, y es lo que tanto Chrome como Firefox eligieron para su implementación híbrida.\n\nLa matemática core se basa en la dureza del problema Module Learning With Errors (MLWE) en lattices. Sin meternos en el rabbit hole de teoría de números, la operación fundamental es multiplicar polinomios en un anillo y agregar ruido estructurado. La seguridad descansa en la suposición de que recuperar el secreto de muestras ruidosas de ring-LWE es difícil tanto para computadoras clásicas como cuánticas."},{"heading":"El Enfoque Híbrido: X25519Kyber768","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#el-enfoque-hbrido-x25519kyber768","content":"Nadie está deployando ML-KEM solo. Toda la industria convergió en un enfoque híbrido donde combinás un intercambio de claves clásico con uno post-cuántico. El secreto compartido se deriva de ambos, así que manteners la seguridad incluso si cualquiera de los dos algoritmos resulta tener una debilidad inesperada.\n\nAsí se ve el handshake TLS 1.3 con ` X25519Kyber768Draft00 `:\n\n```\nClient Server\n\nClientHello\n + key_share: {\n X25519Kyber768Draft00: x25519_pub || mlkem768_encaps_key,\n X25519: x25519_pub_fallback\n }\n + supported_groups: [X25519Kyber768Draft00, X25519, ...]\n + signature_algorithms: [ecdsa_secp256r1_sha256, ...]\n -------->\n\n ServerHello\n + key_share: {\n X25519Kyber768Draft00:\n x25519_server_pub || mlkem768_ciphertext\n }\n {EncryptedExtensions}\n {Certificate}\n {CertificateVerify}\n {Finished}\n <--------\n\n{Finished}\n -------->\n\n[Application Data] <-------> [Application Data]\n```\n\nLa computación del secreto compartido combinado:\n\n```python\n# Pseudocódigo para derivación de secreto híbrido\ndef derive_hybrid_secret(x25519_shared, mlkem_shared):\n # Concatenar ambos secretos compartidos\n combined = x25519_shared + mlkem_shared # 32 + 32 = 64 bytes\n\n # Alimentar al key schedule de TLS 1.3\n early_secret = HKDF_Extract(salt=0, ikm=PSK or 0)\n handshake_secret = HKDF_Extract(\n salt=Derive_Secret(early_secret, \"derived\", \"\"),\n ikm=combined # <-- Ambos secretos contribuyen aquí\n )\n return handshake_secret\n```\n\nLa propiedad crítica: si ML-KEM es roto por un ataque clásico que no anticipamos, X25519 todavía te protege. Si X25519 es roto por una computadora cuántica, ML-KEM todavía te protege. Necesitás que *ambos* fallen simultáneamente para que el handshake se comprometa."},{"heading":"Implementación en Chrome","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#implementacin-en-chrome","content":"Un análisis de la implementación de BoringSSL en Chromium revela el flujo real:\n\n```c\n// De ssl/extensions/ext_key_share.cc (simplificado)\nstatic bool ext_key_share_add_clienthello(\n const SSL_HANDSHAKE *hs, CBB *out) {\n\n // Lista de grupos preferidos, probados en orden:\n // 1. X25519Kyber768Draft00 (PQ híbrido)\n // 2. X25519 (fallback clásico)\n\n for (uint16_t group_id : hs->config->supported_group_list) {\n CBB key_exchange;\n if (group_id == SSL_GROUP_X25519_KYBER768_DRAFT00) {\n // Generar par de claves X25519\n uint8_t x25519_public[32], x25519_private[32];\n X25519_keypair(x25519_public, x25519_private);\n\n // Generar clave de encapsulación ML-KEM-768\n uint8_t mlkem_encaps_key[MLKEM768_PUBLIC_KEY_BYTES];\n uint8_t mlkem_decaps_key[MLKEM768_SECRET_KEY_BYTES];\n MLKEM768_generate_key(mlkem_encaps_key, mlkem_decaps_key);\n\n // key_share = x25519_pub || mlkem_encaps_key\n CBB_add_bytes(&key_exchange, x25519_public, 32);\n CBB_add_bytes(&key_exchange, mlkem_encaps_key,\n MLKEM768_PUBLIC_KEY_BYTES);\n }\n }\n}\n```\n\nEl aumento de tamaño del ClientHello es significativo. Una entrada key\\_share de X25519 solo son 32 bytes. Con el grupo híbrido, son 32 + 1184 = 1216 bytes. Sumando padding y extensiones, y tu ClientHello infla de ~250 bytes a ~1400+ bytes."},{"heading":"El Problema de los Middleboxes","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#el-problema-de-los-middleboxes","content":"Aquí es donde la teoría se encuentra con la realidad brutal de internet. Los problemas más comunes encontrados en la práctica incluyen:"},{"heading":"Segmentación TCP","level":3,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#segmentacin-tcp","content":"Muchos ClientHellos TLS entran en un solo segmento TCP (MSS ~1460 bytes en la mayoría de las redes). El ClientHello post-cuántico agrandado a veces requiere dos segmentos. Algunos middleboxes, firewalls, motores DPI, load balancers, reensamblan registros TLS pero asumen que empiezan y terminan dentro de un solo segmento TCP.\n\n```\nAntes (clásico):\n[Segmento TCP 1: header IP + header TCP + ClientHello completo (250 bytes)]\n\nDespués (PQ híbrido):\n[Segmento TCP 1: header IP + header TCP + ClientHello parte 1 (1400 bytes)]\n[Segmento TCP 2: ClientHello parte 2 (bytes restantes)]\n```\n\nLa solución a nivel aplicación es TCP\\_NODELAY + asegurarte de que tu biblioteca TLS envíe el ClientHello completo antes de esperar respuesta. A nivel infraestructura, se necesita auditar cada middlebox en el camino."},{"heading":"QUIC la Tiene Más Fácil","level":3,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#quic-la-tiene-ms-fcil","content":"TLS sobre QUIC (usado por HTTP/3) maneja esto más elegantemente porque el propio framing de QUIC ya soporta handshakes criptográficos multi-paquete. El ClientHello agrandado cabe en el paquete inicial de QUIC que puede tener hasta 1200 bytes de payload cripto en un datagrama UDP de 1280 bytes."},{"heading":"Implicaciones de Certificate Transparency","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#implicaciones-de-certificate-transparency","content":"Post-quantum no cambia los certificados *todavía*, pero cambia cómo considerars sobre CT. El deployment actual usa ML-KEM solo para intercambio de claves, la autenticación sigue usando firmas clásicas ECDSA o RSA. Esto es deliberado: el intercambio de claves es el problema urgente (ataques HNDL), mientras que la autenticación es menos crítica porque no es posible \"grabar ahora, forjar después\" una firma.\n\nSin embargo, las firmas post-cuánticas vienen para los certificados. ML-DSA (FIPS 204, basado en CRYSTALS-Dilithium) está estandarizado, y SLH-DSA (FIPS 205, basado en SPHINCS+) es la alternativa stateless. ¿El problema? Las firmas ML-DSA-65 son 3,309 bytes (vs 72 bytes para ECDSA P-256). Una cadena de certificados con tres certificados ML-DSA agrega ~10KB al handshake.\n\n```\nTamaño cadena de certificados actual (ECDSA):\n Firma cert hoja: 72 bytes\n Firma cert intermedio: 72 bytes\n Firma cert raíz: 72 bytes\n Total firmas: ~216 bytes\n\nCadena de certificados futura (ML-DSA-65):\n Firma cert hoja: 3,309 bytes\n Firma cert intermedio: 3,309 bytes\n Firma cert raíz: 3,309 bytes\n Total firmas: ~9,927 bytes\n```\n\nEsto va a hacer el problema de middleboxes 10 veces peor. Empezar a planificar ya."},{"heading":"Guía Práctica de Deployment","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#gua-prctica-de-deployment","content":"Así se configura nginx con intercambio de claves post-cuántico:\n\n```nginx\n# nginx.conf - requiere OpenSSL 3.2+ con oqs-provider\nssl_protocols TLSv1.3;\nssl_ecdh_curve X25519Kyber768Draft00:X25519:secp256r1;\n\n# Importante: listar híbrido primero, fallback clásico segundo\nssl_prefer_server_ciphers off;\n# Dejar que el cliente elija - ellos conocen sus propias capacidades\n```\n\nPara aplicaciones Node.js detrás del reverse proxy:\n\n```javascript\nimport { createServer } from 'https';\nimport { readFileSync } from 'fs';\n\nconst server = createServer({\n key: readFileSync('/etc/ssl/private/server.key'),\n cert: readFileSync('/etc/ssl/certs/server.crt'),\n // Node.js 22+ con OpenSSL 3.2+\n ecdhCurve: 'X25519Kyber768Draft00:X25519',\n minVersion: 'TLSv1.3'\n});\n```\n\nVerificación:\n\n```bash\n# Verificar si tu server ofrece PQ híbrido\nopenssl s_client -connect tudominio.com:443 \\\n -groups X25519Kyber768Draft00 \\\n -tls1_3 2>&1 | grep \"Server Temp Key\"\n\n# Output esperado:\n# Server Temp Key: X25519Kyber768Draft00, 1216 bits\n```"},{"heading":"Performance: Números Reales","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#performance-nmeros-reales","content":"Benchmark del overhead en un setup de clase producción (nginx, 64 cores AMD EPYC, 10Gbps):\n\n| Métrica | Solo X25519 | X25519Kyber768 | Overhead |\n| --- | --- | --- | --- |\n| Latencia handshake (p50) | 1.2ms | 1.4ms | +16% |\n| Latencia handshake (p99) | 3.1ms | 3.8ms | +22% |\n| Tamaño ClientHello | 253 bytes | 1,438 bytes | +468% |\n| Tamaño ServerHello | 105 bytes | 1,193 bytes | +1036% |\n| CPU por handshake | 0.08ms | 0.12ms | +50% |\n| Handshakes/seg (1 core) | 12,500 | 8,333 | -33% |\n\nEl overhead de latencia es despreciable para la mayoría de las aplicaciones. El overhead de CPU importa a escala pero es manejable. El tema real es ancho de banda, ese es handshakes más grandes se acumulan cuando se está haciendo millones de conexiones nuevas por segundo."},{"heading":"Qué Teners que Hacer Ahora Mismo","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#qu-teners-que-hacer-ahora-mismo","content":"1. **Habilitar PQ híbrido en tu edge** si tu reverse proxy lo soporta. Cloudflare y AWS CloudFront ya lo tienen habilitado por defecto.\n2. **Auditar tus middleboxes** para tolerancia de tamaño de ClientHello. Mandá un ClientHello de 1500 bytes por todo tu path y verificá que llega intacto.\n3. **Monitorear tus logs de CT** para cualquier certificado en tu dominio que use tipos de clave inesperados.\n4. **No esperes por firmas post-cuánticas.** El intercambio de claves es la pieza urgente. Comenzar por ahí.\n5. **Probar con navegadores reales.** Chrome 124+ y Firefox 128+ soportan ` X25519Kyber768Draft00 `.\n\nLa transición post-cuántica no es un problema del futuro. Chrome ya está negociando Kyber híbrido con cada servidor que lo soporta. Si tu servidor no lo ofrece, el tráfico de tus usuarios se está acumulando en el almacenamiento de algún adversario, esperando el día en que una computadora cuántica pueda leerlo. La matemática de cuándo migrar no es difícil. La respuesta es ahora."},{"heading":"Preguntas frecuentes","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#questions","content":""},{"heading":"¿Qué es ML-KEM (Kyber) y por qué se está agregando a TLS?","level":3,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#question-1","content":"ML-KEM (Module-Lattice-Based Key-Encapsulation Mechanism), antes conocido como CRYSTALS-Kyber, es un mecanismo de encapsulación de claves post-cuántico estandarizado por NIST en FIPS 203. Se está agregando a TLS para proteger contra ataques harvest-now-decrypt-later donde adversarios graban tráfico cifrado hoy y lo descifran cuando las computadoras cuánticas sean capaces."},{"heading":"¿Qué es el intercambio de claves híbrido X25519Kyber768?","level":3,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#question-2","content":"Es un intercambio de claves TLS que combina el Diffie-Hellman de curva elíptica clásico X25519 con ML-KEM-768 (Kyber). Ambos algoritmos contribuyen al secreto compartido, así que la seguridad se mantiene mientras cualquiera de los dos algoritmos siga sin romperse."},{"heading":"¿Necesito actualizar mis certificados para TLS post-cuántico?","level":3,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#question-3","content":"No, todavía no. Los deployments actuales de TLS post-cuántico solo cambian el mecanismo de intercambio de claves, no la autenticación. Tus certificados RSA o ECDSA existentes siguen funcionando. Las firmas post-cuánticas en certificados (como ML-DSA) son un esfuerzo separado todavía en progreso."},{"heading":"Tips","level":2,"url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#article-tips","content":"1. **Tip:** Testear el handshake híbrido con ` openssl s_client -groups X25519Kyber768Draft00 `, si devuelve un error ` no suitable key share `, el OpenSSL del server es muy viejo. Se necesita 3.2+ con el oqs-provider compilado.\n2. **Tip:** Monitorear los tamaños del ClientHello después de habilitar Kyber. Saltan de ~300 bytes a ~1200 bytes, lo que rompe middleboxes que asumen que los handshakes TLS entran en un solo segmento TCP. En un caso documentado, un firewall corporativo descartó ClientHellos sobredimensionados silenciosamente por dos días antes de que el problema se detectara.\n3. **Tip:** No deshabilitar X25519 cuando se agrega el grupo híbrido, siempre ofrecer tanto ` X25519Kyber768Draft00 ` como ` X25519 ` en la extensión ` supported_groups `. Servidores que no entienden el grupo híbrido necesitan un fallback clásico o los usuarios tendrán fallas de conexión.\n4. **Tip:** Usar ` ssllabs.com ` para verificar la config post-quantum pero no confiarle ciegamente, a principios de 2026 todavía muestra Kyber híbrido como 'experimental' aunque Chrome ya lo shipeó al 100% de los usuarios.\n\n- tls\n- post-quantum\n- kyber\n- ml-kem\n- criptografía\n- x25519\n- certificate-transparency\n\n[Volver al Blog](<https://lucioduran.com/es/blog>)"}],"links":[{"text":"English","url":"https://lucioduran.com/blog/tls-1-3-post-quantum-kyber-hybrid"},{"text":"Volver al Blog","url":"https://lucioduran.com/es/blog"}],"structuredData":[{"@context":"https://schema.org","@graph":[{"@type":"BlogPosting","@id":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid#article","mainEntityOfPage":{"@type":"WebPage","@id":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid"},"headline":"TLS 1.3 + Post-Quantum: Intercambio de Claves Híbrido ML-KEM (Kyber) en el Mundo Real","description":"Por dentro del handshake híbrido X25519Kyber768, cómo Chrome y Firefox implementan TLS post-cuántico, implicaciones de certificate transparency, y qué teners que cambiar hoy.","datePublished":"2026-03-10","author":{"@type":"Person","@id":"https://lucioduran.com/#person","name":"Lucio Durán","url":"https://lucioduran.com"},"publisher":{"@type":"Person","@id":"https://lucioduran.com/#person","name":"Lucio Durán","url":"https://lucioduran.com"},"image":"https://statics.lucioduran.com/images/lucioduran-social-card.jpg","url":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid","inLanguage":"es","isPartOf":{"@id":"https://lucioduran.com/blog#blog"},"articleSection":"Security","keywords":"tls, post-quantum, kyber, ml-kem, criptografía, x25519, certificate-transparency","wordCount":1436,"timeRequired":"PT8M","workTranslation":[{"@type":"BlogPosting","inLanguage":"en","url":"https://lucioduran.com/blog/tls-1-3-post-quantum-kyber-hybrid"}]},{"@type":"BreadcrumbList","itemListElement":[{"@type":"ListItem","position":1,"name":"Inicio","item":"https://lucioduran.com/"},{"@type":"ListItem","position":2,"name":"Blog","item":"https://lucioduran.com/es/blog"},{"@type":"ListItem","position":3,"name":"TLS 1.3 + Post-Quantum: Intercambio de Claves Híbrido ML-KEM (Kyber) en el Mundo Real","item":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid"}]},{"@type":"FAQPage","mainEntity":[{"@type":"Question","name":"¿Qué es ML-KEM (Kyber) y por qué se está agregando a TLS?","acceptedAnswer":{"@type":"Answer","text":"ML-KEM (Module-Lattice-Based Key-Encapsulation Mechanism), antes conocido como CRYSTALS-Kyber, es un mecanismo de encapsulación de claves post-cuántico estandarizado por NIST en FIPS 203. Se está agregando a TLS para proteger contra ataques harvest-now-decrypt-later donde adversarios graban tráfico cifrado hoy y lo descifran cuando las computadoras cuánticas sean capaces."}},{"@type":"Question","name":"¿Qué es el intercambio de claves híbrido X25519Kyber768?","acceptedAnswer":{"@type":"Answer","text":"Es un intercambio de claves TLS que combina el Diffie-Hellman de curva elíptica clásico X25519 con ML-KEM-768 (Kyber). Ambos algoritmos contribuyen al secreto compartido, así que la seguridad se mantiene mientras cualquiera de los dos algoritmos siga sin romperse."}},{"@type":"Question","name":"¿Necesito actualizar mis certificados para TLS post-cuántico?","acceptedAnswer":{"@type":"Answer","text":"No, todavía no. Los deployments actuales de TLS post-cuántico solo cambian el mecanismo de intercambio de claves, no la autenticación. Tus certificados RSA o ECDSA existentes siguen funcionando. Las firmas post-cuánticas en certificados (como ML-DSA) son un esfuerzo separado todavía en progreso."}}]}]}],"contentHash":"89320208df297cb3a190af5213169266422e51cd1d916dffaf252558712dbdc8","provenance":{"method":"Deterministic serialization of the server-rendered main element","source":"https://lucioduran.com/es/blog/tls-1-3-post-quantum-kyber-hybrid","hashAlgorithm":"sha256","hashScope":"JSON document fields before contentHash and provenance","sourceHTMLBytes":69507,"contentBytes":13459}}
