Skip to content

Speed up reads from binary buffers - #10

Merged
jallum merged 3 commits into
mainfrom
perf/binary-cursor-fast-path
Aug 31, 2026
Merged

Speed up reads from binary buffers#10
jallum merged 3 commits into
mainfrom
perf/binary-cursor-fast-path

Conversation

@jallum

@jallum jallum commented Aug 31, 2026

Copy link
Copy Markdown
Owner

Why

Reading one number currently asks the generic iodata helper to copy out a tiny slice. Most callers pass a binary, so that general-purpose work is paid for every scalar, offset, and vtable entry.

What changed

  • Read scalars directly from binary buffers with binary pattern matching.
  • Read strings/byte ranges from binaries with binary_part/3.
  • Keep the existing iodata path as the fallback, so supported inputs do not change.
  • Add Benchee scripts for the cursor alternatives and public encode/read/get operations.

How it works (ELI5)

The old path took every tiny value to a helper that can unpack any nested list shape. The fast path first notices that the buffer is already one flat binary and picks the bytes straight out. Nested iodata still goes to the original helper.

Benchee results

Apple M4 Pro, Elixir 1.19.4, Erlang/OTP 28.

Scenario Before After Change Memory before Memory after
Full decode 67.34 K ops/s 143.81 K ops/s 2.14x faster 44.72 KB 36.61 KB
Nested get 1,792.21 K ops/s 3,392.71 K ops/s 1.89x faster 1.38 KB 1.13 KB
Encode control 73.87 K ops/s 75.74 K ops/s no material change 68.80 KB 68.80 KB

The isolated u32 cursor benchmark measured direct binary matching at 29.38 M ops/s versus 13.61 M ops/s for the current iodata slice (2.16x), with 40 B versus 64 B and 1 versus 11 reductions.

Run with:

mix run bench/cursor_read.exs
mix run bench/runtime.exs

Verification

  • mix format --check-formatted
  • MIX_ENV=test mix test (111 tests, 0 failures)

@jallum
jallum merged commit b7c5900 into main Aug 31, 2026
4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant