概述
使用方法:将缓存中数据转换成字符串并且进行了加密,然后将加密后的字符串通过SOCKET通信传输,接收方收到后,将字符串解密并且还原出数据。
可单独用于结构体的序列也可用于结构体序列+有规则字符串的序列,看似简单,其实万能而通用,有许多游戏都是这么传数据的,无非是改一改加密和解密的算法罢了。
unit EDcode;
//编码/解码函数库
{$WARNINGS OFF}
interface
uses
Windows, SysUtils, Classes;
const
BUFFERSIZE=32768;
DEFBLOCKSIZE=24;
HEADCHAR = '#';
TAILCHAR = '!';
const
CM_TEST = 1000;
CM_TEST2 = 1001;
const
SM_TEST = 9000;
SM_TEST2 = 9001;
type
TDefaultMessage=packed record //Size=18
MsgID: word;
Param1: Integer;
Param2: integer;
Param3: integer;
Param4: Integer;
end;
function EncodeMessage (smsg: TDefaultMessage): AnsiString;
function DecodeMessage (str: AnsiString): TDefaultMessage;
function EncodeString (str: AnsiString): AnsiString;
function DecodeString (str: AnsiString): AnsiString;
function EncodeBuffer (buf: PAnsiChar; bufsize: integer): AnsiString;
procedure DecodeBuffer (src: AnsiString; buf: PAnsiChar; bufsize: integer);
function MakeDefaultMsg (msgid:word; param1,param2,param3,param4:integer):TDefaultMessage;
var
CSEncode: TRTLCriticalSection;
implementation
var
EncBuf, TempBuf: PAnsiChar;
function MakeDefaultMsg (msgid:word; param1,param2,param3,param4:integer):TDefaultMessage;
begin
result.MsgID := msgid;
result.Param1 := param1;
result.Param2 := param2;
result.Param3 := param3;
result.Param4 := param4;
end;
procedure Encode6BitBuf (src, dest: PAnsiChar; srclen, destlen: integer);
var
i, restcount, destpos: integer;
made, ch, rest: byte;
begin
try
restcount := 0;
rest := 0;
destpos := 0;
for i:=0 to srclen - 1 do begin
if destpos >= destlen then break;
ch := byte (src[i]);
made := byte ((rest or (ch shr (2+restcount))) and $3F);
rest := byte (((ch shl (8 - (2+restcount))) shr 2) and $3F);
Inc (restcount, 2);
if restcount < 6 then begin
dest[destpos] := AnsiChar(made + $3C);
Inc (destpos);
end else begin
if destpos < destlen-1 then begin
dest[destpos] := AnsiChar(made + $3C);
dest[destpos+1] := AnsiChar(rest + $3C);
Inc (destpos, 2);
end else begin
dest[destpos] := AnsiChar(made + $3C);
Inc (destpos);
end;
restcount := 0;
rest := 0;
end;
end;
if restcount > 0 then begin
dest[destpos] := AnsiChar (rest + $3C);
Inc (destpos);
end;
dest[destpos] := #0;
except
end;
end;
procedure Decode6BitBuf (source: AnsiString; buf: PAnsiChar; buflen: integer);
const
Masks: array[2..6] of byte = ($FC, $F8, $F0, $E0, $C0);
var
i, len, bitpos, madebit, bufpos: integer;
ch, tmp, _byte: Byte;
begin
try
len := Length (source);
bitpos := 2;
madebit := 0;
bufpos := 0;
tmp := 0;
for i:=1 to len do begin
if Integer(source[i]) - $3C >= 0 then
ch := Byte(source[i]) - $3C
else begin
bufpos := 0;
break;
end;
if bufpos >= buflen then break;
if (madebit+6) >= 8 then begin
_byte := Byte(tmp or ((ch and $3F) shr (6-bitpos)));
buf[bufpos] := AnsiChar(_byte);
Inc (bufpos);
madebit := 0;
if bitpos < 6 then Inc (bitpos, 2)
else begin
bitpos := 2;
continue;
end;
end;
tmp := Byte (Byte(ch shl bitpos) and Masks[bitpos]);
Inc (madebit, 8-bitpos);
end;
buf [bufpos] := #0;
except
end;
end;
function DecodeMessage (str: AnsiString): TDefaultMessage;
var
msg: TDefaultMessage;
begin
try
EnterCriticalSection (CSencode);
Decode6BitBuf (str, EncBuf, 1024);
Move (EncBuf^, msg, sizeof(TDefaultMessage));
Result := msg;
finally
LeaveCriticalSection (CSencode);
end;
end;
function DecodeString (str: AnsiString): AnsiString;
begin
try
EnterCriticalSection (CSencode);
Decode6BitBuf (str, EncBuf, BUFFERSIZE);
Result := StrPas (EncBuf);
finally
LeaveCriticalSection (CSencode);
end;
end;
procedure DecodeBuffer (src: AnsiString; buf: PAnsiChar; bufsize: integer);
begin
try
EnterCriticalSection (CSencode);
Decode6BitBuf (src, EncBuf, BUFFERSIZE);
Move (EncBuf^, buf^, bufsize);
finally
LeaveCriticalSection (CSencode);
end;
end;
function EncodeMessage (smsg: TDefaultMessage): AnsiString;
begin
try
EnterCriticalSection (CSencode);
Move (smsg, TempBuf^, sizeof(TDefaultMessage));
Encode6BitBuf (TempBuf, EncBuf, sizeof(TDefaultMessage), 1024);
Result := StrPas (EncBuf);
finally
LeaveCriticalSection (CSencode);
end;
end;
function EncodeString (str: AnsiString): AnsiString;
begin
try
EnterCriticalSection (CSencode);
Encode6BitBuf (PAnsiChar(str), EncBuf, Length(str), BUFFERSIZE);
Result := StrPas (EncBuf);
finally
LeaveCriticalSection (CSencode);
end;
end;
function EncodeBuffer (buf: PAnsiChar; bufsize: integer): AnsiString;
begin
try
EnterCriticalSection (CSencode);
if bufsize < BUFFERSIZE then begin
Move (buf^, TempBuf^, bufsize);
Encode6BitBuf (TempBuf, EncBuf, bufsize, BUFFERSIZE);
Result := StrPas (EncBuf);
end else
Result := '';
finally
LeaveCriticalSection (CSencode);
end;
end;
initialization
begin
GetMem (EncBuf, BUFFERSIZE + 100);
GetMem (TempBuf, 2048);
InitializeCriticalSection(CSEncode);
end;
finalization
begin
FreeMem (EncBuf, BUFFERSIZE + 100);
FreeMem (TempBuf, 2048);
DeleteCriticalSection(CSEncode);
end;
end.
转载于:https://www.cnblogs.com/hnxxcxg/p/4888966.html
最后
以上就是霸气发带为你收集整理的缓存和字符串相互转换的全部内容,希望文章能够帮你解决缓存和字符串相互转换所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复