Bcrypt vs Argon2: quale hash di password nel 2026

Bcrypt e Argon2 sono le due funzioni di hashing di password più utilizzate oggi. Entrambe sono progettate per essere lente e resistenti agli attacchi di forza bruta, a differenza di MD5 o SHA-256 che sono veloci per costruzione. Argon2 ha vinto la Password Hashing Competition nel 2015 ed è oggi la scelta raccomandata da OWASP per le nuove applicazioni. Bcrypt resta un'ottima scelta matura e ampiamente supportata. Questo articolo spiega con precisione le differenze per aiutarti a decidere.

Perché un hash di password è diverso

Un hash crittografico classico come SHA-256 è progettato per essere veloce: si vogliono hashare GB di dati al secondo. Per le password, questa proprietà è un difetto: un attaccante che recupera la tua tabella utenti può testare miliardi di password al secondo su una GPU. Una funzione di hashing di password (PHF, password hashing function) cerca invece di essere:

  • Lenta per costruzione, con un parametro di costo regolabile
  • Salata, per impedire le rainbow table e gli attacchi paralleli su più account
  • Resistente all'hardware specializzato (GPU, FPGA, ASIC) per limitare lo speedup adversarial

Il sale e il parametro di costo sono memorizzati insieme all'hash, in una stringa unica tipicamente nella forma $algo$params$sale$hash. Ciò permette di aumentare il costo nel tempo senza forzare la migrazione immediata dei vecchi hash.

Bcrypt: 1999, Blowfish, parametro cost

Bcrypt è stato progettato da Niels Provos e David Mazières per OpenBSD nel 1999. Si basa sull'algoritmo di cifratura Blowfish, di cui sfrutta l'elevato costo di inizializzazione delle tabelle. Bcrypt espone un solo parametro, cost (o rounds), che definisce il numero di iterazioni nella forma 2^cost. Aumentare cost di 1 raddoppia il tempo di calcolo.

Formato di output tipico:

$2y$12$N9qo8uLOickgx2ZMRZoMyeIjZAgcfl7p92ldGxad68LJZdL17lhWy
 |  |  |                      |
 |  |  cost = 12               sel + hash en base64
 |  variante (2y = openbsd)
 algo bcrypt

Bcrypt limita l'input a 72 byte: una password più lunga viene troncata silenziosamente, il che rappresenta una nota insidia. Il rimedio abituale è pre-hashare con SHA-256 e poi codificare in base64 prima di bcrypt, ma questo può introdurre null byte problematici in alcune implementazioni. Argon2 non ha questo limite.

Argon2: 2015, vincitore PHC, 3 varianti

Argon2 è stato progettato da Alex Biryukov, Daniel Dinu e Dmitry Khovratovich. Ha vinto la Password Hashing Competition nel luglio 2015 ed è standardizzato dalla RFC 9106 (2021). Argon2 espone tre parametri:

  • Memory cost (m): quantità di memoria utilizzata, in KiB
  • Time cost (t): numero di iterazioni sul blocco di memoria
  • Parallelism (p): numero di thread paralleli

Argon2 esiste in tre varianti:

  • Argon2d: accesso alla memoria dipendente dai dati. Più resistente agli attacchi GPU, ma sensibile agli attacchi side-channel (timing, cache).
  • Argon2i: accesso alla memoria indipendente dai dati. Resistente ai side-channel, leggermente meno resistente agli attacchi GPU.
  • Argon2id: ibrido, parte in modalità i e poi passa in modalità d. Raccomandato di default da RFC 9106 e OWASP.

I parametri raccomandati da OWASP nel 2026 per Argon2id: m=19456 KiB (19 MiB), t=2, p=1. Formato di output tipico:

$argon2id$v=19$m=19456,t=2,p=1$c2VsX2FsZWF0b2lyZQ$aGFzaF9jYWxjdWxl
 |         |   |                  |                 |
 |         |   parametres          sel base64        hash base64
 |         version
 algo argon2id

Perché Argon2id è raccomandato

La resistenza all'hardware specializzato è oggi il criterio decisivo. Bcrypt usa poca memoria (~4 KiB), il che permette a una GPU di fascia alta di testare centinaia di migliaia di hash al secondo. Argon2id è memory-hard: forzare diversi MiB di memoria per tentativo riduce drasticamente il parallelismo raggiungibile su GPU e rende la progettazione di ASIC dedicati economicamente non redditizia.

La modalità ibrida di Argon2id offre inoltre una protezione contro gli attacchi side-channel durante la prima metà del calcolo. È questa combinazione che giustifica il suo posto come raccomandazione di default di OWASP, di NIST SP 800-63B (dalla revisione 2024) e della RFC 9106.

Tabella comparativa

