Criptografía – ROT13

ROT13 es un método criptográfico clásico basado en el cifrado por sustitución, de su nombre se entiende “rotar 13 posiciones”. Este consiste en el desplazamiento de las letras del alfabeto latino, es decir se altera el orden, lo cual se logra sustituyendo sucesivamente cada letra por la letra que se encuentra 13 posiciones más adelante en el alfabeto.

Los números, símbolos, espacios y otros caracteres son ignorados permaneciendo en su posición original.

El siguiente es un esquema del método de cifrado ROT13.

El esquema muestra que la letra A se convierte en N, B se convierte en O, C se convierte en P y así sucesivamente hasta llegar a M que se convierte en Z. Pero la secuencia se invierte a partir de N donde este se convierte en A, O se convierte en B, P se convierte en C y así sucesivamente hasta llegar a Z que se convierte en M.

Historia


ROT13 es en realidad un caso particular de un grupo simple de algoritmos de cifrado llamado cifrados Cesar, los cuales están basados en el cifrado por sustitución y pertenecen a la criptografía clásica.

Este método de cifrado data de al menos 600-500 años A.C (procedencia hebrea), y fue redescubierto en la década de los 80 para ser utilizado por un grupo de noticias que intentaba ofuscar chistes que podrían ser ofensivos para algunos lectores o evitar que el chiste fuera leído muy pronto.

El método resulto útil en cuanto a la compatibilidad, porque al trabajar solo sobre letras se garantizaba que no hubiera problemas relacionados con caracteres extraños.  El ROT13 (valor de rotación 13),  a diferencia de ROT-N donde el valor de rotación N no esta definido (un caso es ROT-3 que seria el cifrado Cesar original),  permite utilizar el mismo algoritmo para cifrar y descifrar al aplicarse sobre el alfabeto latino que tiene 26 letras, ya que 26 = 13 * 2, y este esta incluido en el juego de caracteres ASCII que puede cubrir al menos los idiomas occidentales. Por lo tanto el valor de rotación 13 resulta conveniente para este alfabeto de 26 letras.

Los servidores UNIX poseen el comando tr, que puede utilizarse para cifrar o descifrar ROT13 y también ROT-N. La sintaxis de tr:

tr '[A-Z][a-z]' '[N-ZA-M][n-za-m]' < archivo

En matemáticas


Dado el alfabeto latino (que no tiene Ñ) con 26 letras, le asignamos un numero a cada una de modo que A= 1, B = 2, C = 3, … etc, y obtenemos el siguiente conjunto finito de orden ascendente:

N = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 16, 16, 17 , 18, 19 , 20, 21, 22, 23, 24, 25, 26 }.

Para realizar un cifrado ROT13 sobre el conjunto N, se utiliza la siguiente función:

Por ejemplo para cifrar el texto HOLA, sabemos que H = 8, 0 = 15, L = 12, A = 1. Aplicamos la función para cada letra:

f(8) = 8 + 13 = 21 ≡ U

f(15) = 15 – 13 = 2 ≡ B

f(12) = 12 + 13 = 25 ≡ Y

f(1) = 1 + 13 = 14 ≡ N

El resultado cifrado es UBYN.

Para descifrar lo único que tenemos que hacer es aplicar nuevamente la misma función sobre el texto cifrado,  sabemos que U= 21, B = 2, Y = 25, N = 14. Aplicamos la función para cada letra:

f(21) = 21 – 13 = 8 ≡ H

f(2) = 2 + 13 = 15 ≡ O

f(25) = 25 – 13 = 12 ≡ L

f(14) = 14 – 13 = 1 ≡ A

El resultado es el texto original HOLA.

Visto gráficamente:

Esta función resulta ser involutiva porque es su propia inversa, en criptografía se le denomina cifrado reciproco.

Utilidad


ROT13 no es un cifrado de utilidad para tratar información de comercio electrónico o de bancos, no ofrece seguridad real (al menos en nuestros tiempos). Es un cifrado débil que al utilizar un desplazamiento constante no tiene clave, para el descifrado un atacante no necesita mas que simplemente saber que se esta usando ROT13, y aunque no lo supiese el algoritmo podría romperse fácilmente con un análisis de frecuencia u otro método.

Hoy en día ROT13 sigue siendo utilizado con los mismos o similares fines que en los 80, como lo hace por ejemplo el grupo de noticias USENET en sus artículos. También suele utilizarse para ocultar el resultado de adivinanzas, alguna información en foros, realizar juegos de letras, y etc.

Implementación


A continuación se exhiben y explican algunos ejemplos de la implementación del cifrado ROT13 en algunos lenguajes de programación. La idea es tomar una cadena de caracteres para cifrarla y descifrarla mientras se van imprimiendo los resultados en pantalla.

Notas:
* Los ejemplos pretenden ser legibles, no óptimos.
* Los códigos fuentes completos de los ejemplos están al final.

Ensamblador (ASM) x86

La sintaxis es para NASM.

