Go CRC Code Example (Online Runner)
Go CRC-8/16/32/64 examples with preset variants, hex/decimal output, and file checksums matching the CRC tools.
Online calculator: use the site CRC text tool.
Calculation method
Each CRC preset defines width, polynomial, init value, xor-out, and reflect-in/out flags. The helper computes the CRC bit-by-bit to match the tool output.
Implementation notes
- Package: no external dependencies; CRCs are implemented directly in Go.
- Implementation: outputs uppercase hex or decimal values to match the tool formatting.
- Notes: CRCs are not cryptographic; any byte change (including newlines) changes the result.
Text CRC example
go
package main
import (
"fmt"
)
type CRCVariant struct {
ID string
Width int
Poly uint64
Init uint64
XorOut uint64
RefIn bool
RefOut bool
}
var crc32ISO = CRCVariant{ID: "crc32-iso-hdlc", Width: 32, Poly: 0x04C11DB7, Init: 0xFFFFFFFF, XorOut: 0xFFFFFFFF, RefIn: true, RefOut: true}
func reflectBits(value uint64, width int) uint64 {
var out uint64
for i := 0; i < width; i++ {
if value&1 == 1 {
out |= 1 << uint(width-1-i)
}
value >>= 1
}
return out
}
func crcMask(width int) uint64 {
if width >= 64 {
return ^uint64(0)
}
return (uint64(1) << uint(width)) - 1
}
func computeCRC(data []byte, preset CRCVariant) uint64 {
width := preset.Width
mask := crcMask(width)
crc := preset.Init & mask
topBit := uint64(1) << uint(width-1)
for _, b := range data {
cur := uint64(b)
if preset.RefIn {
cur = reflectBits(cur, 8)
}
crc ^= cur << uint(width-8)
for i := 0; i < 8; i++ {
if crc&topBit != 0 {
crc = (crc << 1) ^ preset.Poly
} else {
crc <<= 1
}
crc &= mask
}
}
if preset.RefOut {
crc = reflectBits(crc, width)
}
crc ^= preset.XorOut
return crc & mask
}
func main() {
value := computeCRC([]byte("hello"), crc32ISO)
fmt.Printf("%08X\n", value)
}File CRC example
go
package main
import (
"fmt"
"os"
)
type CRCVariant struct {
Width int
Poly uint64
Init uint64
XorOut uint64
RefIn bool
RefOut bool
}
var crc64ECMA = CRCVariant{Width: 64, Poly: 0x42F0E1EBA9EA3693, Init: 0x0000000000000000, XorOut: 0x0000000000000000, RefIn: false, RefOut: false}
func reflectBits(value uint64, width int) uint64 {
var out uint64
for i := 0; i < width; i++ {
if value&1 == 1 {
out |= 1 << uint(width-1-i)
}
value >>= 1
}
return out
}
func crcMask(width int) uint64 {
if width >= 64 {
return ^uint64(0)
}
return (uint64(1) << uint(width)) - 1
}
func computeCRC(data []byte, preset CRCVariant) uint64 {
width := preset.Width
mask := crcMask(width)
crc := preset.Init & mask
topBit := uint64(1) << uint(width-1)
for _, b := range data {
cur := uint64(b)
if preset.RefIn {
cur = reflectBits(cur, 8)
}
crc ^= cur << uint(width-8)
for i := 0; i < 8; i++ {
if crc&topBit != 0 {
crc = (crc << 1) ^ preset.Poly
} else {
crc <<= 1
}
crc &= mask
}
}
if preset.RefOut {
crc = reflectBits(crc, width)
}
crc ^= preset.XorOut
return crc & mask
}
func main() {
file, err := os.CreateTemp("", "crc-example-*.bin")
if err != nil {
panic(err)
}
defer os.Remove(file.Name())
file.WriteString("hello")
file.Close()
data, err := os.ReadFile(file.Name())
if err != nil {
panic(err)
}
fmt.Printf("%016X\n", computeCRC(data, crc64ECMA))
}Complete script (implementation + tests)
go
package main
import (
"fmt"
"os"
"strconv"
)
type CRCVariant struct {
ID string
Label string
Width int
Poly uint64
Init uint64
XorOut uint64
RefIn bool
RefOut bool
}
var CRCVariants = []CRCVariant{
{ID: "crc8-autosar", Label: "CRC-8/AUTOSAR", Width: 8, Poly: 0x2F, Init: 0xFF, XorOut: 0xFF, RefIn: false, RefOut: false},
{ID: "crc8-bluetooth", Label: "CRC-8/BLUETOOTH", Width: 8, Poly: 0xA7, Init: 0x00, XorOut: 0x00, RefIn: true, RefOut: true},
{ID: "crc8-cdma2000", Label: "CRC-8/CDMA2000", Width: 8, Poly: 0x9B, Init: 0xFF, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-darc", Label: "CRC-8/DARC", Width: 8, Poly: 0x39, Init: 0x00, XorOut: 0x00, RefIn: true, RefOut: true},
{ID: "crc8-dvb-s2", Label: "CRC-8/DVB-S2", Width: 8, Poly: 0xD5, Init: 0x00, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-gsm-a", Label: "CRC-8/GSM-A", Width: 8, Poly: 0x1D, Init: 0x00, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-gsm-b", Label: "CRC-8/GSM-B", Width: 8, Poly: 0x49, Init: 0x00, XorOut: 0xFF, RefIn: false, RefOut: false},
{ID: "crc8-hitag", Label: "CRC-8/HITAG", Width: 8, Poly: 0x1D, Init: 0xFF, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-i-432-1", Label: "CRC-8/I-432-1", Width: 8, Poly: 0x07, Init: 0x00, XorOut: 0x55, RefIn: false, RefOut: false},
{ID: "crc8-i-code", Label: "CRC-8/I-CODE", Width: 8, Poly: 0x1D, Init: 0xFD, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-lte", Label: "CRC-8/LTE", Width: 8, Poly: 0x9B, Init: 0x00, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-maxim-dow", Label: "CRC-8/MAXIM-DOW", Width: 8, Poly: 0x31, Init: 0x00, XorOut: 0x00, RefIn: true, RefOut: true},
{ID: "crc8-mifare-mad", Label: "CRC-8/MIFARE-MAD", Width: 8, Poly: 0x1D, Init: 0xC7, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-nrsc-5", Label: "CRC-8/NRSC-5", Width: 8, Poly: 0x31, Init: 0xFF, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-opensafety", Label: "CRC-8/OPENSAFETY", Width: 8, Poly: 0x2F, Init: 0x00, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-rohc", Label: "CRC-8/ROHC", Width: 8, Poly: 0x07, Init: 0xFF, XorOut: 0x00, RefIn: true, RefOut: true},
{ID: "crc8-sae-j1850", Label: "CRC-8/SAE-J1850", Width: 8, Poly: 0x1D, Init: 0xFF, XorOut: 0xFF, RefIn: false, RefOut: false},
{ID: "crc8-smbus", Label: "CRC-8/SMBUS", Width: 8, Poly: 0x07, Init: 0x00, XorOut: 0x00, RefIn: false, RefOut: false},
{ID: "crc8-tech-3250", Label: "CRC-8/TECH-3250", Width: 8, Poly: 0x1D, Init: 0xFF, XorOut: 0x00, RefIn: true, RefOut: true},
{ID: "crc8-wcdma", Label: "CRC-8/WCDMA", Width: 8, Poly: 0x9B, Init: 0x00, XorOut: 0x00, RefIn: true, RefOut: true},
{ID: "crc16-arc", Label: "CRC-16/ARC", Width: 16, Poly: 0x8005, Init: 0x0000, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-cdma2000", Label: "CRC-16/CDMA2000", Width: 16, Poly: 0xC867, Init: 0xFFFF, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-cms", Label: "CRC-16/CMS", Width: 16, Poly: 0x8005, Init: 0xFFFF, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-dds-110", Label: "CRC-16/DDS-110", Width: 16, Poly: 0x8005, Init: 0x800D, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-dect-r", Label: "CRC-16/DECT-R", Width: 16, Poly: 0x0589, Init: 0x0000, XorOut: 0x0001, RefIn: false, RefOut: false},
{ID: "crc16-dect-x", Label: "CRC-16/DECT-X", Width: 16, Poly: 0x0589, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-dnp", Label: "CRC-16/DNP", Width: 16, Poly: 0x3D65, Init: 0x0000, XorOut: 0xFFFF, RefIn: true, RefOut: true},
{ID: "crc16-en-13757", Label: "CRC-16/EN-13757", Width: 16, Poly: 0x3D65, Init: 0x0000, XorOut: 0xFFFF, RefIn: false, RefOut: false},
{ID: "crc16-genibus", Label: "CRC-16/GENIBUS", Width: 16, Poly: 0x1021, Init: 0xFFFF, XorOut: 0xFFFF, RefIn: false, RefOut: false},
{ID: "crc16-gsm", Label: "CRC-16/GSM", Width: 16, Poly: 0x1021, Init: 0x0000, XorOut: 0xFFFF, RefIn: false, RefOut: false},
{ID: "crc16-ibm-3740", Label: "CRC-16/IBM-3740", Width: 16, Poly: 0x1021, Init: 0xFFFF, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-ibm-sdlc", Label: "CRC-16/IBM-SDLC", Width: 16, Poly: 0x1021, Init: 0xFFFF, XorOut: 0xFFFF, RefIn: true, RefOut: true},
{ID: "crc16-iso-iec-14443-3-a", Label: "CRC-16/ISO-IEC-14443-3-A", Width: 16, Poly: 0x1021, Init: 0xC6C6, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-kermit", Label: "CRC-16/KERMIT", Width: 16, Poly: 0x1021, Init: 0x0000, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-lj1200", Label: "CRC-16/LJ1200", Width: 16, Poly: 0x6F63, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-m17", Label: "CRC-16/M17", Width: 16, Poly: 0x5935, Init: 0xFFFF, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-maxim-dow", Label: "CRC-16/MAXIM-DOW", Width: 16, Poly: 0x8005, Init: 0x0000, XorOut: 0xFFFF, RefIn: true, RefOut: true},
{ID: "crc16-mcrf4xx", Label: "CRC-16/MCRF4XX", Width: 16, Poly: 0x1021, Init: 0xFFFF, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-modbus", Label: "CRC-16/MODBUS", Width: 16, Poly: 0x8005, Init: 0xFFFF, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-nrsc-5", Label: "CRC-16/NRSC-5", Width: 16, Poly: 0x080B, Init: 0xFFFF, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-opensafety-a", Label: "CRC-16/OPENSAFETY-A", Width: 16, Poly: 0x5935, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-opensafety-b", Label: "CRC-16/OPENSAFETY-B", Width: 16, Poly: 0x755B, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-profibus", Label: "CRC-16/PROFIBUS", Width: 16, Poly: 0x1DCF, Init: 0xFFFF, XorOut: 0xFFFF, RefIn: false, RefOut: false},
{ID: "crc16-riello", Label: "CRC-16/RIELLO", Width: 16, Poly: 0x1021, Init: 0xB2AA, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-spi-fujitsu", Label: "CRC-16/SPI-FUJITSU", Width: 16, Poly: 0x1021, Init: 0x1D0F, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-t10-dif", Label: "CRC-16/T10-DIF", Width: 16, Poly: 0x8BB7, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-teledisk", Label: "CRC-16/TELEDISK", Width: 16, Poly: 0xA097, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-tms37157", Label: "CRC-16/TMS37157", Width: 16, Poly: 0x1021, Init: 0x89EC, XorOut: 0x0000, RefIn: true, RefOut: true},
{ID: "crc16-umts", Label: "CRC-16/UMTS", Width: 16, Poly: 0x8005, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc16-usb", Label: "CRC-16/USB", Width: 16, Poly: 0x8005, Init: 0xFFFF, XorOut: 0xFFFF, RefIn: true, RefOut: true},
{ID: "crc16-xmodem", Label: "CRC-16/XMODEM", Width: 16, Poly: 0x1021, Init: 0x0000, XorOut: 0x0000, RefIn: false, RefOut: false},
{ID: "crc32-aixm", Label: "CRC-32/AIXM", Width: 32, Poly: 0x814141AB, Init: 0x00000000, XorOut: 0x00000000, RefIn: false, RefOut: false},
{ID: "crc32-autosar", Label: "CRC-32/AUTOSAR", Width: 32, Poly: 0xF4ACFB13, Init: 0xFFFFFFFF, XorOut: 0xFFFFFFFF, RefIn: true, RefOut: true},
{ID: "crc32-base91-d", Label: "CRC-32/BASE91-D", Width: 32, Poly: 0xA833982B, Init: 0xFFFFFFFF, XorOut: 0xFFFFFFFF, RefIn: true, RefOut: true},
{ID: "crc32-bzip2", Label: "CRC-32/BZIP2", Width: 32, Poly: 0x04C11DB7, Init: 0xFFFFFFFF, XorOut: 0xFFFFFFFF, RefIn: false, RefOut: false},
{ID: "crc32-cd-rom-edc", Label: "CRC-32/CD-ROM-EDC", Width: 32, Poly: 0x8001801B, Init: 0x00000000, XorOut: 0x00000000, RefIn: true, RefOut: true},
{ID: "crc32-cksum", Label: "CRC-32/CKSUM", Width: 32, Poly: 0x04C11DB7, Init: 0x00000000, XorOut: 0xFFFFFFFF, RefIn: false, RefOut: false},
{ID: "crc32-iscsi", Label: "CRC-32/ISCSI (Castagnoli)", Width: 32, Poly: 0x1EDC6F41, Init: 0xFFFFFFFF, XorOut: 0xFFFFFFFF, RefIn: true, RefOut: true},
{ID: "crc32-iso-hdlc", Label: "CRC-32/ISO-HDLC", Width: 32, Poly: 0x04C11DB7, Init: 0xFFFFFFFF, XorOut: 0xFFFFFFFF, RefIn: true, RefOut: true},
{ID: "crc32-jamcrc", Label: "CRC-32/JAMCRC", Width: 32, Poly: 0x04C11DB7, Init: 0xFFFFFFFF, XorOut: 0x00000000, RefIn: true, RefOut: true},
{ID: "crc32-mef", Label: "CRC-32/MEF", Width: 32, Poly: 0x741B8CD7, Init: 0xFFFFFFFF, XorOut: 0x00000000, RefIn: true, RefOut: true},
{ID: "crc32-mpeg-2", Label: "CRC-32/MPEG-2", Width: 32, Poly: 0x04C11DB7, Init: 0xFFFFFFFF, XorOut: 0x00000000, RefIn: false, RefOut: false},
{ID: "crc32-xfer", Label: "CRC-32/XFER", Width: 32, Poly: 0x000000AF, Init: 0x00000000, XorOut: 0x00000000, RefIn: false, RefOut: false},
{ID: "crc64-ecma", Label: "CRC-64/ECMA-182", Width: 64, Poly: 0x42F0E1EBA9EA3693, Init: 0x0000000000000000, XorOut: 0x0000000000000000, RefIn: false, RefOut: false},
{ID: "crc64-iso", Label: "CRC-64/ISO", Width: 64, Poly: 0x000000000000001B, Init: 0xFFFFFFFFFFFFFFFF, XorOut: 0xFFFFFFFFFFFFFFFF, RefIn: true, RefOut: true},
}
func reflectBits(value uint64, width int) uint64 {
var out uint64
for i := 0; i < width; i++ {
if value&1 == 1 {
out |= 1 << uint(width-1-i)
}
value >>= 1
}
return out
}
func crcMask(width int) uint64 {
if width >= 64 {
return ^uint64(0)
}
return (uint64(1) << uint(width)) - 1
}
func computeCRC(data []byte, preset CRCVariant) uint64 {
width := preset.Width
mask := crcMask(width)
crc := preset.Init & mask
topBit := uint64(1) << uint(width-1)
for _, b := range data {
cur := uint64(b)
if preset.RefIn {
cur = reflectBits(cur, 8)
}
crc ^= cur << uint(width-8)
for i := 0; i < 8; i++ {
if crc&topBit != 0 {
crc = (crc << 1) ^ preset.Poly
} else {
crc <<= 1
}
crc &= mask
}
}
if preset.RefOut {
crc = reflectBits(crc, width)
}
crc ^= preset.XorOut
crc &= mask
return crc
}
func formatCRC(value uint64, width int, output string) string {
if output == "decimal" {
return strconv.FormatUint(value, 10)
}
digits := (width + 3) / 4
return fmt.Sprintf("%0*X", digits, value)
}
func crcByID(data []byte, presetID string, output string) (string, error) {
for _, preset := range CRCVariants {
if preset.ID == presetID {
value := computeCRC(data, preset)
return formatCRC(value, preset.Width, output), nil
}
}
return "", fmt.Errorf("unknown preset: %s", presetID)
}
func main() {
// Example: compute CRC-32/ISO-HDLC over text
value, err := crcByID([]byte("hello"), "crc32-iso-hdlc", "hex")
if err != nil {
panic(err)
}
fmt.Println("crc32-iso-hdlc(hello)=", value)
// Example: compute CRC for a file
file, err := os.CreateTemp("", "crc-example-*.bin")
if err != nil {
panic(err)
}
defer os.Remove(file.Name())
file.WriteString("hello")
file.Close()
data, err := os.ReadFile(file.Name())
if err != nil {
panic(err)
}
fileCRC, err := crcByID(data, "crc64-ecma", "hex")
if err != nil {
panic(err)
}
fmt.Println("crc64-ecma(file)=", fileCRC)
}