@@ -36,6 +36,35 @@ Package/REIR integration:
3636 propagation.
3737```
3838
39+ ### Changes since the v0.6 baseline
40+
41+ ``` text
42+ Value-semantics protocols and derives (§14.6, §20.1 L) — IMPLEMENTED:
43+ - Compiler-owned protocols `Clone`, `Eq`, `Ord`, `Hashable` with their
44+ contracts in stdlib (`clone/`, `cmp/`, `hash/`).
45+ - `derives(...)` clause on struct/sum: accepted set is Debug, Clone, Eq,
46+ Ord, Hash, JsonEncode, JsonDecode, Schema, ReviewSchema. Field-level
47+ derive support is checked in RSScript before lowering; resources accept
48+ only Debug/Schema/ReviewSchema.
49+ - `Clone.clone<T>(self: read x) -> fresh T` closes the read-borrow clone
50+ gap; `String.clone` and per-type synthesized `.clone()` are the same
51+ managed-value copy.
52+ - `Map<K,V>` keys and `Set<K>` elements are bound by `Hashable`; a
53+ non-hashable key is rejected in RSScript with a `derives(Eq, Hash)` fix.
54+
55+ Numeric surface (§18.2) — IMPLEMENTED:
56+ - `Math` module: Int intrinsics (abs/min/max/clamp/pow) and Float intrinsics
57+ (abs/min/max/clamp/pow, exp/exp2/log/log2/sin/cos/tanh, sqrt, trunc_float,
58+ floor/ceil/round).
59+ - Scalar conversions/inspection: `Int.to_float`, `Int.to_string`,
60+ `Float.to_string`, `Float.is_nan`/`is_finite`/`is_infinite`,
61+ `String.from_float`, `String.parse_float`.
62+
63+ Soundness/feature fixes folded into the prose (see BUGS.md RSS-1…RSS-13):
64+ - Nested generics, sound payload-variant construction, borrowed-match
65+ payload extraction, callable clone, let-mut clone of read-param init.
66+ ```
67+
3968---
4069
4170## Constitution
@@ -2986,6 +3015,82 @@ safety, blanket implementations, associated types, and auto method resolution
29863015must not leak into source , diagnostics , `. rssi` contracts , package metadata , or
29873016review evidence .
29883017
3018+ #### Compiler - owned protocols and `derives `
3019+
3020+ A small , fixed set of protocols are * * compiler - owned ** : their contract is
3021+ declared in `stdlib / ` but satisfaction is produced by the compiler from a
3022+ `derives (... )` clause on a type declaration rather than written by hand . This is
3023+ the implemented form of the " compiler-owned derives" direction (§20.1 L ) for the
3024+ value - semantics protocols . The shipped derives are :
3025+
3026+ ```text
3027+ Debug structural debug rendering (the implicit default on every type ,
3028+ including resources )
3029+ Clone deep , explicit value copy (protocol Clone , §below )
3030+ Eq total structural equality (protocol Eq )
3031+ Ord lexicographic ordering over declared fields / variants ; implies Eq
3032+ Hash structural hash ; with Eq this satisfies protocol Hashable
3033+ JsonEncode compiler - owned serialization marker (lowers to audited serde )
3034+ JsonDecode compiler - owned deserialization marker (lowers to audited serde )
3035+ Schema review / schema marker ; introduces no executable behavior
3036+ ReviewSchema review / schema marker ; introduces no executable behavior
3037+ ```
3038+
3039+ The value protocols and their contracts are:
3040+
3041+ ``` rust
3042+ protocol Clone { fn clone (self : read Self ) -> fresh Self }
3043+ protocol Eq { fn equals (self : read Self , other : read Self ) -> Bool }
3044+ protocol Ord { fn compare (self : read Self , other : read Self ) -> Int }
3045+ protocol Hashable { fn hash_value (self : read Self ) -> Int }
3046+ ```
3047+
3048+ A managed `struct ` or `sum ` satisfies one of these by listing it in
3049+ `derives (... )`; the compiler expands the derive into a structural implementation
3050+ over every field . The builtin value scalars satisfy these protocols directly
3051+ with no derive , with one deliberate exception : every value scalar (`Int `,
3052+ `Float `, `String `, `Bool `, `Char `, …) is `Clone `, but `Float `/ `Float32 `/ `Float64 `
3053+ are * * not ** `Eq `, `Ord `, or `Hashable ` (IEEE - 754 equality is not total ), so a
3054+ `Float ` may not be a `Map `/ `Set ` key and a `derives (Eq )` over a `Float ` field is
3055+ rejected .
3056+
3057+ ```rust
3058+ struct User derives (Eq , Hash , Clone ) {
3059+ id : Int
3060+ name : String
3061+ }
3062+ ```
3063+
3064+ Rules that hold for compiler-owned derives:
3065+
3066+ ``` text
3067+ closed set only the names listed above are accepted; any other name is
3068+ rejected with an "unsupported derive" diagnostic.
3069+ field-checked every field of a derived type must itself support the derive.
3070+ A derive over a non-supporting field (e.g. `Eq` over a `Float`
3071+ field) is rejected with an RSScript diagnostic before lowering,
3072+ not as a leaked rustc trait-bound error.
3073+ Ord implies Eq `derives(Ord)` also provides `Eq`; `Hashable` requires
3074+ `derives(Hash)` together with `Eq` (so `derives(Eq, Hash)` or
3075+ `derives(Ord, Hash)`), enforcing "equal values hash equal".
3076+ resources a `resource` supports only `Debug`, `Schema`, and `ReviewSchema`.
3077+ Value derives (`Clone`, `Eq`, `Ord`, `Hash`, `JsonEncode`,
3078+ `JsonDecode`) on a resource are rejected: they would copy or
3079+ compare a move-only RAII value.
3080+ pure contract these protocols introduce no mutation, retention, native, or
3081+ unsafe boundary, and add no capability gate.
3082+ ```
3083+
3084+ ` Clone.clone<T>(self: read x) ` copies a value out of a shared (` read ` ) borrow
3085+ into a ` fresh ` owned value. This closes the "clone gap" where a ` read ` field or
3086+ ` read ` parameter cannot otherwise be moved into a constructor or a collection;
3087+ ` String.clone ` and the per-type ` .clone() ` synthesized for any ` derives(Clone) `
3088+ type are the same managed-value copy.
3089+
3090+ ` Hashable ` is the bound on ` Map<K, V> ` keys and ` Set<K> ` elements (§18.2): a
3091+ non-hashable key is rejected in RSScript with a ` derives(Eq, Hash) ` suggestion
3092+ instead of leaking a trait-bound error from the Rust backend.
3093+
29893094#### 14.6.1 Receiver-call shorthand
29903095
29913096A ** receiver-call expression** is a syntactic shorthand for a qualified function
@@ -3764,6 +3869,7 @@ Unit
37643869Bool
37653870Int
37663871Float
3872+ Math
37673873String
37683874Bytes
37693875Buffer
@@ -3800,6 +3906,7 @@ Span
38003906Log
38013907Test
38023908Assert
3909+ Clone / Eq / Ord / Hashable (compiler-owned value protocols, §14.6)
38033910```
38043911
38053912The prototype ships these signatures as ordinary bundled ` .rssi ` files under
@@ -4039,9 +4146,60 @@ pub fn Json.array_fold<T: Struct>(
40394146) -> Result <fresh T , JsonError >
40404147```
40414148
4149+ The scalar conversion and ` Float ` inspection surface covers ` Int ` /` Float ` /` String `
4150+ interchange and floating-point classification. All are ` pure ` :
4151+
4152+ ``` rust
4153+ pub fn Int . to_string (value : read Int ) -> fresh String
4154+ pub fn Int . to_float (value : read Int ) -> Float
4155+
4156+ pub fn Float . to_string (value : read Float ) -> fresh String
4157+ pub fn Float . is_nan (value : read Float ) -> Bool
4158+ pub fn Float . is_finite (value : read Float ) -> Bool
4159+ pub fn Float . is_infinite (value : read Float ) -> Bool
4160+
4161+ pub fn String . from_float (value : Float ) -> fresh String
4162+ pub fn String . parse_float (value : read String ) -> Option <Float >
4163+ ```
4164+
4165+ The ` Math ` core surface provides ` Int ` and ` Float ` numeric intrinsics. They are
4166+ pure value functions with no capability gate, lowering to ordinary Rust ` f64 ` /` i64 `
4167+ operations in the backend (and to direct VM opcodes under the register VM):
4168+
4169+ ``` rust
4170+ pub fn Math . abs (value : Int ) -> Int
4171+ pub fn Math . min (left : Int , right : Int ) -> Int
4172+ pub fn Math . max (left : Int , right : Int ) -> Int
4173+ pub fn Math . clamp (value : Int , min : Int , max : Int ) -> Int
4174+ pub fn Math . pow (base : Int , exponent : Int ) -> Int
4175+
4176+ pub fn Math . abs_float (value : Float ) -> Float
4177+ pub fn Math . min_float (left : Float , right : Float ) -> Float
4178+ pub fn Math . max_float (left : Float , right : Float ) -> Float
4179+ pub fn Math . clamp_float (value : Float , min : Float , max : Float ) -> Float
4180+ pub fn Math . pow_float (base : Float , exponent : Float ) -> Float
4181+
4182+ pub fn Math . exp (value : Float ) -> Float
4183+ pub fn Math . exp2 (value : Float ) -> Float
4184+ pub fn Math . log (value : Float ) -> Float
4185+ pub fn Math . log2 (value : Float ) -> Float
4186+ pub fn Math . sin (value : Float ) -> Float
4187+ pub fn Math . cos (value : Float ) -> Float
4188+ pub fn Math . tanh (value : Float ) -> Float
4189+
4190+ pub fn Math . sqrt (value : Float ) -> Float
4191+ pub fn Math . trunc_float (value : Float ) -> Float
4192+ pub fn Math . floor (value : Float ) -> Int
4193+ pub fn Math . ceil (value : Float ) -> Int
4194+ pub fn Math . round (value : Float ) -> Int
4195+ ```
4196+
40424197The minimum ` Path ` , ` Map ` , and ` Set ` core surfaces cover package-manager-style
4043- path inspection and ordinary keyed/indexed working sets. ` Map ` and ` Set ` retain
4044- inserted non-Copy values by contract:
4198+ path inspection and ordinary keyed/indexed working sets. A ` Map<K, V> ` key and a
4199+ ` Set<K> ` element must satisfy the compiler-owned ` Hashable ` protocol (§14.6):
4200+ a builtin scalar key, or a managed ` struct ` /` sum ` that ` derives(Eq, Hash) ` . A
4201+ non-hashable key is rejected in RSScript, not by the Rust backend. ` Map ` and
4202+ ` Set ` retain inserted non-Copy values by contract:
40454203
40464204``` rust
40474205pub fn Path . from_string (value : read String ) -> fresh Path
@@ -4180,6 +4338,136 @@ Error composition in RSScript is always explicit at the call site. Unlike Rust's
41804338visible ` map_error ` call that a reviewer can audit. The ` ? ` operator propagates
41814339errors within the same error type; crossing error types requires explicit mapping.
41824340
4341+ The remaining bundled facades are review-visible library boundaries. Facades that
4342+ touch the filesystem, time, environment, subprocess, randomness, encoding/regex
4343+ engines, or telemetry are ` native ` (the effect is in every signature); pure value
4344+ facades such as ` Url ` parsing and ` Csv ` row parsing are not. The signatures below
4345+ are representative core surfaces, not the full bundled ` .rssi ` ; the authoritative
4346+ contracts live under ` stdlib/ ` .
4347+
4348+ Filesystem — ` File ` is a ` resource ` (move-only RAII, §6.4); path-level helpers are
4349+ free functions:
4350+
4351+ ``` rust
4352+ resource File
4353+
4354+ pub fn File . open (path : read Path ) -> Result <File , FileError >
4355+ pub fn File . open_read (path : read Path ) -> Result <File , FileError >
4356+ pub fn File . open_write (path : read Path ) -> Result <File , FileError >
4357+ pub fn File . read_all_string (file : mut File ) -> Result <String , FileError >
4358+ pub fn File . read_into (file : mut File , buffer : mut Buffer ) -> Result <Bool , FileError >
4359+ pub fn File . write_string (file : mut File , text : read String ) -> Result <Unit , FileError >
4360+ pub fn File . write_buffer (file : mut File , buffer : read Buffer ) -> Result <Unit , FileError >
4361+
4362+ pub fn File . exists (path : read Path ) -> Bool effects (native )
4363+ pub fn File . read_string (path : read Path ) -> Result <String , FileError > effects (native )
4364+ pub fn File . write_string_to_path (path : read Path , text : read String ) -> Result <Unit , FileError >
4365+ effects (native )
4366+ pub fn File . write_atomic (path : read Path , text : read String ) -> Result <Unit , FileError >
4367+ effects (native )
4368+ pub fn FileError . message (error : read FileError ) -> String effects (pure )
4369+
4370+ pub native fn Directory . exists (path : read Path ) -> Bool effects (native )
4371+ pub native fn Directory . is_dir (path : read Path ) -> Bool effects (native )
4372+ pub native fn Directory . create_all (path : read Path ) -> Result <Unit , FileError >
4373+ effects (native )
4374+ pub native fn Directory . list_paths (path : read Path ) -> Result <fresh List <Path >, FileError >
4375+ effects (native )
4376+ pub native fn Directory . remove_dir_all (path : read Path ) -> Result <Unit , FileError >
4377+ effects (native )
4378+ pub native fn Directory . rename (from : read Path , to : read Path ) -> Result <Unit , FileError >
4379+ effects (native )
4380+ ```
4381+
4382+ JSON — parsing and typed field/path access return typed ` JsonError ` ; encoding and
4383+ field-builder helpers are ` pure ` . The full surface adds ` field_* ` /` at_* ` accessors
4384+ and ` at_*_or ` fallbacks:
4385+
4386+ ``` rust
4387+ struct JsonValue
4388+ struct JsonLiteral
4389+
4390+ pub fn Json . parse (text : read String ) -> Result <fresh JsonValue , JsonError >
4391+ pub fn Json . parse_file (path : read Path ) -> Result <fresh JsonValue , JsonError >
4392+ pub fn Json . decode<T : Struct >(value : read JsonValue ) -> Result <fresh T , JsonError >
4393+ pub fn Json . decode_text<T : Struct >(text : read String ) -> Result <fresh T , JsonError >
4394+ pub fn Json . to_string (value : read JsonValue ) -> fresh String effects (pure )
4395+ pub fn Json . field (value : read JsonValue , name : read String ) -> Result <fresh JsonValue , JsonError >
4396+ pub fn Json . field_string (value : read JsonValue , name : read String ) -> Result <String , JsonError >
4397+ pub fn Json . at (value : read JsonValue , path : read String ) -> Result <fresh JsonValue , JsonError >
4398+ pub fn Json . at_int_or (value : read JsonValue , path : read String , fallback : Int ) -> Int
4399+ effects (pure )
4400+ ```
4401+
4402+ Time, environment, randomness, and subprocess facades are ` native ` :
4403+
4404+ ``` rust
4405+ struct Instant
4406+ struct Duration
4407+
4408+ pub native fn Clock . now () -> fresh Instant effects (native )
4409+ pub native fn Clock . system_unix_ms () -> Int effects (native )
4410+ pub native fn Instant . elapsed (start : read Instant ) -> fresh Duration effects (native )
4411+ pub native fn Duration . ms (value : Int ) -> fresh Duration effects (native )
4412+ pub native fn Duration . as_ms (value : read Duration ) -> Int effects (native )
4413+
4414+ pub native fn Env . get (name : read String ) -> Option <fresh String > effects (native )
4415+ pub native fn Env . get_or_default (name : read String , default : read String ) -> fresh String
4416+ effects (native )
4417+ pub native fn Env . current_dir () -> Result <fresh Path , FileError > effects (native )
4418+ pub native fn Env . home_dir () -> Option <fresh Path > effects (native )
4419+
4420+ pub native fn Uuid . new_v4 () -> fresh String effects (native )
4421+ pub native fn Random . int (min : Int , max : Int ) -> Int effects (native )
4422+ pub native fn Random . float () -> Float effects (native )
4423+ pub native fn Random . bytes (len : Int ) -> fresh Bytes effects (native )
4424+
4425+ pub native fn Process . run_stdout (command : read String , args : read List <String >)
4426+ -> Result <String , String > effects (native )
4427+ pub native fn Process . run (command : read String , args : read List <String >)
4428+ -> Result <fresh ProcessOutput , String > effects (native )
4429+ pub native fn Process . run_timeout (
4430+ command : read String , args : read List <String >, timeout_ms : Int ,
4431+ ) -> Result <fresh ProcessOutput , String > effects (native )
4432+ ```
4433+
4434+ Encoding, regex, and logging facades. ` Base64 ` /` Hex ` /` Url ` component encoding and
4435+ ` Regex ` are ` native ` ; ` Log ` emission is a ` native ` telemetry boundary:
4436+
4437+ ``` rust
4438+ pub native fn Base64 . encode (value : read String ) -> fresh String effects (native )
4439+ pub native fn Base64 . decode (text : read String ) -> Result <fresh Bytes , DecodeError >
4440+ effects (native )
4441+ pub native fn Hex . encode (value : read Bytes ) -> fresh String effects (native )
4442+ pub native fn Url . encode_component (value : read String ) -> fresh String effects (native )
4443+
4444+ pub native fn Regex . compile (pattern : read String ) -> Result <fresh Regex , RegexError >
4445+ effects (native )
4446+ pub native fn Regex . is_match (regex : read Regex , value : read String ) -> Bool
4447+ effects (native )
4448+ pub native fn Regex . captures (regex : read Regex , value : read String ) -> fresh List <String >
4449+ effects (native )
4450+ pub native fn Regex . replace_all (
4451+ regex : read Regex , value : read String , replacement : read String ,
4452+ ) -> fresh String effects (native )
4453+
4454+ pub fn Log . write (message : read String ) -> Unit effects (native )
4455+ pub fn Log . error (message : read String ) -> Unit effects (native )
4456+ pub fn Log . write_json (value : read JsonValue ) -> Unit effects (native )
4457+ ```
4458+
4459+ Pure value facades — ` Url ` parsing and ` Csv ` row parsing carry no ` native ` effect:
4460+
4461+ ``` rust
4462+ pub fn Url . from_string (value : read String ) -> fresh Url
4463+ pub fn Url . to_string (url : read Url ) -> fresh String effects (pure )
4464+
4465+ pub fn Csv . open_read (path : read Path ) -> Result <File , CsvError >
4466+ pub fn Csv . read_into (file : mut File , buffer : mut RowBuffer ) -> Result <Unit , CsvError >
4467+ pub fn Csv . parse_row (buffer : read RowBuffer ) -> Result <fresh Row , CsvError >
4468+ pub fn Row . field_string (row : read Row , index : Int ) -> Result <String , CsvError >
4469+ ```
4470+
41834471Agent, GPU, model-client, and domain-specific network clients are use-case
41844472libraries, not language core. The bundled HTTP surface is intentionally only a
41854473small façade: ` stdlib/http/http.rssi ` covers handler request/response values, and
@@ -4534,11 +4822,20 @@ K. Explicit error composition (design principle — v0.6 implemented)
45344822 anyhow/eyre-style erased errors (these hide error provenance from review).
45354823
45364824L. Compiler-owned derives (restricted code generation)
4825+ - Status: the value-semantics derives (`Clone`, `Eq`, `Ord`, `Hash`) and the
4826+ implicit `Debug` are IMPLEMENTED, together with the `Clone`/`Eq`/`Ord`/
4827+ `Hashable` protocols they satisfy (§14.6). `JsonEncode`/`JsonDecode`/
4828+ `Schema`/`ReviewSchema` are accepted derive names with serde/review-marker
4829+ semantics; remaining work here is package-level serialization review facts.
45374830 - RSScript supports a limited set of compiler-owned derive directives on
45384831 structs and sums:
45394832
45404833 struct User derives(Debug, Clone, Eq, Ord, Hash, JsonEncode, JsonDecode, Schema) { ... }
45414834
4835+ - the accepted set is exactly Debug, Clone, Eq, Ord, Hash, JsonEncode,
4836+ JsonDecode, Schema, ReviewSchema; any other name is rejected. Every field of
4837+ a derived type must itself support the derive (checked in RSScript, not by
4838+ the Rust backend). Resources support only Debug, Schema, and ReviewSchema.
45424839 - generated code must produce visible .rssi signatures and review facts.
45434840 - generated code must not introduce hidden control flow, mutation, or
45444841 resource acquisition.
0 commit comments