...
cadena  DB      "Hola Mundo", 13, 10        ;cadena de caracteres
cadLen  EQU     $ - cadena                  ;longitud de la cadena
...
rot13:
	MOV     edx, [esp + 4]	    ;copia el parámetro cadena:DWORD en EDX
	MOV     ecx, [esp + 8]	    ;copia el parámetro cadLen:DWORD en ECX

        .loop:                    	    ;comienza el bucle para analizar los bytes de cadena:DWORD
                MOV     al, BYTE [edx]	    ;copia el byte de la posición actual de cadena:DWORD en AL para analizarlo

                CMP     al, 'A'             ;compara AL con: [ASCII:A = Dec:65 = Hex:41]
                JB      .next               ;si es menor, se ignora el byte y se salta a .next para analizar el siguiente byte

                CMP     al, 'N'             ;compara AL con: [ASCII:N = Dec:78 = Hex:4E]
                JB      .add13              ;si es menor, se salta a .add13 para realizar el desplazamiento sumándole 13

                CMP     al, 'Z'             ;compara AL con: [ASCII:Z = Dec:90 = Hex:5A]
                JBE     .sub13              ;si es menor o igual, se salta a .sub13 para realizar el desplazamiento restándole 13

                CMP     al, 'a'             ;compara AL con: [ASCII:a = Dec:97 = Hex:61]
                JB      .next               ;si es menor, se ignora el byte y se salta a .next para analizar el siguiente byte

                CMP     al, 'n'             ;compara AL con: [ASCII:n = Dec:110 = Hex:6E]
                JB      .add13              ;si es menor, se salta a .add13 para realizar el desplazamiento sumándole 13

                CMP     al, 'z'             ;compara AL con: [ASCII:z = Dec:122 = Hex:7A]
                JA      .next	            ;si es mayor, se ignora el byte y se salta a .next para analizar el siguiente byte
                                            ;si es menor o igual, continua en .sub13 para realizar el desplazamiento restándole 13

        .sub13:                         ;
                SUB     al, 13          ;resta 13 al byte en AL
                MOV     [edx], al       ;copia AL a la posición actual de cadena:DWORD
                JMP     .next	        ;salta a .next para analizar el siguiente byte

        .add13:                         ;
                ADD     al, 13          ;suma 13 al byte en AL
                MOV     [edx], al       ;copia AL a la posición actual de cadena:DWORD
                                        ;continua en .next para analizar el siguiente byte

        .next:                      ;
                ADD     edx, 1      ;incrementa cadena:DWORD en uno para poder analizar al siguiente byte
                LOOP    .loop       ;disminuye cadLen:DWORD en uno, y continua el bucle solo si es mayor que 0.

        .end:
        RET     4     ;retorna limpiando las variables locales de la pila
...

C

...
char cadena[] = { 'H', 'o', 'l', 'a', ' ', 'M', 'u', 'n', 'd', 'o', '\r', '\n', '\0' };        //cadena de caracteres terminada en \0
...
void rot13(char *cadena)
{
        int c;
        int i = 0;                         //valor de la posición actual en la cadena
        while (cadena[i] != '\0') {        //comienza el bucle para analizar los caracteres de la cadena[] hasta llegar a \0
                c = cadena[i];              //introduce el carácter de la posición actual de la cadena en la variable c

                if (c >= 'A' && c < 'N') {                //compara c con A y N
                        cadena[i] = c + 13;               //si es igual o mayor que A y menor que N, se realiza un desplazamiento sumándole 13
                } else if (c >= 'N' && c <= 'Z') {        //compara c con N y Z
                        cadena[i] = c - 13;               //si es igual o mayor que N e igual o menor que Z, se realiza un desplazamiento restándole 13
                } else if (c >= 'a' && c < 'n') {         //compara c con a y n
                        cadena[i] = c + 13;               //si es igual o mayor que a y menor que n, se realiza un desplazamiento sumándole 13
                } else if (c >= 'n' && c <= 'z') {        //compara c con n y z
                        cadena[i] = c - 13;               //si es igual o mayor que n e igual o menor que z, se realiza un desplazamiento restándole 13
                }

	        i++;        //incrementa la variable i en uno para poder analizar el siguiente carácter
        }
}
...

Java

...
static String cadena = "Hola Mundo";    //cadena de caracteres
...
static String rot13(String cadena) {
    char c;
    StringBuilder temp = new StringBuilder();        //crea un StringBuilder para construir la cadena resultante en la variable temp

    for (int i = 0 ; i < cadena.length() ; i++) {    //comienza el bucle para analizar los caracteres de la cadena
        c = cadena.charAt(i);                        //se obtiene el carácter de la posición actual de la cadena y se guarda en la variable c

        if (c >= 'A' && c < 'N') {            //compara c con A y N
            c += 13;                          //si es igual o mayor que A y menor que N, se realiza un desplazamiento sumándole 13
        } else if (c >= 'N' && c <= 'Z') {    //compara c con N y Z
            c -= 13;                          //si es igual o mayor que N e igual o menor que Z, se realiza un desplazamiento restándole 13
        } else if (c >= 'a' && c < 'n') {     //compara c con a y n
            c += 13;                          //si es igual o mayor que a y menor que n, se realiza un desplazamiento sumándole 13
        } else if (c >= 'n' && c <= 'z') {    //compara c con n y z
            c -= 13;                          //si es igual o mayor que n e igual o menor que z, se realiza un desplazamiento restándole 13
        }

        temp.append(c);    //se añade c en temp
    }

    return temp.toString();    //retornamos la variable temp, la cual contiene la cadena cifrada o descifrada
}
...

Código fuente:
* ASM x86 – Windows – ROT13
* ASM x86 – Linux -ROT13
* C – ROT13
* Java – ROT13

Más información:
* Wikipedia – ROT13


, , , , , , , ,

  1. Deja un comentario

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión / Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión / Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión / Cambiar )

Google+ photo

Estás comentando usando tu cuenta de Google+. Cerrar sesión / Cambiar )

Conectando a %s

A %d blogueros les gusta esto: