Base64编码及解码

来源:互联网 发布:手机无线鼠标软件 编辑:程序博客网 时间:2024/05/16 06:14

头文件:

#if !defined(AFX_XMLHELPERTESTDLG_H__6E861DDC_B564_412B_9BF7_1A542E3BF1E3__INCLUDED_)
#define AFX_XMLHELPERTESTDLG_H__6E861DDC_B564_412B_9BF7_1A542E3BF1E3__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

class CBase64 : public CWnd
{
// Construction
public:
 CBase64();
 CString Encode(LPBYTE szEncoding, int nSize);
 int Decode(LPCTSTR szDecoding, char *szOutput);
 UINT read_bits(int nNumBits, int * pBitsRead, int& lp);
 void write_bits(UINT nBits,
       int nNumBits,
       char *szOutput,
       int& i);
// Attributes
public:

// Operations
public:

// Overrides
 // ClassWizard generated virtual function overrides
 //{{AFX_VIRTUAL(CBase64)
 //}}AFX_VIRTUAL

// Implementation
public:

 virtual ~CBase64();

 // Generated message map functions
protected:
 //{{AFX_MSG(CBase64)
  // NOTE - the ClassWizard will add and remove member functions here.
 //}}AFX_MSG
 DECLARE_MESSAGE_MAP()

private:
 BYTE *m_szInput;
 long m_lszInput;
 CString m_sBase64Alphabet;
 int m_nMask[9];
 int m_nBitsRemaining;
 int m_nInputSize;
 long m_lBitStorage;
};

//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.

#endif // !defined(AFX_XMLHELPERTESTDLG_H__6E861DDC_B564_412B_9BF7_1A542E3BF1E3__INCLUDED_)

CPP文件:
#include "stdafx.h"
#include "base64.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
// CBase64

CBase64::CBase64()
{
 m_sBase64Alphabet =_T( "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/" );

 m_nMask[0]=0;
 m_nMask[1]=1;
 m_nMask[2]=3;
 m_nMask[3]=7;
 m_nMask[4]=15;
 m_nMask[5]=31;
 m_nMask[6]=63;
 m_nMask[7]=127;
 m_nMask[8]=255;
m_nBitsRemaining=0;
m_nInputSize=0;
m_lszInput=0;
m_szInput=0;
//m_lBitStorage=0;
}

CBase64::~CBase64()
{
}


BEGIN_MESSAGE_MAP(CBase64, CWnd)
 //{{AFX_MSG_MAP(CBase64)
  // NOTE - the ClassWizard will add and remove mapping macros here.
 //}}AFX_MSG_MAP
END_MESSAGE_MAP()


/////////////////////////////////////////////////////////////////////////////
// CBase64 message handlersLPCTSTR
CString CBase64::Encode(LPBYTE szEncoding, int nSize)
{
 CString sOutput = _T( "" );

 int nNumBits = 6;
 UINT nDigit;
 int lp = 0;

 ASSERT( szEncoding != NULL );
 if( szEncoding == NULL )
  return sOutput;
 m_szInput = szEncoding;
 m_nInputSize = nSize;

 m_nBitsRemaining = 0;
 nDigit = read_bits( nNumBits, &nNumBits, lp );
 while( nNumBits > 0 )
 {
  sOutput += m_sBase64Alphabet[ (int)nDigit ];
  nDigit = read_bits( nNumBits, &nNumBits, lp );
 }
 // Pad with '=' as per RFC 1521
 while( sOutput.GetLength() % 4 != 0 )
 {
  sOutput += '=';
 }
 return sOutput;
}

// The size of the output buffer must not be less than
// 3/4 the size of the input buffer. For simplicity,
// make them the same size.LPCTSTR LPTSTR
int CBase64::Decode(LPCTSTR szDecoding,char * szOutput)
{
 CString sInput;
    int c, lp =0;
 int nDigit;
    int nDecode[ 256 ];

 ASSERT( szDecoding != NULL );
 ASSERT( szOutput != NULL );
 if( szOutput == NULL )
  return 0;
 if( szDecoding == NULL )
  return 0;
 sInput = szDecoding;
 if( sInput.GetLength() == 0 )
  return 0;

 // Build Decode Table
 //
 for( int i = 0; i < 256; i++ )
  nDecode[i] = -2; // Illegal digit
 for( i=0; i < 64; i++ )
 {
  nDecode[ m_sBase64Alphabet[ i ] ] = i;
  nDecode[ m_sBase64Alphabet[ i ] | 0x80 ] = i; // Ignore 8th bit
  nDecode[ '=' ] = -1;
  nDecode[ '=' | 0x80 ] = -1; // Ignore MIME padding char
    }

 // Clear the output buffer
 memset( szOutput, 0, sInput.GetLength() + 1 );

 // Decode the Input
 //
 for( lp = 0, i = 0; lp < sInput.GetLength(); lp++ )
 {
  c = sInput[ lp ];
  nDigit = nDecode[ c & 0x7F ];
  if( nDigit < -1 )
  {
   return 0;
  }
  else if( nDigit >= 0 )
   // i (index into output) is incremented by write_bits()
   write_bits( nDigit & 0x3F, 6, szOutput, i );
    }
 return i;
}


UINT CBase64::read_bits(int nNumBits, int * pBitsRead, int& lp)
{
    ULONG lScratch;
    while( ( m_nBitsRemaining < nNumBits ) &&
     ( lp < m_nInputSize ) )
 {
  int c = m_szInput[ lp++ ];
        m_lBitStorage <<= 8;
        m_lBitStorage |= (c & 0xff);
  m_nBitsRemaining += 8;
    }
    if( m_nBitsRemaining < nNumBits )
 {
  lScratch = m_lBitStorage << ( nNumBits - m_nBitsRemaining );
  *pBitsRead = m_nBitsRemaining;
  m_nBitsRemaining = 0;
    }
 else
 {
  lScratch = m_lBitStorage >> ( m_nBitsRemaining - nNumBits );
  *pBitsRead = nNumBits;
  m_nBitsRemaining -= nNumBits;
    }
    return (UINT)lScratch & m_nMask[nNumBits];
}


void CBase64::write_bits(UINT nBits,
       int nNumBits,
       char *szOutput,
       int& i)
{
 UINT nScratch;

 m_lBitStorage = (m_lBitStorage << nNumBits) | nBits;
 m_nBitsRemaining += nNumBits;
 while( m_nBitsRemaining > 7 )
 {
  nScratch = m_lBitStorage >> (m_nBitsRemaining - 8);
  szOutput[ i++ ] = nScratch & 0xFF;
  m_nBitsRemaining -= 8;
 }
}

这个类我一直在用~~~

原创粉丝点击