トップへ(mam-mam.net/)

OpenSSLで暗号化、復号化 ~Delphiソースコード集

検索:

OpenSSLで暗号化、復号化 ~Delphiソースコード集

(OpenSSLを使用せずにAES暗号化復号化したい場合は DelphiでAES暗号化AES復号化ができるユニット(クラス) を参照)
OpenSSLを使って、
AES-256-ECB(鍵長32バイト、ブロック長16バイト)暗号化と復号化、
AES-256-CBC(鍵長32バイト、ブロック長16バイト、初期ベクトル16バイト)暗号化と復号化を行います。

(1)libeay32.dll、ssleay32.dllファイルの入手

https://indy.fulgan.com/SSL/
等からOpenSSLファイルをダウンロードし、解凍してlibeay32.dll、ssleay32.dllファイル を、パスの通った場所(c:\windows等)又は今から作成するプログラムと同じ位置に配置します。

(2)MamOpenSSL.pasファイルのダウンロード

MamOpenSSL.pasファイルをダウンロードします。

(3)ソースコードの記述

uses MamOpenSSl;

procedure TForm1.Button1Click(Sender: TObject);
var KeyS,IvS:AnsiString;
    Key,iv:TBytes;
    DecDataS:String;
    DecData:TBytes;
    res:boolean;
    EncDataBase64:string;
begin
  //鍵の準備
  KeyS:='12345678901234567890123456789012';
  Key:=TEncoding.ASCII.GetBytes(KeyS);

  //初期ベクトルIVの準備
  ivS :='1234567890123456';
  iv:=TEncoding.ASCII.GetBytes(ivS);

  //暗号化するデータの準備
  DecDataS:='暗号化したい文字列';
  //暗号化する文字列を文字コードUTF8としてバイト型配列に代入
  DecData:=TEncoding.UTF8.GetBytes(DecDataS);

  //AES256ECBで暗号化(BASE64エンコード)する
  res:=MamEncAes256Ecb(DecData,key,EncDataBase64);
  if res then
  begin
    memo1.Lines.Add(EncDataBase64);
  end;

  //AES256ECBで復号化する
  res:=MamDecAes256Ecb(DecData,key,EncDataBase64);
  if res then
  begin
    DecDataS:=TEncoding.UTF8.GetString(DecData);
    memo1.Lines.Add(DecDataS);
  end;

  //AES256CBCで暗号化(BASE64エンコード)する
  res:=MamEncAes256Cbc(DecData,key,iv,EncDataBase64);
  if res then
  begin
    memo1.Lines.Add(EncDataBase64);
  end;

  //AES256CBCで復号化する
  res:=MamDecAes256Cbc(DecData,key,iv,EncDataBase64);
  if res then
  begin
    DecDataS:=TEncoding.UTF8.GetString(DecData);
    memo1.Lines.Add(DecDataS);
  end;
end;

(4)実行結果

AES-256-ECB
 暗号化したBASE64文字列:rv89qBijJzMOez3uiSswKYo8Xps+1nsjzweLVDlrKn0=
 復号化した文字列   :暗号化したい文字列

AES-256-CBC
 暗号化したBASE64文字列:aA6ctZehh3WAe1RcMn4oACec3IPf+AMdJGvrh5otVyk=
 復号化した文字列   :暗号化したい文字列

(5)PHPでの実行結果と同じか確認する

<?php
//UTF-8ファイル

$data="暗号化したい文字列";
$key="12345678901234567890123456789012";
$iv ="1234567890123456";

$enc=openssl_encrypt($data, 'AES-256-ECB', $key, 0, null);//暗号化
echo $enc."<br>\n";

$dec=openssl_decrypt($enc,  'AES-256-ECB', $key, 0, null);//複合化
echo $dec."<br>\n";

$enc=openssl_encrypt($data, 'AES-256-CBC', $key, 0, $iv);//暗号化
echo $enc."<br>\n";

$dec=openssl_decrypt($enc,  'AES-256-CBC', $key, 0, $iv);//複合化
echo $dec."<br>\n";
?>
rv89qBijJzMOez3uiSswKYo8Xps+1nsjzweLVDlrKn0=
暗号化したい文字列
aA6ctZehh3WAe1RcMn4oACec3IPf+AMdJGvrh5otVyk=
暗号化したい文字列

