Base64
Base64 è un sistema di codifica che consente la traduzione di dati binari (contenenti sequenze di 8 bit) in stringhe di testo ASCII, rappresentando i dati sulla base di sessantaquattro caratteri ASCII diversi.
Viene usato principalmente come codifica di dati binari nelle e-mail, per convertire i dati nel formato ASCII.
L'algoritmo
L'algoritmo che effettua la conversione suddivide il file in gruppi da 6 bit, i quali possono quindi contenere valori da zero a sessantatré. Ogni possibile valore viene convertito in un carattere ASCII secondo la seguente tabella:
| Valore | ASCII |
|---|---|
| 0 | A
|
| 1 | B
|
| 2 | C
|
| 3 | D
|
| 4 | E
|
| 5 | F
|
| 6 | G
|
| 7 | H
|
| 8 | I
|
| 9 | J
|
| 10 | K
|
| 11 | L
|
| 12 | M
|
| 13 | N
|
| 14 | O
|
| 15 | P
|
| Valore | ASCII |
|---|---|
| 16 | Q
|
| 17 | R
|
| 18 | S
|
| 19 | T
|
| 20 | U
|
| 21 | V
|
| 22 | W
|
| 23 | X
|
| 24 | Y
|
| 25 | Z
|
| 26 | a
|
| 27 | b
|
| 28 | c
|
| 29 | d
|
| 30 | e
|
| 31 | f
|
| Valore | ASCII |
|---|---|
| 32 | g
|
| 33 | h
|
| 34 | i
|
| 35 | j
|
| 36 | k
|
| 37 | l
|
| 38 | m
|
| 39 | n
|
| 40 | o
|
| 41 | p
|
| 42 | q
|
| 43 | r
|
| 44 | s
|
| 45 | t
|
| 46 | u
|
| 47 | v
|
| Valore | ASCII |
|---|---|
| 48 | w
|
| 49 | x
|
| 50 | y
|
| 51 | z
|
| 52 | 0
|
| 53 | 1
|
| 54 | 2
|
| 55 | 3
|
| 56 | 4
|
| 57 | 5
|
| 58 | 6
|
| 59 | 7
|
| 60 | 8
|
| 61 | 9
|
| 62 | +
|
| 63 | /
|
Il set di sessantaquattro caratteri scelto per rappresentare i sessantaquattro valori (0-63) varia a seconda dell'implementazione scelta. L'obiettivo solitamente è di scegliere sessantaquattro caratteri che siano comuni alla maggior parte delle codifiche e che siano anche stampabili.
Le altre varianti, solitamente derivate dal Base64, condividono queste proprietà ma differiscono nella scelta degli ultimi due caratteri; per esempio la variante URL e file name safe (RFC 4648/Base64URL), usa - e _.
L'algoritmo causa un aumento delle dimensioni dei dati del 33%, poiché ogni gruppo di 3 byte viene convertito in quattro caratteri. Questo supponendo che per rappresentare un carattere si utilizzi un intero byte.
Se per rappresentare i caratteri ASCII si usassero 7 bit (che sarebbero sufficienti) e non otto, l'aumento di dimensioni sarebbe solo del 17%. Poiché però per rappresentare i caratteri ASCII si usano convenzionalmente 8 bit (sette per il carattere, lasciando il restante bit nullo), allora si ottiene l'aumento delle dimensioni descritto poco fa.
Esempio di codifica
Dati 3 byte che contengono i valori , , , partendo dalla loro rappresentazione binaria, applichiamo l'algoritmo:
Rappresentazione ASCII: A B C
| | |
Rappresentazione binaria: 01000001 01000010 01000011
/ \ / \ / \
Suddivisione in gruppi da 6 bit: 010000 01 0100 0010 01 000011
|----| \------/ \------/ |----|
I 4 valori dedotti: 010000 010100 001001 000011
\/ \/ \/ \/
Il valore decimale: 16 20 9 3
| | | |
Il valore codificato: Q U J D
Quindi la sequenza di valori (ABC) viene convertita nella sequenza (QUJD).
Se la lunghezza del messaggio originale non è un multiplo di 3 byte il numero dei bit che costituiscono il risultato non sarà un multiplo di sei. Verranno quindi inseriti bit nulli (zero) alla fine (quattro o due), e nel valore codificato vengono aggiunti da zero a due simboli = (padding character) sufficienti a raggiungere un multiplo di quattro simboli. Ciascun padding character indica pertanto l'aggiunta di una coppia di bit nulli. Il padding non è comunque indispensabile per la decodifica e alcune implementazioni non lo utilizzano. Il padding è indispensabile solo qualora si vogliano concatenare messaggi codificati.
Quindi, preso un singolo byte di valore (A), esso viene convertito nella sequenza (QQ==), il singolo valore (B) viene convertito in (Qg==), mentre la sequenza (AB) diventa (QUI=).
Possibile routine di conversione
union conv
{
unsigned int l;
struct bytes
{
char b1;
char b2;
char b3;
char b4;
} b;
};
char convert (char c)
{
if (c == 63)
return 47;
else if (c == 62)
return 43;
else if (c >= 52)
return c - 4;
else if (c >= 26)
return c + 71;
else
return c + 65;
}
unsigned int toBase64(char b1, char b2, char b3)
{
conv src, dest;
src.b.b1 = b3;
src.b.b2 = b2;
src.b.b3 = b1;
src.b.b4 = 0;
//conv.l == b4 b3 b2 b1
dest.b.b1 = convert(src.b.b1 & 0x3f);
src.l = src.l >> 6;
dest.b.b2 = convert(src.b.b1 & 0x3f);
src.l = src.l >> 6;
dest.b.b3 = convert(src.b.b1 & 0x3f);
src.l = src.l >> 6;
dest.b.b4 = convert(src.b.b1 & 0x3f);
return dest.l;
}
Varianti
Esistono varianti di questa codifica, che differiscono principalmente nella scelta dei due caratteri usati per rappresentare i valori 62 e 63 e per il padding char. In particolare molto usata è la variante che usa i caratteri - e _ come valori 62 e 63 (al posto di + e /) e non usa padding; questa variante è particolarmente utile quando la stringa codificata deve essere usata in un URL o in un filename.
Collegamenti esterni
- (EN) Denis Howe, Base64, in Free On-line Dictionary of Computing. Disponibile con licenza GFDL
- Implementazione in C per la codifica in Base64
- Base64 decode / encode Archiviato il 10 agosto 2022 in Internet Archive. Decodifica Base64
- Base64 Decode Decodifica Base64