Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Общие вопросы Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 30.12.2012, 15:28   #1
Abrokadawr
 
Регистрация: 03.11.2011
Сообщений: 8
По умолчанию Что-то неправильное в использовании CryptoAPI

Среда : Delphi XE
Поставил перед собой цель разработки DLL-библиотеки шифрования файлов тремя алгоритмами(RC2, RC4, AES-256). Вот что получилось:
Код:
library Project1;

uses
  Windows,
  SysUtils,
  dialogs,
  Classes, WCrypt2;

var CRYPT_ALG, HASH_ALG : integer;
    CRT_HANDLE          : HCRYPTPROV;
    HASH_HANDLE         : HCRYPTHASH;
    KEY_HANDLE          : HCRYPTKEY;
    BLOCKSIZE           : byte;

{$R *.res}

function CreateHashKey(pass:shortstring):boolean;
begin
  CryptCreateHash(CRT_HANDLE, HASH_ALG, 0, 0, @HASH_HANDLE);
  CryptHashData(HASH_HANDLE, @pass[1], length(pass), 0);
  CryptDeriveKey(CRT_HANDLE, CRYPT_ALG, HASH_HANDLE, 0, @KEY_HANDLE);
  CryptDestroyHash(HASH_HANDLE);

  result:=true;

   {If (CryptCreateHash(CRT_HANDLE, HASH_ALG, 0, 0, @HASH_HANDLE) = false) or
     (CryptHashData(HASH_HANDLE, @pass[1], length(pass), 0) = false) or
     (CryptDeriveKey(CRT_HANDLE, CRYPT_ALG, HASH_HANDLE, 0, @KEY_HANDLE)=false) or
     (CryptDestroyHash(HASH_HANDLE)=false) then
    begin
      result:=false;
      exit;
    end;}
end;


function EncryptFile(const Input_FilePath, OutPut_FilePath, Password : ShortString; const Algorithm : byte=0): byte; stdcall;
var InpFile, OutFile: File;
    data: PByte;
    dat:string;
    ln: DWord;
    d:string;
begin
  try
  //======================ОПРЕДЕЛЕНИЕ АЛГОРИТМА ШИФРОВАНИЯ===============================
    case Algorithm of
      0:
        begin
          CRYPT_ALG:=CALG_AES_256;
          HASH_ALG:=CALG_SHA_256;
          BLOCKSIZE:=16;
        end;
      1:
        begin
          CRYPT_ALG:=CALG_RC2;
          HASH_ALG:=CALG_MD5;
          BLOCKSIZE:=8;
        end;
      2:
        begin
          CRYPT_ALG:=CALG_RC4;
          HASH_ALG:=CALG_MD5;
          BLOCKSIZE:=1;
        end;
      else
        begin
          result:=1;
          exit;
        end;
    end;
  //=====================================================================================
  //===========================ПРОВЕРКА СУЩЕСТВОВАНИЯ ВХОДНОГО ФАЙЛА=====================
    if not FileExists(Input_FilePath) then
      begin
        result:=1;
        exit;
      end;
  //=====================================================================================
  //====================================ОСНОВНОЙ КОД=====================================
    If not CryptAcquireContext(@CRT_HANDLE, nil, nil, PROV_RSA_AES, CRYPT_VERIFYCONTEXT) then
      begin
        result:=2;
        exit;
      end;

    If not CreateHashKey(password) then
      begin
        result:=2;
        exit;
      end;

    AssignFile(InpFile, Input_FilePath);
    AssignFile(OutFile, OutPut_FilePath);

    Reset(InpFile, 1);
    Rewrite(OutFile, 1);

    GetMem(data, 512);

    while not eof(InpFile) do
      begin
        BlockRead(InpFile, data^, BLOCKSIZE, ln);


        If not CryptEncrypt(KEY_HANDLE, 0, eof(InpFile), 0, data, @ln, ln) then
          showmessage(inttostr(GetLastError));


        BlockWrite(OutFile, data^, ln);
      end;



    FreeMem(data, 512);
    CloseFile(InpFile);
    CloseFile(OutFile);
    CryptReleaseContext(CRT_HANDLE, 0);

    result:=0;
  except
    result:=2;
  end;
end;

function DecryptFile(const Input_FilePath, OutPut_FilePath, Password : ShortString; const Algorithm : byte=0): byte; stdcall;
begin

end;











exports EncryptFile, DecryptFile;

begin
end.
При вот таком использовании:

Код:
procedure TForm1.Button1Click(Sender: TObject);
var hLib: HModule;
    test: function (const Input_FilePath, OutPut_FilePath, Password : ShortString; const Algorithm : byte=0): byte; stdcall;
begin
  memo1.Clear;

  hLib:=LoadLibrary('project1.dll');
  Test:=GetProcAddress(hLib, 'EncryptFile');

  Memo1.Lines.Add(Inttostr(Test('TestIn.txt','TestOut1.txt','qwerty100500',strtoint(edit1.Text))));
  Memo1.Lines.Add(Inttostr(Test('TestIn.txt','TestOut2.txt','qwerty100500',strtoint(edit2.text))));
  Memo1.Lines.Add(Inttostr(Test('TestIn.txt','TestOut3.txt','qwerty100500')));

  FreeLibrary(hLib);
end;
(В файле TestIn содержится запись "Абвгдейка")

Получаю такие выходные данные:
  • TestOut1: ?лЁ›‹Ж°®алЁ›‹Ж°®
  • TestOut2.txt: ^Хл!Н№ЕЮє
  • TestOut3.txt : Абвгдейка

(В TestOut3 , Абвгдейка дополнена пробелами до 16 байт)

Т.е. получается, что RC2, RC4 шифруется коряво, а AES-256 вообще не шифрует. При чем во время шифования вываливаются сообщения (ShowMessage в цикле) с кодом ошибки 234, что означает недостаточное кол-во памяти для буфера(насколько я понял из MSDN). Но блин этого быть не может, ибо я пробовал и 5МБ выделять бестолку

Ну и собственно вопрос: где косяк и как его исправить?
Abrokadawr вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
CryptoAPI, Delphi: Что нужно изменить в проге, чтоб стал мой вариант (задание по программированию)? Fissa Помощь студентам 6 07.12.2012 20:43
MS Word x64 объявление функций, при использовании пишет, что файл не найден 48 или 53 ошибка Ecosasha Microsoft Office Word 2 09.10.2012 12:06
Что с типами данных при использовании math.h Jugger Общие вопросы C/C++ 4 23.10.2011 23:01
Что за пароль при использовании в Тесте БД Access? kunag Помощь студентам 2 31.05.2010 13:38
CryptoAPI: вопрос по ф-ям Lisi4ka Компоненты Delphi 1 28.09.2008 14:53