18 Stimmen

CRC32 rückgängig machen

Ich suche nach einer Möglichkeit, die eine CRC32-Prüfsumme . Es gibt zwar Lösungen, aber sie sind entweder schlecht geschrieben , sehr technisch und/oder in der Versammlung . Assembly ist (derzeit) jenseits meiner Kenntnisse, also hoffe ich, dass jemand eine Implementierung in einer höheren Sprache zusammenstellen kann. Ruby ist ideal, aber ich kann PHP, Python, C, Java, usw. analysieren.

Hat jemand Lust?

29voto

Cade Roux Punkte 85601

Ein CRC32 ist nur umkehrbar, wenn die ursprüngliche Zeichenfolge 4 Byte oder weniger beträgt.

9voto

Fozi Punkte 4831

Lesen Sie das Dokument mit dem Titel "Umkehrung von Theorie und Praxis der CRC". .

Dies ist C#:

public class Crc32
{
    public const uint poly = 0xedb88320;
    public const uint startxor = 0xffffffff;

    static uint[] table = null;
    static uint[] revtable = null;

    public void FixChecksum(byte[] bytes, int length, int fixpos, uint wantcrc)
    {
        if (fixpos + 4 > length) return;

        uint crc = startxor;
        for (int i = 0; i < fixpos; i++) {
            crc = (crc >> 8) ^ table[(crc ^ bytes[i]) & 0xff];
        }

        Array.Copy(BitConverter.GetBytes(crc), 0, bytes, fixpos, 4);

        crc = wantcrc ^ startxor;
        for (int i = length - 1; i >= fixpos; i--) {
            crc = (crc << 8) ^ revtable[crc >> (3 * 8)] ^ bytes[i];
        }

        Array.Copy(BitConverter.GetBytes(crc), 0, bytes, fixpos, 4);
    }

    public Crc32()
    {
        if (Crc32.table == null) {
            uint[] table = new uint[256];
            uint[] revtable = new uint[256];

            uint fwd, rev;
            for (int i = 0; i < table.Length; i++) {
                fwd = (uint)i;
                rev = (uint)(i) << (3 * 8);
                for (int j = 8; j > 0; j--) {
                    if ((fwd & 1) == 1) {
                        fwd = (uint)((fwd >> 1) ^ poly);
                    } else {
                        fwd >>= 1;
                    }

                    if ((rev & 0x80000000) != 0) {
                        rev = ((rev ^ poly) << 1) | 1;
                    } else {
                        rev <<= 1;
                    }
                }
                table[i] = fwd;
                revtable[i] = rev;
            }

            Crc32.table = table;
            Crc32.revtable = revtable;
        }
    }
}

2voto

Frank Bollack Punkte 23412

Cade Roux hat Recht mit der Umkehrung von CRC32.

Die von Ihnen genannten Links bieten eine Lösung, um einen ungültig gewordenen CRC-Wert zu korrigieren, indem der ursprüngliche Bytestrom geändert wird. Diese Korrektur wird erreicht, indem einige (unwichtige) Bytes geändert werden und so der ursprüngliche CRC-Wert wiederhergestellt wird.

2voto

Jeremy Adsitt Punkte 384

Sie können ihn umkehren, indem Sie die Bits zurücksetzen, um die ursprünglichen 32 Bits zu erzeugen, wenn Sie das Poly wissen, mit dem er erstellt wurde. Wenn Sie jedoch den CRC32-Wert einer bestimmten Datei umkehren und eine Reihe von Bytes am Ende der Datei anhängen möchten, um den ursprünglichen CRC-Wert zu erhalten, habe ich in diesem Thread einen Code in PHP veröffentlicht:

Ich habe ein bisschen Zeit darauf verwendet und hoffe, dass es jemandem helfen kann, der an schwierigeren Problemen arbeitet: CRC32 rückgängig machen Zum Wohl!

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X