#pragma pack(push, 1)
typedef union _B64
{
struct
{
unsigned int a4:6;
unsigned int a3:6;
unsigned int a2:6;
unsigned int a1:6;
};
unsigned char b[3];
} b64;
#pragma pack(pop)
inline unsigned int Base64TableIndex(char ch)
{
#if 0
const char base64table[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
char *p = base64table;
while (*p!=ch) p++;
return p - base64table;
#else
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;
if (ch == '+')
return 62;
if (ch == '/')
return 63;
return 64;
#endif
}
HRESULT DecodeBase64(const char*pIn, int nInLen, CComBSTR& bstrCharset, BSTR*pOutVal)
{
int nSize;
if (!pOutVal)
return E_POINTER;
if (!nInLen)
return S_FALSE;
*pOutVal = NULL;
int nOutSize = nInLen*3/4+1;
char *pDecodedContent = new char[nOutSize];
int num;
b64 junk;
char *pOut = pDecodedContent;
char ch;
unsigned int idx;
num = 0;
for (int i=0; i<nInLen; i++)
{
ch = *pIn++;
if (ch == '=')
{
if (num==2)
{
*pOut++=junk.b[2];
}else
if (num==3)
{
*pOut++=junk.b[2];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[1];
}
else
{
*pOut++=junk.b[2];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[1];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[0];
}
num=0;
break;
}
idx = Base64TableIndex(ch);
if (idx<64)
{
switch(num)
{
case 0:
junk.a1 = idx;
num = 1;
break;
case 1:
junk.a2 = idx;
num = 2;
break;
case 2:
junk.a3 = idx;
num = 3;
break;
case 3:
junk.a4 = idx;
num = 4;
break;
default:
*pOut++=junk.b[2];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[1];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[0];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
junk.a1 = idx;
num=1;
break;
}
}
}
if (num==2)
{
*pOut++=junk.b[2];
}else
if (num==3)
{
*pOut++=junk.b[2];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[1];
}
else
if (num==4)
{
*pOut++=junk.b[2];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[1];
if ((pOut - pDecodedContent) >= nOutSize)
goto error;
*pOut++=junk.b[0];
}
nSize = pOut - pDecodedContent;
pDecodedContent[nSize] = 0;
if (bstrCharset!="")
bstrCharset.ToLower();
/*
это для KOI-8
if (bstrCharset == "koi8-r")
{
for (int i=0; i<nSize; i++)
{
// @@ тут нужна таблица KOI-8
pDecodedContent = g_koi2win[(unsigned char)pDecodedContent];
}
}
*/
*pOutVal = CComBSTR(nSize+1, pDecodedContent).Copy();
error:
delete [] pDecodedContent;
return *pOutVal ? S_OK : S_FALSE;
}
Кто знает о base64 ???
Благодарю всех!
Лови, вот что у меня есть в эту тему, это было написано для почтовой COMпоненты, и вроде работало ;)
Нифига себе ириска !!! Ну... спасибо.