Conversation
parse_f64 assumes a null terminator (it derives length via str_len), which is unsafe on a byte span embedded in a larger buffer -- the exact case a zero-copy parser faces. Factor the body into parse_f64_len(s, len), bounded by an explicit length, and have parse_f64 delegate with str_len(s). No behaviour change for existing callers.
Extend number parsing to the full RFC 8259 grammar (fraction + exponent). A number with a fraction or exponent yields a float value, parsed with correct rounding via parse_f64_len over the zero-copy source span; integer-looking numbers keep yielding an i64 exactly as before. Value gains is_float/float_val, with value_is_float and value_float accessors (value_float widens integers so it is defined for any NUMBER); emit writes floats in shortest round-trippable form. Closes #349.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Closes #349.
Problem
std.data.jsonparsed integer numbers only. Downstreammach-gltfneeds fullJSON numeric support (node transforms, accessor bounds, keyframes, material
factors are all floats), so the loader cannot progress past structural parsing
until floats land here.
Change
int frac? exp?). Anumber carrying a fraction or exponent becomes a float; an integer-looking
number keeps yielding an
i64, byte-for-byte the same path and error messagesas before.
std.text.parse's bignum decimal→f64 machinery over the zero-copy sourcespan — no allocation, no copy.
Valuegainsis_float+float_val. New accessors:value_is_float(v) bool— whether the number was parsed as a float.value_float(v) f64— the float value, or an integer widened tof64, so itis defined for any
NUMBER.value_number(v) i64unchanged; documented as the integer-number accessor.emitwrites floats in shortest round-trippable form (fmt.write_f64).Enabling change (
std.text.parse)parse_f64derives its length viastr_len, assuming null termination — unsafeon a span embedded in a larger buffer, which is exactly the zero-copy JSON case.
Factored the body into
parse_f64_len(s, len)(bounded by an explicit length);parse_f64now delegates. No behaviour change for existing callers.Tests
json (+14): float with fraction / exponent / signed & uppercase exponent /
negative, integer-stays-integer, mixed int+float array, float in object,
malformed rejection (
1.,1e,1.5e), emit exact bytes, built-float emit,and parse→emit→parse round-trip. parse (+2):
parse_f64_lenbounded span (doesnot read past
len) and zero length. Full suite: 620 passed / 0 failed(
std.data.json52→66). riscv64 cross smoke test green.