다음과 같이 코드 코드를 복사합니다.
유닛 MD5;
인터페이스
용도
Windows, 메시지, SysUtils, 변형, 클래스, 그래픽, 컨트롤, 양식,
대화 상자, StdCtrls;
유형
MD5Count = DWORD의 배열 [0 .. 1];
MD5State = DWORD의 배열 [0 .. 3];
MD5Block = DWORD의 배열 [0 .. 15];
MD5CBits = 바이트 배열 [0 .. 7];
MD5Digest = 바이트 배열 [0 .. 15];
MD5Buffer = 바이트 배열 [0 .. 63];
MD5Context = 기록
상태: MD5State;
개수: MD5Count;
버퍼: MD5Buffer;
끝;
절차 MD5Init(var 컨텍스트: MD5Context);
절차 MD5Update(var 컨텍스트: MD5Context; 입력: PAnsiChar;
길이: 긴 단어);
절차 MD5Final(var 컨텍스트: MD5Context; var 다이제스트: MD5Digest);
함수 MD5File(N: 문자열): MD5Digest;
함수 MD5Print(D: MD5Digest): AnsiString;
함수 MD5F(파일 이름: AnsiString): AnsiString;
함수 MD5S(Str: AnsiString): AnsiString;
// MD5F는 파일의 MD5 값을 계산하는 것이고, MD5S는 문자열의 MD5 값을 계산하는 것입니다!
var
패딩: MD5Buffer = ($80, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00,
$00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00,
$00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00,
$00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00, $00,
$00, $00, $00, $00, $00, $00, $00, $00);
구현
함수 F(x, y, z: DWORD): DWORD;
시작하다
결과 := (x와 y) 또는 ((x가 아님)과 z);
끝;
함수 G(x, y, z: DWORD): DWORD;
시작하다
결과 := (x 및 z) 또는 (y 및 (z 아님));
끝;
함수 H(x, y, z: DWORD): DWORD;
시작하다
결과 := x xor y xor z;
끝;
함수 I(x, y, z: DWORD): DWORD;
시작하다
결과 := y xor (x 또는 (z 아님));
끝;
프로시저 rot(var x: DWORD; N: 바이트);
시작하다
x := (x shl N) 또는 (x shr (32 - N));
끝;
프로시저 FF(var a: DWORD; b, c, D, x: DWORD; s: 바이트; ac: DWORD);
시작하다
inc(a, F(b, c, D) + x + ac);
썩음(a, s);
inc(a,b);
끝;
프로시저 GG(var a: DWORD; b, c, D, x: DWORD; s: 바이트; ac: DWORD);
시작하다
inc(a, G(b, c, D) + x + ac);
썩음(a, s);
inc(a,b);
끝;
프로시저 HH(var a: DWORD; b, c, D, x: DWORD; s: 바이트; ac: DWORD);
시작하다
inc(a, H(b, c, D) + x + ac);
썩음(a, s);
inc(a,b);
끝;
절차 II(var a: DWORD; b, c, D, x: DWORD; s: 바이트; ac: DWORD);
시작하다
inc(a, I(b, c, D) + x + ac);
썩음(a, s);
inc(a,b);
끝;
절차 Encode(소스, 대상: 포인터; 개수: longword);
var
s:PByte;
T: PDWORD;
나: 긴 단어;
시작하다
s := 소스;
T := 대상;
for I := 1 to Count div 4 do
시작하다
ㅋ := s^;
Inc(들);
T^ := T^ 또는 (s^ shl 8);
Inc(들);
T^ := T^ 또는 (s^ shl 16);
Inc(들);
T^ := T^ 또는 (s^ shl 24);
Inc(들);
Inc(T);
끝;
끝;
절차 Decode(소스, 대상: 포인터; 개수: longword);
var
s: PDWORD;
T: P바이트;
I: 긴 단어;
시작하다
s := 소스;
T := 대상;
for I := 1부터 계산까지
시작하다
T^ := s^ 및 $FF;
Inc(T);
T^ := (s^ shr 8) 및 $FF;
Inc(T);
T^ := (s^ shr 16) 및 $FF;
Inc(T);
T^ := (s^ shr 24) 및 $FF;
Inc(T);
Inc(들);
끝;
끝;
절차 변환(버퍼: 포인터; var 상태: MD5State);
var
a, b, c, D: DWORD;
블록: MD5Block;
시작하다
인코딩(버퍼, @Block, 64);
a := 상태[0];
b := 상태[1];
c := 상태[2];
D := 상태[3];
FF(a, b, c, D, 블록[0], 7, $D76AA478);
FF(D, a, b, c, 블록[1], 12, $E8C7B756);
FF(c, D, a, b, 블록[2], 17, $242070DB);
FF(b, c, D, a, 블록[3], 22, $C1BDCEEE);
FF(a, b, c, D, 블록[4], 7, $F57C0FAF);
FF(D, a, b, c, 블록[5], 12, $4787C62A);
FF(c, D, a, b, 블록[6], 17, $A8304613);
FF(b, c, D, a, 블록[7], 22, $FD469501);
FF(a, b, c, D, 블록[8], 7, $698098D8);
FF(D, a, b, c, 블록[9], 12, $8B44F7AF);
FF(c, D, a, b, 블록[10], 17, $FFFF5BB1);
FF(b, c, D, a, 블록[11], 22, $895CD7BE);
FF(a, b, c, D, 블록[12], 7, $6B901122);
FF(D, a, b, c, 블록[13], 12, $FD987193);
FF(c, D, a, b, 블록[14], 17, $A679438E);
FF(b, c, D, a, 블록[15], 22, $49B40821);
GG(a, b, c, D, 블록[1], 5, $F61E2562);
GG(D, a, b, c, 블록[6], 9, $C040B340);
GG(c, D, a, b, 블록[11], 14, $265E5A51);
GG(b, c, D, a, 블록[0], 20, $E9B6C7AA);
GG(a, b, c, D, 블록[5], 5, $D62F105D);
GG(D, a, b, c, 블록[10], 9, $2441453);
GG(c, D, a, b, 블록[15], 14, $D8A1E681);
GG(b, c, D, a, 블록[4], 20, $E7D3FBC8);
GG(a, b, c, D, 블록[9], 5, $21E1CDE6);
GG(D, a, b, c, 블록[14], 9, $C33707D6);
GG(c, D, a, b, 블록[3], 14, $F4D50D87);
GG(b, c, D, a, 블록[8], 20, $455A14ED);
GG(a, b, c, D, 블록[13], 5, $A9E3E905);
GG(D, a, b, c, 블록[2], 9, $FCEFA3F8);
GG(c, D, a, b, 블록[7], 14, $676F02D9);
GG(b, c, D, a, 블록[12], 20, $8D2A4C8A);
HH(a, b, c, D, 블록[5], 4, $FFFA3942);
HH(D, a, b, c, 블록[8], 11, $8771F681);
HH(c, D, a, b, 블록[11], 16, $6D9D6122);
HH(b, c, D, a, 블록[14], 23, $FDE5380C);
HH(a, b, c, D, 블록[1], 4, $A4BEEA44);
HH(D, a, b, c, 블록[4], 11, $4BDECFA9);
HH(c, D, a, b, 블록[7], 16, $F6BB4B60);
HH(b, c, D, a, 블록[10], 23, $BEBFBC70);
HH(a, b, c, D, 블록[13], 4, $289B7EC6);
HH(D, a, b, c, 블록[0], 11, $EAA127FA);
HH(c, D, a, b, 블록[3], 16, $D4EF3085);
HH(b, c, D, a, 블록[6], 23, $4881D05);
HH(a, b, c, D, 블록[9], 4, $D9D4D039);
HH(D, a, b, c, 블록[12], 11, $E6DB99E5);
HH(c, D, a, b, 블록[15], 16, $1FA27CF8);
HH(b, c, D, a, 블록[2], 23, $C4AC5665);
II(a, b, c, D, 블록[0], 6, $F4292244);
II(D, a, b, c, 블록[7], 10, $432AFF97);
II(c, D, a, b, 블록[14], 15, $AB9423A7);
II(b, c, D, a, 블록[5], 21, $FC93A039);
II(a, b, c, D, 블록[12], 6, $655B59C3);
II(D, a, b, c, 블록[3], 10, $8F0CCC92);
II(c, D, a, b, 블록[10], 15, $FFFFF47D);
II(b, c, D, a, 블록[1], 21, $85845DD1);
II(a, b, c, D, 블록[8], 6, $6FA87E4F);
II(D, a, b, c, 블록[15], 10, $FE2CE6E0);
II(c, D, a, b, 블록[6], 15, $A3014314);
II(b, c, D, a, 블록[13], 21, $4E0811A1);
II(a, b, c, D, 블록[4], 6, $F7537E82);
II(D, a, b, c, 블록[11], 10, $BD3AF235);
II(c, D, a, b, 블록[2], 15, $2AD7D2BB);
II(b, c, D, a, 블록[9], 21, $EB86D391);
inc(상태[0], a);
inc(상태[1], b);
inc(상태[2], c);
inc(상태[3], D);
끝;
절차 MD5Init(var 컨텍스트: MD5Context);
시작하다
컨텍스트를 사용하여 수행
시작하다
주[0] := $67452301;
상태[1] := $EFCDAB89;
상태[2] := $98BADCFE;
상태[3] := $10325476;
개수[0] := 0;
개수[1] := 0;
ZeroMemory(@Buffer, SizeOf(MD5Buffer));
끝;
끝;
절차 MD5Update(var 컨텍스트: MD5Context; 입력: PAnsiChar;
길이: 긴 단어);
var
색인: 장문;
PartLen: 긴 단어;
나: 긴 단어;
시작하다
컨텍스트를 사용하여 수행
시작하다
Index := (Count[0] shr 3) 및 $3F;
inc(개수[0], 길이 shl 3);
Count[0] < (길이 shl 3)이면
inc(개수[1]);
inc(개수[1], 길이 shr 29);
끝;
PartLen := 64 - 색인;
길이 >= PartLen인 경우
시작하다
CopyMemory(@Context.Buffer[Index], 입력, PartLen);
Transform(@Context.Buffer, Context.State);
나는 := PartLen;
while I + 63 < 길이
시작하다
Transform(@Input[I], Context.State);
inc(I, 64);
끝;
인덱스 := 0;
끝
또 다른
나는 := 0;
CopyMemory(@Context.Buffer[Index], @Input[I], 길이 - I);
끝;
절차 MD5Final(var 컨텍스트: MD5Context; var 다이제스트: MD5Digest);
var
비트: MD5CBits;
색인: 장문;
PadLen: 긴 단어;
시작하다
디코드(@Context.Count, @Bits, 2);
Index := (Context.Count[0] shr 3) 및 $3F;
인덱스 < 56이면
PadLen := 56 - 색인
또 다른
PadLen := 120 - 인덱스;
MD5Update(컨텍스트, @PADDING, PadLen);
MD5Update(컨텍스트, @Bits, 8);
디코드(@Context.State, @Digest, 4);
ZeroMemory(@Context, SizeOf(MD5Context));
끝;
함수 MD5String(M: AnsiString): MD5Digest;
var
컨텍스트: MD5컨텍스트;
시작하다
MD5Init(컨텍스트);
MD5Update(Context, PAnsiChar(M), 길이(M));
MD5Final(컨텍스트, 결과);
끝;
함수 MD5File(N: 문자열): MD5Digest;
var
파일핸들: THandle;
MapHandle: THandle;
뷰포인터: 포인터;
컨텍스트: MD5컨텍스트;
시작하다
MD5Init(컨텍스트);
FileHandle := CreateFile(PWideChar(WideString(N)), GENERIC_READ,
FILE_SHARE_READ 또는 FILE_SHARE_WRITE, nil, OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL 또는 FILE_FLAG_SEQUENTIAL_SCAN, 0);
FileHandle <> INVALID_HANDLE_VALUE인 경우
노력하다
MapHandle := CreateFileMapping(FileHandle, nil, PAGE_READONLY, 0, 0, nil);
MapHandle <> 0이면
노력하다
ViewPointer := MapViewOfFile(MapHandle, FILE_MAP_READ, 0, 0, 0);
ViewPointer <> nil인 경우
노력하다
MD5Update(Context, ViewPointer, GetFileSize(FileHandle, nil));
마지막으로
UnmapViewOfFile(ViewPointer);
끝;
마지막으로
CloseHandle(MapHandle);
끝;
마지막으로
CloseHandle(파일핸들);
끝;
MD5Final(컨텍스트, 결과);
끝;
함수 MD5Print(D: MD5Digest): AnsiString;
var
나: 바이트;
const
숫자: Ansichar의 배열 [0 .. 15] = ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'a', 'b', 'c', 'd', 'e', 'f');
시작하다
결과 := '';
for I := 0 ~ 15 do
결과 := 결과 + 숫자[(D[I] shr 4) 및 $0F] + 숫자[D[I] 및 $0F];
끝;
함수 MD5Match(D1, D2: MD5Digest): 부울;
var
나: 바이트;
시작하다
나는 := 0;
결과 := 참;
Result 및 (I < 16) do
시작하다
결과 := D1[I] = D2[I];
Inc(I);
끝;
끝;
함수 MD5S(Str: AnsiString): AnsiString;
시작하다
결과 := MD5Print(MD5String(Str));
끝;
함수 MD5F(파일 이름: AnsiString): AnsiString;
시작하다
결과 := MD5Print(MD5File(string(파일 이름)));
끝;