| Andrew Cooke | Contents | Latest | RSS | Twitter | Previous | Next


Welcome to my blog, which was once a mailing list of the same name and is still generated by mail. Please reply via the "comment" links.

Always interested in offers/projects/new ideas. Eclectic experience in fields like: numerical computing; Python web; Java enterprise; functional languages; GPGPU; SQL databases; etc. Based in Santiago, Chile; telecommute worldwide. CV; email.

Personal Projects

Lepl parser for Python.

Colorless Green.

Photography around Santiago.

SVG experiment.

Professional Portfolio

Calibration of seismometers.

Data access via web services.

Cache rewrite.

Extending OpenSSH.

C-ORM: docs, API.

Last 100 entries

Spray Painting Bike Frame; Weeks 10 + 11; Change: No Longer Possible To Merge Metadata; Books on Old Age; Health Tree Maps; MRA - Men's Rights Activists; Writing Good C++14; Risk Assessment - Fukushima; The Future of Advertising and Surveillance; Travelling With Betaferon; I think I know what I dislike so much about Metafilter; Weeks 8 + 9; More; Pastamore - Bad Italian in Vitacura; History Books; Iraq + The (UK) Governing Elite; Answering Some Hard Questions; Pinochet: The Dictator's Shadow; An Outsider's Guide To Julia Packages; Nobody gives a shit; Lepton Decay Irregularity; An Easier Way; Julia's BinDeps (aka How To Install Cairo); Good Example Of Good Police Work (And Anonymity Being Hard); Best Santiago Burgers; Also; Michael Emmerich (Vibrator Translator) Interview (Japanese Books); Clarice Lispector (Brazillian Writer); Books On Evolution; Looks like Ara (Modular Phone) is dead; Index - Translations From Chile; More Emotion in Chilean Wines; Week 7; Aeon Magazine (Science-ish); QM, Deutsch, Constructor Theory; Interesting Talk Transcripts; Interesting Suggestion Of Election Fraud; "Hard" Books; Articles or Papers on depolarizing the US; Textbook for "QM as complex probabilities"; SFO Get Libor Trader (14 years); Why Are There Still So Many Jobs?; Navier Stokes Incomplete; More on Benford; FBI Claimed Vandalism; Architectural Tessellation; Also: Go, Blake's 7; Delusions of Gender (book); Crypto AG DID work with NSA / GCHQ; UNUMS (Universal Number Format); MOOCs (Massive Open Online Courses); Interesting Looking Game; Euler's Theorem for Polynomials; Weeks 3-6; Reddit Comment; Differential Cryptanalysis For Dummies; Japanese Graphic Design; Books To Be Re-Read; And Today I Learned Bugs Need Clear Examples; Factoring a 67 bit prime in your head; Islamic Geometric Art; Useful Julia Backtraces from Tasks; Nothing, however, is lost with less discomfort than that which, when lost, cannot be missed; Article on Didion; Cost of Living by City; British Slavery; Derrida on Metaphor; African SciFi; Traits in Julia; Alternative Japanese Lit; Pulic Key as Address (Snow); Why Information Grows; The Blindness Of The Chilean Elite; Some Victoriagate Links; This Is Why I Left StackOverflow; New TLS Implementation; Maths for Physicists; How I Am 8; 1000 Word Philosophy; Cyberpunk Reading List; Detailed Discussion of Message Dispatch in ParserCombinator Library for Julia; FizzBuzz in Julia w Dependent Types; kokko - Design Shop in Osaka; Summary of Greece, Currently; LLVM and GPUs; See Also; Schoolgirl Groyps (Maths); Japanese Lit; Another Example - Modular Arithmetic; Music from United; Python 2 and 3 compatible alternative.; Read Agatha Christie for the Plot; A Constructive Look at TempleOS; Music Thread w Many Recommendations; Fixed Version; A Useful Julia Macro To Define Equality And Hash; k3b cdrom access, OpenSuse 13.1; Week 2; From outside, the UK looks less than stellar; Huge Fonts in VirtualBox; Keen - Complex Emergencies

© 2006-2015 Andrew Cooke (site) / post authors (content).

16bit CRC Algorithms

From: andrew cooke <andrew@...>

Date: Wed, 31 Jul 2013 16:24:58 -0400

If you need to implement a 16bit CRC algorithm, this is an excellent


If you have some data and are trying to work out what CRC was used, this
excellent tool is a huge help:


The only missing puzzle is that no-one explains the difference between
CRC-CCITT (0xffff) and XModem.  It turns out that XModem has an initial
remainder of zero.  So you could say that XModem is CRC-CCITT (0x0000).