(6)参考:MamOpenSSL.pasファイルのソース

{ ******* OpenSSL ライブラリ Copyright 2018 Mam ******* }
unit MamOpenSSL;

interface
uses System.SysUtils,IdSSLOpenSSLHeaders,system.NetEncoding,WinApi.Windows;

//AES-128-ECB暗号化(暗号化したいデータ,キー(16バイト) out:暗号化データ)
function MamEncAes128Ecb(
  DecData,Key:TBytes;out EncData:TBytes):Boolean;overload;
//AES-128-ECB暗号化(暗号化したいデータ,キー(16バイト) out:暗号化データのBASE64)
function MamEncAes128Ecb(
  DecData,Key:TBytes;out EncDataBase64:String):Boolean;overload;

//AES-192-ECB暗号化(暗号化したいデータ,キー(24バイト) out:暗号化データ)
function MamEncAes192Ecb(
  DecData,Key:TBytes;out EncData:TBytes):Boolean;overload;
//AES-192-ECB暗号化(暗号化したいデータ,キー(24バイト) out:暗号化データのBASE64)
function MamEncAes192Ecb(
  DecData,Key:TBytes;out EncDataBase64:String):Boolean;overload;

//AES-256-ECB暗号化(暗号化したいデータ,キー(32バイト) out:暗号化データ)
function MamEncAes256Ecb(
  DecData,Key:TBytes;out EncData:TBytes):Boolean;overload;
//AES-256-ECB暗号化(暗号化したいデータ,キー(32バイト) out:暗号化データのBASE64)
function MamEncAes256Ecb(
  DecData,Key:TBytes;out EncDataBase64:String):Boolean;overload;


//AES-128-ECB複合化(out:複合化されたデータ,キー(16バイト) ,暗号化データ)
function MamDecAes128Ecb(
  out DecData:TBytes;Key,EncData:TBytes):Boolean;overload;
//AES-128-ECB複合化(out:複合化されたデータ,キー(16バイト) ,暗号化データのBASE64)
function MamDecAes128Ecb(
  out DecData:TBytes;Key:TBytes;EncDataBase64:String):Boolean;overload;

//AES-192-ECB複合化(out:複合化されたデータ,キー(24バイト) ,暗号化データ)
function MamDecAes192Ecb(
  out DecData:TBytes;Key,EncData:TBytes):Boolean;overload;
//AES-192-ECB複合化(out:複合化されたデータ,キー(24バイト) ,暗号化データのBASE64)
function MamDecAes192Ecb(
  out DecData:TBytes;Key:TBytes;EncDataBase64:String):Boolean;overload;

//AES-256-ECB複合化(out:複合化されたデータ,キー(32バイト) ,暗号化データ)
function MamDecAes256Ecb(
  out DecData:TBytes;Key,EncData:TBytes):Boolean;overload;
//AES-256-ECB複合化(out:複合化されたデータ,キー(32バイト) ,暗号化データのBASE64)
function MamDecAes256Ecb(
  out DecData:TBytes;Key:TBytes;EncDataBase64:String):Boolean;overload;


//AES-128-CBC暗号化(暗号化したいデータ,キー(16バイト),初期ベクトル(16バイト) out:暗号化データ)
function MamEncAes128Cbc(
  DecData,Key,Iv:TBytes;out EncData:TBytes):Boolean;overload;
//AES-128-CBC暗号化(暗号化したいデータ,キー(16バイト),初期ベクトル(16バイト) out:暗号化データのBASE64)
function MamEncAes128Cbc(
  DecData,Key,Iv:TBytes;out EncDataBase64:String):Boolean;overload;

//AES-192-CBC暗号化(暗号化したいデータ,キー(24バイト),初期ベクトル(16バイト) out:暗号化データ)
function MamEncAes192Cbc(
  DecData,Key,Iv:TBytes;out EncData:TBytes):Boolean;overload;
