La semana pasada, aprendimos la teoría numérica necesaria para la criptografía de clave pública.
Esta semana vamos a poner a trabajar ese conocimiento y vamos a construir varios
esquemas de criptografía de clave pública seguros. Pero primero es necesario definir qué es
la criptografía de clave pública y qué significa que la criptografía de clave pública sea
segura. Así, permitidme recordaros que en un esquema de criptografía de clave pública hay un
algoritmo de encriptación, normalmente denotado como E, y un algoritmo de
desencriptado que denotamos como D. En cualquier caso, aquí el algoritmo de encriptación usa una
clave pública, mientras que el de desencriptado usa una clave privada. Este par se denomina
par de claves. Y la clave pública se utiliza para encriptar mensajes mientras que la clave privada
se utiliza para desencriptarlos. Por tanto, en este caso, un mensaje "m" se encripta usando
la clave pública y lo que se obtiene de ello es el texto cifrado, "c". Y, de forma similar,
el texto cifrado se usa para alimentar el algoritmo de desencriptado usando la clave privada y lo que
se obtiene del algoritmo de desencriptado es el mensaje original, "m". La encripción de clave
pública tiene muchas aplicaciones. La semana pasada vimos la aplicación clásica, el
establecimiento de sesión, esto es, intercambio de claves. Y por ahora vamos a limitarnos al intercambio de
claves que sea seguro sólo contra escucha. Y, si recordáis cómo funciona el protocolo,
básicamente Alice, lo que ella hará es generar un par de claves pública y privada.
Enviará la clave pública a Bob. Bob generará un valor aleatorio "x", que
servirá como su secreto compartido y, entonces, envía "x" encriptada a Alice,
encriptada con su clave pública [de Alice]. Alice puede desencriptar, recuperar "x" y ahora ambos
disponen de este secreto compartido, "x", que pueden utilizar para comunicarse de forma segura
entre ellos. El atacante, por supuesto, todo lo que puede ver es la clave pública, la
encriptación de "x" con la clave pública, de la cual no debería poder obtener ninguna
información sobre "x". Vamos a definir esto de forma más precisa para entender
qué significa no ser capaz de averiguar nada sobre "x". La criptografía pública,
de hecho, tiene muchas otras aplicaciones. Por ejemplo, es muy útil en
aplicaciones no interactivas. Así, pensad en un sistema de correo electrónico, por ejemplo. Aquí, Bob
quiere enviar correo a Alice y, cuando Bob envía el correo, el correo pasa de
agente de transporte a agente de transporte hasta que llega a Alice, momento en el que Alice deberá
desencrciptar. La forma en que el sistema de correo está implementado está diseñada según una
configuración no interactiva en la que Bob envía el correo y entonces Alice se supone que lo
recibirá. Y Alice no debería tener que comunicarse con Bob a fin de desencriptar
el correo. Por tanto, en este caso, a causa de la falta de interactividad, no existe la oportunidad
de establecer un secreto compartido entre Alice y Bob. Por tanto, en este caso, lo que
ocurrirá es que Bob, básicamente, enviará el correo encriptado utilizando la clave pública de
Alice. Del mismo modo que él envía el correo, cualquiera en el mundo puede enviar el correo encriptado a
Alice, encriptado usando su clave pública [de Alice]. Cuando Alice recibe este correo, ella utiliza
su clave privada para desencriptar el texto cifrado y recuperar el mensaje en texto llano.
Por supuesto, el inconveniente en un sistema como éste es que, de hecho, Bob necesita, de algún modo,
obtener la clave pública de Alice. Así, por ahora, vamos a asumir, simplemente, que Bob ya dispone
de la clave pública de Alice, pero más adelante, cuando hablemos sobre firmas digitales,
veremos cómo se puede hacer esto de forma muy eficiente utilizando lo que se
llama gestión de clave pública y, como ya he dicho, volveremos a ello más adelante.
Lo más importante que quiero que recordéis es que la criptografía de clave pública se
utiliza para establecer sesiones. Esto es muy común en la web, donde la criptografía de
clave pública se utiliza para establecer una clave segura entre un navegador web y un servidor web.
Y la criptografía de clave pública también es muy útil para aplicaciones no interactivas,
en las que cualquiera en el mundo, de forma no interactiva, necesita enviar un mensaje
a Alice, pudiendo encriptar el mensaje usando la clave pública de Alice y Alice puede desencriptar
y recuperar el texto llano. Por tanto, permitidme que os recuerde con algo más de detalle qué
es un sistema de criptografía de clave pública. Bien, consiste en tres algoritmos, G, E y D.
G se denomina algoritmo de generación de claves. Básicamente lo que hace es
generar este par de claves, la clave pública y la clave privada. Tal como se indica aquí, G no usa
argumentos, pero en la vida real, G realmente usa un argumento denominado el parámetro
de seguridad, que especifica el tamaño de las claves que se generan con este algoritmo de
generación de claves. Luego está este algoritmo de encriptación, como es habitual, que usa una
clave pública y un mensaje y genera un texto cifrado, y un algoritmo de desencriptado que
usa la clave privada correspondiente y un texto cifrado y genera el correspondiente
mensaje. Como siempre, para [la condición de] consistencia, diremos que si encriptamos un mensaje
según una determinada clave pública y luego lo desencriptamos con la clave privada correspondiente,
deberemos obtener de nuevo el mensaje original. Ahora, ¿qué significa para un sistema criptográfico de clave pública
que sea seguro? Voy a empezar definiendo seguridad contra escucha
y luego definiremos la seguridad contra ataques activos. La forma de
definir seguridad contra escucha es muy similar a la del caso simétrico que hemos
visto la semana pasada, así que vamos a pasar por ello rápidamente, sólo como repaso.
Básicamente, el juego de ataque se define como sigue. Definimos estos dos experimentos,
experimento cero y experimento uno. En cada experimento el retador generará
un par de claves pública y privada. Le dará la clave pública
al adversario. El adversario emitirá dos mensajes, m0 y m1 de la misma
longitud y lo que recibe es la encripción de m0 o la
encripción de m1. En el experimento cero obtiene la encripción de m0. En el experimento
uno obtiene la encripción de m1. Y entonces el adversario se supone de debe indicar cuál
ha recibido, ¿Ha recibido la encripción de m0 o ha recibido la encripción de m1? Así,
en este juego, el atacante sólo obtiene un texto cifrado. Esto corresponde a un ataque
de escucha en el que se limita a "escuchar" dicho texto cifrado "c". Y ahora
su objetivo es determinar si el texto cifrado "c" es la encripción de m0 o m1. No se
permite manipular el texto cifrado "c" por ahora. Y, como es costumbre, diremos que el
esquema de criptografía de clave pública es semánticamente seguro si el atacante no puede
distinguir el experimento cero del experimento uno. En otras palabras, no puede
diferenciar si recibió la encripción de m0 o la encripción de m1. Antes de pasar
a los ataques activos, quiero mencionar una relación inmediata entre la definición que acabamos
de ver y la definición de seguridad de escucha para cifrado simétrico.
Si lo recordáis, cuando hablamos sobre seguridad de escucha para cifrado
simétrico, distinguíamos entre el caso en que la clave se usaba una vez y el caso en que la
clave se usaba varias veces. Y, de hecho, vimos que existe una clara
separación. Por ejemplo, el cuaderno de un solo uso es seguro si la clave se usa para encriptar
un único mensaje, pero es completamente inseguro si la clave se usa para encriptar múltiples
mensajes. Y, de hecho, teníamos dos definiciones diferentes, si os acordáis, teníamos una
definición para seguridad de un solo uso y una definición diferente, que era más
exigente, cuando la clave se usaba varias veces. La definición que os he mostrado en
la transparencia anterior es muy similar a la definición de seguridad de un solo uso para
cifras simétricas. Y, de hecho, resulta que para la criptografía de clave pública, si un
sistema es seguro en el caso de un solo uso de la clave, en cierto sentido, también es seguro para uso múltiple de
la clave. En otras palabras, no es necesario proporcionar explícitamente al atacante la habilidad
para requerir encripciones de mensajes de su elección, ya que puede crear encripciones
por si mismo. Dispone de la clave pública y, por tanto, puede
por si mismo encriptar cualquier mensaje que desee. Como resultado, cualquier par de claves pública y privada
de algún modo inherentemente se usan para encriptar varios mensajes ya que el atacante
podría encriptar muchos, muchos mensajes de su elección usando la clave
pública que le hemos proporcionado en el primer paso. Y así, como resultado, de hecho
la definición de seguridad para un solo uso es suficiente para implicar seguridad de varios usos y
es por ello que nos referimos al concepto como indistinguibilidad bajo un ataque de
texto llano escogido. Así, este es sólo un punto menor para explicar por qué en la configuración de criptografía
de clave pública no necesitamos una definición más compleja para aprehender
la seguridad ante escucha. Ahora que entendemos la seguridad ante escucha,
vamos a ver adversarios mas fuertes que pueden montar ataques activos. Entonces, en
particular, veamos el ejemplo del correo electronico. Así, aquí tenemos a nuestro amigo Bob
que quiere enviar enviar un correo a su amiga Caroline. Y resulta que Caroline tiene una
cuenta en Gmail. Y esto funciona básicamente así, el correo electrónico se envía encriptado al
servidor de Gmail. El servidor de Gmail desencripta el correo electrónico, mira quienes son los
destinatarios y luego, si es que el destinatario es Caroline,
reenvia el correo electrónico a Caroline. Si el destinatario es el atacante, se
lo reenvia al atacante. Esto es similar a cómo trabaja realmente Gmail,
porque el remitente enviaría el correo encriptado sobre SSL al servidor Gmail,
el servidor Gmail terminaría [la sesión] SSL y reenviaría el mensaje a los destinatarios
apropiados. Ahora supongamos que Bob encripta el correo usando un sistema que
permita al adversario manipular el texto cifrado sin ser detectado. Por
ejemplo, imaginad que el correo está encriptado usando el modo contador o
similar. Entonces, cuando el atacante intercepta este correo puede cambiar el destinatario
de forma que ahora el destinatario sea attacker@gmail.com. Y sabemos que, para el
modo contador, por ejemplo. esto es muy fácil de hacer. El atacante sabe que el
correo está dirigido a Caroline, él está sólo interesado en el cuerpo del correo. Por tanto, puede
fácilmente cambiar el destinatario del correo a attacker@gmail.com y ahora, cuando el servidor
recibe el correo, lo desencriptará, verá que el destinatario se supone que es el
atacante y reenviará el cuerpo del mensaje al atacante. Ahora el atacante ha podido
leer el cuerpo del mensaje que estaba destinado a Caroline. Así,
este es un ejemplo clásico de ataque activo, y podéis ver lo que el atacante ha conseguido:
puede desencriptar cualquier texto cifrado en el que el destinatario sea "to:attacker",
esto es, un texto cifrado en el que el texto llano empiece por "to:attacker". Así, nuestro objetivo es empiece
diseñar sistemas de clave pública que sean seguros incluso si el atacante puede manipular
el texto cifrado y, posiblemente, desencriptar algunos textos cifrados. Y, de nuevo, quiero
enfatizar que aquí el objetivo del atacante es obtener el cuerpo del mensaje. El atacante
ya sabía que el correo estaba destinado a Caroline. Y todo lo que él tenía que hacer
era cambiar el destinatario. Así, este ataque mediante manipulación motiva la
definición de seguridad de texto cifrado escogido. y, de hecho, esta es la noción estándar de
seguridad para la criptografía de clave pública. Así, permitidme explicaros cómo funciona el esquema del
ataque. Como ya dije, nuestro objetivo es construir sistemas que sean seguros bajo esta noción tan
conservadora de encripción. Así, tenemos un esquema de encripción G, E, D y digamos que
está definido sobre nuestro espacio de mensajes y de textos cifrados M, C. Como es habitual, vamos
a definir dos experimentos, experimento cero y experimento uno. Así, aquí "b" indica si
el retador está implementando el experimento cero el el experimento
uno. El retador empieza generando una clave pública y una clave privada y entonces proporciona
la clave privada al adversario. Ahora el adversario puede decir "Bien, aquí hay un puñado de
textos cifrados, por favor desencríptalos por mí." Así que el adversario envía el texto cifrado
c1 y obtiene la desencripción del texto cifrado c1, esto es, m1. Y lo repite
una y otra vez, de forma que envía el texto cifrado c2 y obtiene la desencripción,
que es m2, el texto cifrado c3 y lo obtiene desencriptado, m3, y así en adelante.
Finalmente, el adversario dice: "Esta fase de interrogación ha acabado" y ahora
remite básicamente dos mensajes de la misma longitud, m0 y m1, como es habitual, y
recibe en respuesta el texto cifrado de desafío, "c", que es la encriptación de m0 o
la encriptación de m1, dependiendo de si estamos en el experimento cero o el
experimento uno. Ahora el adversario puede continuar enviando solicitudes de texto
cifrado. Así, puede continuar remitiendo solicitudes de desencriptado. Así, el remite
un texto cifrado y recibe el texto desencriptado, pero, por supuesto, ahora tiene que haver una
limitación. Si el atacante pudiese solicitar textos cifrados arbitrarios de su elección,
por supuesto que podría romper el desafío. Lo único que tendría que hacer es remitir al
retador el texto cifrado "c" como una solicitud de desencriptado y entonces se le diría si en la
fase de desafío se le ha dado la encriptación de m0 o la encriptación de m1.
Como resultado, ponemos la siguiente limitación, que dice que él puede de hecho enviar cualquier
texto cifrado de su elección, excepto el texto cifrado del desafío. Así, el atacante
podrá solicitar el desencriptado de cualquier texto cifrado de su elección que no sea el
texto cifrado del desafío. Y, a pesar de que se le hayan dado todos esos textos desencriptados, a pesar de todo
no debería ser capaz de decir si ha recibido la encriptación de m0 o la
encriptación de m1. Por tanto, daros cuenta de que se trata de una definición muy conservadora. Proporciona
al atacante más poder del que vimos en la transparencia anterior. En la transparencia anterior,
el atacante sólo podía desencriptar mensajes si el texto llano empezada con "to:attacker".
Aquí, lo que vemos es que el atacante puede desencriptar cualquier texto cifrado de su elección,
siempre se que sea distinto del texto cifrado del desafío, "c". ¿De acuerdo? Y entonces su
objetivo es decir si el texto cifrado del desafío es la encriptación de m0 o la
encriptación de m1. Y, como es habitual, si no puede hacerlo, en otras palabras, su respuesta
ante el experimento cero es básicamente la misma respuesta que en el experimento
uno, sin ser capaz de diferenciar la encriptación de m0 de la encriptación de
m1 a pesar del poder del que disponía, entonces decimos que el sistema es semánticamente
seguro frente a ataque de texto cifrado escogido, seguro CCA. En ocasiones se utiliza este acrónimo,
el acrónimo de INDistinguible frente a un Ataque de texto Cifrado esCogido [IND-CCA], pero me voy
a limitar a llamarlo "seguro CCA". Así, vamos a ver como esto refleja el ejemplo con el correo electrónico
que vimos antes. Supongamos que el sistema de encriptación usado es tal que simplemente dada
un mensaje encriptado el atacante puede cambiar el destinatario, digamos, de Alice
a Charlie. Entonces, así es como él ganaría el juego CCA. Bien, en el
primer paso recibe, por supuesto, la clave pública. Y entonces el atacante lo que hará
es proporcionar dos mensajes de igual longitud, esto es, en el primer mensaje el cuerpo contendrá
un cero. En el segundo mensaje el cuerpo contendrá un uno. Pero ambos mensajes están dirigidos a
Alice. Y, en respuesta, él recibirá el texto cifrado del desafío, "c".
Bien, así que ahora tenemos nuestro texto cifrado del desafío, "c". Ahora, lo que hará el
atacante es utilizar su habilidad para modificar el destinatario.
Y devolverá un texto cifrado c' [c prima] en el que c' es la encriptación del
mensaje para Charlie con el cuerpo del desafío, "b". Esto es, si os acordáis, o
cero o uno. Ahora, como que el texto llano es diferente, sabemos que
el texto cifrado debe también ser diferente. En particular, c' debe ser diferente del
texto del desafío "c", ¿no es así? Esto es, c' debe ser diferente de "c". Y como
consecuencia, el pobre retador ahora tiene que desencriptar, por definición del juego CCA.
El retador tiene que desencriptar cualquier texto crifrado que no sea igual a un texto cifrado enviado
por el retador. Así, el retador desencripta, le da al adversario m'. Básicamente proporciona
al adversario "b". Y ahora el adversario puede mostrar "b" como resultado del desafío
y gana el juego con ventaja 1. Así, su ventaja con este esquema particular
era uno. Simplemente porque el atacante era capaz de cambiar el texto cifrado del
retador de un destinatario a otro, lo que le permite ganar el juego CCA con
ventaja uno. Así, como ya dije, [el modelo] de seguridad de texto cifrado escogido es en
realidad la noción de seguridad correcta para los sistemas de criptografía de clave pública. Y este es
un concepto muy interesante. De algún modo, aunque el atacante tenga la habilidad para
desencriptar todo lo que quiera, excepto el texto cifrado del desafío, no es capaz de
conocer el texto cifrado del retador. Así, lo que haremos lo que haremos durante lo que queda de este módulo y,
de hecho, también el próximo, es construir sistemas seguros CCA. Se tiene que
destacar que es posible y voy a mostraros exactamente cómo
hacerlo. Y, de hecho, los sistemas seguros CCA que construiremos
son los que se utilizan en el mundo real. Y cada vez que se ha intentado implementar un
sistema de criptografía de clave pública que no ha sido seguro CCA, alguien ha encontrado un
ataque y ha sido capaz de romperlo. Y vamos a ver algunos ejemplos de esos ataques
en unos pocos segmentos.