That is the ONLY difference.  I have working code with test vectors.  God
knows what crack some people were smoking when they wrote that they are
different beasts...

What a painful, wasted afternoon.

CRC16 Code

From: andrew cooke <andrew@...>

Date: Sat, 3 Aug 2013 15:13:39 -0400

Here's the C code.  As I noted above it's basically from
http://www.barrgroup.com/Embedded-Systems/How-To/CRC-Calculation-C-Code but it
includes explicit values, validated via

uint16_t straight_16(uint16_t value) {
    return value;

uint16_t reverse_16(uint16_t value) {
    uint16_t reversed = 0;
    for (int i = 0; i < 16; ++i) {
        reversed <<= 1;
        reversed |= value & 0x1;
        value >>= 1;
    return reversed;

uint8_t straight_8(uint8_t value) {
    return value;

uint8_t reverse_8(uint8_t value) {
    uint8_t reversed = 0;
    for (int i = 0; i < 8; ++i) {
        reversed <<= 1;
        reversed |= value & 0x1;
        value >>= 1;
    return reversed;

uint16_t crc16(uint8_t const *message, int nBytes,
        bit_order_8 data_order, bit_order_16 remainder_order,
        uint16_t remainder, uint16_t polynomial) {
    for (int byte = 0; byte < nBytes; ++byte) {
        remainder ^= (data_order(message[byte]) << 8);
        for (uint8_t bit = 8; bit > 0; --bit) {
            if (remainder & 0x8000) {
                remainder = (remainder << 1) ^ polynomial;
            } else {
                remainder = (remainder << 1);
    return remainder_order(remainder);

uint16_t crc16ccitt(uint8_t const *message, int nBytes) {
    return crc16(message, nBytes, straight_8, straight_16, 0xffff, 0x1021);

uint16_t crc16ccitt_xmodem(uint8_t const *message, int nBytes) {
    return crc16(message, nBytes, straight_8, straight_16, 0x0000, 0x1021);

uint16_t crc16ccitt_kermit(uint8_t const *message, int nBytes) {
    uint16_t swap = crc16(message, nBytes, reverse_8, reverse_16, 0x0000, 0x1021);
    return swap << 8 | swap >> 8;

uint16_t crc16ccitt_1d0f(uint8_t const *message, int nBytes) {
    return crc16(message, nBytes, straight_8, straight_16, 0x1d0f, 0x1021);

uint16_t crc16ibm(uint8_t const *message, int nBytes) {
    return crc16(message, nBytes, reverse_8, reverse_16, 0x0000, 0x8005);

I've modified the code slightly to remove various private things and simplify
slightly, so it's just possible I broke something - please check before
using.  Also, remmeber that this is not as efficient as using a lookup-table
per byte (but you can generate the table from the info above).


Missed a bit

From: andrew cooke <andrew@...>

Date: Sat, 3 Aug 2013 15:37:20 -0400

You also need this...

typedef uint16_t bit_order_16(uint16_t value);
typedef uint8_t bit_order_8(uint8_t value);

(which was hiding in a header file).


thanks for CRC16-CCITT XMODEM

From: "Sanchez, Denis" <Denis.Sanchez@...>

Date: Thu, 5 Dec 2013 15:39:36 +0000


Just a little mail to say thank you for your post on your blog.
I finally find the way to calculate this CRC and convert into excel macro.
I was hard to find algo for XMODEM.


Update on CRCs

From: andrew cooke <andrew@...>

Date: Sat, 5 Apr 2014 10:43:20 -0300

The last month or so I've learned a lot more about CRCs (as part of a longer
term project to understand finite fields).

Here are two references for CRCs that are better / more authoritative than
anything I could produce:


The first link above clarifies why there are two implementations for
algorithms that reverse the input bytes: one is slow but obviously correct
(just reverse each byte); the other is faster but looks very odd at first
glance (reverse the rest of the world).

According to the second link above, what I have called crc16ccitt is actually
CCITT-FALSE ("An algorithm commonly misidentified as CRC-CCITT").  See
http://reveng.sourceforge.net/crc-catalogue/16.htm for full details.

Finally, I have implemented fast versions (with tables and, where appropriate,
"reverse the world" implementations) for ALL the algorithms described in the
catalogue.  The code is written in Julia and is available at 

I hope to extend that code at some point so that it can be used as a
command-line tool for calculating CRCs (so you don't need to use julia).  But
even if you don't know julia it should be fairly easy to use in its current
state (email me at andrew@... if this is important to you and I can
give instructions).


Comment on this post