Hashwertvergleich

Status
Nicht offen für weitere Antworten.
G

Guest

Gast
Hi,

ich hab hier n eigentlich einfaches Problem, dass ich aber irgendwie nicht so richtig lösen kann. :cry:

Also zum einen habe ich eine Datei in der ein 32 Zeichen langer Hashwert als String steht. Diesen soll ich mit einem selbst ermittelten Hashwert abgleichen, der mir über die Klasse MessaageDigest als byte[] zurück gegeben wird.

Für einen Vergleich hatte ich jetzt mein byte[] genommen, diese in einem BigInteger abgelegt und mit Hilfe von BigInteger#toString(16) in einen String umgewandelt.

Danach kann ich die beiden Strings mit Hilfe von String#equals(Object) ohne Probleme vergleichen.

Leider hat die Sache einen Hacken. Und zwar genau dann, wenn der ermittelte Hashwert eine führende 0 hat. Diese verschwindet nämlich bei der Umwandlung über BigInteger (ist ja auch klar) zum String. Dadurch sind die Strings beim Vergleich dann natürlich nicht mehr gleich, obwohl die Hashwerte vielleicht sogar richtig wären.

Kann mir vielleicht einer von euch weiterhelfen und mir vielleicht sagen wie ich ein byte[] in einen String umwandeln kann ohne die führenden Nullen zu verlieren, oder vielleicht auch wie ich einen String in ein byte[] bringen kann das dem von mir ermittelten entspricht bzw. mit diesem vergleichen werden kann? :bahnhof:

Achja ermittelt wird der Hashwert nach MD5.

Ich könnte vor dem String-Vergleich ja grundsätzlich meinen ermittelten String prüfen und diesem, wenn er keine 32 Zeichen hat, noch führende 0en anhängen. Aber das wäre irgendwie nicht sauber finde ich.

Hoffe ihr könnt mir helfen.

Vielen Dank schon mal !!!!

Gruß
Stefan
 

20mithrandir

Aktives Mitglied
Also ich lasse meine Digests grundsätzlich immer noch durch einen Base64Converter durchlaufen (sollen ja evtl. in XML-Nachrichten versendet werden) und somit bekomme ich als Ergebnis meiner "encrypt" Methoden eh immer einen String. Da ist der Vergleich dann ja kein Problem mehr, z.B.:

Code:
public static String encrypt( String plaintext ) throws NoSuchAlgorithmException, UnsupportedEncodingException
{
	MessageDigest md = MessageDigest.getInstance( "SHA" );
	md.update( plaintext.getBytes( "UTF-8" ) );
	byte raw[] = md.digest();
	String hash = (new BASE64Encoder()).encode( raw );
	return hash;
}
 
G

Guest

Gast
20mithrandir hat gesagt.:
Also ich lasse meine Digests grundsätzlich immer noch durch einen Base64Converter durchlaufen (sollen ja evtl. in XML-Nachrichten versendet werden) und somit bekomme ich als Ergebnis meiner "encrypt" Methoden eh immer einen String. Da ist der Vergleich dann ja kein Problem mehr, z.B.:

Code:
public static String encrypt( String plaintext ) throws NoSuchAlgorithmException, UnsupportedEncodingException
{
	MessageDigest md = MessageDigest.getInstance( "SHA" );
	md.update( plaintext.getBytes( "UTF-8" ) );
	byte raw[] = md.digest();
	String hash = (new BASE64Encoder()).encode( raw );
	return hash;
}

Danke für den Tip aber so bekomme ich keine gleichen Werte.

Ich bekomme einen 32-stelligen String der bereits einen Hashwert darstellt. Um jetzt einen Vergleichswert zu ermitteln mache ich folgendes:

Code:
File f = new File("ich bin eine Datei");
MessageDigest md = MessageDigest.getInstance("MD5");
InputStream is = new FileInputStream(f);
byte[] buffer = new byte[8192];
int read = 0;
while ((read = is.read(buffer)) > 0) {
    md.update(buffer, 0, read);
}
is.close();
byte[] baMD5 = md.digest();

Daraus erhalte ich ein byte[] mit 16 Werten, die ich dann in einen 32-stelligen String umwandeln muss. Dazu habe ich einfach gemacht:

Code:
BigInteger bi = new BigInteger(baMD5); // Genau hier entfällt natürlich eine mögliche führende 0
String sFileHash = bi.toString(16).toUpperCase();

Anschließend vergleiche ich dann über String#equals(Object) meinen ermittelten String (sFileHash) mit dem übergebenen String.

Und egal was ich bis jetzt versucht habe. Wenn ich versuche aus dem übergebenen Hashwert ein byte[] zu machen, dann kommt am Ende nie das raus was ich beim Auslesen der Datei ermittelt habe.
 
G

Guest

Gast
So, ich hab mein Problem jetzt anders gelöst. Da ich auf keine vernünftige Lösung gekommen bin, wie ich zwei wirklich passende Strings ermitteln kann verwende ich BigInteger als "Vergleichsobjekt".

Zum einen habe ich ja das byte[] von MessageDigest, dass ich über "new BigInteger(byte[])" in einem BigInteger ablegen kann. Dann habe ich noch einen String der eine hexadezimale Zahl darstellt, den ich per "new BigInteger(String, 16)" ebenfalls in einem BigInteger ablegen kann.

Zum Vergleich verwende ich dann einfach BigInteger#equals(Object)
 
Status
Nicht offen für weitere Antworten.

Neue Themen


Oben