//AES-192-CBC暗号化(暗号化したいデータ,キー(24バイト),初期ベクトル(16バイト) out:暗号化データのBASE64)
function MamEncAes192Cbc(
  DecData,Key,Iv:TBytes;out EncDataBase64:String):Boolean;overload;

//AES-256-CBC暗号化(暗号化したいデータ,キー(32バイト),初期ベクトル(16バイト) out:暗号化データ)
function MamEncAes256Cbc(
  DecData,Key,Iv:TBytes;out EncData:TBytes):Boolean;overload;
//AES-256-CBC暗号化(暗号化したいデータ,キー(32バイト),初期ベクトル(16バイト) out:暗号化データのBASE64)
function MamEncAes256Cbc(
  DecData,Key,Iv:TBytes;out EncDataBase64:String):Boolean;overload;


//AES-128-CBC複合化(out:複合化されたデータ,キー(16バイト),初期ベクトル(16バイト) ,暗号化データ)
function MamDecAes128Cbc(
  out DecData:TBytes;Key,Iv,EncData:TBytes):Boolean;overload;
//AES-128-CBC複合化(out:複合化されたデータ,キー(16バイト),初期ベクトル(16バイト) ,暗号化データのBASE64)
function MamDecAes128Cbc(
  out DecData:TBytes;Key,Iv:TBytes;EncDataBase64:String):Boolean;overload;

//AES-192-CBC複合化(out:複合化されたデータ,キー(24バイト),初期ベクトル(16バイト) ,暗号化データ)
function MamDecAes192Cbc(
  out DecData:TBytes;Key,Iv,EncData:TBytes):Boolean;overload;
//AES-192-CBC複合化(out:複合化されたデータ,キー(24バイト),初期ベクトル(16バイト) ,暗号化データのBASE64)
function MamDecAes192Cbc(
  out DecData:TBytes;Key,Iv:TBytes;EncDataBase64:String):Boolean;overload;

//AES-256-CBC複合化(out:複合化されたデータ,キー(32バイト),初期ベクトル(16バイト) ,暗号化データ)
function MamDecAes256Cbc(
  out DecData:TBytes;Key,Iv,EncData:TBytes):Boolean;overload;
//AES-256-CBC複合化(out:複合化されたデータ,キー(32バイト),初期ベクトル(16バイト) ,暗号化データのBASE64)
function MamDecAes256Cbc(
  out DecData:TBytes;Key,Iv:TBytes;EncDataBase64:String):Boolean;overload;


implementation

