MD5 - сравнить файлы

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

pztrn
незнакомец
Сообщения: 9
Зарегистрирован: 18.07.2010 07:48:52

MD5 - сравнить файлы

Сообщение pztrn »

Необходимо сравнить несколько файлов на локальной машине и на удаленной по MD5. Есть ли какая-нибудь документация по этому поводу? Или кто-нибудь может предоставить пример? :-)
Mr.Smart
долгожитель
Сообщения: 1796
Зарегистрирован: 29.03.2008 00:01:11
Откуда: из леса!

Сообщение Mr.Smart »

смотрим и изучаем модуль md5 :wink:
Timid
постоялец
Сообщения: 290
Зарегистрирован: 21.11.2007 20:33:15

Сообщение Timid »

Вопрос в удаленной машине.
На чем она будет работать? Если на PHP, то можно использовать mcrypt. Он совместим с библиотеками SecureBlackBox.
Mr.Smart
долгожитель
Сообщения: 1796
Зарегистрирован: 29.03.2008 00:01:11
Откуда: из леса!

Сообщение Mr.Smart »

Timid Я с вами согласен, но данный форум посвящён чему? Я так думаю, что не трудно догадаться, следовательно все вопросы должны быть (я всё же надеюсь на это) по freepascal, а для PHP есть соответствующие ресурсы...
pztrn
незнакомец
Сообщения: 9
Зарегистрирован: 18.07.2010 07:48:52

Сообщение pztrn »

Задача следующая - слить с сервера файл, генерируемый "find . ! -type d -print0 | xargs -0 md5sum", взять оттуда данные и сравнить с md5 локального файла.

Я просто не совсем понимаю как это реализовать :-(
Mr.Smart
долгожитель
Сообщения: 1796
Зарегистрирован: 29.03.2008 00:01:11
Откуда: из леса!

Сообщение Mr.Smart »

  • Качаем библиотеку synapse;
  • Скачиваем файл с сервера;
  • генерируем хешь;
  • сравниваем.

скачать при помощи synapse

Код: Выделить всё

...
uses ...,httpsend,...;
....
var
 f: TFileStream;
begin
  f:=TFileStream.Create('бла-бла',fmCreate);
  HttpGetBinary('http://бла-бла',f);
 f.free;
...


сравнить файл

Код: Выделить всё

...
uses ...,md5,...;
...
begin
  if hash_file=MD5Print(MD5File('бла-бла')) then
   ....
  else
   ...
...


ps Мой совет, перед тем как задавать вопрос попробуйте всё таки почитать форум и т.д. т.к. вопрос вида
просто не совсем понимаю как это реализовать

не внушает доверия...
Timid
постоялец
Сообщения: 290
Зарегистрирован: 21.11.2007 20:33:15

Сообщение Timid »

Ищите примеры для Delphi.
Например, в библиотеке компонент dcpclypt2 есть хорошие примеры.

Но Вам нужно гораздо большее. Научитесь загружать файл с помощью Indy или Synapse.
Научитесь работать со строками (коллекциями строк).
И т.д.
Иначе Вы не разберетесь в коде примера, который просите :)

И, кстати, вопросы "взаимодействие FP и PHP" очень даже приветствуются. :)
Аватара пользователя
WAYFARER
энтузиаст
Сообщения: 564
Зарегистрирован: 09.10.2009 00:00:04
Откуда: г. Курган

Сообщение WAYFARER »

pztrn писал(а):Задача следующая - слить с сервера файл, генерируемый "find . ! -type d -print0 | xargs -0 md5sum", взять оттуда данные и сравнить с md5 локального файла.

"Слить с сервера" понятие растяжимое весьма... какой сервер то? По какому протоколу файл получать будем?

Добавлено спустя 51 минуту 46 секунд:
PS. кстати о взаимодействии с пхп вообще проблем никаких нет и реализуется все за 1 минуту, может кому и пригодится
На примере получения того же хеша. используя Indy это можно сделать так:
php(index.php):

Код: Выделить всё

<?php
$hash = md5_file($_GET["filename"]);
print $hash
?>


Pascal:

Код: Выделить всё

