Refer to: http://en.wikipedia.org/wiki/Base64
Base64 content-transfer-encoding (rfc2045)
Base64 encoding/Decoding for any file, mainly used for mime mail content encoding/Decoding
// 11111100 0xfc
// 11000000 0x3
// 11110000 0xf0
/// 00001111 0xf
// 11000000 0xc0
// 00111111 0x3f
Byte * lmmimeencodebase64 (const byte * octetsource, int size)
{
Byte * m_base64_table = "abcdefghijklmnopqrstuvwxyzabcdefghijklmnopqrstuvwxyz0123456789 + /";
Int base64size = (size) + 2)/3) * 4) + 1)/76*78 + 78; // Add "/R/N" for each Line'
Byte * strencode = (byte *) malloc (base64size );
Byte ctemp [4];
// By rfc2045 -- the encoded output stream must be represented in lines of no more than 76 characters each
Int linelength = 0;
Int I, Len, j = 0;
Memset (strencode, 0, base64size );
For (I = 0; I <size; I + = 3)
{
Memset (ctemp, 0, 4 );
// Ctemp [0] = octetsource [I];
// Ctemp [1] = octetsource [I + 1];
// Ctemp [2] = octetsource [I + 2];
// Len = strlen (char *) ctemp );
If (I <size-3 ){
Len = 3;
Ctemp [0] = octetsource [I];
Ctemp [1] = octetsource [I + 1];
Ctemp [2] = octetsource [I + 2];
}
Else {
Len = 0;
If (I <size ){
Ctemp [0] = octetsource [I];
++ Len;
}
If (I <size-1 ){
Ctemp [1] = octetsource [I + 1];
++ Len;
}
If (I <size-2 ){
Ctemp [2] = octetsource [I + 2];
++ Len;
}
// Dbuplintf ("Temp [0] = % d", ctemp [0]);
// Dbuplintf ("Temp [1] = % d", ctemp [1]);
// Dbuplintf ("Temp [2] = % d", ctemp [2]);
// Dbuplintf ("strencode [0] = % d", (INT) ctemp [0] & 0xfc)> 2 );
// Dbuplintf ("strencode [1] = % d", (INT) ctemp [0] & 0x3) <4 | (INT) ctemp [1] & 0xf0)> 4 );
// Dbuplintf ("strencode [2] = % d", (INT) ctemp [1] & 0xf) <2 | (INT) ctemp [2] & 0xc0)> 6 );
// Dbuplintf ("strencode [3] = % d", (INT) ctemp [2] & 0x3f );
// Dbuplintf ("strencode [0] = % C", m_base64_table [(INT) ctemp [0] & 0xfc)> 2]);
// Dbuplintf ("strencode [1] = % C", m_base64_table [(INT) ctemp [0] & 0x3) <4 | (INT) ctemp [1] & 0xf0)> 4]);
// Dbuplintf ("strencode [2] = % C", m_base64_table [(INT) ctemp [1] & 0xf) <2 | (INT) ctemp [2] & 0xc0)> 6]);
// Dbuplintf ("strencode [3] = % C", m_base64_table [(INT) ctemp [2] & 0x3f]);
}
If (LEN = 3)
{
Strencode [J ++] = m_base64_table [(INT) ctemp [0] & 0xfc)> 2];
Strencode [J ++] = m_base64_table [(INT) ctemp [0] & 0x3) <4 | (INT) ctemp [1] & 0xf0)> 4];
Strencode [J ++] = m_base64_table [(INT) ctemp [1] & 0xf) <2 | (INT) ctemp [2] & 0xc0)> 6];
Strencode [J ++] = m_base64_table [(INT) ctemp [2] & 0x3f];
Linelength + = 4;
If (linelength> = 76) {strencode [J ++] = '/R'; strencode [J ++] ='/N'; linelength = 0 ;}
}
Else if (LEN = 2)
{
Strencode [J ++] = m_base64_table [(INT) ctemp [0] & 0xfc)> 2];
Strencode [J ++] = m_base64_table [(INT) ctemp [0] & 0x3) <4 | (INT) ctemp [1] & 0xf0)> 4];
Strencode [J ++] = m_base64_table [(INT) ctemp [1] & 0x0f) <2];
Strencode [J ++] = ';
Linelength + = 4;
If (linelength> = 76) {strencode [J ++] = '/R'; strencode [J ++] ='/N'; linelength = 0 ;}
}
Else if (LEN = 1)
{
Strencode [J ++] = m_base64_table [(INT) ctemp [0] & 0xfc)> 2];
Strencode [J ++] = m_base64_table [(INT) ctemp [0] & 0x3) <4];
Strencode [J ++] = ';
Strencode [J ++] = ';
Linelength + = 4;
If (linelength> = 76) {strencode [J ++] = '/R'; strencode [J ++] ='/N'; linelength = 0 ;}
}
Memset (ctemp, 0, 4 );
}
// Strencode [J] = '/0 ';
// Dbuplintf ("-- finished encode base64size = % d, j = % d", base64size, J );
// For (I = J; I <base64size; I ++ ){
// Dbuplintf ("-- rest char is: % C", strencode [I]);
//}
Return strencode;
}
Byte getbase64value (char ch)
{
If (CH> = 'A') & (CH <= 'Z '))
Return ch-'A ';
If (CH> = 'A') & (CH <= 'Z '))
Return ch-'A' + 26;
If (CH> = '0') & (CH <= '9 '))
Return ch-'0' + 52;
Switch (CH)
{
Case '+ ':
Return 62;
Case '/':
Return 63;
Case '=':/* base64 padding */
Return 0;
Default:
Return 0;
}
}
Byte * lmmimedecodebase64 (const byte * strsource, int * psize)
{
Byte * m_base64_table = "abcdefghijklmnopqrstuvwxyzabcdefghijklmnopqrstuvwxyz0123456789 + /";
Int I, J, K, size = strlen (char *) strsource );
Int n = 0;
// Return Value
Byte * octetdecode = (byte *) malloc (size)-1)/4) * 3 );
Byte ctemp [5];
Int length = 0;
Int ASC [4];
For (I = 0; I <size; I + = 4)
{
Memset (ctemp, 0, 5 );
Ctemp [0] = strsource [I];
Ctemp [1] = strsource [I + 1];
Ctemp [2] = strsource [I + 2];
Ctemp [3] = strsource [I + 3];
Length + = 4;
If (length = 76)
{
I + = 2;
Length = 0;
}
For (j = 0; j <4; j ++)
{
// If (ctemp [J] = '){
// ASC [J] = 0;
//} Else {
For (k = 0; k <(INT) strlen (char *) m_base64_table); k ++)
{
If (ctemp [J] = m_base64_table [k]) ASC [J] = K;
}
//}
}
If ('= ctemp [2] &' = ctemp [3])
{
Octetdecode [n ++] = (byte) (INT) (ASC [0] <2 | ASC [1] <2> 6 );
}
Else if ('= ctemp [3])
{
Octetdecode [n ++] = (byte) (INT) (ASC [0] <2 | ASC [1] <2> 6 );
Octetdecode [n ++] = (byte) (INT) (ASC [1] <4 | ASC [2] <2> 4 );
}
Else
{
Octetdecode [n ++] = (byte) (INT) (ASC [0] <2 | ASC [1] <2> 6 );
Octetdecode [n ++] = (byte) (INT) (ASC [1] <4 | ASC [2] <2> 4 );
Octetdecode [n ++] = (byte) (INT) (ASC [2] <6 | ASC [3] <2> 2 );
}
// Ctemp [0] = getbase64value (char) strsource [I]);
// Ctemp [1] = getbase64value (char) strsource [I + 1]);
// Ctemp [2] = getbase64value (char) strsource [I + 2]);
// Ctemp [3] = getbase64value (char) strsource [I + 3]);
// Length + = 4;
// If (length = 76)
//{
// I + = 2;
// Length = 0;
//}
// Octetdecode [n ++] = (ctemp [0] <2) | (ctemp [1]> 4 );
// Octetdecode [n ++] = (ctemp [1] <4) | (ctemp [2]> 2 );
// Octetdecode [n ++] = (ctemp [2] <6) | (ctemp [3]);
}
* Psize = N;
Return octetdecode;
}