unit DCP.View;
interface
uses
Winapi.Windows,
Winapi.Messages, System.SysUtils, System.Variants, System.Classes,
Vcl.Graphics,
Vcl.Controls,
Vcl.Forms,
Vcl.Dialogs,
Vcl.StdCtrls,
Vcl.ExtCtrls;
type
TForm1 =
class(TForm)
CipherText: TLabeledEdit;
Key: TLabeledEdit;
IV: TLabeledEdit;
Decrypt: TButton;
Text: TLabeledEdit;
procedure DecryptClick(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
uses
DCPcrypt2, DCPrijndael, DCPbase64, DCPmd5;
{$R *.dfm}
type
TBuffer =
record
private
FBytes: TBytes;
function GetByte(
const AIndex: Integer): Byte;
function GetMemory: PByte;
function GetSize: Int64;
procedure SetByte(
const AIndex: Integer;
const AValue: Byte);
procedure SetSize(
const AValue: Int64);
public
constructor Create(
const ABuffer: Pointer;
const ASize: Integer);
class function FromHexString(
const AHexString:
string): TBuffer;
static;
function ToRawByteString: RawByteString;
property Bytes[
const AIndex: Integer]: Byte
read GetByte
write SetByte;
default;
property Memory: PByte
read GetMemory;
property Size: Int64
read GetSize
write SetSize;
end;
constructor TBuffer.Create(
const ABuffer: Pointer;
const ASize: Integer);
begin
SetLength(FBytes, ASize);
if (Assigned(ABuffer)
and (ASize > 0))
then
begin
Move(ABuffer^, FBytes[0], ASize);
end;
end;
class function TBuffer.FromHexString(
const AHexString:
string): TBuffer;
const
HexCharSet: TSysCharSet = ['
0' .. '
9', '
a' .. '
f', '
A' .. '
F'];
var
Buffer:
string;
Bytes: TBytes;
I: Integer;
Index: Integer;
Text:
string;
begin
Buffer := StringReplace(AHexString, '
0x', '
', [rfIgnoreCase, rfReplaceAll]);
SetLength(Text, Length(Buffer));
Index := 0;
for I := 1
to Length(Buffer)
do
begin
if CharInSet(Buffer[I], HexCharSet)
then
begin
Inc(
Index);
Text[
Index] := Buffer[I];
end;
end;
SetLength(Bytes, (
Index div 2));
HexToBin(PWideChar(Text), PByte(Bytes), Length(Bytes));
Result := TBuffer.Create(@Bytes[0], Length(Bytes));
end;
function TBuffer.GetByte(
const AIndex: Integer): Byte;
begin
Result := FBytes[AIndex];
end;
function TBuffer.GetMemory: PByte;
begin
Result := PByte(FBytes);
end;
function TBuffer.GetSize: Int64;
begin
Result := Length(FBytes);
end;
procedure TBuffer.SetByte(
const AIndex: Integer;
const AValue: Byte);
begin
FBytes[AIndex] := AValue;
end;
procedure TBuffer.SetSize(
const AValue: Int64);
begin
SetLength(FBytes, AValue);
end;
function TBuffer.ToRawByteString: RawByteString;
begin
Result := UTF8Encode(TEncoding.UTF8.GetString(FBytes));
end;
procedure RemoveZeroPadding(ABuffer: TBuffer);
var
I: Integer;
begin
for I := ABuffer.Size - 1
downto 0
do
begin
if ABuffer[I] = 0
then
begin
ABuffer.Size := ABuffer.Size - 1;
end;
end;
end;
procedure TForm1.DecryptClick(Sender: TObject);
// aes:U2FsdGVkX1+aaWM2vHVan/zOH4E+9J2g/0Ylv4C1qgA=
// iv:34983c5eb8f1596da582a4aa93ca8016
// salt:9a696336bc755a9f
// ciphertext:fcce1f813ef49da0ff4625bf80b5aa00
// key:a28401b8f61012a6bde7a7a1df3f4303d6b009f9a5844a022a3ba4abbb0e6596
var
Cipher: TDCP_rijndael;
I: Integer;
LCipherText: TBuffer;
LIV: TBuffer;
LKey: TBuffer;
begin
{ Ciphertext }
LCipherText := TBuffer.FromHexString(CipherText.Text);
{ Key }
LKey := TBuffer.FromHexString(Key.Text);
{ IV }
LIV := TBuffer.FromHexString(IV.Text);
{ Decryption }
Cipher := TDCP_rijndael.Create(Self);
try
Cipher.Init(LKey.Memory^, 256, LIV.Memory);
Cipher.DecryptCBC(LCipherText.Memory^, LCipherText.Memory^, LCipherText.Size);
RemoveZeroPadding(LCipherText);
Text.Text := LCipherText.ToRawByteString;
finally
Cipher.Free;
end;
end;
end.