Šifra RC4 je základní proudová symetrická šifra představená Ronaldem Rivestem z roku 1994. Vyniká svoji jednoduchostí, ale i nízkou úrovní bezpečnosti.

Proudová šifra RC4

Šifra RC4 představuje jednoduchou proudovou šifru, představena byla Ronaldem Rivestem v roce 1994. Dnes se již nedoporučuje využívat, neboť není bezpečná. Využívá se však stále v některých starších protokolech, jako WEP (pro přenos WiFi).

Princip

Šifra se skládá z několika dílčích kroků:

  1. KSA (Key-scheduling algorithm) je krok, který inicializuje pole S (používá se při šifrování) o velikosti od 1 do 255, velikost je určena počtem bajtů klíče. Jednotlivé prvky pole jsou inicializovány dle následujícího předpisu (předpokládáme, že máme klíč uložen v poli klic):

    for i from 0 to 255
        S[i] := i
    endfor
    j := 0
    for i from 0 to 255
        j := (j + S[i] + klic[i mod velikostKlice]) mod 256
        prohod hodnoty: S[i] a S[j]
    endfor
                
  2. PRGA (Pseudo-random generation algorithm) je krok, který promíchá jednotlivé prvky v poli S dle následujícího postupu:

    i := 0
    j := 0
    while (generujVýstup):
        i := (i + 1) mod 256
        j := (j + S[i]) mod 256
        prohod hodnoty: S[i] a S[j]
        K := S[(S[i] + S[j]) mod 256]
        odešli K
    endwhile
                
  3. Generátor pseudonáhodných čísel v následujícím kroku potřebujeme generátor pseudonáhodných čísel (tj. takový, který generuje na základě vstupu výstup, jenž připomíná náhodný řetězec, ale zároveň při stejném vstupu lze výstup generátoru reprodukovat). Algoritmus dle vygenerované náhodné hodnoty vybere příslušnou buňku v poli S a odešle ji jako další prvek klíče.

Programování

Následuje ukázka možné implementace šifry RC4 (zdroj ZDE).

import sys
def rc4(data, key, skip):
    x = 0
    box = range(256)
    x = 0
    for i in range(256):
        x = (x + box[i] + ord(key[i % len(key)])) % 256
        tmp = box[i]
        tmp2 = box[x]
        box[i] = box[x]
        box[x] = tmp

    x = 0
    y = 0
    out = []
    if skip > 0:
        for i in range(skip):
            x = (x + 1) % 256
            y = (y + box[x]) % 256
            box[x], box[y] = box[y], box[x]
	
    for char in data:
        x = (x + 1) % 256
        y = (y + box[x]) % 256
        box[x], box[y] = box[y], box[x]
        k = box[(box[x] + box[y]) % 256]
        print k
        out.append(chr(ord(char) ^ k))

    return ''.join(out)
    
rc4("ahojLidi", "12345678", 0)