Criterio Bcrypt Argon2id
Anno19992015
StandardizzazioneDe facto, USENIX 1999RFC 9106 (2021)
Parametricostmemory, time, parallelism
Memoria utilizzata~4 KiBConfigurabile (~19 MiB raccomandato)
Memory-hardNo
Resistenza GPUModerataForte
Resistenza side-channelBuona (constant-time)Buona (modalità id)
Limite di input72 byteNessuno
Raccomandazione OWASP 2026AccettabilePreferito
Maturità ecosistemaMolto ampiaAmpia dal ~2018

Prestazioni e resistenza agli attacchi

Su un server moderno, un bcrypt a cost=12 impiega circa 250 ms e un argon2id con i parametri OWASP circa 100-300 ms a seconda della macchina. Il tempo assoluto non è il criterio: ciò che conta è il rapporto tra il tuo costo (un calcolo, una volta per login) e quello dell'attaccante (miliardi di calcoli su GPU per craccare un dump).

Su una RTX 4090, hashcat raggiunge circa 200.000 bcrypt/s a cost=12, contro qualche decina di migliaia di argon2id a 19 MiB. A parità di tempo di calcolo lato server, Argon2id rallenta l'attaccante da 5 a 10 volte di più rispetto a bcrypt, e il divario si amplia con le nuove generazioni di GPU.

Esempi PHP

PHP supporta entrambi nativamente tramite password_hash() e password_verify() da PHP 7.2 per Argon2i (e 7.3 per Argon2id). Il costruttore PHP gestisce sale e formato automaticamente.

Bcrypt

$hash = password_hash($password, PASSWORD_BCRYPT, ['cost' => 12]);
$ok   = password_verify($password, $hash);

if (password_needs_rehash($hash, PASSWORD_BCRYPT, ['cost' => 12])) {
    $hash = password_hash($password, PASSWORD_BCRYPT, ['cost' => 12]);
}

Argon2id

$opts = [
    'memory_cost' => 19456,  // 19 MiB
    'time_cost'   => 2,
    'threads'     => 1,
];
$hash = password_hash($password, PASSWORD_ARGON2ID, $opts);
$ok   = password_verify($password, $hash);

if (password_needs_rehash($hash, PASSWORD_ARGON2ID, $opts)) {
    $hash = password_hash($password, PASSWORD_ARGON2ID, $opts);
}

Puoi generare o identificare hash di qualsiasi tipo con il nostro generatore di hash e il nostro identificatore di hash.

Raccomandazione

Per una nuova applicazione nel 2026, scegli Argon2id con i parametri OWASP come baseline (m=19456, t=2, p=1), da regolare in base al tempo target (tipicamente da 250 a 500 ms). Se gestisci un'applicazione esistente in bcrypt, non c'è urgenza di migrare: bcrypt a cost=12 o superiore resta sicuro nel 2026. Approfitta di un password_needs_rehash() al prossimo login per migrare progressivamente gli utenti attivi verso Argon2id.

Evita assolutamente MD5, SHA-1 e SHA-256 nudo per le password (vedi il nostro comparativo MD5 vs SHA-256). Nessuno di questi algoritmi è progettato per questo uso.

Domande frequenti

Bcrypt è ancora sicuro nel 2026?

Sì, a condizione di usare un cost sufficiente (minimo 12, 14 se possibile). Bcrypt non ha una vulnerabilità crittografica nota. La sua unica debolezza relativa rispetto ad Argon2id è la sua bassa impronta in memoria, che lo rende più accessibile agli attacchi GPU e FPGA.

Bisogna migrare una base bcrypt verso Argon2id?

Non con urgenza. Una migrazione progressiva con password_needs_rehash() è l'approccio raccomandato: a ogni login riuscito, ri-hashi la password in Argon2id. Dopo qualche mese, la maggior parte degli utenti attivi è migrata, e puoi forzare un reset per gli account dormienti.

Qual è il numero giusto di thread per Argon2id?

OWASP raccomanda p=1 di default. Aumentare p non porta nulla se il tuo server web tratta già molte richieste in parallelo, e complica il tuning. Privilegia piuttosto l'aumento di m (memoria) che è la leva principale di resistenza GPU.

Cos'è un «bcrypt decrypter»?

Non esiste un decrittatore bcrypt: la funzione è a senso unico per costruzione. Gli strumenti che pretendono di «decrittare» bcrypt non fanno altro che testare dizionari di password comuni contro l'hash. È esattamente la stessa cosa di un attaccante che avesse la tua tabella.

Argon2i o Argon2id?

Argon2id in tutti i casi per le password. Argon2i è leggermente più sicuro rispetto ai side-channel ma più debole rispetto agli attacchi GPU. Argon2id combina i vantaggi di entrambi ed è esplicitamente raccomandato dalla RFC 9106 per l'hashing di password.

Bisogna pepare (pepper) oltre al sale?

Il sale è sufficiente per la grande maggioranza delle applicazioni. Un pepe (chiave segreta memorizzata fuori dal database e utilizzata come HMAC prima dell'hash) aggiunge uno strato in caso di fuga della base senza compromissione del server applicativo. Argon2id non lo fornisce nativamente, va composto manualmente.