CRC16

Bryan Olson fakeaddress at nowhere.org
Fri Sep 23 17:35:18 EDT 2005


Tuvas wrote:
> Anyone know a module that does CRC16 for Python? I have an aplication
> that I need to run it, and am not having alot of sucess. I have a
> program in C that uses a CRC16 according to CCITT standards, but need
> to get a program that tests it with python as well. Thanks!

I'll include one below. There's a tricky bit in that most standards
assume a serial bit stream, not byte data, leading to the relection
issue discussed in the reference in the doc. Let me know if gets
the same answers as your C version.

--
--Bryan

===============================================================
#!/usr/bin/env python

# crc16.py by Bryan G. Olson, 2005
# This module is free software and may be used and
# distributed under the same terms as Python itself.

"""
     CRC-16 in Python, as standard as possible. This is
     the 'reflected' version, which is usually what people
     want. See Ross N. Williams' /A Painless Guide to
     CRC error detection algorithms/.
"""

from array import array


def crc16(string, value=0):
     """ Single-function interface, like gzip module's crc32
     """
     for ch in string:
         value = table[ord(ch) ^ (value & 0xff)] ^ (value >> 8)
     return value


class CRC16(object):
     """ Class interface, like the Python library's cryptographic
         hash functions (which CRC's are definitely not.)
     """

     def __init__(self, string=''):
         self.val = 0
         if string:
             self.update(string)

     def update(self, string):
         self.val = crc16(string, self.val)

     def checksum(self):
         return chr(self.val >> 8) + chr(self.val & 0xff)

     def hexchecksum(self):
         return '%04x' % self.val

     def copy(self):
         clone = CRC16()
         clone.val = self.val
         return clone


# CRC-16 poly: p(x) = x**16 + x**15 + x**2 + 1
# top bit implicit, reflected
poly = 0xa001
table = array('H')
for byte in range(256):
     crc = 0
     for bit in range(8):
         if (byte ^ crc) & 1:
             crc = (crc >> 1) ^ poly
         else:
             crc >>= 1
         byte >>= 1
     table.append(crc)

crc = CRC16()
crc.update("123456789")
assert crc.checksum() == '\xbb\x3d'




More information about the Python-list mailing list