MD5

Origem: Wikipédia, a enciclopédia livre.
Ir para: navegação, pesquisa

O MD5 (Message-Digest algorithm 5) é um algoritmo de hash de 128 bits unidirecional desenvolvido pela RSA Data Security, Inc., descrito na RFC 1321, e muito utilizado por softwares com protocolo ponto-a-ponto (P2P, ou Peer-to-Peer, em inglês) na verificação de integridade de arquivos e logins.

Foi desenvolvido em 1991 por Ronald Rivest para suceder ao MD4 que tinha alguns problemas de segurança. Por ser um algoritmo unidirecional, uma hash md5 não pode ser transformada novamente no texto que lhe deu origem. O método de verificação é, então, feito pela comparação das duas hash (uma da mensagem original confiável e outra da mensagem recebida). O MD5 também é usado para verificar a integridade de um arquivo através, por exemplo, do programa md5sum, que cria a hash de um arquivo. Isto pode-se tornar muito útil para downloads de arquivos grandes, para programas P2P que constroem o arquivo através de pedaços e estão sujeitos a corrupção dos mesmos. Como autenticação de login é utilizada em vários sistemas operacionais unix e em muitos sites com autentificação.

Em 2008, Ronald Rivest e outros, publicaram uma nova versão do algoritmo o MD6 com hash de tamanhos 224, 256, 384 ou 512 bits. O algoritmo MD6 iria participar do concurso para ser o novo algoritmo SHA-3[1] [2] , porém logo depois removeu-o do concurso por considerá-lo muito lento, anunciando que os computadores de hoje são muito lentos para usar o MD6.

Vulnerabilidade[editar | editar código-fonte]

Como o MD5 faz apenas uma passagem sobre os dados, se dois prefixos com o mesmo hash forem construídos, um sufixo comum pode ser adicionado a ambos para tornar uma colisão mais provável. Deste modo é possível que duas strings diferentes produzam o mesmo hash. O que não garante que a partir de uma senha criptografada específica consiga-se a senha original, mas permite uma possibilidade de decifrar algumas senhas a partir de um conjunto grande de senhas criptografadas.

Pseudocódigo[editar | editar código-fonte]

Segue-se um pseudocódigo para o algoritmo MD5

//Definir r como o seguinte
var int[64] r, k
r[ 0..15] := {7, 12, 17, 22,  7, 12, 17, 22,  7, 12, 17, 22,  7, 12, 17, 22} 
r[16..31] := {5,  9, 14, 20,  5,  9, 14, 20,  5,  9, 14, 20,  5,  9, 14, 20}
r[32..47] := {4, 11, 16, 23,  4, 11, 16, 23,  4, 11, 16, 23,  4, 11, 16, 23}
r[48..63] := {6, 10, 15, 21,  6, 10, 15, 21,  6, 10, 15, 21,  6, 10, 15, 21}

//Utilizar a parte inteira dos senos de inteiros como constantes:
for i from 0 to 63
    k[i] := floor(abs(sin(i + 1)) × 2^32)

//Iniciar as variáveis:
var int h0 := 0x67452301
var int h1 := 0xEFCDAB89
var int h2 := 0x98BADCFE
var int h3 := 0x10325476

//Pre-processamento:
append "1" bit to message
append "0" bits until message length in bits ≡ 448 (mod 512)
append bit length of message as 64-bit little-endian integer to message

//Processar a mensagem em pedaços sucessivos de 512-bits:
for each 512-bit chunk of message
    break chunk into sixteen 32-bit little-endian words w(i), 0 ≤ i ≤ 15

    //Inicializar o valor do hash para este pedaço:
    var int a := h0
    var int b := h1
    var int c := h2
    var int d := h3

    //Loop principal:
    for i from 0 to 63
        if 0 ≤ i ≤ 15 then
            f := (b and c) or ((not b) and d)
            g := i
        else if 16 ≤ i ≤ 31
            f := (d and b) or ((not d) and c)
            g := (5×i + 1) mod 16
        else if 32 ≤ i ≤ 47
            f := b xor c xor d
            g := (3×i + 5) mod 16
        else if 48 ≤ i ≤ 63
            f := c xor (b or (not d))
            g := (7×i) mod 16
 
        temp := d
        d := c
        c := b
        b := ((a + f + k[i] + w(g)) leftrotate r[i]) + b
        a := temp

    //Adicionar este pedaço do hash ao resultado:
    h0 := h0 + a
    h1 := h1 + b 
    h2 := h2 + c
    h3 := h3 + d

var int digest := h0 append h1 append h2 append h3 //(expressed as little-endian)

Nota: Ao invés da formulação do RFC 1321 acima exibida, considera-se mais eficiente a seguinte implementação:

(0  ≤ i ≤ 15): f := d xor (b and (c xor d))
(16 ≤ i ≤ 31): f := c xor (d and (b xor c))

Hashes MD5[editar | editar código-fonte]

Os hashes MD5 de 128-bit (16-byte) são normalmente representados por uma sequência de 32 caracteres hexadecimais. O seguinte mostra uma string ASCII com 43-bytes e o hash correspondente:

 MD5("The quick brown fox jumps over the lazy dog") 
  = 9e107d9d372bb6826bd81d3542a419d6

Mesmo uma pequena alteração na mensagem vai criar um hash completamente diferente, ex. ao mudar d para c:

 MD5("The quick brown fox jumps over the lazy cog") 
  = 1055d3e698d289f2af8663725127bd4b

O Hash de uma string vazia é:

 MD5("") 
  = d41d8cd98f00b204e9800998ecf8427e

Salgar (Salting)[editar | editar código-fonte]

Para aumentar a segurança em alguns sistemas, usa-se a tática de adicionar um texto fixo no texto original a ser criptografado. Deste modo se o sal for "wiki" e a senha for "1234", a pseudo-senha poderá ser "wiki1234" e assim mesmo que alguém tenha o MD5 de 1234 por ser uma senha comum ele não terá de wiki1234. Porém caso o "sal" seja simples como no exemplo e houver o MD5 de "wiki1234" é possível descobrir o sal e deste modo decriptografar as senhas mais comuns. Por este motivo geralmente o "sal" é algo complexo.

Ver também[editar | editar código-fonte]

Ligações externas[editar | editar código-fonte]

Referências

  1. Ronald Rivest, The MD6 hash function A proposal to NIST for SHA-3
  2. Federal Register / Vol. 72, No. 212 (PDF). Federal Register. Government Printing Office (Friday, November 2, 2007). Página visitada em 2008-11-06.