I don’t know why but Erlang bit syntax always confused me. I always skipped it while reading the docs, until, well, now that I need it. I should say this is not meant to be an exhaustive how-to by any means. It’s just a collection of notes, but howto sounded better. ðŸ™‚ There are better guides out there. [Reference docs too.]

Anyway. Here’s some binary data in Erlang:

<<16#1192c05a:32>>

What does all this mean? Let’s analyze it, left to right.

This specifies we want to express the number in base 16.`16#`

- We have an eight digits hex number.
- No type specification is provided: default is unsigned integer.
- No unit specification is provided: default for integer is 1, which means ‘bits’.
Size specification: this tells erlang to consider 32 units, which in our case means 32 bits, since we are dealing with bits.`:32`

Let’s evaluate it:

86> <<16#2092105a:32>>. <<32,146,16,90>>

What if we forget to specify the size spec? In that case the default will apply and since we’re dealing with an integer type, the default is 8 (bits). For Erlang this means we are going to return the least significant byte:

87> <<16#2092105a>>. <<90>>

Now that we know that, we can get a subset of bits by setting the size accordingly:

88> <<16#2092105a:16>>. <<16,90>> %two least significant bytes

We don’t need to specify a size multiple of 8:

89> <<16#1192FFFF:15>>. <<255,127:7>>

It’s pretty cool how easy it is to slice bytes apart at the bit level. I was sort of surprised that if we slice some internal bits it looks like the bits at the right are moved to the left. E.g. here we take the 4 least significant bits of the first 0xFF:

90> <<16#FF:4,0,16#FF,0>>.

but instead of obtaining:

<<16:4,0,255,0>> F 00 FF 00

we get:

<<240,15,240,0:4>> F0 0F F0 0 [240 == F0]

Also, the value doesn’t need to be a literal, it can be an expression:

91> N = 16#FF00FF01. 4278255361 92> <<N:32>>. <<255,0,255,1>>

And therefore, given some binary data, we can also pattern-match it super easily:

<SourcePort:16, DestinationPort:16, CheckSum:16, Payload/binary>> = SomeBinary.

There’s more to Erlang bit syntax than this, but I’ll stop here for now.