var param,response:tstringlist; i:integer;
begin
param := TStringList.Create;
IdHTTP1.HandleRedirects:=true;
response := TStringList.Create;
response.Text := idhttp1.Post('http://localhost/hesh/index.php?filename='+Edit1.text, param);
 //передаем параметр пхп скрипту и получаем хеш(edit1.text = Файл на удаленном сервере хеш которого надо получить)
param.Free;
form1.Memo1.Lines := response; //собственно выводим

а дальше делаем с ним все что захотим...
pztrn
незнакомец
Сообщения: 9
Зарегистрирован: 18.07.2010 07:48:52

Сообщение pztrn »

Протокол, естественно, HTTP
Спасибо за советы, сегодня буду пробовать (как доберусь до рабочего компьютера)

Да, я новичок, поэтому могу не представлять как это все можно оформить
pztrn
незнакомец
Сообщения: 9
Зарегистрирован: 18.07.2010 07:48:52

Сообщение pztrn »

Вот и проблемка с MD5:

Код: Выделить всё

procedure TForm1.Button2Click(Sender: TObject);
begin
  Index := 0;
    fn := TStringList.Create;
  md5s := TStringList.Create;

  fn.LoadFromFile(ExtractFilePath(Application.EXEName) + 'hashes.name');

  try repeat
  MD5Print(MD5File(fn.Strings[Index]));
  Form1.Memo1.Lines.Append('File ' + IntToStr(Index) + ': ' + fn.Strings[Index] + ' Created (Hash: ' +  MD5Print(MD5File(fn.Strings[Index])) + ')');
  md5s.Add(MD5Print(MD5File(fn.Strings[Index])));
  Index := Index + 1;

  until Index = fn.Count;
  finally
    Form1.Memo1.Lines.Append('Files count: ' + IntToStr(fn.Count));
    md5s.SaveToFile(ExtractFilePath(Application.EXEName) + 'hashes.md5');
    fn.Free;
    md5s.Free;
  end;

end;


Файлы бинарные, и результат всегда d41d8cd98f00b204e9800998ecf8427e
fpc 2.4.0, lazarus-svn (последний срез), linux
Timid
постоялец
Сообщения: 290
Зарегистрирован: 21.11.2007 20:33:15

Сообщение Timid »

Странно, в коде, вроде нет ошибок.

Попробуйте извлекать имя из массива в отдельную переменную перед передачей в MD5File:

Код: Выделить всё

  LFileName := fn.Strings.String[Index];
  ...
pztrn
незнакомец
Сообщения: 9
Зарегистрирован: 18.07.2010 07:48:52

Сообщение pztrn »

Ага, помогло, спасибо.

Теперь главная загвоздка - как убрать блокировку главной формы при подсчете хеша, не вынося при этом MD5File в отдельный тред...
Mr.Smart
долгожитель
Сообщения: 1796
Зарегистрирован: 29.03.2008 00:01:11
Откуда: из леса!

Сообщение Mr.Smart »

Код: Выделить всё

Application.ProcessMessages


Добавлено спустя 26 секунд:
Вызываем в цикле подсчёта хеша
pztrn
незнакомец
Сообщения: 9
Зарегистрирован: 18.07.2010 07:48:52

Сообщение pztrn »

Да, я в курсе про Application.ProcessMessages, однако у меня файлы размером в 50-200 мбайт (текстуры), поэтому фриз все же существует :(
Ткните меня в нужную сторону, возможно, можно переделать подобный кусок кода от TProcess:

Код: Выделить всё

CompProc := TProcess.Create(nil);
          with TProcess.Create(nil) do
          begin
            CommandLine := cmdl;
            {$IFDEF WIN32}CommandLine := cmdlw;{$ENDIF}
            Execute;
            repeat
              Application.ProcessMessages;
              Sleep(10);
            until not Running;
            Free;
          end;
Timid
постоялец
Сообщения: 290
Зарегистрирован: 21.11.2007 20:33:15

Сообщение Timid »

Нет-нет, сделай отдельный объект - поток в отдельном модуле.
Но вообще-то тогда лучше загрузить файл в поток, а уже его пересчитывать.
MD5Stream, кажется. :)
Ответить