Prüf-/Checksumme für Datei?

  • Das mache ich fast immer! Den Beitrag habe ich allerdings nicht gesehen.


    Mein Versuch lief über exf.exe und StdoutRead - allerdings komme ich dann wieder nicht zurecht mit dem Extrahieren der Checksumme ^^


    Da kommt dann je nach Abfrage folgendes raus...


    exf.exe -osfv -crc32 mspaint.exe | findstr /R /I /C:"\<mspaint.exe" --> mspaint.exe 645b000f


    oder


    exf.exe -crc32 mspaint.exe | findstr /R /I /C:"\<crc32" --> 645b000f ?CRC32*mspaint.exe

  • Gibt es eine Funktion, mit der man eine Prüf-/Checksumme einer Datei ermitteln kann sodass ein Skript weiß das es sich um die richtige Datei handelt?

    Ich mache das mit der Funktion _WinAPI_ComputeCrc32... im Anhang findest du dazu mein Script und auch eine Demo.

  • Hi Bitnugger !


    Ohne zu bewerten meine Frage : Was gibt es an der Lösung von trancexx auszusetzen ?

    dieselwiesel muss sie programmiertechnisch ja nicht verstehen.

    Und was ist der Vorteil von CRC32 zu MD5 ? In der Version von trancexx gibt es eine MD5-Variante, die den virtuellen Speicher verwendet. Die ist bei Dateigrößen > 250 MB signifikant schneller.


    Edit : Mit Vorteil meine ich keinen allgemein technischen Vergleich von CRC32 zu MD5 !

    Es geht nur darum, was die eine oder andere Variante für dieselwiesel an Vorteilen bringt.

    In beiden Fällen erhält er eine 'Prüfsumme', um Dateien auf Identität zu prüfen.


    Hier ein Quellcode, der vorerst nur die ihre CRC32 Variante enthält :

    Gruß Musashi

  • Ohne zu bewerten meine Frage : Was gibt es an der Lösung von trancexx auszusetzen ?

    Ehrlich gesagt, muss ich zu meiner Schande gestehen, dass ich den Link zu dieser Lösung völlig übersehen habe. Auszusetzen hätte ich daran, dass ich damit nur die Checksummen von Files ermitteln kann, wohingegen du meiner Funktion auch eine DllStruct oder einen Memory-Pointer übergeben kannst, was aber für dieselwiesel keine Rolle spielt, denn genau das will er ja - Checksummen von Files ermitteln.


    Und was ist der Vorteil von CRC32 zu MD5 ? In der Version von trancexx gibt es eine MD5-Variante, die den virtuellen Speicher verwendet. Die ist bei Dateigrößen > 250 MB signifikant schneller.

    Das ist natürlich ein sehr gutes Argument, um die Lösung von trancexx mal unter die Lupe zu nehmen. Vermutet hätte ich, das CRC32 in beiden Fällen deutlich schneller als MD5 ist... wie man sich doch irren kann. Den entscheidenden Vorteil von trancexx Funktionen ist, dass die Größe der Dateien nicht auf den verfügbaren Speicher begrenzt ist, wie es bei meiner Funktion der Fall ist. In meiner Funktion waren übrigens noch 2 böse Fehler drin... die ich aber schon korrigiert habe und nun kann man auch einfach einen String übergeben, für den dann eine Prüfsumme erstellt wird.

    DllCall('ntdll.dll', 'none', 'RtlFillMemory', 'struct*', $tData, 'ulong_ptr', $iLength, 'byte', FileRead($vCheck))

    2x Quatsch... denn bei RtlFillMemory kann $iValue max. 8 Bytes groß sein... und mit FileRead muss die Datei binär eingelesen werden. $iValue ist der Wert, mit dem der Speicher gefüllt werden soll - in diesem Fall ist das FileRead($vCheck).


    Hm, mal schauen, evtl. baue ich die Funktionen von trancexx so um, dass sie auch mit DllStructs und Memory-Pointern funktionieren. Oder hast du Lust dazu, denn mir fehlt momentan die Zeit?

  • Hm, mal schauen, evtl. baue ich die Funktionen von trancexx so um, dass sie auch mit DllStructs und Memory-Pointern funktionieren. Oder hast du Lust dazu, denn mir fehlt momentan die Zeit ?

    Dazu müsste ICH erst mal genau analysieren, was trancexx da so macht - für Dich wahrscheinlich kein großes Problem :P.

    Ich werde es zumindest mal versuchen - unabhängig ob eine(r) der Profis vorher die Lösung postet !

    'Zeitmangel' ist leider auch bei mir das Zauberwort, daher werde ich es laaangsam angehen.

    Am Ende könnte es so aussehen, als hätte Arnold Schwarzenegger an der 'Mona Lisa' 'rumgepinselt, andererseits schadet es ja nie, seinen Horizont zu erweitern ;).


    dieselwiesel :

    Du kannst mein Beispiel aus Beitrag #7 verwenden. Wenn Dir MD5 lieber ist, nehme halt diese Funktion von trancexx - einfach ans Ende Deines Skriptes kopieren.

    EDIT 2 : Verwende bitte das aktualisierte Skript aus meinem Beitrag #12


    EDIT :

    Bitnugger - hier, nur zur Orientierung, ein Zeitvergleich mit einer 550 MB Datei :

    Gruß Musashi

    86598-musashi-c64-png

    2 Mal editiert, zuletzt von Musashi () aus folgendem Grund: auf aktualisiertes Skript hingewiesen

  • Hi Bitnugger !


    Ich habe etwas mit den 'Highspeed-Varianten' von trancexx aus dem Link

    https://www.autoitscript.com/f…2-md4-md5-sha1-for-files/

    gespielt (exemplarisch mit MD5). Dabei ist mir folgendes aufgefallen :

    Bis zu einer Dateigröße von max. 2 GB ist sie sehr schnell. Darüber hinaus muss zwingend mit #AutoIt3Wrapper_UseX64=y kompiliert werden, sonst läuft die Funktion auf einen Fehler. Mit UseX64=y geht es auch > 2 GB, liefert dann aber ein falsches Ergebnis !


    Ich habe allerdings eine andere Variante für MD5 von trancexx gefunden, die geht auch mit UseX64=n da sie die Prüfsummen 'blockweise' ermittelt.

    Hier ein Skript mit der alternativen Variante von trancexx und der Standardvariante _Crypt_HashFile :


    Getestet auf meinem PC mit einer 10 GB Datei (UseX64=n) :

    -> MD5 - trancexx benötigt 28 Sekunden

    -> _Crypt_HashFile MD5 benötigt 114 Sekunden

    (auch bei einer 30 GB Datei bleibt das Verhältnis 1:4 erhalten)


    Ach ja, von WARD gibt es auch eine Maschinencode-Version, aber die ist langsamer !


    dieselwiesel :

    Diese Diskussion geht mittlerweile weit über Deine ursprüngliche Frage hinaus, ich hoffe das stört Dich nicht. Gehört ja zum Thema des Threads ;).


    Gruß Musashi

  • Ich habe etwas mit den 'Highspeed-Varianten' von trancexx aus dem Link

    https://www.autoitscript.com/f…2-md4-md5-sha1-for-files/

    gespielt (exemplarisch mit MD5). Dabei ist mir folgendes aufgefallen :

    Bis zu einer Dateigröße von max. 2 GB ist sie sehr schnell. Darüber hinaus muss zwingend mit #AutoIt3Wrapper_UseX64=y kompiliert werden, sonst läuft die Funktion auf einen Fehler. Mit UseX64=y geht es auch > 2 GB, liefert dann aber ein falsches Ergebnis !

    Habe ich mir gestern auch noch angetan und bin auch zu diesem Ergebnis gekommen - bei > 2 GB ist es MapViewOfFile, dass mit Error 3 aussteigt. Das falsche Ergebnis bei > 2 GB konnte ich auch nicht korrigieren, indem ich evtl. falsche Typen bei den DllCall's angepasst hatte, wenn UseX64=y ist... und laut der Liste von @BugFix sind die auch alle ok, soweit ich das beurteilen kann, doch sie sind zumindest nicht identisch mit den analogen _WinAPI-Funktionen... z.B. _WinAPI_MapViewOfFile.


    Ein wirklich sehr interessantes Thema... dass leider sehr viel Zeit verschlingt... die ich momentan aber nicht habe. ;-)

  • Ein wirklich sehr interessantes Thema... dass leider sehr viel Zeit verschlingt... die ich momentan aber nicht habe. ;-)

    Wem sagst Du das :P. Ich denke, wir haben soweit auch alles herausgearbeitet !


    Das 2 GB Problem tritt übrigens bei allen 'Highspeed-Verfahren' von trancexx auf, also bei :

    https://www.autoitscript.com/f…2-md4-md5-sha1-for-files/


    Die alternative MD5-Variante aus meinem Beitrag #10 ist bei einer Dateigröße von z.B. 1,5 GB nur unwesentlich langsamer, läuft aber auch mit Riesendateien (30 GB +) und ohne UseX64=y :

    Geschwindigkeitstest (auf meinem PC) :

    FileGetsize = 1612185627 (1.5 GB)

    -> MD5 - trancexx (Highspeed) = 3,77 Sekunden

    -> MD5 - trancexx (alternativ) = 4,04 Sekunden

    -> MD5 _Crypt_HashFile (Standard) = 17,10 Sekunden

    ==> Die 'Highspeed-Variante' ist für mich daher obsolet.


    dieselwiesel : Allgemeines Fazit

    Ich schlage vor, Du verwendest zur Prüfsummenbildung das MD5 Verfahren. MD5-Hashes von Dateien lassen sich ebenso leicht vergleichen wie CRC32-Prüfsummen.

    Ob Du nun die Variante von trancexx oder die AutoIt-Standardfunktion nimmst, hängt von der Größe der Dateien ab (trancexx ist gut 4 x schneller).


    Falls es trancexx wird, dann die Funktion in Dein Skript kopieren und #include <WinAPI.au3>

    Hier ein bereinigtes Beispiel :

    (statt einen Dateinamen direkt einzutragen, kannst Du auch ein Array (Fileliste) abarbeiten)

    (oder als Download)


    Wenn Du noch weitere Fragen hast, tue Dir keinen Zwang an ;).

    Gruß Musashi

  • Es sollen nur kleinere Dateien geprüft werden. Kann ich die Varianten für X86 und X64 eigentlich gleichermaßen verwenden?

    Ja !

    EDIT : dieselwiesel  

    Die Einstellung #AutoIt3Wrapper_UseX64 spielt dbzgl. keine Rolle.

    1. In den Includebereich am Anfang Deines Skriptes #include <WinAPI.au3> einfügen

    2. Den Quellcode der Funktion von trancexx, also Func _MD5ForFile($sFile) in das Skript kopieren


    Schaue einfach mal in das Beispiel aus Beitrag #12 !


    Gruß Musashi

  • Ohne jetzt groß die Version von trancexx angeschaut zu haben, geh ich stark davon aus dass die Daten komplett im Ram verarbeitet werden, daher die 2GB Grenze wenn es als x86 kompilliert wurde, daher auch mehr als 2GB bei x64.

    Das Ganze würde auch den Geschwindigkeitsvorteil seiner Version erklären.

  • Das Ganze würde auch den Geschwindigkeitsvorteil seiner Version erklären

    Ihrer... trancexx ist ein/e "Zweibeiner/Frau" ;-)


    Ja, so ist es... aber eben nicht für sehr große Dateien geeignet und der Geschwindigkeitsverlust beim blockweise Einlesen ist eher marginal, bringt aber den Vorteil, dass die Dateien beinahe beliebig groß sein dürfen.

  • geh ich stark davon aus dass die Daten komplett im Ram verarbeitet werden, daher die 2GB Grenze wenn es als x86 kompilliert wurde

    Ein 32-Bit System hat einen Adressraum von 2^32 also 4 GB, ziehen wir davon zur Sicherheit mal 1 GB ab (Verbrauch durch andere Anwendungen usw.), bleiben noch 3 GB freier Arbeitsspeicher.

    Ich denke nicht, dass es mit dem RAM zu tun hat.

    Ich würde eher auf ein Problem mit int32 oder dword in einer der API's tippen, die liegen bei 2.147.483.647 (max. Wert = 2^31 - 1). Das ist aber nur eine Vermutung !


    Der Zeitunterschied zwischen den Varianten von trancexx ist nicht besonders :

    FileGetsize = 1612185627 (1.5 GB)

    -> MD5 - trancexx (im Speicher) = 3,77 Sekunden

    -> MD5 - trancexx (blockweise) = 4,04 Sekunden


    Die Blockvariante ist aber immer noch deutlich schneller als die Standard-Crypt :

    30 GB : UseX64=n :

    MD5 - trancexx (blockweise) = 122,53 Sekunden

    MD5 _Crypt_HashFile = 368,95 Sekunden

    30 GB : UseX64=y :

    MD5 - trancexx (blockweise) = 149,90 Sekunden

    MD5 _Crypt_HashFile = 326,06 Sekunden


    Falls man aber nur ein paar Dateien (< 100 MB) verarbeiten möchte, kann man ruhig _Crypt_Hashfile verwenden - so bleibt man beim AutoIt-Standardverfahren.


    Gruß Musashi

  • Windows vergibt normal bei 32-bit Programmen nicht mehr als 2 GB Arbeitsspeicher, selbst wenn das Windows eine 64-bit Version ist.

    Ich schaue mir gerade einen Thread (in einem anderen Forum) zu diesem Thema an.

    Dort 'fetzen' sich die Experten köstlich über die Frage, wieviel Speicher einem 32-Bit Programm unter Windows 64-Bit zur Verfügung stehen kann ^^.

    https://www.heise.de/forum/hei…zen/posting-9662298/show/


    Ich will also nicht ausschließen dass Du Recht hast, und dass das Problem mit der 'Speicherversion' von trancexx damit zu tun hat ;).


    Siehe auch : https://blogs.msdn.microsoft.c…ing/20050601-24/?p=35483/


    Gruß Musashi