Wire quantizers
The places an f64 becomes the decimal string a venue is sent or an order is signed over — the roster, the source gate that holds them exact, and the cliff they amplify.
A wire quantizer is any place in this workspace where an f64 crosses into rust_decimal and comes
back out as the string that is sent to a venue or signed into an order hash.
crates/vike-bridge-core/tests/wire_quantizer_probe.rs is both the measurement probe and the
committed gate over that family. It exists because a survey of the non-f64 numeric surface reported
nothing to fix — and reached that verdict by reading source, which is exactly what this program
exists to distrust.
The roster is a constant, not a sentence
vike-bridge-core's own format.rs header used to end "rust_decimal exists only here and at OKX",
and that had stopped being true. There are three files, not two, and the third —
crates/bridges/hyperliquid/src/px.rs — is a whole module of quantizers whose own doc had called
itself the twin of format_to_step since it was written. The correction was not to fix the sentence
but to delete it: the probe's WIRE_FILES constant is the list, its source gate walks exactly those
files, and the prose points at the constant.
What these functions amplify
The probe's own table names the cliff at each site, and it is the reason the family gets a gate rather than a comment:
| site | the decision | one ULP upstream becomes |
|---|---|---|
format_to_step and its float twin | (value / step).trunc() | a whole tick or lot |
format_scaled_to_step_f | the same truncation, after an exact rational rescale | a whole step |
okx's to_contracts | a truncation through contract size and step | a whole contract step |
hyperliquid's clamp_price | midpoint-away-from-zero | a whole tick, inside the signed action hash |
hyperliquid's round_size | toward zero | a whole lot |
polymarket's to_base_units | a round at an exact half | one micro-unit, inside the signed order |
Why this is not a last-bit problem
Two boxes disagreeing by one ULP produce two prices that differ in the sixteenth digit — invisible, and arguably harmless. Push those same two prices through a quantizer whose decision is a truncation or an exact-midpoint comparison and the two boxes emit different wire strings: a different limit price, a different size, and for the two signing venues a different signature over a different order.
The truncation cuts both ways, and the silent direction is the one the header adds. Quantizing down
stops an overshoot past a limit, which a venue rejects loudly; the opposite artifact is quiet, since a
value sitting one ULP below a grid point emits a whole step less. Whether the ordinary
round-then-format chain ever hit that was unmeasured until this probe measured it — the answer was
150 of 4096, a whole step dropped on a value already on the grid, with no perturbation applied at
all. That measurement produced the cure, and the row records 0/4096 today.
The source gate
the_wire_quantizers_reach_decimal_through_a_string is the half that runs on every ordinary test
pass, and it has three arms.
A required spelling. Every file in WIRE_FILES must contain Decimal::from_str. This is the
non-vacuity arm: a scan that opened the wrong path, or read an empty file, would report a confident
zero banned hits, so a positive hit is demanded to make that failure loud.
A banned set, in two families. Decimal::from_f64 and Decimal::from_f32 are the wrong door
into Decimal — they convert the binary value's full noise, where the string route converts the number
the caller meant, and at an exact decimal midpoint the two round opposite ways. The second family is
an enumerated set of platform-libm method spellings: a wire quantizer's job is exact arithmetic, and
a transcendental appearing in one would put a platform-dependent value inside the amplifier
rather than upstream of it. Square root is deliberately absent, because the standard requires it
correctly rounded.
A reached-file roster. round_size's grid witness calls into hyperliquid's instruments module for
its lot step, deliberately — the witness can only ask its question against the same f64 the grid was
built from. The cost is a powi on the path of a quantizer whose output is signed, in a file
WIRE_FILES does not scan. REACHED_FILES puts it under the libm half of the ban, because before
that roster the only thing standing between a signed order size and a runtime-base powf was prose.
The one exemption is a literal base ten with an exponent the witness itself bounds at 22, where every
power of ten is exactly representable — measured bit-identical across both platforms. The rule
generalizes: a literal 10 or 2 needs nothing, an arbitrary runtime base needs the libm crate.
The hash pin, and what it does not claim
The probe also hashes each quantizer's output over a fixed corpus. That corpus is pure arithmetic
— a linear congruential generator and the four operations, never a transcendental — because generating
inputs with platform-dependent functions would make every column diverge because of the inputs
rather than the subject, a false positive that reads exactly like a real one. A control row hashes the
generator's own output, so a table where every other row moved is a function regression, while one
where the control moved too is a broken corpus. Each row carries a distinctness floor, so a collapsed
corpus cannot pass as agreement, and unrecorded rows read "RECORD" — a placeholder that cannot match
a sixteen-character hex hash on length or on content, so an unfinished recording is never mistakable
for a measured value.
One site is covered by the source gate and not by the hash pin, for a stated reason: okx's
to_contracts is a method on a client, so calling it means standing up a signer and a transport
double. It is not unpinned either — crates/bridges/okx/tests/offline/r6_okx_parity.rs compares it
bit-for-bit against the frozen fixtures/r6 export, a stronger statement than a hash for the values
that fixture carries and a weaker one for every value it does not.
Polymarket's to_base_units is reached by neither half. It is private, its public caller sits
behind a crate feature this crate does not take, and WIRE_FILES names neither its file nor any file
reaching it — so the sharpest cliff in the table above is the one this probe cannot see, and the
header says outright that it deserves a probe in its own crate. Both gaps are declared rather than
left implied.
Related: the data model and the venues tree.
Test doubles
One owned double per seam, behind a `test-support` feature a default build never compiles — the scripted WS streams, the in-memory history store, the recording broker, and the sanitized capture writer.
Live smokes
The tier that touches a real account — never run by an ordinary `cargo test`, credential-gated wherever an account is involved, demo-only, dispatched by hand, and fronted by one shared credential refusal that a test actually runs.