calamity-inc/u64-dyn

Variable-length 64-bit integer codings that take at most 9 bytes.

Installs: 1

Dependents: 0

Suggesters: 0

Security: 0

Stars: 0

Watchers: 1

Forks: 1

Language:C

pkg:composer/calamity-inc/u64-dyn

dev-senpai 2025-10-30 11:02 UTC

This package is not auto-updated.

Last update: 2025-11-18 03:02:28 UTC


README

Variable-length 64-bit integer codings that take at most 9 bytes.

Guide

  • Biased variants (indicated with a b) need less bytes to encode certain sequences.
  • Prefixed variants (indicated with a p) are a lot faster to read due to the first byte indicating the sequence length.
  • For signed codings, there is also a to indicate arithmetic negation as opposed to bitwise negation.

Implementations

Specifications

u64_dyn

The first 56 bits of the integer are encoded in up to eight little-endian 7-bit groups where the most significant bit indicates if another byte follows. The final 8 bits are encoded as-is.

Value Encoded As
0x7f 7f
0x80 80 01
0x4000 80 80 01
0xffffffffffffffff ff ff ff ff ff ff ff ff ff

u64_dyn_b

Same as u64_dyn but for each continuation bit (i.e., "another byte follows"), 1 is subtracted from the remaining value after shifting. Decoding compensates by adding a bias.

Value Encoded As
0x7f 7f
0x80 80 00
0x4000 80 7f
0xffffffffffffffff ff fe fe fe fe fe fe fe fe

Contrived sequences which would exceed 2^64 (e.g. ff ff fe fe fe fe fe fe fe) are illegal. Decoders can detect them (by checking v > UINT64_MAX - bias before adding the bias) and should return an error appropriately.

u64_dyn_p

Same as u64_dyn but the continuation bits are all moved to the first byte:

0xxxxxxx
10xxxxxx xxxxxxxx
110xxxxx xxxxxxxx xxxxxxxx
1110xxxx xxxxxxxx xxxxxxxx xxxxxxxx
11110xxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx
111110xx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx
1111110x xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx
11111110 xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx
11111111 xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx xxxxxxxx

Prefixing does not change the length of coded values.

Value Encoded As
0x7f 7f
0x80 80 02
0x4000 C0 80 02
0xffffffffffffffff ff ff ff ff ff ff ff ff ff

u64_dyn_bp

This coding uses the biasing of u64_dyn_b and the prefixing of u64_dyn_p.

Value Encoded As
0x7f 7f
0x80 80 00
0x4000 80 fe
0xffffffffffffffff ff 7f bf df ef f7 fb fd fe

i64_dyn_a

The i64 value is split into (neg, u63) like so:

neg := i64 < 0
if neg:
    u63 := (~i64 + 1) & ~(1 << 63)
else:
    u63 := i64

This is rejoined into a u64 with neg in bit 6:

u64 := (neg << 6) | ((u63 & ~0x3f) << 1) | (u63 & 0x3f)

This value is then encoded using u64_dyn. When decoding, if neg is set the original value is recovered with:

i64 := ~(u63 - 1) | (1 << 63)
Value Encoded As
42 2a
0x2000 80 80 01
-1 41
-9223372036854775808 40

i64_dyn_b

The i64 value is split into (neg, u63) like so:

neg := i64 < 0
if neg:
    u63 := ~i64
else:
    u63 := i64

This is rejoined into a u64 with neg in bit 6:

u64 := (neg << 6) | ((u63 & ~0x3f) << 1) | (u63 & 0x3f)

This value is then encoded using u64_dyn_b. Decoding is the same in reverse.

Value Encoded As
42 2a
0x2000 80 7f
-1 40
-9223372036854775808 ff fe fe fe fe fe fe fe fe

i64_dyn_bp

The i64 value is converted to u64 just like in i64_dyn_b. However, in this case the u64 is coded with u64_dyn_bp.

Value Encoded As
42 2a
0x2000 80 fe
-1 40
-9223372036854775808 ff 7f bf df ef f7 fb fd fe