function MamEncAes128Ecb(
  DecData,Key:TBytes;out EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Encl,Padl:integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<16 then
  begin
    l:=length(Key);
    SetLength(Key,16);
    ZeroMemory(@Key[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_EncryptInit_ex(ctx,EVP_aes_128_ecb,nil,@key[0],nil);
  setLength(EncData, (length(DecData) div 16+1)*16);
  EVP_EncryptUpdate(ctx,@EncData[0],@Encl,@DecData[0],length(DecData));
  EVP_EncryptFinal_ex(ctx,@EncData[Encl],@Padl);
  EVP_CIPHER_CTX_free(ctx);
  SetLength(EncData,Encl+Padl);
  unload;
  Result:=true;
end;
function MamEncAes128Ecb(
  DecData,Key:TBytes;out EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  result:=MamEncAes128Ecb(DecData,Key,EncData);
  EncData:=TNetEncoding.Base64.Encode(EncData);
  EncDataBase64:=TEncoding.ASCII.GetString(EncData);
end;

function MamEncAes192Ecb(
  DecData,Key:TBytes;out EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Encl,Padl:integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<24 then
  begin
    l:=length(Key);
    SetLength(Key,24);
    ZeroMemory(@Key[l],24-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_EncryptInit_ex(ctx,EVP_aes_192_ecb,nil,@key[0],nil);
  setLength(EncData, (length(DecData) div 16+1)*16);
  EVP_EncryptUpdate(ctx,@EncData[0],@Encl,@DecData[0],length(DecData));
  EVP_EncryptFinal_ex(ctx,@EncData[Encl],@Padl);
  EVP_CIPHER_CTX_free(ctx);
  SetLength(EncData,Encl+Padl);
  unload;
  Result:=true;
end;
function MamEncAes192Ecb(
  DecData,Key:TBytes;out EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  result:=MamEncAes192Ecb(DecData,Key,EncData);
  EncData:=TNetEncoding.Base64.Encode(EncData);
  EncDataBase64:=TEncoding.ASCII.GetString(EncData);
end;

function MamEncAes256Ecb(DecData,Key:TBytes;
  out EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Encl,Padl:integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<32 then
  begin
    l:=length(Key);
    SetLength(Key,32);
    ZeroMemory(@Key[l],32-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_EncryptInit_ex(ctx,EVP_aes_256_ecb,nil,@key[0],nil);
  setLength(EncData, (length(DecData) div 16+1)*16);
  EVP_EncryptUpdate(ctx,@EncData[0],@Encl,@DecData[0],length(DecData));
  EVP_EncryptFinal_ex(ctx,@EncData[Encl],@Padl);
  EVP_CIPHER_CTX_free(ctx);
  SetLength(EncData,Encl+Padl);
  unload;
  Result:=true;
end;
function MamEncAes256Ecb(DecData,Key:TBytes;
  out EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  result:=MamEncAes256Ecb(DecData,Key,EncData);
  EncData:=TNetEncoding.Base64.Encode(EncData);
  EncDataBase64:=TEncoding.ASCII.GetString(EncData);
end;




function MamDecAes128Ecb(
  out DecData:TBytes;Key,EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Decl,Padl:Integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<16 then
  begin
    l:=length(Key);
    SetLength(Key,16);
    ZeroMemory(@Key[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_DecryptInit_ex(ctx,EVP_aes_128_ecb,nil,@key[0],nil);
  setLength(DecData,length(EncData));
  EVP_DecryptUpdate(ctx,@DecData[0],LongWord(pointer(@Decl)),
    @EncData[0],Length(EncData));
  EVP_DecryptFinal_ex(ctx,@DecData[Decl],LongWord(Pointer(@Padl)));
  setlength(DecData,Decl+Padl);
  unload;
  Result:=True;
end;
function MamDecAes128Ecb(
  out DecData:TBytes;Key:TBytes;EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  EncData:=TEncoding.ASCII.GetBytes(EncDataBase64);
  EncData:=TNetEncoding.Base64.Decode(EncData);
  Result:=MamDecAes128Ecb(DecData,Key,EncData);
end;

function MamDecAes192Ecb(
  out DecData:TBytes;Key,EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Decl,Padl:Integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<24 then
  begin
    l:=length(Key);
    SetLength(Key,24);
    ZeroMemory(@Key[l],24-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_DecryptInit_ex(ctx,EVP_aes_192_ecb,nil,@key[0],nil);
  setLength(DecData,length(EncData));
  EVP_DecryptUpdate(ctx,@DecData[0],LongWord(pointer(@Decl)),
    @EncData[0],Length(EncData));
  EVP_DecryptFinal_ex(ctx,@DecData[Decl],LongWord(Pointer(@Padl)));
  setlength(DecData,Decl+Padl);
  unload;
  Result:=True;
end;
function MamDecAes192Ecb(
  out DecData:TBytes;Key:TBytes;EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  EncData:=TEncoding.ASCII.GetBytes(EncDataBase64);
  EncData:=TNetEncoding.Base64.Decode(EncData);
  Result:=MamDecAes192Ecb(DecData,Key,EncData);
end;

function MamDecAes256Ecb(
  out DecData:TBytes;Key,EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Decl,Padl:Integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<32 then
  begin
    l:=length(Key);
    SetLength(Key,32);
    ZeroMemory(@Key[l],32-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_DecryptInit_ex(ctx,EVP_aes_256_ecb,nil,@key[0],nil);
  setLength(DecData,length(EncData));
  EVP_DecryptUpdate(ctx,@DecData[0],LongWord(pointer(@Decl)),
    @EncData[0],Length(EncData));
  EVP_DecryptFinal_ex(ctx,@DecData[Decl],LongWord(Pointer(@Padl)));
  setlength(DecData,Decl+Padl);
  unload;
  Result:=True;
end;
function MamDecAes256Ecb(
  out DecData:TBytes;Key:TBytes;EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  EncData:=TEncoding.ASCII.GetBytes(EncDataBase64);
  EncData:=TNetEncoding.Base64.Decode(EncData);
  Result:=MamDecAes256Ecb(DecData,Key,EncData);
end;




function MamEncAes128Cbc(
  DecData,Key,Iv:TBytes;out EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Encl,Padl:integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<16 then
  begin
    l:=length(Key);
    SetLength(Key,16);
    ZeroMemory(@Key[l],16-l);
  end;
  if length(Iv)<16 then
  begin
    l:=length(Iv);
    SetLength(Iv,16);
    ZeroMemory(@Iv[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_EncryptInit_ex(ctx,EVP_aes_128_cbc,nil,@key[0],@Iv[0]);
  setLength(EncData, (length(DecData) div 16+1)*16);
  EVP_EncryptUpdate(ctx,@EncData[0],@Encl,@DecData[0],length(DecData));
  EVP_EncryptFinal_ex(ctx,@EncData[Encl],@Padl);
  EVP_CIPHER_CTX_free(ctx);
  SetLength(EncData,Encl+Padl);
  unload;
  Result:=true;
end;
function MamEncAes128Cbc(
  DecData,Key,Iv:TBytes;out EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  result:=MamEncAes128Cbc(DecData,Key,Iv,EncData);
  EncData:=TNetEncoding.Base64.Encode(EncData);
  EncDataBase64:=TEncoding.ASCII.GetString(EncData);
end;

function MamEncAes192Cbc(
  DecData,Key,Iv:TBytes;out EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Encl,Padl:integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<24 then
  begin
    l:=length(Key);
    SetLength(Key,24);
    ZeroMemory(@Key[l],24-l);
  end;
  if length(Iv)<16 then
  begin
    l:=length(Iv);
    SetLength(Iv,16);
    ZeroMemory(@Iv[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_EncryptInit_ex(ctx,EVP_aes_192_cbc,nil,@key[0],@Iv[0]);
  setLength(EncData, (length(DecData) div 16+1)*16);
  EVP_EncryptUpdate(ctx,@EncData[0],@Encl,@DecData[0],length(DecData));
  EVP_EncryptFinal_ex(ctx,@EncData[Encl],@Padl);
  EVP_CIPHER_CTX_free(ctx);
  SetLength(EncData,Encl+Padl);
  unload;
  Result:=true;
end;
function MamEncAes192Cbc(
  DecData,Key,Iv:TBytes;out EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  result:=MamEncAes192Cbc(DecData,Key,Iv,EncData);
  EncData:=TNetEncoding.Base64.Encode(EncData);
  EncDataBase64:=TEncoding.ASCII.GetString(EncData);
end;

function MamEncAes256Cbc(
  DecData,Key,Iv:TBytes;out EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Encl,Padl:integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<32 then
  begin
    l:=length(Key);
    SetLength(Key,32);
    ZeroMemory(@Key[l],32-l);
  end;
  if length(Iv)<16 then
  begin
    l:=length(Iv);
    SetLength(Iv,16);
    ZeroMemory(@Iv[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_EncryptInit_ex(ctx,EVP_aes_256_cbc,nil,@key[0],@Iv[0]);
  setLength(EncData, (length(DecData) div 16+1)*16);
  EVP_EncryptUpdate(ctx,@EncData[0],@Encl,@DecData[0],length(DecData));
  EVP_EncryptFinal_ex(ctx,@EncData[Encl],@Padl);
  EVP_CIPHER_CTX_free(ctx);
  SetLength(EncData,Encl+Padl);
  unload;
  Result:=true;
end;
function MamEncAes256Cbc(
  DecData,Key,Iv:TBytes;out EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  result:=MamEncAes256Cbc(DecData,Key,Iv,EncData);
  EncData:=TNetEncoding.Base64.Encode(EncData);
  EncDataBase64:=TEncoding.ASCII.GetString(EncData);
end;




function MamDecAes128Cbc(
  out DecData:TBytes;Key,Iv,EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Decl,Padl:Integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<16 then
  begin
    l:=length(Key);
    SetLength(Key,16);
    ZeroMemory(@Key[l],16-l);
  end;
  if length(Iv)<16 then
  begin
    l:=length(Iv);
    SetLength(Iv,16);
    ZeroMemory(@Iv[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_DecryptInit_ex(ctx,EVP_aes_128_cbc,nil,@key[0],@Iv[0]);
  setLength(DecData,length(EncData));
  EVP_DecryptUpdate(ctx,@DecData[0],LongWord(pointer(@Decl)),
    @EncData[0],Length(EncData));
  EVP_DecryptFinal_ex(ctx,@DecData[Decl],LongWord(Pointer(@Padl)));
  setlength(DecData,Decl+Padl);
  unload;
  Result:=True;
end;
function MamDecAes128Cbc(
  out DecData:TBytes;Key,Iv:TBytes;EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  EncData:=TEncoding.ASCII.GetBytes(EncDataBase64);
  EncData:=TNetEncoding.Base64.Decode(EncData);
  Result:=MamDecAes128Cbc(DecData,Key,Iv,EncData);
end;

function MamDecAes192Cbc(
  out DecData:TBytes;Key,Iv,EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Decl,Padl:Integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<24 then
  begin
    l:=length(Key);
    SetLength(Key,24);
    ZeroMemory(@Key[l],24-l);
  end;
  if length(Iv)<16 then
  begin
    l:=length(Iv);
    SetLength(Iv,16);
    ZeroMemory(@Iv[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_DecryptInit_ex(ctx,EVP_aes_192_cbc,nil,@key[0],@Iv[0]);
  setLength(DecData,length(EncData));
  EVP_DecryptUpdate(ctx,@DecData[0],LongWord(pointer(@Decl)),
    @EncData[0],Length(EncData));
  EVP_DecryptFinal_ex(ctx,@DecData[Decl],LongWord(Pointer(@Padl)));
  setlength(DecData,Decl+Padl);
  unload;
  Result:=True;
end;
function MamDecAes192Cbc(
  out DecData:TBytes;Key,Iv:TBytes;EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  EncData:=TEncoding.ASCII.GetBytes(EncDataBase64);
  EncData:=TNetEncoding.Base64.Decode(EncData);
  Result:=MamDecAes192Cbc(DecData,Key,Iv,EncData);
end;

function MamDecAes256Cbc(
  out DecData:TBytes;Key,Iv,EncData:TBytes):Boolean;overload;
var ctx:PEVP_CIPHER_CTX;
    Decl,Padl:Integer;
    l:integer;
begin
  Result:=false;
  if not load then exit;
  if length(Key)<32 then
  begin
    l:=length(Key);
    SetLength(Key,32);
    ZeroMemory(@Key[l],32-l);
  end;
  if length(Iv)<16 then
  begin
    l:=length(Iv);
    SetLength(Iv,16);
    ZeroMemory(@Iv[l],16-l);
  end;
  ctx:=EVP_CIPHER_CTX_new();
  EVP_CIPHER_CTX_init(ctx);
  EVP_DecryptInit_ex(ctx,EVP_aes_256_cbc,nil,@key[0],@Iv[0]);
  setLength(DecData,length(EncData));
  EVP_DecryptUpdate(ctx,@DecData[0],LongWord(pointer(@Decl)),
    @EncData[0],Length(EncData));
  EVP_DecryptFinal_ex(ctx,@DecData[Decl],LongWord(Pointer(@Padl)));
  setlength(DecData,Decl+Padl);
  unload;
  Result:=True;
end;
function MamDecAes256Cbc(
  out DecData:TBytes;Key,Iv:TBytes;EncDataBase64:String):Boolean;overload;
var EncData:TBytes;
begin
  EncData:=TEncoding.ASCII.GetBytes(EncDataBase64);
  EncData:=TNetEncoding.Base64.Decode(EncData);
  Result:=MamDecAes256Cbc(DecData,Key,Iv,EncData);
end;

end.