迴圈冗餘校驗（，通稱「CRC」）是一種根據網路資料封包或電腦檔案等資料產生簡短固定位數驗證碼的一種雜湊函式，主要用來檢測或校驗資料傳輸或者儲存後可能出現的錯誤。生成的數字在傳輸或者儲存之前計算出來並且附加到資料後面，然後接收方進行檢驗確定資料是否發生變化。由於本函式易於用二進位制的電腦硬體使用、容易進行數學分析並且尤其善於檢測傳輸通道幹擾引起的錯誤，因此獲得廣泛應用。此方法是由於 1961 年發表 。 CRCs 經常被叫做「校驗和」，但是這樣的說法嚴格來說並不是準確的，因為技術上來說，校驗「和」是透過加法來計算的，而不是 CRC 這裡的除法。 「糾錯碼」（，簡稱 ECC）常常和 CRCs 緊密相關，其語序糾正在傳輸過程中所產生的錯誤。這些編碼方式常常和數學原理緊密相關。例如常見於通訊或資訊傳遞上 BCH 碼、前向錯誤更正、錯誤檢測與糾正等。 簡介 CRC 是兩個位元組資料流採用二進位制除法（沒有進位，使用 XOR 來代替減法）相除所得到的餘數。其中被除數是需要計算校驗和的資訊資料流的二進製表示；除數是一個長度為 n1 的預定義（短）的二進位制數，通常用多項式的系數來表示。在做除法之前，要在資訊資料之後先加上 n 個 0。 CRC 是基於有限域 GF 2（即除以 2 的同餘）的多項式環。簡單的來說，就是所有系數都為 0 或 1（又叫做二進位制）的多項式系數的集合，並且集合對於所有的代數操作都是封閉的。例如： x3 x x 1 x3 2x 1 equiv x3 1 2 會變成 0，因為對系數的加法運算都會再取 2 的模數。乘法也是類似的： x2 xx 1 x3 2x2 x equiv x3 x 同樣可以對多項式作除法並且得到商和餘數。例如，如果用 x3 x2 x 除以 x 1。會得到： frac x3 x2 xx1 x2 1 frac 1x1 也就是說， x3 x2 x x2 1x 1 1 等價於： x2 x 1 x x2 1x 1 1 這裡除法得到了商 x2 1 和餘數 1，因為是奇數所以最後一位是 1。 字串中的每一位其實就對應了這樣型別的多項式的系數。為了得到 CRC，首先將其乘以 xn，這裡 n 是一個固定多項式的，然後再將其除以這個固定的多項式，餘數的系數就是 CRC。 在上面的等式中，x2x1 表示了本來的資訊位是 111 x1 是所謂的鑰匙，而餘數 1（也就是 x0）就是 CRC key 的最高次為 1 所以將原來的資訊乘上 x1 來得到 x3 x2 x，也可視為原來的資訊位補 1 個零成為 1110。 一般來說，其形式為： M x cdot xn Q x cdot K x R x 這裡 M x 是原始的資訊多項式。K x 是 n 階的「鑰匙」多項式。M x cdot xn 表示了將原始資訊後面加上 n 個 0。R x 是餘數多項式，即是 CRC「校驗和」。在通訊中，傳送者在原始的資訊資料 M 後附加上 n 位的 R（替換本來附加的 0）再傳送。接收者收到 M 和 R 後，檢查 M x cdot xn R x 是否能被 K x 整除。如果是，那麼接收者認為該資訊是正確的。值得注意的是 M x cdot xn R x 就是傳送者所想要傳送的資料。這個串又叫做 codeword 實現 變體 CRC 有幾種不同的變體： shiftRegister 可以逆向使用，這樣就需要檢測最低位的值，每次向右移動一位。這就要求 polynomial 生成逆向的資料位結果。實際上這是最常用的一個變體。 可以先將資料最高位讀到移位暫存器，也可以先讀最低位。在通訊協議中，為了保留 CRC 的突發錯誤檢測特性，通常按照物理層傳送資料位的方式計算 CRC。 為了檢查 CRC，需要在全部的碼字上進行 CRC 計算，而不是僅僅計算訊息（Message）的 CRC 並把它與 CRC 比較。如果結果是 0，那麼就透過這項檢查。這是因為碼字 M x cdot xn R x Q x cdot K x 可以被 K x 整除。 移位暫存器可以初始化成 1 而不是 0。同樣，在用演算法處理之前，訊息的最初 n 個資料位要取反。這是因為未經修改的 CRC 無法區分只有起始 0 的個數不同的兩條訊息。而經過這樣的取反過程，CRC 就可以正確地分辨這些訊息了。 CRC 在附加到訊息資料流（Message stream）的時候可以進行位元組取反。這樣，CRC 的檢查可以用直接的方法計算訊息的 CRC、取反、然後與訊息資料流中的 CRC 比較這個過程來完成，也可以透過計算全部的訊息來完成。在後一種方法中，正確訊息的結果不再是 0，而是 sum_in2n1 xi 除以 K x 得到的結果。這個結果叫作核驗多項式 C x，它的十六進製表示也叫作幻數。 按照慣例，使用 CRC32 多項式以及 CRC16CCITT 多項式時通常都要取反。CRC32 的核驗多項式是 C x x31 x30 x26 x25 x24 x18 x15 x14 x12 x11 x10 x8 x6 x5 x4 x3 x 1。 對於要處理的資料 M x 有前置 0 時，用 xm L x 與 M xxn 兩式相加作反相運算，使得前置的 0 變成 1 後，再作 mod 2 運算得到 CRC。公式： M x cdot xn xm L x Q x cdot K x R xBRL x sum_i0n1 xi BRT x M x cdot xn L x R x BR 例： M x 01111 K x x3 x2 1 1101 ，這裡可知 n3 M xx3 01111000 因 sum_i0n1 xi，n3 故 L x 階數從 2 開始 L x x2 x1 x0 111 用 xm L x 求得一組 n 個 1 及 m 個 0 以便與 M xxn 相加 令 m 5，Xm L x X5 L x 11100000 （bitwise shift） M xxn xm L x 01111000 11100000 10011000（使 M 前置的 0 變成 1） 用 10011000 mod2 K x 求得餘 R x 011 T x M xxn L x R x 01111000 111 011 01111100 送出 BR 接收端 L x 111 且開頭不為 1 m 5 BR 可反推 M xxn xm L x R x 01111000 11100000 011 10011011BR 用 10011011 mod2 1101 可驗證能被 K x 整除。 錯誤檢測能力 CRC 的錯誤檢測能力依賴於關鍵多項式的階次以及所使用的特定關鍵多項式。誤碼多項式 E x 是接收到的訊息碼字與正確訊息碼字的異或結果。當且僅當誤碼多項式能夠被 CRC 多項式整除的時候 CRC 演算法無法檢查到錯誤。 由於 CRC 的計算基於除法，任何多項式都無法檢測出一組全為零的資料出現的錯誤或者前面丟失的零。但是，可以根據 CRC 的變體來解決這個問題。 所有隻有一個資料位的錯誤都可以被至少有兩個非零系數的任意多項式檢測到。誤碼多項式是 xk，並且 xk 只能被 i le k 的多項式 xi 整除。 CRC 可以檢測出所有間隔距離小於多項式階次的雙位錯誤，在這種情況下的誤碼多項式是 E x xi xk xk cdot xik 1 i k。 如上所述，xk 不能被 CRC 多項式整除，它得到一個 xik 1 項。根據定義，滿足多項式整除 xik 1 的 ik 最小值就是多項式的階次。最高階次的多項式是本原多項式，帶有二進位制系數的 n 階多項式 CRC 多項式規範 下面的表格略去了「初始值」、「反射值」以及「最終異或值」。 對於一些複雜的校驗和來說這些十六進位制數值是很重要的，如 CRC32 以及 CRC64。通常小於 CRC16 的 CRC 不需要使用這些值。 通常可以透過改變這些值來得到各自不同的校驗和，但是校驗和演算法機制並沒有變化。 CRC 標準化問題 由於 CRC12 有三種常用的形式，所以 CRC12 的定義會有歧義 在應用的 CRC8 的兩種形式都有數學上的缺陷。 據稱 CRC16 與 CRC32 至少有 10 種形式，但沒有一種在數學上是最優的。 同樣大小的 CCITT CRC 與 ITU CRC 不同，這個機構在不同時期定義了不同的校驗和。 常用 CRC（按照 ITUIEEE 規範） 名稱 多項式 表示法：正常或者翻轉 CRC1 x 1（用途：硬體，也稱為奇偶校驗位） 0x1 or 0x1 0x1 CRC5CCITT x5 x3 x 1（ITU G704 標準） 0xB（0x） CRC5USB x5 x2 1（用途：USB 信令包） 0x5 or 0x14 0x9 CRC7 x7 x3 1（用途：通訊系統） 0x9 or 0x48 0x11 CRC8ATM x8 x2 x 1（用途：ATM HEC PMBUS （參見 SMBUS org ）） 0x7 或 0xE0 0xC1 CRC8CCITT x8 x7 x3 x2 1（用途：1Wire 匯流排） 0x8D CRC8DallasMaxim x8 x5 x4 1（用途：1Wire bus） 0x31 或 0x8C CRC8 x8 x7 x6 x4 x2 1 0xD5（0x） CRC10 x10 x9 x5 x4 x 1 0x233（0x） CRC12 x12 x11 x3 x2 x 1（用途：通訊系統） 0x80F 或 0xF01 0xE03 CRC16Fletcher 參見 Fletchers checksum 用於 Adler32 A B CRC CRC16CCITT x16 x12 x5 1（X25 V41 Bluetooth PPP IrDA） 0x1021 或 0x8408 0x0811 CRC16IBM x16 x15 x2 1（用途：Modbus） 0x8005 或 0xA001 0x4003 CRC16BBS x16 x15 x10 x3（用途：XMODEM 協議） 0x8408（0x） CRC32Adler 參見 Adler32 參見 Adler32 CRC32MPEG2 參見 IEEE 8023 參見 IEEE 8023 CRC32IEEE 8023 x32 x26 x23 x22 x16 x12 x11 x10 x8 x7 x5 x4 x2 x 1 0x04C11DB7 或 0xEDB88320 0xDB710641 CRC32C Castagnoli x32 x28 x27 x26 x25 x23 x22 x20 x19 x18 x14 x13 x11 x10 x9 x8 x6 1 0x1EDC6F41 或 0x82F63B78 0x05EC76F1 CRC64ISO x64 x4 x3 x 1（用途 ISO 3309） 0x000000000000001B 或 0xD800000000000000 0xB000000000000001 CRC64ECMA182 x64 x62 x57 x55 x54 x53 x52 x47 x46 x45 x40 x39 x38 x37 x35 x33 x32 x31 x29 x27 x24 x23 x22 x21 x19 x17 x13 x12 x10 x9 x7 x4 x 1（參見 ECMA182 p63） 0x42F0E1EBA9EA3693 或 0xC96C5795D7870F42 0x92D8AF2BAF0E1E85 CRC128 IEEEITU 標準。被 MD5 SHA1 取代 CRC160 IEEEITU 標準。被 MD5 SHA1 取代 CRC 與資料完整性 儘管在錯誤檢測中非常有用，CRC 並不能可靠地驗證資料完整性（即資料沒有發生任何變化），這是因為 CRC 多項式是線性結構，可以非常容易地故意改變資料而維持 CRC 不變，參見 CRC and how to Reverse it 中的證明。可以用訊息鑑別碼驗證資料完整性。 CRC 發生碰撞的情況 與所有其它的雜湊函式一樣，在一定次數的碰撞測試之後 CRC 也會接近 100 出現碰撞。CRC 中每增加一個資料位，碰撞機率就會減少接近 50，如 CRC20 與 CRC21 相比。 理論上來講，CRC64 的碰撞機率大約是每 18 個 CRC 碼出現一次。 由於 CRC 的不分解多項式特性，所以經過合理設計的較少位數的 CRC 可能會與使用較多資料位但是設計很差的 CRC 的效率相媲美。在這種情況下 CRC32 幾乎同 CRC40 一樣優秀。 設計 CRC 多項式 生成多項式的選擇是 CRC 演算法實現中最重要的部分，所選擇的多項式必須有最大的錯誤檢測能力，同時保證總體的碰撞機率最小。多項式最重要的屬性是它的長度，也就是最高非零系數的數值，因為它直接影響著計算的校驗和的長度。 最常用的多項式長度有 9 位（CRC8） 17 位（CRC16） 33 位（CRC32） 65 位（CRC64） 在構建一個新的 CRC 多項式或者改進現有的 CRC 時，一個通用的數學原則是使用滿足所有模運算不可分解多項式約束條件的多項式。 這種情況下的不可分解是指多項式除了 1 與它自身之外不能被任何其它的多項式整除。 生成多項式的特性可以從演算法的定義中推匯出來： 如果 CRC 有多於一個的非零系數，那麼 CRC 能夠檢查出輸入訊息中的所有單資料位錯誤。 CRC 可以用於檢測短於 2k 的輸入訊息中的所有雙位錯誤，其中 k 是多項式的最長的不可分解部分的長度。 如果多項式可以被 x1 整除，那麼不存在可以被它整除的有奇數個非零系數的多項式。因此，它可以用來檢測輸入訊息中的奇數個錯誤，就像奇偶校驗函式那樣。 參見 總的分類 糾錯碼 校驗和演算法列表 奇偶校驗位 特殊技術參考 Adler32 Fletchers checksum 參考文獻 外部連結 Tutorial and C implementation of CRC 所引用網址程式碼執行存在問題 Cyclic redundancy check a simple guide to what it means for your data CD and DVD discs httpwwwsoftwarepatchcomtipscyclicredundancyhtml The CRC Pitstop Williams R（199309）A Painless Guide to CRC Error Detection Algorithms Understanding Cyclic Redundancy Check Black R（199402）Fast CRC32 in SoftwareAlgorithm 4 is used in Linux and infozips zip and unzip Barr M（199911 199912 200001）checksums CRCs and their source code Embedded Systems Programming CRC32 Generating a checksum for a file C implementation by Brian Friesen Online Tool to compute common CRCs（8163264）from strings Online CRC calculator Online CRC Tool Generator of synthesizable CRC functions Online Char ASCII HEX Binary Base64 etc EncoderDecoder with MD2 MD4 MD5 SHA12 CRC etc hashing algorithms CRC16 to CRC64 collision research Reversing CRC Theory and Practice Category 校驗和演算法 Category 二進位制算術 Category 有限域