Bitwise Operations
Ferlium provides bitwise operations through the Bits trait. They are useful for low-level encoding, flag sets, and packed representations. The standard library implements Bits for int and bool, so the same function names work on both.
Logical operations
bit_and, bit_or, bit_xor, and bit_not perform the usual boolean operations bit by bit:
bit_and(0b1101, 0b1011)
bit_or(0b1100, 0b0011)
bit_xor(0b1010, 0b1100)
bit_not(0)
bit_not(0) evaluates to -1 because int is a signed two’s-complement integer.
On bool, these collapse to the matching logical operators:
(bit_and(true, false), bit_or(true, false), bit_xor(true, true), bit_not(true))
Shifts and rotations
shift_left and shift_right move bits by a given amount, filling with zeros (shift right on a negative int preserves the sign):
shift_left(1, 4)
shift_right(0b10100, 2)
rotate_left and rotate_right move bits without losing them: bits that fall off one end re-enter at the other.
rotate_left(1, 3)
The shift and rotation amount is always an int.
Counting bits
count_ones and count_zeros return the number of set and unset bits:
count_ones(0b10110)
count_ones(true)
For int, count_zeros uses the full machine width (typically 64 bits), so count_zeros(0) returns the integer width. For bool, the width is 1.
Single-bit helpers
bit(position) constructs a value with only the bit at position set. Because the result type cannot be inferred from arguments alone, you usually need a type annotation:
(bit(3): int)
set_bit, clear_bit, and test_bit operate on a single bit of an existing value:
set_bit(0b1000, 1)
clear_bit(0b1111, 2)
test_bit(0b1010, 1)
These compose naturally:
let flags = set_bit(set_bit(0, 0), 3);
(test_bit(flags, 0), test_bit(flags, 1), test_bit(flags, 3))
Notes on bool
Because bool holds a single bit, some operations behave specially:
shift_leftandshift_rightalways returnfalse, since the bit is shifted out.rotate_leftandrotate_rightare the identity, since there is nowhere for the bit to move.bit(0)istrue;bit(n)for any othernisfalse.set_bit,clear_bit, andtest_bitonly affect position0; other positions leave the value unchanged or returnfalse.
This lets generic code over Bits work uniformly on both types without special casing.
What comes next
The next chapter shows how Ferlium values can be converted to JSON and plain text, through (de)serialization.