feat(text): Text.to_float; a void function's return <value> is an error
Text.to_float reads a leading decimal number (strtod), the twin of Text.to_int, for data files. A return with a value in a function that returns nothing now says so where it is, instead of reaching clang as 'store void'. Seed regenerated. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
f5ab5cf88a
commit
c57eafcacc
8 changed files with 38133 additions and 37958 deletions
5
changes/text-to-float.md
Normal file
5
changes/text-to-float.md
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
bump: minor
|
||||
type: feat
|
||||
**`Text.to_float(s)`** - a leading decimal number read from a string as a `float` (`strtod`
|
||||
underneath), the twin of `Text.to_int`. A game's data files carry fractions - an effect's
|
||||
strength, a model's reach - and there was no way to read one back.
|
||||
5
changes/void-return-error.md
Normal file
5
changes/void-return-error.md
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
bump: patch
|
||||
type: fix
|
||||
**`return <value>` in a function that returns nothing is an error.** It used to reach clang as
|
||||
`store void`, which fails the link with an LLVM message about void types and no line in the
|
||||
program; it now says where, in words.
|
||||
27
docs/language/text/text-to_float.md
Normal file
27
docs/language/text/text-to_float.md
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
---
|
||||
id: text-to_float
|
||||
name: Text.to_float
|
||||
category: text
|
||||
kind: namespace-method
|
||||
tokens: Text.to_float
|
||||
sig: Text.to_float(s) -> float
|
||||
tip: Parse a leading decimal number from a string.
|
||||
order: 11
|
||||
ns: Text
|
||||
member: to_float
|
||||
---
|
||||
|
||||
Reads an optional sign, the leading digits, a decimal point and an exponent from <code>s</code> and returns them as a <code>float</code>, stopping at the first character that cannot continue a number - so <code>Text.to_float("0.25 m")</code> is <code>0.25</code>. A string with no leading number yields <code>0.0</code>. It is the float twin of <code>Text.to_int</code>, for reading a data file or a typed value.
|
||||
|
||||
Parameters:
|
||||
- `s` — the string to parse
|
||||
|
||||
```ludic
|
||||
program ParseSpeed {
|
||||
var typed: string = "3.2"
|
||||
|
||||
handler Apply phase Update {
|
||||
let speed = Text.to_float(typed) # 3.2
|
||||
}
|
||||
}
|
||||
```
|
||||
|
|
@ -117,6 +117,7 @@ function emit_for(st: Node) -> void {
|
|||
}
|
||||
|
||||
function emit_return(st: Node) -> void {
|
||||
if (st.a != null) and (ret_ty == "void") { perr("a function that returns nothing cannot return a value") }
|
||||
if (st.a != null) {
|
||||
let v = emit_expr(st.a)
|
||||
store_at(llty(ret_ty), coerce_code(v, ret_ty), "%retval")
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@
|
|||
function is_text_ns(meth: pointer) -> bool {
|
||||
if (meth == "length") or (meth == "char_at") or (meth == "slice") { return true }
|
||||
if (meth == "equals") or (meth == "concat") or (meth == "to_int") or (meth == "from_int") { return true }
|
||||
if (meth == "to_float") { return true }
|
||||
if (meth == "starts_with") or (meth == "ends_with") { return true }
|
||||
if (meth == "contains") or (meth == "index_of") { return true }
|
||||
if (meth == "upper") or (meth == "lower") or (meth == "trim") or (meth == "repeat") { return true }
|
||||
|
|
@ -47,6 +48,11 @@ function emit_text_ns(meth: pointer, e: Node) -> Val {
|
|||
let c = emit_bind(`load i8, ptr {a}`)
|
||||
return val(emit_bind(`zext i8 {c} to i32`), "int")
|
||||
}
|
||||
if (meth == "to_float") { # parse a leading decimal number, 0.0 if none
|
||||
fp_declare("declare double @strtod(ptr, ptr)\n")
|
||||
let d = emit_bind(`call double @strtod(ptr {s.code}, ptr null)`)
|
||||
return val(emit_bind(`fptrunc double {d} to float`), "float")
|
||||
}
|
||||
if (meth == "to_int") { # parse a leading integer, 0 if none
|
||||
return val(emit_bind(`call i32 @atoi(ptr {s.code})`), "int")
|
||||
}
|
||||
|
|
|
|||
38023
selfhost/ludicc.seed.ll
38023
selfhost/ludicc.seed.ll
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
|
@ -1352,6 +1352,7 @@ program LudicLsp {
|
|||
if (meth == "equals") { return "Text.equals(a, b) -> bool" }
|
||||
if (meth == "concat") { return "Text.concat(a, b) -> string" }
|
||||
if (meth == "to_int") { return "Text.to_int(s) -> int" }
|
||||
if (meth == "to_float") { return "Text.to_float(s) -> float" }
|
||||
if (meth == "from_int") { return "Text.from_int(n) -> string" }
|
||||
if (meth == "upper") { return "Text.upper(s) -> string" }
|
||||
if (meth == "lower") { return "Text.lower(s) -> string" }
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue