博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
【Delphi】Base64加解密模块
阅读量:6922 次
发布时间:2019-06-27

本文共 13710 字,大约阅读时间需要 45 分钟。

支持D2007之前的版本。

1 {
*******************************************************} 2 {
} 3 {
YxdInclude Base64加解密模块 } 4 {
} 5 {
版权所有 (C) 2013 GXT YangYxd } 6 {
} 7 {
*******************************************************} 8 9 unit uBase64; 10 11 interface 12 13 uses SysUtils, Classes; 14 15 type 16 {
$IFDEF UNICODE} 17 Base64String = AnsiString; 18 {
$ELSE} 19 Base64String = string; 20 {
$ENDIF} 21 22 // 按源长度SourceSize返回Base64编码所需缓冲区字节数 23 function Base64EncodeBufSize(SourceSize: Integer): Integer; 24 // 获取Sourec的Base64编码,Base64Buf必须有足够长度。返回实际编码字节数 25 function Base64Encode(const Source; SourceSize: Integer; var Base64Buf): Integer; overload; 26 // 将Source编码为Base64字符串返回 27 function Base64Encode(const Source; SourceSize: Integer): Base64String; overload; 28 // 将Source从StartPos开始的Size长度的内容源编码为Base64,写入流Dest。 29 // Size=0 表示一直编码到文件尾 30 procedure Base64Encode(Source, Dest: TStream; StartPos: Int64 = 0; Size: Int64 = 0); overload; 31 // 把字符串Str编码为Base64字符串返回 32 {
$IFDEF UNICODE} 33 function StrToBase64(const Str: AnsiString): Base64String; overload; 34 function StrToBase64(const Str: string): Base64String; overload; 35 {
$ELSE} 36 function StrToBase64(const Str: string): Base64String; 37 {
$ENDIF} 38 39 // 按给定的编码源Source和长度SourceSize计算并返回解码缓冲区所需字节数 40 function Base64DecodeBufSize(const Base64Source; SourceSize: Integer): Integer; 41 // 将Base64编码源Base64Source解码,Buf必须有足够长度。返回实际解码字节数 42 function Base64Decode(const Base64Source; SourceSize: Integer; var Buf): Integer; overload; 43 // 将Source从StartPos开始的Size长度的Base64编码内容解码,写入流Dest。 44 // Size=0 表示一直解码到文件尾 45 procedure Base64Decode(Source, Dest: TStream; StartPos: Int64 = 0; Size: Int64 = 0); overload; 46 // 将Base64编码源Base64Source解码为字符串返回 47 function Base64Decode(const Base64Source; SourceSize: Integer): string; overload; 48 // 把Base64字符串Base64Str解码为字符串返回 49 function Base64ToStr(const Base64Str: Base64String): string; 50 // 把字符串转为Unicode再编码成Base64字符串 51 function StrToUnicodeBase64(const Value: string): string; 52 function UnicodeBase64ToStr(const Value: string): string; 53 54 function StrBase64ToUNICODE(const Value: string): string; 55 56 implementation 57 58 const 59 Base64_Chars: array[0..63] of AnsiChar = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'; 60 Base64_Bytes: array[0..79] of Byte = 61 ( 62 62, 0, 0, 0, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 0, 63 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 64 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 65 0, 0, 0, 0, 0, 0, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 66 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51 67 ); 68 69 type 70 Base64Proc = function(const Source; SourceSize: Integer; var Buf): Integer; 71 72 73 function StrToUnicodeBase64(const Value: string): string; 74 var 75 cSize: Integer; 76 tmp: Byte; 77 i: Integer; 78 ppszW: array of Byte; 79 ww: WideString; 80 begin 81 ww := Value; 82 cSize := length(ww) * 2; 83 SetLength(ppszW, cSize); 84 try 85 Move(ww[1], ppszW[0], cSize); 86 i := 0; 87 while i < cSize do begin 88 tmp := ppszw[i]; 89 ppszw[i] := ppszw[i + 1]; 90 ppszw[i + 1] := tmp; 91 inc(i, 2); 92 end; 93 Result := Base64Encode(ppszW[0], High(ppszW)+1); 94 finally 95 SetLength(ppszW, 0); 96 end; 97 end; 98 99 function StrBase64ToUNICODE(const Value: string): string;100 begin101 Result := UnicodeBase64ToStr(Value);102 end;103 104 function UnicodeBase64ToStr(const Value: string): string;105 var106 cSize: Integer;107 tmp: Byte;108 i: Integer;109 ppszW: array of Byte;110 ww: WideString;111 begin112 ww := Value;113 cSize := length(ww);114 SetLength(ppszW, cSize);115 Base64Decode(Value[1], Length(ww), ppszW[0]);116 try117 i := 0;118 while i < High(ppszW) do begin119 tmp := ppszw[i];120 ppszw[i] := ppszw[i + 1];121 ppszw[i + 1] := tmp;122 inc(i, 2);123 end;124 Result := Trim(WideString(ppszW));125 finally126 SetLength(ppszW, 0);127 end;128 end;129 130 procedure Base64Stream(Source, Dest: TStream; Proc: Base64Proc;131 StartPos, Size: Int64; RBufSize, WBufSize: Integer);132 var133 RBuf: array of Byte;134 WBuf: array of Byte;135 RSize, WSize: Integer;136 begin137 if (StartPos < 0) or (StartPos >= Source.Size) then Exit;138 Source.Position := StartPos;139 if (Size <= 0) or (Size > Source.Size - Source.Position) then140 Size := Source.Size141 else142 Size := Size + Source.Position;143 SetLength(RBuf, RBufSize);144 SetLength(WBuf, WBufSize);145 while Size <> Source.Position do146 begin147 if RBufSize > Size - Source.Position then148 RBufSize := Size - Source.Position;149 RSize := Source.Read(RBuf[0], RBufSize);150 WSize := Proc(RBuf[0], RSize, WBuf[0]);151 Dest.Write(WBuf[0], WSize);152 end;153 end;154 155 function Base64EncodeBufSize(SourceSize: Integer): Integer;156 begin157 Result := ((SourceSize + 2) div 3) shl 2;158 end;159 160 (****************************************************************************161 * *162 * BASE64 Encode hint: *163 * *164 * addr: (high) 4 byte 3 byte 2 byte 1 byte (low) *165 * sourec ASCII(3 bytes): 33333333 22222222 11111111 *166 * bswap: 11111111 22222222 33333333 00000000 *167 * b4 = Base64_Chars[(source >> 8) & 63]: [00333333]->44444444 *168 * b3 = Base64_Chars[(source >> 14) & 63]: [00222233]->33333333 *169 * b2 = Base64_Chars[(source >> 20) & 63]: [00112222]->22222222 *170 * b1 = Base64_Chars[source >> 26]: [00111111]->11111111 *171 * b4 << 24 b3 << 16 b2 << 8 b1 *172 * dest BASE64(4 bytes) 44444444 33333333 22222222 11111111 *173 * *174 ****************************************************************************)175 176 function Base64Encode(const Source; SourceSize: Integer; var Base64Buf): Integer;177 asm178 push ebp179 push esi180 push edi181 push ebx182 mov esi, eax // esi = Source183 mov edi, ecx // edi = Buf184 mov eax, edx185 cdq186 mov ecx, 3187 div ecx // edx = SourceSize % 3188 mov ecx, eax // ecx = SourceSize / 3189 test edx, edx 190 jz @@1191 inc eax // eax = (SourceSize + 2) / 3192 @@1:193 push eax194 push edx195 lea ebp, Base64_Chars196 jecxz @Last197 cld198 @EncodeLoop: // while (ecx > 0){
199 mov edx, [esi] // edx = 00000000 33333333 22222222 11111111200 bswap edx // edx = 11111111 22222222 33333333 00000000201 push edx202 push edx203 push edx204 pop ebx // ebx = edx205 shr edx, 20206 shr ebx, 26 // ebx = 00111111207 and edx, 63 // edx = 00112222208 mov ah, [ebp + edx] // *(word*)edi = (Base64_Chars[edx] << 8) |209 mov al, [ebp + ebx] // Base64_Chars[ebx]210 stosw // edi += 2211 pop edx // edx = 11111111 22222222 33333333 00000000212 pop ebx // ebx = edx213 shr edx, 8214 shr ebx, 14215 and edx, 63 // edx = 00333333216 and ebx, 63 // ebx = 00222233217 mov ah, [ebp + edx] // *(word*)edi = (Base64_Chars[edx] << 8) |218 mov al, [ebp + ebx] // Base64_Chars[ebx]219 stosw // edi += 2220 add esi, 3 // esi += 3221 loop @EncodeLoop // }222 @Last:223 pop ecx // ecx = SourceSize % 3224 jecxz @end // if (ecx == 0) return225 mov eax, 3d3d0000h // preset 2 bytes '='226 mov [edi], eax227 test ecx, 2228 jnz @@3229 mov al, [esi] // if (ecx == 1)230 shl eax, 4 // eax = *esi << 4231 jmp @@4232 @@3:233 mov ax, [esi] // else234 xchg al, ah // eax = ((*esi << 8) or *(esi + 1)) << 2235 shl eax, 2236 @@4:237 add edi, ecx // edi += ecx238 inc ecx // ecx = last encode bytes239 @LastLoop:240 mov edx, eax // for (; cex > 0; ecx --, edi --)241 and edx, 63 // {242 mov dl, [ebp + edx] // edx = eax & 63243 mov [edi], dl // *edi = Base64_Chars[edx]244 shr eax, 6 // eax >>= 6245 dec edi // }246 loop @LastLoop247 @end:248 pop eax249 shl eax, 2 // return encode bytes250 pop ebx251 pop edi252 pop esi253 pop ebp254 end;255 256 function Base64Encode(const Source; SourceSize: Integer): Base64String;257 begin258 SetLength(Result, Base64EncodeBufSize(SourceSize));259 Base64Encode(Source, SourceSize, Result[1]);260 end;261 262 procedure Base64Encode(Source, Dest: TStream; StartPos: Int64; Size: Int64);263 begin264 Base64Stream(Source, Dest, Base64Encode, StartPos, Size, 6144, 8192);265 end;266 267 {
$IFDEF UNICODE}268 function StrToBase64(const Str: AnsiString): Base64String;269 begin270 Result := Base64Encode(Str[1], Length(Str));271 end;272 273 function StrToBase64(const Str: string): Base64String;274 begin275 Result := StrToBase64(AnsiString(Str));276 end;277 {
$ELSE}278 function StrToBase64(const Str: string): Base64String;279 begin280 Result := Base64Encode(Str[1], Length(Str));281 end;282 {
$ENDIF}283 284 function Base64DecodeBufSize(const Base64Source; SourceSize: Integer): Integer;285 asm286 mov ecx, eax // ecx = Source + Size287 add ecx, edx288 mov eax, edx // eax = Size / 4 * 3289 shr edx, 2290 shr eax, 1291 add eax, edx292 mov edx, eax293 jz @@2294 @@1:295 dec ecx296 cmp byte ptr [ecx], 61297 jne @@2 // if (*--ecx == '=')298 dec eax // eax --299 jmp @@1300 @@2: // return eax: BufSize; edx: Size / 4 * 3301 end;302 303 function Base64Decode(const Base64Source; SourceSize: Integer; var Buf): Integer;304 asm305 push ebp306 push esi307 push edi308 push ebx309 mov esi, eax // esi = Source310 mov edi, ecx // edi = Buf311 mov ebx, edx312 call Base64DecodeBufSize313 push eax // eax = Base64DecodeBufSize(Source, SourceSize)314 sub edx, eax // edx -= eax // edx: '=' count315 lea ebp, Base64_Bytes316 shr ebx, 2 // ebx = SourceSize / 4317 test ebx, ebx318 jz @end319 push edx320 cld321 @DecodeLoop: // for (; ebx > 0; ebx --; edi += 3)322 mov ecx, 4 // {323 xor eax, eax324 @xchgLoop: // for (ecx = 4, eax = 0; ecx > 0; ecx --)325 movzx edx, [esi] // {326 sub edx, 43 // edx = *(int*)esi - 43327 shl eax, 6 // eax <<= 6328 or al, [ebp + edx]// al |= Base64_Bytes[edx]329 inc esi // esi ++330 loop @xchgLoop // }331 bswap eax // bswap(eax)332 dec ebx // if (ebx == 1) break333 jz @Last334 shr eax, 8 // eax >>= 8335 stosw // *edi = ax; edi += 2336 shr eax, 16 // eax >>= 16337 stosb // *edi++ = al338 jmp @DecodeLoop // }339 @Last:340 pop ecx 341 xor ecx, 3 // ecx = last bytes342 @LastLoop: // for (; ecx > 0; ecx --)343 shr eax, 8 // {
344 stosb // eax >>= 8; *edi ++ = al345 loop @LastLoop // }346 @end:347 pop eax // return eax348 pop ebx349 pop edi350 pop esi351 pop ebp352 end;353 354 procedure Base64Decode(Source, Dest: TStream; StartPos: Int64; Size: Int64);355 begin356 Base64Stream(Source, Dest, Base64Decode, StartPos, Size, 8192, 6144);357 end;358 359 {
$IFDEF UNICODE}360 function Base64Decode(const Base64Source; SourceSize: Integer): string;361 var362 s: AnsiString;363 begin364 SetLength(s, Base64DecodeBufSize(Base64Source, SourceSize));365 Base64Decode(Base64Source, SourceSize, s[1]);366 Result := string(s);367 end;368 {
$ELSE}369 function Base64Decode(const Base64Source; SourceSize: Integer): string;370 begin371 SetLength(Result, Base64DecodeBufSize(Base64Source, SourceSize));372 Base64Decode(Base64Source, SourceSize, Result[1]);373 end;374 {
$ENDIF}375 376 function Base64ToStr(const Base64Str: Base64String): string;377 begin378 Result := Base64Decode(Base64Str[1], Length(Base64Str));379 end;380 381 382 end.

转载注明出处,谢谢。

 

转载于:https://www.cnblogs.com/yangyxd/articles/3930680.html

你可能感兴趣的文章
NMath矩阵分解的两种方式
查看>>
启动AVD时log提示“emulator-X disconnected! Cancelling 'X activity launch'!”
查看>>
10个最新手机美食APP界面设计欣赏
查看>>
SQL查找重复行
查看>>
关于加密、签名及证书
查看>>
Android之service探究
查看>>
ASP.NET下Word文档的在线编辑、保存和全文关键字搜索的完整示例
查看>>
SYBASE存储过程详解
查看>>
集体智慧算法
查看>>
压缩原理及无线的一点思考
查看>>
ifcfg-p1p1
查看>>
Linux磁盘和文件系统
查看>>
LINUX iptables防火墙规则的匹配条件
查看>>
linux解决磁盘indoe满了问题
查看>>
mysql索引的类型和优缺点
查看>>
CentOS-6.5 安装教程-配置篇-网卡配置
查看>>
Java取整数
查看>>
redis的存储的5种数据类型
查看>>
情感+事业,强者必学的定律
查看>>
Discovery CentOS6.4 issue
查看>>