aboutsummaryrefslogtreecommitdiff
path: root/stdlib/source
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--stdlib/source/library/lux/control/concurrency/thread.lux16
-rw-r--r--stdlib/source/library/lux/control/parser/synthesis.lux2
-rw-r--r--stdlib/source/library/lux/control/parser/text.lux2
-rw-r--r--stdlib/source/library/lux/data/text.lux147
-rw-r--r--stdlib/source/library/lux/data/text/encoding/utf8.lux25
-rw-r--r--stdlib/source/library/lux/ffi.js.lux72
-rw-r--r--stdlib/source/library/lux/ffi.jvm.lux387
-rw-r--r--stdlib/source/library/lux/ffi.py.lux153
-rw-r--r--stdlib/source/library/lux/ffi/export.js.lux96
-rw-r--r--stdlib/source/library/lux/ffi/export.jvm.lux106
-rw-r--r--stdlib/source/library/lux/ffi/export.lua.lux112
-rw-r--r--stdlib/source/library/lux/ffi/export.py.lux89
-rw-r--r--stdlib/source/library/lux/ffi/export.rb.lux144
-rw-r--r--stdlib/source/library/lux/static.lux22
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/directive/lux.lux24
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/generation/python/host.lux60
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/case.lux69
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/function.lux3
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/runtime.lux7
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/lua/case.lux13
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/ruby/case.lux3
-rw-r--r--stdlib/source/library/lux/tool/compiler/language/lux/synthesis/simple.lux6
-rw-r--r--stdlib/source/library/lux/tool/compiler/phase.lux1
-rw-r--r--stdlib/source/library/lux/world/file.lux3
-rw-r--r--stdlib/source/program/aedifex/artifact/extension.lux1
-rw-r--r--stdlib/source/test/lux/ffi.js.lux41
-rw-r--r--stdlib/source/test/lux/ffi.jvm.lux167
-rw-r--r--stdlib/source/test/lux/ffi.lua.lux26
-rw-r--r--stdlib/source/test/lux/ffi.py.lux26
-rw-r--r--stdlib/source/test/lux/ffi.rb.lux22
-rw-r--r--stdlib/source/test/lux/ffi/export.js.lux33
-rw-r--r--stdlib/source/test/lux/ffi/export.jvm.lux186
-rw-r--r--stdlib/source/test/lux/ffi/export.lua.lux33
-rw-r--r--stdlib/source/test/lux/ffi/export.py.lux33
-rw-r--r--stdlib/source/test/lux/ffi/export.rb.lux43
-rw-r--r--stdlib/source/unsafe/lux/data/binary.lux6
36 files changed, 1460 insertions, 719 deletions
diff --git a/stdlib/source/library/lux/control/concurrency/thread.lux b/stdlib/source/library/lux/control/concurrency/thread.lux
index 07de8c1c7..5e76521ed 100644
--- a/stdlib/source/library/lux/control/concurrency/thread.lux
+++ b/stdlib/source/library/lux/control/concurrency/thread.lux
@@ -17,6 +17,8 @@
[number
["n" nat]
["f" frac]]]
+ [meta
+ ["[0]" configuration]]
[time
["[0]" instant]]]]
[//
@@ -68,14 +70,18 @@
(def: .public parallelism
Nat
- (with_expansions [<jvm> (|> (java/lang/Runtime::getRuntime)
- (java/lang/Runtime::availableProcessors)
- ffi.of_int
- .nat)]
+ (with_expansions [<default> 1
+ <jvm> (<| (configuration.for [... TODO: Remove this when Rembulan is no longer being used.
+ ["lua_compiler?" ""]
+ <default>])
+ (|> (java/lang/Runtime::getRuntime)
+ (java/lang/Runtime::availableProcessors)
+ ffi.of_int
+ .nat))]
(for [@.old <jvm>
@.jvm <jvm>]
... Default
- 1)))
+ <default>)))
(with_expansions [<jvm> (as_is (def: runner
java/util/concurrent/ScheduledThreadPoolExecutor
diff --git a/stdlib/source/library/lux/control/parser/synthesis.lux b/stdlib/source/library/lux/control/parser/synthesis.lux
index 894f7da68..d0cebbb12 100644
--- a/stdlib/source/library/lux/control/parser/synthesis.lux
+++ b/stdlib/source/library/lux/control/parser/synthesis.lux
@@ -111,7 +111,7 @@
(exception.except ..cannot_parse input)))))]
[bit bit! /.bit Bit bit.equivalence]
- [i64 i64! /.i64 (I64 Any) i64.equivalence]
+ [i64 i64! /.i64 I64 i64.equivalence]
[f64 f64! /.f64 Frac frac.equivalence]
[text text! /.text Text text.equivalence]
[local local! /.variable/local Nat n.equivalence]
diff --git a/stdlib/source/library/lux/control/parser/text.lux b/stdlib/source/library/lux/control/parser/text.lux
index 72f97501b..de79a42b5 100644
--- a/stdlib/source/library/lux/control/parser/text.lux
+++ b/stdlib/source/library/lux/control/parser/text.lux
@@ -1,6 +1,6 @@
(.using
[library
- [lux {"-" or and not local}
+ [lux {"-" and not local}
[abstract
[monad {"+" Monad do}]]
[control
diff --git a/stdlib/source/library/lux/data/text.lux b/stdlib/source/library/lux/data/text.lux
index 177192e95..01e39705f 100644
--- a/stdlib/source/library/lux/data/text.lux
+++ b/stdlib/source/library/lux/data/text.lux
@@ -1,23 +1,23 @@
(.using
- [library
- [lux {"-" char}
- ["@" target]
- [abstract
- [hash {"+" Hash}]
- [monoid {"+" Monoid}]
- [equivalence {"+" Equivalence}]
- [order {"+" Order}]
- [monad {"+" do}]
- [codec {"+" Codec}]]
- [control
- ["[0]" maybe]]
- [data
- [collection
- ["[0]" list ("[1]#[0]" mix)]]]
- [math
- [number
- ["n" nat]
- ["[0]" i64]]]]])
+ [library
+ [lux {"-" char}
+ ["@" target]
+ [abstract
+ [hash {"+" Hash}]
+ [monoid {"+" Monoid}]
+ [equivalence {"+" Equivalence}]
+ [order {"+" Order}]
+ [monad {"+" do}]
+ [codec {"+" Codec}]]
+ [control
+ ["[0]" maybe]]
+ [data
+ [collection
+ ["[0]" list ("[1]#[0]" mix)]]]
+ [math
+ [number
+ ["n" nat]
+ ["[0]" i64]]]]])
(type: .public Char
Nat)
@@ -182,48 +182,77 @@
[[pre post] (..split_by pattern template)]
(in ($_ "lux text concat" pre replacement post)))))
+(for [@.js (as_is (macro: (defined? tokens lux)
+ (case tokens
+ (^ (list it))
+ {.#Right [lux (list (` (.case ("js type-of" ("js constant" (~ it)))
+ "undefined"
+ .false
+
+ (~' _)
+ .true)))]}
+
+ _
+ {.#Left ""}))
+ (macro: (if_nashorn tokens lux)
+ (case tokens
+ (^ (list then else))
+ {.#Right [lux (list (if (and (..defined? "java")
+ (..defined? "java.lang")
+ (..defined? "java.lang.Object"))
+ then
+ else))]}
+
+ _
+ {.#Left ""})))]
+ (as_is))
+
(def: .public (replaced pattern replacement template)
(-> Text Text Text Text)
- (for [@.old
- (:as Text
- ("jvm invokevirtual:java.lang.String:replace:java.lang.CharSequence,java.lang.CharSequence"
- (:as (Primitive "java.lang.String") template)
- (:as (Primitive "java.lang.CharSequence") pattern)
- (:as (Primitive "java.lang.CharSequence") replacement)))
- @.jvm
- (:as Text
- ("jvm member invoke virtual" [] "java.lang.String" "replace" []
- (:as (Primitive "java.lang.String") template)
- ["Ljava/lang/CharSequence;" (:as (Primitive "java.lang.CharSequence") pattern)]
- ["Ljava/lang/CharSequence;" (:as (Primitive "java.lang.CharSequence") replacement)]))
- ... TODO: Comment/turn-off when generating a JS compiler using a JVM-based compiler because Nashorn's implementation of "replaceAll" is incorrect.
- @.js
- (:as Text
- ("js object do" "replaceAll" template [pattern replacement]))
- @.python
- (:as Text
- ("python object do" "replace" template pattern replacement))
- ... TODO @.lua
- @.ruby
- (:as Text
- ("ruby object do" "gsub" template pattern replacement))
- @.php
- (:as Text
- ("php apply" (:expected ("php constant" "str_replace"))
- pattern replacement template))
- ... TODO @.scheme
- ... TODO @.common_lisp
- ... TODO @.r
- ]
- ... Inefficient default
- (loop [left ""
- right template]
- (case (..split_by pattern right)
- {.#Some [pre post]}
- (again ($_ "lux text concat" left pre replacement) post)
-
- {.#None}
- ("lux text concat" left right)))))
+ (with_expansions [... Inefficient default
+ <default> (loop [left ""
+ right template]
+ (case (..split_by pattern right)
+ {.#Some [pre post]}
+ (again ($_ "lux text concat" left pre replacement) post)
+
+ {.#None}
+ ("lux text concat" left right)))]
+ (for [@.old
+ (:as Text
+ ("jvm invokevirtual:java.lang.String:replace:java.lang.CharSequence,java.lang.CharSequence"
+ (:as (Primitive "java.lang.String") template)
+ (:as (Primitive "java.lang.CharSequence") pattern)
+ (:as (Primitive "java.lang.CharSequence") replacement)))
+ @.jvm
+ (:as Text
+ ("jvm member invoke virtual" [] "java.lang.String" "replace" []
+ (:as (Primitive "java.lang.String") template)
+ ["Ljava/lang/CharSequence;" (:as (Primitive "java.lang.CharSequence") pattern)]
+ ["Ljava/lang/CharSequence;" (:as (Primitive "java.lang.CharSequence") replacement)]))
+ @.js
+ ... TODO: Remove this when Nashorn is no longer being used.
+ (..if_nashorn
+ <default>
+ (:as Text
+ ("js object do" "replaceAll" template [pattern replacement])))
+ @.python
+ (:as Text
+ ("python object do" "replace" template pattern replacement))
+ ... TODO @.lua
+ @.ruby
+ (:as Text
+ ("ruby object do" "gsub" template pattern replacement))
+ @.php
+ (:as Text
+ ("php apply" (:expected ("php constant" "str_replace"))
+ pattern replacement template))
+ ... TODO @.scheme
+ ... TODO @.common_lisp
+ ... TODO @.r
+ ]
+ ... Inefficient default
+ <default>)))
(implementation: .public equivalence
(Equivalence Text)
diff --git a/stdlib/source/library/lux/data/text/encoding/utf8.lux b/stdlib/source/library/lux/data/text/encoding/utf8.lux
index bcc1a0ee2..ac4a452be 100644
--- a/stdlib/source/library/lux/data/text/encoding/utf8.lux
+++ b/stdlib/source/library/lux/data/text/encoding/utf8.lux
@@ -1,15 +1,15 @@
(.using
- [library
- [lux "*"
- ["@" target]
- ["[0]" ffi]
- [abstract
- [codec {"+" Codec}]]
- [control
- ["[0]" try {"+" Try}]]
- [data
- ["[0]" binary {"+" Binary}]]]]
- ["[0]" //])
+ [library
+ [lux "*"
+ ["@" target]
+ ["[0]" ffi]
+ [abstract
+ [codec {"+" Codec}]]
+ [control
+ ["[0]" try {"+" Try}]]
+ [data
+ ["[0]" binary {"+" Binary}]]]]
+ ["[0]" //])
(with_expansions [<jvm> (as_is (ffi.import: java/lang/String
["[1]::[0]"
@@ -19,7 +19,8 @@
@.jvm (as_is <jvm>)
@.js
- (as_is (ffi.import: Uint8Array)
+ (as_is (ffi.import: Uint8Array
+ ["[1]::[0]"])
... On Node
(ffi.import: Buffer
diff --git a/stdlib/source/library/lux/ffi.js.lux b/stdlib/source/library/lux/ffi.js.lux
index ddcac1a30..8cae0a976 100644
--- a/stdlib/source/library/lux/ffi.js.lux
+++ b/stdlib/source/library/lux/ffi.js.lux
@@ -1,26 +1,26 @@
(.using
- [library
- [lux {"-" Symbol}
- ["[0]" meta]
- [abstract
- [monad {"+" do}]]
- [control
- ["[0]" io]
- ["[0]" maybe]
- ["<>" parser ("[1]#[0]" monad)
- ["<[0]>" code {"+" Parser}]]]
- [data
- ["[0]" product]
- ["[0]" text
- ["%" format]]
- [collection
- ["[0]" list ("[1]#[0]" functor)]]]
- [type
- abstract]
- [macro {"+" with_symbols}
- [syntax {"+" syntax:}]
- ["[0]" code]
- ["[0]" template]]]])
+ [library
+ [lux {"-" Symbol}
+ ["[0]" meta]
+ [abstract
+ [monad {"+" do}]]
+ [control
+ ["[0]" io]
+ ["[0]" maybe]
+ ["<>" parser ("[1]#[0]" monad)
+ ["<[0]>" code {"+" Parser}]]]
+ [data
+ ["[0]" product]
+ ["[0]" text
+ ["%" format]]
+ [collection
+ ["[0]" list ("[1]#[0]" functor)]]]
+ [type
+ abstract]
+ [macro {"+" with_symbols}
+ [syntax {"+" syntax:}]
+ ["[0]" code]
+ ["[0]" template]]]])
(abstract: .public (Object brand) Any)
@@ -79,6 +79,13 @@
<code>.local_symbol
..nullable)))
+(def: constant_import
+ (Parser Field)
+ (<code>.form ($_ <>.and
+ (<>#in true)
+ <code>.local_symbol
+ ..nullable)))
+
(type: Common_Method
(Record
[#name Text
@@ -177,7 +184,8 @@
(type: Import
(Variant
{#Class [Class_Declaration Text (List Member)]}
- {#Function Static_Method}))
+ {#Function Static_Method}
+ {#Constant Field}))
(def: class_declaration
(Parser Class_Declaration)
@@ -188,11 +196,12 @@
(def: import
(Parser Import)
- (<>.or (<>.and ..class_declaration
- (<>.else ["" (list)]
- (<code>.tuple (<>.and <code>.text
- (<>.some member)))))
- (<code>.form ..common_method)))
+ ($_ <>.or
+ (<>.and ..class_declaration
+ (<code>.tuple (<>.and <code>.text
+ (<>.some member))))
+ (<code>.form ..common_method)
+ ..constant_import))
(def: (with_io with? without)
(-> Bit Code Code)
@@ -320,6 +329,13 @@
io?
try?
outputT)))
+
+ {#Constant [_ name :output:]}
+ (in (list (` (.def: (~ (code.local_symbol name))
+ (~ (nullable_type :output:))
+ (.:expected
+ (~ (<| (without_null g!temp :output:)
+ (` ("js constant" (~ (code.text name)))))))))))
)))
(template: .public (type_of object)
diff --git a/stdlib/source/library/lux/ffi.jvm.lux b/stdlib/source/library/lux/ffi.jvm.lux
index a93701270..a1d5abe96 100644
--- a/stdlib/source/library/lux/ffi.jvm.lux
+++ b/stdlib/source/library/lux/ffi.jvm.lux
@@ -1,12 +1,10 @@
(.using
[library
- ["[0]" lux {"-" Primitive Type type int char :as function}
+ [lux {"-" Primitive Type type int char :as}
["[0]" meta]
[abstract
- ["[0]" monad {"+" Monad do}]
- ["[0]" enum]]
+ ["[0]" monad {"+" do}]]
[control
- ["[0]" function]
["[0]" io]
["[0]" maybe]
["[0]" try {"+" Try}]
@@ -26,17 +24,17 @@
["[0]" code]
["[0]" template]]
[target
- [jvm
+ ["[0]" jvm "_"
[encoding
["[0]" name {"+" External}]]
- ["[0]" type {"+" Type Argument Typed}
+ ["[1]" type {"+" Type Argument Typed}
["[0]" category {"+" Void Value' Value Return' Return Method Primitive Object Class Array Var Parameter Declaration}]
["[0]" box]
["[0]" descriptor]
["[0]" signature]
["[0]" reflection]
["[0]" parser]]]]
- ["[1]_[0]" type ("[1]#[0]" equivalence)
+ ["[0]" type ("[1]#[0]" equivalence)
["[0]" check]]]])
(def: internal
@@ -47,12 +45,12 @@
(def: signature
(All (_ category)
(-> (Type category) Text))
- (|>> type.signature signature.signature))
+ (|>> jvm.signature signature.signature))
(def: reflection
(All (_ category)
(-> (Type (<| Return' Value' category)) Text))
- (|>> type.reflection reflection.reflection))
+ (|>> jvm.reflection reflection.reflection))
(template [<name> <class>]
[(`` (def: .public <name>
@@ -101,15 +99,15 @@
(def: boxes
(Dictionary (Type Value) Text)
- (|> (list [type.boolean box.boolean]
- [type.byte box.byte]
- [type.short box.short]
- [type.int box.int]
- [type.long box.long]
- [type.float box.float]
- [type.double box.double]
- [type.char box.char])
- (dictionary.of_list type.hash)))
+ (|> (list [jvm.boolean box.boolean]
+ [jvm.byte box.byte]
+ [jvm.short box.short]
+ [jvm.int box.int]
+ [jvm.long box.long]
+ [jvm.float box.float]
+ [jvm.double box.double]
+ [jvm.char box.char])
+ (dictionary.of_list jvm.hash)))
(template [<name> <pre> <post>]
[(def: (<name> unboxed boxed raw)
@@ -329,32 +327,32 @@
(-> Primitive_Mode (Type Primitive) Code)
(case mode
{#ManualPrM}
- (cond (# type.equivalence = type.boolean type) (` ..Boolean)
- (# type.equivalence = type.byte type) (` ..Byte)
- (# type.equivalence = type.short type) (` ..Short)
- (# type.equivalence = type.int type) (` ..Integer)
- (# type.equivalence = type.long type) (` ..Long)
- (# type.equivalence = type.float type) (` ..Float)
- (# type.equivalence = type.double type) (` ..Double)
- (# type.equivalence = type.char type) (` ..Character)
+ (cond (# jvm.equivalence = jvm.boolean type) (` ..Boolean)
+ (# jvm.equivalence = jvm.byte type) (` ..Byte)
+ (# jvm.equivalence = jvm.short type) (` ..Short)
+ (# jvm.equivalence = jvm.int type) (` ..Integer)
+ (# jvm.equivalence = jvm.long type) (` ..Long)
+ (# jvm.equivalence = jvm.float type) (` ..Float)
+ (# jvm.equivalence = jvm.double type) (` ..Double)
+ (# jvm.equivalence = jvm.char type) (` ..Character)
... else
(undefined))
{#AutoPrM}
- (cond (# type.equivalence = type.boolean type)
+ (cond (# jvm.equivalence = jvm.boolean type)
(` .Bit)
- (or (# type.equivalence = type.short type)
- (# type.equivalence = type.byte type)
- (# type.equivalence = type.int type)
- (# type.equivalence = type.long type))
+ (or (# jvm.equivalence = jvm.short type)
+ (# jvm.equivalence = jvm.byte type)
+ (# jvm.equivalence = jvm.int type)
+ (# jvm.equivalence = jvm.long type))
(` .Int)
- (or (# type.equivalence = type.float type)
- (# type.equivalence = type.double type))
+ (or (# jvm.equivalence = jvm.float type)
+ (# jvm.equivalence = jvm.double type))
(` .Frac)
- (# type.equivalence = type.char type)
+ (# jvm.equivalence = jvm.char type)
(` .Nat)
... else
@@ -380,7 +378,7 @@
[parser.array? elementT
(case (parser.primitive? elementT)
{.#Some elementT}
- (` {.#Primitive (~ (code.text (..reflection (type.array elementT)))) {.#End}})
+ (` {.#Primitive (~ (code.text (..reflection (jvm.array elementT)))) {.#End}})
{.#None}
(` {.#Primitive (~ (code.text array.type_name))
@@ -587,7 +585,7 @@
($_ <>.either
(<>.and class_name^ (<>#in (list)))
(<code>.form (<>.and class_name^ (<>.some (parameter^ type_vars))))))]
- (in (type.class (name.safe name) parameters))))
+ (in (jvm.class (name.safe name) parameters))))
(exception: .public (unknown_type_variable [name Text
type_vars (List (Type Var))])
@@ -601,13 +599,13 @@
[name <code>.local_symbol
_ (..assertion ..unknown_type_variable [name options]
(list.member? text.equivalence (list#each parser.name options) name))]
- (in (type.var name))))
+ (in (jvm.var name))))
(def: wildcard^
(Parser (Type Parameter))
(do <>.monad
[_ (<code>.this! (' ?))]
- (in type.wildcard)))
+ (in jvm.wildcard)))
(template [<name> <comparison> <constructor>]
[(def: <name>
@@ -617,14 +615,14 @@
<code>.tuple
(# <>.monad each <constructor>)))]
- [upper^ < type.upper]
- [lower^ > type.lower]
+ [upper^ < jvm.upper]
+ [lower^ > jvm.lower]
)
(def: (parameter^ type_vars)
(-> (List (Type Var)) (Parser (Type Parameter)))
(<>.rec
- (.function (_ _)
+ (function (_ _)
(let [class^ (..class^' parameter^ type_vars)]
($_ <>.either
(..type_variable type_vars)
@@ -645,25 +643,25 @@
(def: primitive^
(Parser (Type Primitive))
($_ <>.either
- (itself^ type.boolean)
- (itself^ type.byte)
- (itself^ type.short)
- (itself^ type.int)
- (itself^ type.long)
- (itself^ type.float)
- (itself^ type.double)
- (itself^ type.char)
+ (itself^ jvm.boolean)
+ (itself^ jvm.byte)
+ (itself^ jvm.short)
+ (itself^ jvm.int)
+ (itself^ jvm.long)
+ (itself^ jvm.float)
+ (itself^ jvm.double)
+ (itself^ jvm.char)
))
(def: array^
(-> (Parser (Type Value)) (Parser (Type Array)))
(|>> <code>.tuple
- (# <>.monad each type.array)))
+ (# <>.monad each jvm.array)))
(def: (type^ type_vars)
(-> (List (Type Var)) (Parser (Type Value)))
(<>.rec
- (.function (_ type^)
+ (function (_ type^)
($_ <>.either
..primitive^
(..parameter^ type_vars)
@@ -674,7 +672,7 @@
(Parser (Type Void))
(do <>.monad
[_ (<code>.symbol! ["" (reflection.reflection reflection.void)])]
- (in type.void)))
+ (in jvm.void)))
(def: (return^ type_vars)
(-> (List (Type Var)) (Parser (Type Return)))
@@ -683,7 +681,7 @@
(def: var^
(Parser (Type Var))
- (# <>.monad each type.var <code>.local_symbol))
+ (# <>.monad each jvm.var <code>.local_symbol))
(def: vars^
(Parser (List (Type Var)))
@@ -698,7 +696,7 @@
(<code>.form (<>.and (..valid_class_name (list))
(<>.some var^)))
))]
- (in (type.declaration name variables))))
+ (in (jvm.declaration name variables))))
(def: (class^ type_vars)
(-> (List (Type Var)) (Parser (Type Class)))
@@ -1203,7 +1201,7 @@
(def: $Object
(Type Class)
- (type.class "java.lang.Object" (list)))
+ (jvm.class "java.lang.Object" (list)))
(syntax: .public (class: [.let [! <>.monad]
im inheritance_modifier^
@@ -1222,7 +1220,7 @@
(list#each (method->parser class_vars fully_qualified_class_name))
(list#mix <>.either (<>.failure ""))))]]
(in (list (` ("jvm class"
- (~ (declaration$ (type.declaration full_class_name class_vars)))
+ (~ (declaration$ (jvm.declaration full_class_name class_vars)))
(~ (class$ super))
[(~+ (list#each class$ interfaces))]
(~ (inheritance_modifier$ im))
@@ -1237,7 +1235,7 @@
annotations ..annotations^
members (<>.some (..method_decl^ class_vars))])
(in (list (` ("jvm class interface"
- (~ (declaration$ (type.declaration full_class_name class_vars)))
+ (~ (declaration$ (jvm.declaration full_class_name class_vars)))
[(~+ (list#each class$ supers))]
[(~+ (list#each annotation$ annotations))]
(~+ (list#each method_decl$ members)))))))
@@ -1297,7 +1295,7 @@
{.#None}
(in (list (` (: (-> (.Primitive "java.lang.Object") (~ check_type))
- (.function ((~ g!_) (~ g!unchecked))
+ (function ((~ g!_) (~ g!unchecked))
(~ check_code))))))
))))
@@ -1349,13 +1347,13 @@
(do [! meta.monad]
[arg_inputs (monad.each !
(: (-> [Bit (Type Value)] (Meta [Bit Code]))
- (.function (_ [maybe? _])
+ (function (_ [maybe? _])
(with_symbols [arg_name]
(in [maybe? arg_name]))))
#import_member_args)
.let [input_jvm_types (list#each product.right #import_member_args)
arg_types (list#each (: (-> [Bit (Type Value)] Code)
- (.function (_ [maybe? arg])
+ (function (_ [maybe? arg])
(let [arg_type (value_type (value@ #import_member_mode commons) arg)]
(if maybe?
(` (Maybe (~ arg_type)))
@@ -1415,7 +1413,7 @@
{#AutoPrM}
(with_expansions [<special+>' (template.spliced <special+>)
<cond_cases> (template [<primitive> <pre> <post>]
- [(# type.equivalence = <primitive> unboxed)
+ [(# jvm.equivalence = <primitive> unboxed)
(with_expansions [<post>' (template.spliced <post>)]
[<primitive>
(` (.|> (~ raw) (~+ <pre>)))
@@ -1443,23 +1441,23 @@
(` (.|> (~ unboxed/boxed) (~+ post))))))]
[#1 with_automatic_input_conversion ..unbox
- [[type.boolean (list (` (.:as (.Primitive (~ (code.text box.boolean)))))) []]
- [type.byte (list (` (.:as (.Primitive (~ (code.text box.byte)))))) []]
- [type.short (list (` (.:as (.Primitive (~ (code.text box.short)))))) []]
- [type.int (list (` (.: (.Primitive (~ (code.text box.int)))))) []]
- [type.long (list (` (.:as (.Primitive (~ (code.text box.long)))))) []]
- [type.char (list (` (.:as (.Primitive (~ (code.text box.char)))))) []]
- [type.float (list (` (.:as (.Primitive (~ (code.text box.float)))))) []]
- [type.double (list (` (.:as (.Primitive (~ (code.text box.double)))))) []]]]
+ [[jvm.boolean (list (` (.:as (.Primitive (~ (code.text box.boolean)))))) []]
+ [jvm.byte (list (` (.:as (.Primitive (~ (code.text box.byte)))))) []]
+ [jvm.short (list (` (.:as (.Primitive (~ (code.text box.short)))))) []]
+ [jvm.int (list (` (.: (.Primitive (~ (code.text box.int)))))) []]
+ [jvm.long (list (` (.:as (.Primitive (~ (code.text box.long)))))) []]
+ [jvm.char (list (` (.:as (.Primitive (~ (code.text box.char)))))) []]
+ [jvm.float (list (` (.:as (.Primitive (~ (code.text box.float)))))) []]
+ [jvm.double (list (` (.:as (.Primitive (~ (code.text box.double)))))) []]]]
[#0 with_automatic_output_conversion ..box
- [[type.boolean (list) [(` (.: (.Primitive (~ (code.text box.boolean)))))]]
- [type.byte (list) [(` (.: (.Primitive (~ (code.text box.byte)))))]]
- [type.short (list) [(` (.: (.Primitive (~ (code.text box.short)))))]]
- [type.int (list) [(` (.: (.Primitive (~ (code.text box.int)))))]]
- [type.long (list) [(` (.: (.Primitive (~ (code.text box.long)))))]]
- [type.char (list) [(` (.: (.Primitive (~ (code.text box.char)))))]]
- [type.float (list) [(` (.: (.Primitive (~ (code.text box.float)))))]]
- [type.double (list) [(` (.: (.Primitive (~ (code.text box.double)))))]]]]
+ [[jvm.boolean (list) [(` (.: (.Primitive (~ (code.text box.boolean)))))]]
+ [jvm.byte (list) [(` (.: (.Primitive (~ (code.text box.byte)))))]]
+ [jvm.short (list) [(` (.: (.Primitive (~ (code.text box.short)))))]]
+ [jvm.int (list) [(` (.: (.Primitive (~ (code.text box.int)))))]]
+ [jvm.long (list) [(` (.: (.Primitive (~ (code.text box.long)))))]]
+ [jvm.char (list) [(` (.: (.Primitive (~ (code.text box.char)))))]]
+ [jvm.float (list) [(` (.: (.Primitive (~ (code.text box.float)))))]]
+ [jvm.double (list) [(` (.: (.Primitive (~ (code.text box.double)))))]]]]
)
(def: (un_quoted quoted)
@@ -1470,7 +1468,7 @@
(-> Primitive_Mode (List (Type Value)) (List [Bit Code]) (List Code))
(|> inputs
(list.zipped/2 classes)
- (list#each (.function (_ [class [maybe? input]])
+ (list#each (function (_ [class [maybe? input]])
(|> (if maybe?
(` (: (.Primitive (~ (code.text (..reflection class))))
((~! !!!) (~ (..un_quoted input)))))
@@ -1486,7 +1484,7 @@
(def: syntax_inputs
(-> (List Code) (List Code))
- (|>> (list#each (.function (_ name)
+ (|>> (list#each (function (_ name)
(list name (` (~! <code>.any)))))
list#conjoint))
@@ -1507,7 +1505,7 @@
(` (All ((~ g!_) (~+ =class_tvars))
(.Primitive (~ (code.text full_name)) [(~+ =class_tvars)]))))))
getter_interop (: (-> Text Code)
- (.function (_ name)
+ (function (_ name)
(let [getter_name (code.symbol ["" (..import_name import_format method_prefix name)])]
(` (def: (~ getter_name)
(~ enum_type)
@@ -1516,7 +1514,7 @@
{#ConstructorDecl [commons _]}
(do meta.monad
- [.let [classT (type.class full_name (list))
+ [.let [classT (jvm.class full_name (list))
def_name (code.symbol ["" (..import_name import_format method_prefix (value@ #import_member_alias commons))])
jvm_interop (|> [classT
(` ("jvm member invoke constructor"
@@ -1564,13 +1562,13 @@
[(~+ (list#each ..var$ (value@ #import_member_tvars commons)))]
(~+ (|> object_ast
(list#each ..un_quoted)
- (list.zipped/2 (list (type.class full_name (list))))
+ (list.zipped/2 (list (jvm.class full_name (list))))
(list#each (with_automatic_input_conversion (value@ #import_member_mode commons)))))
(~+ (|> (jvm_invoke_inputs (value@ #import_member_mode commons) input_jvm_types arg_function_inputs)
(list.zipped/2 input_jvm_types)
(list#each ..decorate_input))))))
jvm_interop (: Code
- (case (type.void? method_return)
+ (case (jvm.void? method_return)
{.#Left method_return}
(|> [method_return
callC]
@@ -1674,7 +1672,7 @@
(do [! meta.monad]
[kind (class_kind declaration)
=members (|> bundles
- (list#each (.function (_ [import_format members])
+ (list#each (function (_ [import_format members])
(list#each (|>> [import_format]) members)))
list.together
(monad.each ! (member_import$ class_type_vars kind declaration)))]
@@ -1688,19 +1686,19 @@
"jvm object cast"
"jvm conversion long-to-int"))]
(`` (cond (~~ (template [<primitive> <array_op>]
- [(# type.equivalence = <primitive> type)
+ [(# jvm.equivalence = <primitive> type)
(in (list (` (<array_op> (~ g!size)))))]
- [type.boolean "jvm array new boolean"]
- [type.byte "jvm array new byte"]
- [type.short "jvm array new short"]
- [type.int "jvm array new int"]
- [type.long "jvm array new long"]
- [type.float "jvm array new float"]
- [type.double "jvm array new double"]
- [type.char "jvm array new char"]))
+ [jvm.boolean "jvm array new boolean"]
+ [jvm.byte "jvm array new byte"]
+ [jvm.short "jvm array new short"]
+ [jvm.int "jvm array new int"]
+ [jvm.long "jvm array new long"]
+ [jvm.float "jvm array new float"]
+ [jvm.double "jvm array new double"]
+ [jvm.char "jvm array new char"]))
... else
- (in (list (` (: (~ (value_type {#ManualPrM} (type.array type)))
+ (in (list (` (: (~ (value_type {#ManualPrM} (jvm.array type)))
("jvm array new object" (~ g!size))))))))))
(exception: .public (cannot_convert_to_jvm_type [type .Type])
@@ -1710,7 +1708,7 @@
(with_expansions [<failure> (as_is (meta.failure (exception.error ..cannot_convert_to_jvm_type [type])))]
(def: (lux_type->jvm_type context type)
(-> Type_Context .Type (Meta (Type Value)))
- (if (lux_type#= .Any type)
+ (if (type#= .Any type)
(# meta.monad in $Object)
(case type
{.#Primitive name params}
@@ -1723,37 +1721,37 @@
_
<failure>)]
- [type.boolean]
- [type.byte]
- [type.short]
- [type.int]
- [type.long]
- [type.float]
- [type.double]
- [type.char]))
+ [jvm.boolean]
+ [jvm.byte]
+ [jvm.short]
+ [jvm.int]
+ [jvm.long]
+ [jvm.float]
+ [jvm.double]
+ [jvm.char]))
(~~ (template [<type>]
- [(text#= (..reflection (type.array <type>)) name)
+ [(text#= (..reflection (jvm.array <type>)) name)
(case params
{.#End}
- (# meta.monad in (type.array <type>))
+ (# meta.monad in (jvm.array <type>))
_
<failure>)]
- [type.boolean]
- [type.byte]
- [type.short]
- [type.int]
- [type.long]
- [type.float]
- [type.double]
- [type.char]))
+ [jvm.boolean]
+ [jvm.byte]
+ [jvm.short]
+ [jvm.int]
+ [jvm.long]
+ [jvm.float]
+ [jvm.double]
+ [jvm.char]))
(text#= array.type_name name)
(case params
{.#Item elementLT {.#End}}
- (# meta.monad each type.array
+ (# meta.monad each jvm.array
(lux_type->jvm_type context elementLT))
_
@@ -1763,17 +1761,17 @@
(case params
{.#End}
(let [[_ unprefixed] (maybe.trusted (text.split_by descriptor.array_prefix name))]
- (# meta.monad each type.array
+ (# meta.monad each jvm.array
(lux_type->jvm_type context {.#Primitive unprefixed (list)})))
_
<failure>)
... else
- (# meta.monad each (type.class name)
+ (# meta.monad each (jvm.class name)
(: (Meta (List (Type Parameter)))
(monad.each meta.monad
- (.function (_ paramLT)
+ (function (_ paramLT)
(do meta.monad
[paramJT (lux_type->jvm_type context paramLT)]
(case (parser.parameter? paramJT)
@@ -1785,7 +1783,7 @@
params)))))
{.#Apply A F}
- (case (lux_type.applied (list A) F)
+ (case (type.applied (list A) F)
{.#None}
<failure>
@@ -1814,19 +1812,19 @@
context meta.type_context
array_jvm_type (lux_type->jvm_type context array_type)
.let [g!extension (code.text (`` (cond (~~ (template [<primitive> <extension>]
- [(# type.equivalence =
- (type.array <primitive>)
+ [(# jvm.equivalence =
+ (jvm.array <primitive>)
array_jvm_type)
<extension>]
- [type.boolean "jvm array length boolean"]
- [type.byte "jvm array length byte"]
- [type.short "jvm array length short"]
- [type.int "jvm array length int"]
- [type.long "jvm array length long"]
- [type.float "jvm array length float"]
- [type.double "jvm array length double"]
- [type.char "jvm array length char"]))
+ [jvm.boolean "jvm array length boolean"]
+ [jvm.byte "jvm array length byte"]
+ [jvm.short "jvm array length short"]
+ [jvm.int "jvm array length int"]
+ [jvm.long "jvm array length long"]
+ [jvm.float "jvm array length float"]
+ [jvm.double "jvm array length double"]
+ [jvm.char "jvm array length char"]))
... else
"jvm array length object")))]]
@@ -1855,21 +1853,21 @@
"jvm object cast"
"jvm conversion long-to-int"))]]
(`` (cond (~~ (template [<primitive> <extension> <box>]
- [(# type.equivalence =
- (type.array <primitive>)
+ [(# jvm.equivalence =
+ (jvm.array <primitive>)
array_jvm_type)
(in (list (` (.|> (<extension> (~ g!idx) (~ array))
"jvm object cast"
(.: (.Primitive (~ (code.text <box>))))))))]
- [type.boolean "jvm array read boolean" box.boolean]
- [type.byte "jvm array read byte" box.byte]
- [type.short "jvm array read short" box.short]
- [type.int "jvm array read int" box.int]
- [type.long "jvm array read long" box.long]
- [type.float "jvm array read float" box.float]
- [type.double "jvm array read double" box.double]
- [type.char "jvm array read char" box.char]))
+ [jvm.boolean "jvm array read boolean" box.boolean]
+ [jvm.byte "jvm array read byte" box.byte]
+ [jvm.short "jvm array read short" box.short]
+ [jvm.int "jvm array read int" box.int]
+ [jvm.long "jvm array read long" box.long]
+ [jvm.float "jvm array read float" box.float]
+ [jvm.double "jvm array read double" box.double]
+ [jvm.char "jvm array read char" box.char]))
... else
(in (list (` ("jvm array read object" (~ g!idx) (~ array))))))))
@@ -1894,22 +1892,22 @@
"jvm object cast"
"jvm conversion long-to-int"))]]
(`` (cond (~~ (template [<primitive> <extension> <box>]
- [(# type.equivalence =
- (type.array <primitive>)
+ [(# jvm.equivalence =
+ (jvm.array <primitive>)
array_jvm_type)
(let [g!value (` (.|> (~ value)
(.:as (.Primitive (~ (code.text <box>))))
"jvm object cast"))]
(in (list (` (<extension> (~ g!idx) (~ g!value) (~ array))))))]
- [type.boolean "jvm array write boolean" box.boolean]
- [type.byte "jvm array write byte" box.byte]
- [type.short "jvm array write short" box.short]
- [type.int "jvm array write int" box.int]
- [type.long "jvm array write long" box.long]
- [type.float "jvm array write float" box.float]
- [type.double "jvm array write double" box.double]
- [type.char "jvm array write char" box.char]))
+ [jvm.boolean "jvm array write boolean" box.boolean]
+ [jvm.byte "jvm array write byte" box.byte]
+ [jvm.short "jvm array write short" box.short]
+ [jvm.int "jvm array write int" box.int]
+ [jvm.long "jvm array write long" box.long]
+ [jvm.float "jvm array write float" box.float]
+ [jvm.double "jvm array write double" box.double]
+ [jvm.char "jvm array write char" box.char]))
... else
(in (list (` ("jvm array write object" (~ g!idx) (~ value) (~ array))))))))
@@ -1967,96 +1965,3 @@
[as_char .Int ..long_to_char ..Long ..char_to_long ..Character of_char]
[as_float .Frac ..double_to_float ..Double ..float_to_double ..Float of_float]
)
-
-(type: (API of)
- (Record
- [#interface of
- #type Code
- #term Code]))
-
-(def: (api of)
- (All (_ of) (-> (Parser of) (Parser (API of))))
- (<code>.form
- ($_ <>.and
- of
- <code>.any
- <code>.any
- )))
-
-(type: Constant
- Text)
-
-(def: constant
- (Parser Constant)
- <code>.local_symbol)
-
-(type: Function
- (Record
- [#variables (List Text)
- #name Text
- #requirements (List [Text Code])]))
-
-(def: function
- (Parser Function)
- (<code>.form
- ($_ <>.and
- (<>.else (list) (<code>.tuple (<>.some <code>.local_symbol)))
- <code>.local_symbol
- (<code>.tuple (<>.some ($_ <>.and
- <code>.local_symbol
- <code>.any
- )))
- )))
-
-(type: Export
- (Variant
- {#Constant (API Constant)}
- {#Function (API Function)}))
-
-(def: export
- (Parser Export)
- ($_ <>.or
- (..api ..constant)
- (..api ..function)
- ))
-
-(syntax: .public (export: [api <code>.local_symbol
- exports (<>.many ..export)])
- (let [initialization (: (List (API Constant))
- (list.all (.function (_ it)
- (case it
- {#Constant it}
- {.#Some it}
-
- _
- {.#None}))
- exports))]
- (in (list (` (..class: "final" (~ (code.local_symbol api))
- (~+ (list#each (.function (_ it)
- (case it
- {#Constant [name type term]}
- (` ("public" "final" "static" (~ (code.local_symbol name)) (~ type)))
-
- {#Function [[variables name requirements] type term]}
- (` ("public" "strict" "static"
- [(~+ (list#each code.local_symbol variables))]
- ((~ (code.local_symbol name))
- [(~+ (|> requirements
- (list#each (.function (_ [name type])
- (list (code.local_symbol name)
- type)))
- list#conjoint))])
- (~ type)
- (~ term)))))
- exports))
- ... Useless constructor
- ("private" [] ((~' new) (~' self) []) [] [])
- ("public" "strict" "static" [] ((~' <clinit>) [])
- (~' void)
- [(~+ (list#each (.function (_ [name type term])
- (` ("jvm member put static"
- (~ (code.text api))
- (~ (code.text name))
- ("jvm object cast" (~ term)))))
- initialization))])
- ))))))
diff --git a/stdlib/source/library/lux/ffi.py.lux b/stdlib/source/library/lux/ffi.py.lux
index 6f6bc2b96..440f8f68b 100644
--- a/stdlib/source/library/lux/ffi.py.lux
+++ b/stdlib/source/library/lux/ffi.py.lux
@@ -1,27 +1,27 @@
(.using
- [library
- [lux "*"
- ["[0]" meta]
- ["@" target]
- [abstract
- [monad {"+" do}]]
- [control
- ["[0]" io]
- ["[0]" maybe]
- ["<>" parser
- ["<[0]>" code {"+" Parser}]]]
- [data
- ["[0]" product]
- ["[0]" text
- ["%" format]]
- [collection
- ["[0]" list ("[1]#[0]" functor mix)]]]
- [type
- abstract]
- [macro {"+" with_symbols}
- [syntax {"+" syntax:}]
- ["[0]" code]
- ["[0]" template]]]])
+ [library
+ [lux {"-" Alias}
+ ["@" target]
+ ["[0]" meta]
+ [abstract
+ [monad {"+" do}]]
+ [control
+ ["[0]" io]
+ ["[0]" maybe]
+ ["<>" parser
+ ["<[0]>" code {"+" Parser}]]]
+ [data
+ ["[0]" product]
+ ["[0]" text
+ ["%" format]]
+ [collection
+ ["[0]" list ("[1]#[0]" monad mix)]]]
+ [macro {"+" with_symbols}
+ [syntax {"+" syntax:}]
+ ["[0]" code]
+ ["[0]" template]]
+ [type
+ abstract]]])
(abstract: .public (Object brand) Any)
@@ -78,10 +78,31 @@
<code>.local_symbol
..noneable)))
+(type: Alias
+ (Maybe Text))
+
+(def: alias
+ (Parser Alias)
+ (<>.maybe (<>.after (<code>.this! (' "as")) <code>.local_symbol)))
+
+(type: Constant
+ [Text
+ Alias
+ Noneable])
+
+(def: constant
+ (Parser Constant)
+ (<code>.form
+ ($_ <>.and
+ <code>.local_symbol
+ ..alias
+ ..noneable
+ )))
+
(type: Common_Method
(Record
[#name Text
- #alias (Maybe Text)
+ #alias Alias
#inputs (List Noneable)
#io? Bit
#try? Bit
@@ -99,7 +120,7 @@
(Parser Common_Method)
($_ <>.and
<code>.local_symbol
- (<>.maybe (<>.after (<code>.this! (' "as")) <code>.local_symbol))
+ ..alias
(<code>.tuple (<>.some ..noneable))
(<>.parses? (<code>.this! (' "io")))
(<>.parses? (<code>.this! (' "try")))
@@ -157,23 +178,26 @@
(if ("python object none?" (~ g!temp))
{.#None}
{.#Some (~ g!temp)})))
- (` (let [(~ g!temp) (~ output)]
- (if (not ("python object none?" (~ g!temp)))
+ (` (.let [(~ g!temp) (~ output)]
+ (.if (.not ("python object none?" (~ g!temp)))
(~ g!temp)
(.panic! "None is an invalid value!"))))))
(type: Import
(Variant
{#Class [Text Text (List Member)]}
- {#Function Static_Method}))
+ {#Function Static_Method}
+ {#Constant Constant}))
(def: import
(Parser Import)
- (<>.or (<>.and <code>.local_symbol
- (<>.else ["" (list)]
- (<code>.tuple (<>.and <code>.text
- (<>.some member)))))
- (<code>.form ..common_method)))
+ ($_ <>.or
+ (<>.and <code>.local_symbol
+ (<>.else ["" (list)]
+ (<code>.tuple (<>.and <code>.text
+ (<>.some member)))))
+ (<code>.form ..common_method)
+ ..constant))
(def: (with_io with? without)
(-> Bit Code Code)
@@ -202,13 +226,13 @@
(def: (make_function g!method g!temp source inputsT io? try? outputT)
(-> Code Code Code (List Noneable) Bit Bit Noneable Code)
(let [g!inputs (input_variables inputsT)]
- (` (def: ((~ g!method)
- [(~+ (list#each product.right g!inputs))])
+ (` (.def: ((~ g!method)
+ [(~+ (list#each product.right g!inputs))])
(-> [(~+ (list#each noneable_type inputsT))]
(~ (|> (noneable_type outputT)
(try_type try?)
(io_type io?))))
- (:expected
+ (.:expected
(~ (<| (with_io io?)
(with_try try?)
(without_none g!temp outputT)
@@ -233,25 +257,25 @@
{.#Item head tail}
(list#mix (function (_ sub super)
(` ("python object get" (~ (code.text sub))
- (:as (..Object .Any) (~ super)))))
+ (.:as (..Object .Any) (~ super)))))
(` ("python import" (~ (code.text head))))
tail)
{.#End}
(` ("python import" (~ (code.text class)))))]
- (in (list& (` (type: (~ g!type)
- (..Object (Primitive (~ (code.text real_class))))))
+ (in (list& (` (.type: (~ g!type)
+ (..Object (.Primitive (~ (code.text real_class))))))
(list#each (function (_ member)
(case member
{#Constructor inputsT}
(let [g!inputs (input_variables inputsT)]
- (` (def: ((~ (qualify "new"))
- [(~+ (list#each product.right g!inputs))])
- (-> [(~+ (list#each noneable_type inputsT))]
- (~ g!type))
- (:expected
+ (` (.def: ((~ (qualify "new"))
+ [(~+ (list#each product.right g!inputs))])
+ (.-> [(~+ (list#each noneable_type inputsT))]
+ (~ g!type))
+ (.:expected
("python apply"
- (:as ..Function (~ imported))
+ (.:as ..Function (~ imported))
(~+ (list#each (with_none g!temp) g!inputs)))))))
{#Field [static? field fieldT]}
@@ -261,13 +285,13 @@
(list (` (.:as (~ (noneable_type fieldT))
("python object get" (~ (code.text field))
(:as (..Object .Any) (~ imported)))))))))
- (` (def: ((~ (qualify field))
- (~ g!object))
- (-> (~ g!type)
- (~ (noneable_type fieldT)))
- (:expected
+ (` (.def: ((~ (qualify field))
+ (~ g!object))
+ (.-> (~ g!type)
+ (~ (noneable_type fieldT)))
+ (.:expected
(~ (without_none g!temp fieldT (` ("python object get" (~ (code.text field))
- (:as (..Object .Any) (~ g!object))))))))))
+ (.:as (..Object .Any) (~ g!object))))))))))
{#Method method}
(case method
@@ -275,7 +299,7 @@
(..make_function (qualify (maybe.else method alias))
g!temp
(` ("python object get" (~ (code.text method))
- (:as (..Object .Any) (~ imported))))
+ (.:as (..Object .Any) (~ imported))))
inputsT
io?
try?
@@ -283,15 +307,15 @@
{#Virtual [method alias inputsT io? try? outputT]}
(let [g!inputs (input_variables inputsT)]
- (` (def: ((~ (qualify (maybe.else method alias)))
- [(~+ (list#each product.right g!inputs))]
- (~ g!object))
- (-> [(~+ (list#each noneable_type inputsT))]
- (~ g!type)
- (~ (|> (noneable_type outputT)
- (try_type try?)
- (io_type io?))))
- (:expected
+ (` (.def: ((~ (qualify (maybe.else method alias)))
+ [(~+ (list#each product.right g!inputs))]
+ (~ g!object))
+ (.-> [(~+ (list#each noneable_type inputsT))]
+ (~ g!type)
+ (~ (|> (noneable_type outputT)
+ (try_type try?)
+ (io_type io?))))
+ (.:expected
(~ (<| (with_io io?)
(with_try try?)
(without_none g!temp outputT)
@@ -309,6 +333,13 @@
io?
try?
outputT)))
+
+ {#Constant [name alias :constant:]}
+ (in (list (` (.def: (~ (code.local_symbol (maybe.else name alias)))
+ (~ (noneable_type :constant:))
+ (.:expected
+ (~ (without_none g!temp :constant:
+ (` ("python constant" (~ (code.text name)))))))))))
)))
(template: .public (lambda <inputs> <output>)
diff --git a/stdlib/source/library/lux/ffi/export.js.lux b/stdlib/source/library/lux/ffi/export.js.lux
new file mode 100644
index 000000000..a73437f72
--- /dev/null
+++ b/stdlib/source/library/lux/ffi/export.js.lux
@@ -0,0 +1,96 @@
+(.using
+ [library
+ [lux "*"
+ [extension {"+" directive:}]
+ ["[0]" meta]
+ ["[0]" static]
+ [abstract
+ ["[0]" monad {"+" do}]]
+ [control
+ ["<>" parser
+ ["<[0]>" code]]]
+ [data
+ [text
+ ["%" format]]
+ [collection
+ ["[0]" list ("[1]#[0]" monad mix)]
+ ["[0]" set]]]
+ ["[0]" macro
+ [syntax {"+" syntax:}]
+ ["[0]" code]]
+ [math
+ ["[0]" random]]
+ [target
+ ["/" js]]
+ [tool
+ [compiler
+ ["[0]" phase]
+ [meta
+ [cache
+ ["[0]" dependency "_"
+ ["[1]" artifact]]]]
+ [language
+ [lux
+ ["[0]" generation]
+ ["[0]" directive]
+ [analysis
+ ["[0]" type]]]]]]]])
+
+(def: definition
+ (-> Code (Meta [Text Code]))
+ (|>> (list)
+ (<code>.result (<| <code>.form
+ (<>.after (<code>.text! "lux def"))
+ (<>.before <code>.any)
+ ($_ <>.and
+ <code>.local_symbol
+ <code>.any)))
+ meta.lifted))
+
+(with_expansions [<extension> (static.random (|>> %.nat (%.format "lua export ") code.text)
+ random.nat)]
+ (directive: (<extension> self phase archive [name <code>.text
+ term <code>.any])
+ (do [! phase.monad]
+ [next directive.analysis
+ [_ term] (<| directive.lifted_analysis
+ type.inferring
+ (next archive term))
+
+ next directive.synthesis
+ term (directive.lifted_synthesis
+ (next archive term))
+
+ dependencies (directive.lifted_generation
+ (dependency.dependencies archive term))
+
+ next directive.generation
+ [interim_artifacts term] (directive.lifted_generation
+ (generation.with_interim_artifacts archive
+ (next archive term)))
+
+ _ (directive.lifted_generation
+ (do !
+ [@self (generation.learn_custom name (list#mix set.has dependencies interim_artifacts))
+ .let [$module (/.var "module")
+ $exports (/.the "exports" $module)
+ definition (/.define (/.var name) term)
+ export (/.when (/.not (/.= (/.string "undefined") (/.type_of $module)))
+ (/.set (/.the name $exports) (/.var name)))
+ code ($_ /.then
+ definition
+ export)]
+ _ (generation.execute! definition)
+ _ (generation.save! @self {.#None} code)]
+ (generation.log! (%.format "Export " (%.text name)))))]
+ (in directive.no_requirements)))
+
+ (syntax: .public (export: [exports (<>.many <code>.any)])
+ (let [! meta.monad]
+ (|> exports
+ (monad.each ! macro.expansion)
+ (# ! each (|>> list#conjoint
+ (monad.each ! ..definition)))
+ (# ! conjoint)
+ (# ! each (list#each (function (_ [name term])
+ (` (<extension> (~ (code.text name)) (~ term))))))))))
diff --git a/stdlib/source/library/lux/ffi/export.jvm.lux b/stdlib/source/library/lux/ffi/export.jvm.lux
new file mode 100644
index 000000000..7473ae233
--- /dev/null
+++ b/stdlib/source/library/lux/ffi/export.jvm.lux
@@ -0,0 +1,106 @@
+(.using
+ [library
+ [lux {"-" function}
+ [control
+ ["<>" parser
+ ["<[0]>" code {"+" Parser}]]]
+ [data
+ [collection
+ ["[0]" list ("[1]#[0]" monad)]]]
+ [macro
+ [syntax {"+" syntax:}]
+ ["[0]" code]]]]
+ ["[0]" //])
+
+(type: (API of)
+ (Record
+ [#interface of
+ #type Code
+ #term Code]))
+
+(def: (api of)
+ (All (_ of) (-> (Parser of) (Parser (API of))))
+ (<code>.form
+ ($_ <>.and
+ of
+ <code>.any
+ <code>.any
+ )))
+
+(type: Constant
+ Text)
+
+(def: constant
+ (Parser Constant)
+ <code>.local_symbol)
+
+(type: Function
+ (Record
+ [#variables (List Text)
+ #name Text
+ #requirements (List [Text Code])]))
+
+(def: function
+ (Parser Function)
+ (<code>.form
+ ($_ <>.and
+ (<>.else (list) (<code>.tuple (<>.some <code>.local_symbol)))
+ <code>.local_symbol
+ (<code>.tuple (<>.some ($_ <>.and
+ <code>.local_symbol
+ <code>.any
+ )))
+ )))
+
+(type: Export
+ (Variant
+ {#Constant (API Constant)}
+ {#Function (API Function)}))
+
+(def: export
+ (Parser Export)
+ ($_ <>.or
+ (..api ..constant)
+ (..api ..function)
+ ))
+
+(syntax: .public (export: [api <code>.local_symbol
+ exports (<>.many ..export)])
+ (let [initialization (: (List (API Constant))
+ (list.all (.function (_ it)
+ (case it
+ {#Constant it}
+ {.#Some it}
+
+ _
+ {.#None}))
+ exports))]
+ (in (list (` (//.class: "final" (~ (code.local_symbol api))
+ (~+ (list#each (.function (_ it)
+ (case it
+ {#Constant [name type term]}
+ (` ("public" "final" "static" (~ (code.local_symbol name)) (~ type)))
+
+ {#Function [[variables name requirements] type term]}
+ (` ("public" "strict" "static"
+ [(~+ (list#each code.local_symbol variables))]
+ ((~ (code.local_symbol name))
+ [(~+ (|> requirements
+ (list#each (.function (_ [name type])
+ (list (code.local_symbol name)
+ type)))
+ list#conjoint))])
+ (~ type)
+ (~ term)))))
+ exports))
+ ... Useless constructor
+ ("private" [] ((~' new) (~' self) []) [] [])
+ ("public" "strict" "static" [] ((~' <clinit>) [])
+ (~' void)
+ [(~+ (list#each (.function (_ [name type term])
+ (` ("jvm member put static"
+ (~ (code.text api))
+ (~ (code.text name))
+ ("jvm object cast" (~ term)))))
+ initialization))])
+ ))))))
diff --git a/stdlib/source/library/lux/ffi/export.lua.lux b/stdlib/source/library/lux/ffi/export.lua.lux
new file mode 100644
index 000000000..1c53e9153
--- /dev/null
+++ b/stdlib/source/library/lux/ffi/export.lua.lux
@@ -0,0 +1,112 @@
+(.using
+ [library
+ [lux "*"
+ [extension {"+" directive:}]
+ ["[0]" meta]
+ ["[0]" static]
+ [abstract
+ ["[0]" monad {"+" do}]]
+ [control
+ ["<>" parser
+ ["<[0]>" code]]]
+ [data
+ [text
+ ["%" format]]
+ [collection
+ ["[0]" list ("[1]#[0]" monad mix)]
+ ["[0]" set]]]
+ ["[0]" macro
+ [syntax {"+" syntax:}]
+ ["[0]" code]]
+ [math
+ ["[0]" random]]
+ [target
+ ["/" lua]]
+ [tool
+ [compiler
+ ["[0]" phase]
+ [meta
+ [cache
+ ["[0]" dependency "_"
+ ["[1]" artifact]]]]
+ [language
+ [lux
+ ["[0]" generation]
+ ["[0]" directive]
+ [analysis
+ ["[0]" type]]]]]]]])
+
+(def: definition
+ (-> Code (Meta [Text Code]))
+ (|>> (list)
+ (<code>.result (<| <code>.form
+ (<>.after (<code>.text! "lux def"))
+ (<>.before <code>.any)
+ ($_ <>.and
+ <code>.local_symbol
+ <code>.any)))
+ meta.lifted))
+
+... [15.2 – Privacy](https://www.lua.org/pil/15.2.html)
+... [15.3 – Packages and Files](https://www.lua.org/pil/15.3.html)
+... [15.4 – Using the Global Table](https://www.lua.org/pil/15.4.html)
+
+(with_expansions [<extension> (static.random (|>> %.nat (%.format "lua export ") code.text)
+ random.nat)]
+ (directive: (<extension> self phase archive [name <code>.text
+ term <code>.any])
+ (do [! phase.monad]
+ [next directive.analysis
+ [_ term] (<| directive.lifted_analysis
+ type.inferring
+ (next archive term))
+
+ next directive.synthesis
+ term (directive.lifted_synthesis
+ (next archive term))
+
+ dependencies (directive.lifted_generation
+ (dependency.dependencies archive term))
+
+ next directive.generation
+ [interim_artifacts term] (directive.lifted_generation
+ (generation.with_interim_artifacts archive
+ (next archive term)))
+
+ _ (directive.lifted_generation
+ (do !
+ [@self (generation.learn_custom name (list#mix set.has dependencies interim_artifacts))
+ .let [$exports (/.var "_REQUIREDNAME")
+ $global (/.var "_G")
+ exporting? (/.not (/.= /.nil $exports))
+ no_exports? (/.= /.nil (/.item $exports $global))
+ initialize_exports! (/.set (list (/.item $exports $global)) (/.table (list)))
+ export_definition! (/.set (|> $global
+ (/.item $exports)
+ (/.item (/.string name))
+ (list))
+ (/.var name))
+ export! (/.when exporting?
+ ($_ /.then
+ (/.when no_exports?
+ initialize_exports!)
+ export_definition!
+ ))]
+ _ (generation.execute! ($_ /.then
+ (/.set (list (/.var name)) term)
+ export!))
+ _ (generation.save! @self {.#None} ($_ /.then
+ (/.local/1 (/.var name) term)
+ export!))]
+ (generation.log! (%.format "Export " (%.text name)))))]
+ (in directive.no_requirements)))
+
+ (syntax: .public (export: [exports (<>.many <code>.any)])
+ (let [! meta.monad]
+ (|> exports
+ (monad.each ! macro.expansion)
+ (# ! each (|>> list#conjoint
+ (monad.each ! ..definition)))
+ (# ! conjoint)
+ (# ! each (list#each (function (_ [name term])
+ (` (<extension> (~ (code.text name)) (~ term))))))))))
diff --git a/stdlib/source/library/lux/ffi/export.py.lux b/stdlib/source/library/lux/ffi/export.py.lux
new file mode 100644
index 000000000..4d820443e
--- /dev/null
+++ b/stdlib/source/library/lux/ffi/export.py.lux
@@ -0,0 +1,89 @@
+(.using
+ [library
+ [lux "*"
+ [extension {"+" directive:}]
+ ["[0]" meta]
+ ["[0]" static]
+ [abstract
+ ["[0]" monad {"+" do}]]
+ [control
+ ["<>" parser
+ ["<[0]>" code]]]
+ [data
+ [text
+ ["%" format]]
+ [collection
+ ["[0]" list ("[1]#[0]" monad mix)]
+ ["[0]" set]]]
+ ["[0]" macro
+ [syntax {"+" syntax:}]
+ ["[0]" code]]
+ [math
+ ["[0]" random]]
+ [target
+ ["/" python]]
+ [tool
+ [compiler
+ ["[0]" phase]
+ [meta
+ [cache
+ ["[0]" dependency "_"
+ ["[1]" artifact]]]]
+ [language
+ [lux
+ ["[0]" generation]
+ ["[0]" directive]
+ [analysis
+ ["[0]" type]]]]]]]])
+
+(def: definition
+ (-> Code (Meta [Text Code]))
+ (|>> (list)
+ (<code>.result (<| <code>.form
+ (<>.after (<code>.text! "lux def"))
+ (<>.before <code>.any)
+ ($_ <>.and
+ <code>.local_symbol
+ <code>.any)))
+ meta.lifted))
+
+(with_expansions [<extension> (static.random (|>> %.nat (%.format "python export ") code.text)
+ random.nat)]
+ (directive: (<extension> self phase archive [name <code>.text
+ term <code>.any])
+ (do [! phase.monad]
+ [next directive.analysis
+ [_ term] (<| directive.lifted_analysis
+ type.inferring
+ (next archive term))
+
+ next directive.synthesis
+ term (directive.lifted_synthesis
+ (next archive term))
+
+ dependencies (directive.lifted_generation
+ (dependency.dependencies archive term))
+
+ next directive.generation
+ [interim_artifacts term] (directive.lifted_generation
+ (generation.with_interim_artifacts archive
+ (next archive term)))
+
+ _ (directive.lifted_generation
+ (do !
+ [@self (generation.learn_custom name (list#mix set.has dependencies interim_artifacts))
+ .let [code (/.set (list (/.item (/.string name) /.globals/0)) term)]
+ _ (generation.execute! code)
+ _ (generation.save! @self {.#None} code)]
+ (generation.log! (%.format "Export " (%.text name)))))]
+ (in directive.no_requirements)))
+
+ (syntax: .public (export: [exports (<>.many <code>.any)])
+ (let [! meta.monad]
+ (|> exports
+ (monad.each ! macro.expansion)
+ (# ! each (|>> list#conjoint
+ (monad.each ! ..definition)))
+ (# ! conjoint)
+ (# ! each (list#each (function (_ [name term])
+ (` (<extension> (~ (code.text name)) (~ term))))))))))
diff --git a/stdlib/source/library/lux/ffi/export.rb.lux b/stdlib/source/library/lux/ffi/export.rb.lux
new file mode 100644
index 000000000..51aab7008
--- /dev/null
+++ b/stdlib/source/library/lux/ffi/export.rb.lux
@@ -0,0 +1,144 @@
+(.using
+ [library
+ [lux {"-" global}
+ [extension {"+" directive:}]
+ ["[0]" meta]
+ ["[0]" static]
+ ["[0]" type]
+ [abstract
+ ["[0]" monad {"+" do}]]
+ [control
+ ["<>" parser
+ ["<[0]>" code]
+ ["<[0]>" text {"+" Parser}]]]
+ [data
+ [text
+ ["%" format]]
+ [collection
+ ["[0]" list ("[1]#[0]" monad mix)]
+ ["[0]" set]]]
+ ["[0]" macro
+ [syntax {"+" syntax:}]
+ ["[0]" code]]
+ [math
+ ["[0]" random]]
+ [target
+ ["/" ruby]]
+ [tool
+ [compiler
+ ["[0]" phase]
+ [meta
+ [cache
+ ["[0]" dependency "_"
+ ["[1]" artifact]]]]
+ [language
+ [lux
+ ["[0]" generation]
+ ["[0]" directive]
+ ["[0]" analysis "_"
+ ["[1]" type]]]]]]]])
+
+(def: upper! (<text>.one_of! "ABCDEFGHIJKLMNOPQRSTUVWXYZ"))
+(def: lower! (<text>.one_of! "abcdefghijklmnopqrstuvwxyz"))
+(def: decimal! (<text>.one_of! "0123456789"))
+(def: sigil! (<text>.one_of! "_"))
+
+(def: tail!
+ ($_ <>.either
+ ..upper!
+ ..lower!
+ ..decimal!
+ ..sigil!
+ ))
+
+(template [<name> <head>]
+ [(def: <name>
+ (Parser Text)
+ (<| <text>.slice
+ (<text>.and! <head>)
+ (<text>.some! ..tail!)))]
+
+ [method ..lower!]
+ [global (<text>.one_of! "$")]
+ [constant ..upper!]
+ )
+
+(type: Name
+ (Variant
+ {#Method Text}
+ {#Global Text}))
+
+(def: name
+ (Parser Name)
+ (<>.or ..method
+ (<>.either ..global
+ ..constant)))
+
+(def: definition
+ (-> Code (Meta [Name Code]))
+ (|>> (list)
+ (<code>.result (<| <code>.form
+ (<>.after (<code>.text! "lux def"))
+ (<>.before <code>.any)
+ ($_ <>.and
+ (<text>.then ..name <code>.local_symbol)
+ <code>.any)))
+ meta.lifted))
+
+(with_expansions [<extension> (static.random (|>> %.nat (%.format "ruby export ") code.text)
+ random.nat)]
+ (directive: (<extension> self phase archive [global? <code>.bit
+ name <code>.text
+ term <code>.any])
+ (do [! phase.monad]
+ [next directive.analysis
+ [type term] (<| directive.lifted_analysis
+ analysis.inferring
+ (next archive term))
+
+ next directive.synthesis
+ term (directive.lifted_synthesis
+ (next archive term))
+
+ dependencies (directive.lifted_generation
+ (dependency.dependencies archive term))
+
+ next directive.generation
+ [interim_artifacts term] (directive.lifted_generation
+ (generation.with_interim_artifacts archive
+ (next archive term)))
+
+ _ (directive.lifted_generation
+ (do !
+ [@self (generation.learn_custom name (list#mix set.has dependencies interim_artifacts))
+ .let [[:input:/* :output:] (type.flat_function type)
+ code (if global?
+ (/.set (list (/.manual name)) term)
+ (case :input:/*
+ {.#End}
+ (/.function (/.manual name) (list)
+ (/.return term))
+
+ _
+ (/.statement (/.apply/* (list (/.string name) term) {.#None}
+ (/.manual "define_method")))))]
+ _ (generation.execute! code)
+ _ (generation.save! @self {.#None} code)]
+ (generation.log! (%.format "Export " (%.text name)))))]
+ (in directive.no_requirements)))
+
+ (syntax: .public (export: [exports (<>.many <code>.any)])
+ (let [! meta.monad]
+ (|> exports
+ (monad.each ! macro.expansion)
+ (# ! each (|>> list#conjoint
+ (monad.each ! ..definition)))
+ (# ! conjoint)
+ (# ! each (list#each (function (_ [name term])
+ (` (<extension> (~+ (case name
+ {#Method name}
+ (list (code.bit #0) (code.text name))
+
+ {#Global name}
+ (list (code.bit #1) (code.text name))))
+ (~ term))))))))))
diff --git a/stdlib/source/library/lux/static.lux b/stdlib/source/library/lux/static.lux
index 6de030bee..e8d213dd8 100644
--- a/stdlib/source/library/lux/static.lux
+++ b/stdlib/source/library/lux/static.lux
@@ -1,6 +1,6 @@
(.using
[library
- [lux {"-" nat int rev}
+ [lux {"-" nat int rev if cond}
["[0]" meta]
[abstract
[monad {"+" do}]]
@@ -9,7 +9,7 @@
["<[0]>" code]]]
[data
[collection
- ["[0]" list ("[1]#[0]" functor)]]]
+ ["[0]" list ("[1]#[0]" functor mix)]]]
[macro
[syntax {"+" syntax:}]
["[0]" code]]
@@ -99,3 +99,21 @@
.let [[_ result] (random.result (random.pcg_32 [..pcg_32_magic_inc seed])
random)]]
(in (list#each format result)))))
+
+(syntax: .public (if [test <code>.any
+ then <code>.any
+ else <code>.any])
+ (do meta.monad
+ [test (meta.eval .Bit test)]
+ (in (list (.if (:as .Bit test)
+ then
+ else)))))
+
+(syntax: .public (cond [test,then/* (<>.some (<>.and <code>.any <code>.any))
+ else <code>.any])
+ (in (list (list#mix (function (_ [test then] else)
+ (` (..if (~ test)
+ (~ then)
+ (~ else))))
+ else
+ (list.reversed test,then/*)))))
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/directive/lux.lux b/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/directive/lux.lux
index 241b28a2b..889d400b0 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/directive/lux.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/directive/lux.lux
@@ -72,10 +72,10 @@
{try.#Failure error}
(phase.except ///.invalid_syntax [extension_name %.code inputs]))))
-(def: (context [module_id artifact_id])
+(def: (context [@module @artifact])
(-> unit.ID unit.ID)
... TODO: Find a better way that doesn't rely on clever tricks.
- [module_id (n.- (++ artifact_id) 0)])
+ [@module (n.- (++ @artifact) 0)])
... TODO: Inline "evaluate!'" into "evaluate!" ASAP
(def: (evaluate!' archive generate code//type codeS)
@@ -90,8 +90,8 @@
[module /////generation.module
id /////generation.next
codeG (generate archive codeS)
- module_id (/////generation.module_id module archive)
- codeV (/////generation.evaluate! (..context [module_id id]) [{.#None} codeG])]
+ @module (/////generation.module_id module archive)
+ codeV (/////generation.evaluate! (..context [@module id]) [{.#None} codeG])]
(in [code//type codeG codeV]))))
(def: .public (evaluate! archive type codeC)
@@ -133,9 +133,9 @@
_
{.#None})]
- module_id (phase.lifted (archive.id module archive))
+ @module (phase.lifted (archive.id module archive))
@self (/////generation.learn [name @abstraction] false (list#mix set.has dependencies interim_artifacts))
- [target_name value directive] (/////generation.define! [module_id @self] {.#None} [(maybe#each product.right @abstraction) codeG])
+ [target_name value directive] (/////generation.define! [@module @self] {.#None} [(maybe#each product.right @abstraction) codeG])
_ (/////generation.save! @self {.#None} directive)]
(in [code//type codeG value]))))
@@ -186,9 +186,9 @@
[dependencies (cache/artifact.dependencies archive codeS)
[interim_artifacts codeG] (/////generation.with_interim_artifacts archive
(generate archive codeS))
- module_id (phase.lifted (archive.id current_module archive))
+ @module (phase.lifted (archive.id current_module archive))
@self (<learn> extension (list#mix set.has dependencies interim_artifacts))
- [target_name value directive] (/////generation.define! [module_id @self] {.#None} [{.#None} codeG])
+ [target_name value directive] (/////generation.define! [@module @self] {.#None} [{.#None} codeG])
_ (/////generation.save! @self {.#None} directive)]
(in [codeG value])))))
@@ -499,7 +499,7 @@
(/////directive.lifted_synthesis
(synthesize archive programA))))
-(def: (define_program archive module_id generate program programS)
+(def: (define_program archive @module generate program programS)
(All (_ anchor expression directive output)
(-> Archive
module.ID
@@ -512,7 +512,7 @@
[interim_artifacts programG] (/////generation.with_interim_artifacts archive
(generate archive programS))
@self (/////generation.learn [/////program.name {.#None}] true (list#mix set.has dependencies interim_artifacts))]
- (/////generation.save! @self {.#None} (program [module_id @self] programG))))
+ (/////generation.save! @self {.#None} (program [@module @self] programG))))
(def: (def::program program)
(All (_ anchor expression directive)
@@ -528,9 +528,9 @@
programS (prepare_program archive analyse synthesize programC)
current_module (/////directive.lifted_analysis
(///.lifted meta.current_module_name))
- module_id (phase.lifted (archive.id current_module archive))
+ @module (phase.lifted (archive.id current_module archive))
_ (/////directive.lifted_generation
- (define_program archive module_id generate program programS))]
+ (define_program archive @module generate program programS))]
(in /////directive.no_requirements))
_
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/generation/python/host.lux b/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/generation/python/host.lux
index dff13d37f..fa18710f9 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/generation/python/host.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/phase/extension/generation/python/host.lux
@@ -1,34 +1,36 @@
(.using
- [library
- [lux "*"
- [abstract
- ["[0]" monad {"+" do}]]
- [control
- ["[0]" function]
- ["<>" parser
- ["<s>" synthesis {"+" Parser}]]]
- [data
- [collection
- ["[0]" dictionary]
- ["[0]" list]]]
- [target
- ["_" python {"+" Expression SVar}]]]]
- ["[0]" // "_"
- ["[1][0]" common {"+" custom}]
- ["//[1]" /// "_"
- ["/" bundle]
+ [library
+ [lux "*"
+ [abstract
+ ["[0]" monad {"+" do}]]
+ [control
+ ["[0]" function]
+ ["<>" parser
+ ["<s>" synthesis {"+" Parser}]]]
+ [data
+ ["[0]" text
+ ["%" format]]
+ [collection
+ ["[0]" dictionary]
+ ["[0]" list]]]
+ [target
+ ["_" python {"+" Expression SVar}]]]]
+ ["[0]" // "_"
+ ["[1][0]" common {"+" custom}]
+ ["//[1]" /// "_"
+ ["/" bundle]
+ ["/[1]" // "_"
+ ["[0]" extension]
+ [generation
+ [extension {"+" Nullary Unary Binary Trinary
+ nullary unary binary trinary}]
+ ["//" python "_"
+ ["[1][0]" runtime {"+" Operation Phase Handler Bundle
+ with_vars}]]]
["/[1]" // "_"
- ["[0]" extension]
- [generation
- [extension {"+" Nullary Unary Binary Trinary
- nullary unary binary trinary}]
- ["//" python "_"
- ["[1][0]" runtime {"+" Operation Phase Handler Bundle
- with_vars}]]]
- ["/[1]" // "_"
- ["[0]" generation]
- ["//[1]" /// "_"
- ["[1][0]" phase]]]]]])
+ ["[0]" generation]
+ ["//[1]" /// "_"
+ ["[1][0]" phase]]]]]])
(def: (array::new size)
(Unary (Expression Any))
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/case.lux b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/case.lux
index b2d828de3..4a5ee59f0 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/case.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/case.lux
@@ -1,36 +1,38 @@
(.using
- [library
- [lux {"-" case exec let if}
- [abstract
- ["[0]" monad {"+" do}]]
- [control
- ["[0]" maybe]]
- [data
- ["[0]" text]
- [collection
- ["[0]" list ("[1]#[0]" functor mix)]]]
- [math
- [number
- ["n" nat]]]
- [target
- ["_" js {"+" Expression Computation Var Statement}]]]]
- ["[0]" // "_"
- ["[1][0]" runtime {"+" Operation Phase Phase! Generator Generator!}]
+ [library
+ [lux {"-" case exec let if}
+ [abstract
+ ["[0]" monad {"+" do}]]
+ [control
+ ["[0]" maybe]]
+ [data
+ ["[0]" text]
+ [collection
+ ["[0]" list ("[1]#[0]" functor mix)]]]
+ [math
+ [number
+ ["n" nat]]]
+ [target
+ ["_" js {"+" Expression Computation Var Statement}]]]]
+ ["[0]" // "_"
+ ["[1][0]" runtime {"+" Operation Phase Phase! Generator Generator!}]
+ ["[1][0]" reference]
+ ["[1][0]" primitive]
+ ["/[1]" // "_"
["[1][0]" reference]
- ["[1][0]" primitive]
["/[1]" // "_"
- ["[1][0]" reference]
+ ["[1][0]" synthesis "_"
+ ["[1]/[0]" case]]
["/[1]" // "_"
- ["[1][0]" synthesis "_"
- ["[1]/[0]" case]]
- ["/[1]" // "_"
- ["[1][0]" synthesis {"+" Member Synthesis Path}]
- ["//[1]" /// "_"
- [reference
- [variable {"+" Register}]]
- ["[1][0]" phase ("[1]#[0]" monad)]
- [meta
- [archive {"+" Archive}]]]]]]])
+ ["[1][0]" synthesis {"+" Synthesis Path}
+ [access
+ ["[0]" member {"+" Member}]]]
+ ["//[1]" /// "_"
+ [reference
+ [variable {"+" Register}]]
+ ["[1][0]" phase ("[1]#[0]" monad)]
+ [meta
+ [archive {"+" Archive}]]]]]]])
(def: .public register
(-> Register Var)
@@ -95,12 +97,9 @@
(do ///////phase.monad
[valueO (expression archive valueS)]
(in (list#mix (function (_ side source)
- (.let [method (.case side
- (^template [<side> <accessor>]
- [{<side> lefts}
- (<accessor> (_.i32 (.int lefts)))])
- ([.#Left //runtime.tuple//left]
- [.#Right //runtime.tuple//right]))]
+ (.let [method (.if (value@ member.#right? side)
+ (//runtime.tuple//right (_.i32 (.int (value@ member.#lefts side))))
+ (//runtime.tuple//left (_.i32 (.int (value@ member.#lefts side)))))]
(method source)))
valueO
(list.reversed pathP)))))
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/function.lux b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/function.lux
index 5461530f7..a3fa9317d 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/function.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/function.lux
@@ -30,7 +30,8 @@
[archive
["[0]" unit]]
["[0]" cache "_"
- ["[1]" artifact]]]]]]])
+ [dependency
+ ["[1]" artifact]]]]]]]])
(def: .public (apply expression archive [functionS argsS+])
(Generator (Reification Synthesis))
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/runtime.lux b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/runtime.lux
index 26f54c884..0f8cbef41 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/runtime.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/js/runtime.lux
@@ -24,12 +24,7 @@
[number {"+" hex}
["[0]" i64]]]
[target
- ["_" js {"+" Expression Var Computation Statement}]]
- [tool
- [compiler
- [language
- [lux
- ["$" version]]]]]]]
+ ["_" js {"+" Expression Var Computation Statement}]]]]
["[0]" /// "_"
["[1][0]" reference]
["//[1]" /// "_"
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/lua/case.lux b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/lua/case.lux
index dfb7908e7..1ad5f6df6 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/lua/case.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/lua/case.lux
@@ -21,7 +21,9 @@
["[1][0]" synthesis "_"
["[1]/[0]" case]]
["/[1]" // "_"
- ["[1][0]" synthesis {"+" Member Synthesis Path}]
+ ["[1][0]" synthesis {"+" Synthesis Path}
+ [access
+ ["[0]" member {"+" Member}]]]
["[1][0]" generation]
["//[1]" /// "_"
[reference
@@ -81,12 +83,9 @@
(do ///////phase.monad
[valueO (expression archive valueS)]
(in (list#mix (function (_ side source)
- (.let [method (.case side
- (^template [<side> <accessor>]
- [{<side> lefts}
- (<accessor> (_.int (.int lefts)))])
- ([.#Left //runtime.tuple//left]
- [.#Right //runtime.tuple//right]))]
+ (.let [method (.if (value@ member.#right? side)
+ (//runtime.tuple//right (_.int (.int (value@ member.#lefts side))))
+ (//runtime.tuple//left (_.int (.int (value@ member.#lefts side)))))]
(method source)))
valueO
(list.reversed pathP)))))
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/ruby/case.lux b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/ruby/case.lux
index f78fb404b..ec725005a 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/ruby/case.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/phase/generation/ruby/case.lux
@@ -29,7 +29,8 @@
["/[1]" // "_"
["[1][0]" generation]
["[1][0]" synthesis {"+" Synthesis Path}
- ["[0]" member {"+" Member}]]
+ [access
+ ["[0]" member {"+" Member}]]]
["//[1]" /// "_"
[reference
["[1][0]" variable {"+" Register}]]
diff --git a/stdlib/source/library/lux/tool/compiler/language/lux/synthesis/simple.lux b/stdlib/source/library/lux/tool/compiler/language/lux/synthesis/simple.lux
index dbf435a6d..bd9463555 100644
--- a/stdlib/source/library/lux/tool/compiler/language/lux/synthesis/simple.lux
+++ b/stdlib/source/library/lux/tool/compiler/language/lux/synthesis/simple.lux
@@ -12,7 +12,7 @@
["%" format]]]
[math
[number
- ["[0]" i64]
+ ["[0]" i64 ("[1]#[0]" equivalence)]
["n" nat]
["i" int]
["f" frac]]]]])
@@ -20,7 +20,7 @@
(type: .public Simple
(Variant
{#Bit Bit}
- {#I64 (I64 Any)}
+ {#I64 I64}
{#F64 Frac}
{#Text Text}))
@@ -50,7 +50,7 @@
[#Text text#= %.text])
[{#I64 reference'} {#I64 sample'}]
- (i.= (.int reference') (.int sample'))
+ (i64#= reference' sample')
_
false)))
diff --git a/stdlib/source/library/lux/tool/compiler/phase.lux b/stdlib/source/library/lux/tool/compiler/phase.lux
index a52f8b796..e09552d2c 100644
--- a/stdlib/source/library/lux/tool/compiler/phase.lux
+++ b/stdlib/source/library/lux/tool/compiler/phase.lux
@@ -1,7 +1,6 @@
(.using
[library
[lux "*"
- ["[0]" debug]
[abstract
[functor {"+" Functor}]
[monad {"+" Monad do}]]
diff --git a/stdlib/source/library/lux/world/file.lux b/stdlib/source/library/lux/world/file.lux
index 2f1d82a31..606cadc3f 100644
--- a/stdlib/source/library/lux/world/file.lux
+++ b/stdlib/source/library/lux/world/file.lux
@@ -306,7 +306,8 @@
["[1]::[0]"
("static" from [Binary] ..Buffer)])
- (ffi.import: FileDescriptor)
+ (ffi.import: FileDescriptor
+ ["[1]::[0]"])
(ffi.import: Stats
["[1]::[0]"
diff --git a/stdlib/source/program/aedifex/artifact/extension.lux b/stdlib/source/program/aedifex/artifact/extension.lux
index 3f934db23..65d336585 100644
--- a/stdlib/source/program/aedifex/artifact/extension.lux
+++ b/stdlib/source/program/aedifex/artifact/extension.lux
@@ -30,6 +30,7 @@
[lux_library]
[jvm_library]
+ [js_library]
[pom]
[sha-1]
[md5]
diff --git a/stdlib/source/test/lux/ffi.js.lux b/stdlib/source/test/lux/ffi.js.lux
index a3c827d26..2b3cb7f96 100644
--- a/stdlib/source/test/lux/ffi.js.lux
+++ b/stdlib/source/test/lux/ffi.js.lux
@@ -1,23 +1,26 @@
(.using
- [library
- [lux "*"
- ["_" test {"+" Test}]
- [abstract
- [monad {"+" do}]]
- [control
- ["[0]" try]]
- [data
- ["[0]" bit ("[1]#[0]" equivalence)]
- ["[0]" text ("[1]#[0]" equivalence)]]
- [math
- ["[0]" random {"+" Random}]
- [number
- ["[0]" nat]
- ["[0]" frac]]]]]
- [\\library
- ["[0]" /]])
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ [abstract
+ [monad {"+" do}]]
+ [control
+ ["[0]" try]]
+ [data
+ ["[0]" bit ("[1]#[0]" equivalence)]
+ ["[0]" text ("[1]#[0]" equivalence)]]
+ [math
+ ["[0]" random {"+" Random}]
+ [number
+ ["[0]" nat]
+ ["[0]" frac]]]]]
+ [\\library
+ ["[0]" /]]
+ ["$[0]" / "_"
+ ["[1][0]" export]])
-(/.import: Uint8Array)
+(/.import: Uint8Array
+ ["[1]::[0]"])
... On Nashorn
(/.import: java/lang/String
@@ -138,4 +141,6 @@
(|> (TextDecoder::new [encoding])
(TextDecoder::decode [binary])))
))))
+
+ $/export.test
)))))
diff --git a/stdlib/source/test/lux/ffi.jvm.lux b/stdlib/source/test/lux/ffi.jvm.lux
index 9eb52d393..2a988f398 100644
--- a/stdlib/source/test/lux/ffi.jvm.lux
+++ b/stdlib/source/test/lux/ffi.jvm.lux
@@ -35,7 +35,9 @@
["[0]" jvm "_"
["[1]" type ("[1]#[0]" equivalence)]]]]]
[\\library
- ["[0]" /]])
+ ["[0]" /]]
+ ["$[0]" / "_"
+ ["[1][0]" export]])
(/.import: java/lang/Boolean)
(/.import: java/lang/Long)
@@ -654,166 +656,6 @@
false)))))
)))
-(def: expected_boolean (/.as_boolean (static.random_bit)))
-(def: expected_byte (/.as_byte (static.random_int)))
-(def: expected_short (/.as_short (static.random_int)))
-(def: expected_int (/.as_int (static.random_int)))
-(def: expected_long (/.as_long (static.random_int)))
-(def: expected_char (/.as_char (static.random_int)))
-(def: expected_float (/.as_float (static.random_frac)))
-(def: expected_double (/.as_double (static.random_frac)))
-(def: expected_string (/.as_string (static.random code.text (random.ascii/lower 2))))
-
-(`` (`` (/.export: Primitives
- ... Constants
- (actual_boolean boolean ..expected_boolean)
- (actual_byte byte ..expected_byte)
- (actual_short short ..expected_short)
- (actual_int int ..expected_int)
- (actual_long long ..expected_long)
- (actual_char char ..expected_char)
- (actual_float float ..expected_float)
- (actual_double double ..expected_double)
-
- ... Methods
- (~~ (template [<type> <+>]
- [(((~~ (template.symbol [<type> "_method"]))
- [left <type>
- right <type>])
- <type>
- ((~~ (template.symbol [/._] ["as_" <type>]))
- (<+> ((~~ (template.symbol [/._] ["of_" <type>])) left)
- ((~~ (template.symbol [/._] ["of_" <type>])) right))))]
-
- [boolean and]
- [byte i.+]
- [short i.+]
- [int i.+]
- [long i.+]
- [char i.+]
- [float f.+]
- [double f.+]
- ))
- )))
-
-(`` (`` (/.import: Primitives
- ["[1]::[0]"
- ("static" actual_boolean boolean)
- ("static" actual_byte byte)
- ("static" actual_short short)
- ("static" actual_int int)
- ("static" actual_long long)
- ("static" actual_char char)
- ("static" actual_float float)
- ("static" actual_double double)
-
- (~~ (template [<type>]
- [("static" (~~ (template.symbol [<type> "_method"])) [<type> <type>] <type>)]
-
- [boolean]
- [byte]
- [short]
- [int]
- [long]
- [char]
- [float]
- [double]
- ))
- ])))
-
-(/.export: Objects
- (actual_string java/lang/String ..expected_string)
-
- ((string_method [left java/lang/String right java/lang/String])
- java/lang/String
- (/.as_string (%.format (/.of_string left) (/.of_string right))))
-
- (([a] left [left a right a]) a left)
- (([a] right [left a right a]) a right))
-
-(/.import: Objects
- ["[1]::[0]"
- ("static" actual_string java/lang/String)
-
- ("static" string_method [java/lang/String java/lang/String] java/lang/String)
-
- ("static" [a] left [a a] a)
- ("static" [a] right [a a] a)])
-
-(def: tiny_int
- (Random Int)
- (random#each (|>> (i64.and (hex "F")) .int)
- random.nat))
-
-(def: tiny_frac
- (Random Frac)
- (random#each (|>> (i64.and (hex "FFFF"))
- .int
- i.frac)
- random.nat))
-
-(`` (`` (def: test|export
- Test
- (do [! random.monad]
- [(~~ (template [<type> <as> <random>]
- [(~~ (template.symbol [left_ <type>])) (# ! each (|>> <as>) <random>)
- (~~ (template.symbol [right_ <type>])) (# ! each (|>> <as>) <random>)]
-
- [boolean /.as_boolean random.bit]
- [byte /.as_byte ..tiny_int]
- [short /.as_short ..tiny_int]
- [int /.as_int ..tiny_int]
- [long /.as_long ..tiny_int]
- [char /.as_char ..tiny_int]
- [float /.as_float ..tiny_frac]
- [double /.as_double ..tiny_frac]
- [string /.as_string (random.ascii/lower 1)]
- ))]
- ($_ _.and
- (_.cover [/.export:]
- (and (bit#= (/.of_boolean ..expected_boolean) (/.of_boolean (Primitives::actual_boolean)))
- (i#= (/.of_byte ..expected_byte) (/.of_byte (Primitives::actual_byte)))
- (i#= (/.of_short ..expected_short) (/.of_short (Primitives::actual_short)))
- (i#= (/.of_int ..expected_int) (/.of_int (Primitives::actual_int)))
- (i#= (/.of_long ..expected_long) (/.of_long (Primitives::actual_long)))
- (i#= (/.of_char ..expected_char) (/.of_char (Primitives::actual_char)))
- (f#= (/.of_float ..expected_float) (/.of_float (Primitives::actual_float)))
- (f#= (/.of_double ..expected_double) (/.of_double (Primitives::actual_double)))
-
- (~~ (template [<=> <+> <type>]
- [(with_expansions [<left> (template.symbol ["left_" <type>])
- <right> (template.symbol ["right_" <type>])
- <of> (template.symbol [/._] ["of_" <type>])
- <method> (template.symbol ["Primitives::" <type> "_method"])]
- (<=> (<+> (<of> <left>) (<of> <right>))
- (<of> (<method> <left> <right>))))]
-
- [bit#= and boolean]
- [i#= i.+ byte]
- [i#= i.+ short]
- [i#= i.+ int]
- [i#= i.+ long]
- [i#= i.+ char]
- [f#= f.+ float]
- [f#= f.+ double]
- ))
-
- (text#= (/.of_string ..expected_string) (/.of_string (Objects::actual_string)))
-
- (text#= (%.format (/.of_string left_string) (/.of_string right_string))
- (/.of_string (Objects::string_method left_string right_string)))
-
- (text#= (/.of_string left_string)
- (/.of_string (Objects::left left_string right_string)))
- (text#= (/.of_string right_string)
- (/.of_string (Objects::right left_string right_string)))
- (i#= (/.of_long left_long)
- (/.of_long (Objects::left left_long right_long)))
- (i#= (/.of_long right_long)
- (/.of_long (Objects::right left_long right_long)))
- ))
- )))))
-
(def: .public test
(<| (_.covering /._)
($_ _.and
@@ -823,5 +665,6 @@
..for_interface
..for_class
..for_exception
- ..test|export
+
+ $/export.test
)))
diff --git a/stdlib/source/test/lux/ffi.lua.lux b/stdlib/source/test/lux/ffi.lua.lux
index e4b83e8ad..682e34763 100644
--- a/stdlib/source/test/lux/ffi.lua.lux
+++ b/stdlib/source/test/lux/ffi.lua.lux
@@ -1,15 +1,17 @@
(.using
- [library
- [lux "*"
- ["_" test {"+" Test}]
- [abstract
- [monad {"+" do}]]
- [control
- ["[0]" io]]
- [math
- ["[0]" random]]]]
- [\\library
- ["[0]" /]])
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ [abstract
+ [monad {"+" do}]]
+ [control
+ ["[0]" io]]
+ [math
+ ["[0]" random]]]]
+ [\\library
+ ["[0]" /]]
+ ["$[0]" / "_"
+ ["[1][0]" export]])
(/.import: (os/getenv [/.String] "io" "?" /.String))
@@ -56,4 +58,6 @@
(case (io.run! (..os/getenv string))
{.#Some _} true
{.#None} true))
+
+ $/export.test
)))))
diff --git a/stdlib/source/test/lux/ffi.py.lux b/stdlib/source/test/lux/ffi.py.lux
index d2eb3f293..efa966c7d 100644
--- a/stdlib/source/test/lux/ffi.py.lux
+++ b/stdlib/source/test/lux/ffi.py.lux
@@ -1,15 +1,17 @@
(.using
- [library
- [lux "*"
- ["_" test {"+" Test}]
- [abstract
- [monad {"+" do}]]
- [math
- ["[0]" random]
- [number
- ["i" int]]]]]
- [\\library
- ["[0]" /]])
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ [abstract
+ [monad {"+" do}]]
+ [math
+ ["[0]" random]
+ [number
+ ["i" int]]]]]
+ [\\library
+ ["[0]" /]]
+ ["$[0]" / "_"
+ ["[1][0]" export]])
(/.import: os
["[1]::[0]"
@@ -58,4 +60,6 @@
(_.cover [/.import:]
(and (i.= (os::R_OK) (os::R_OK))
(not (i.= (os::W_OK) (os::R_OK)))))
+
+ $/export.test
)))))
diff --git a/stdlib/source/test/lux/ffi.rb.lux b/stdlib/source/test/lux/ffi.rb.lux
index b2bc3f369..b7e488547 100644
--- a/stdlib/source/test/lux/ffi.rb.lux
+++ b/stdlib/source/test/lux/ffi.rb.lux
@@ -1,13 +1,15 @@
(.using
- [library
- [lux "*"
- ["_" test {"+" Test}]
- [abstract
- [monad {"+" do}]]
- [math
- ["[0]" random]]]]
- [\\library
- ["[0]" /]])
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ [abstract
+ [monad {"+" do}]]
+ [math
+ ["[0]" random]]]]
+ [\\library
+ ["[0]" /]]
+ ["$[0]" / "_"
+ ["[1][0]" export]])
(/.import: File
["[1]::[0]"
@@ -49,4 +51,6 @@
(_.cover [/.import:]
(same? (..File::SEPARATOR)
(..File::SEPARATOR)))
+
+ $/export.test
)))))
diff --git a/stdlib/source/test/lux/ffi/export.js.lux b/stdlib/source/test/lux/ffi/export.js.lux
new file mode 100644
index 000000000..67e276b8c
--- /dev/null
+++ b/stdlib/source/test/lux/ffi/export.js.lux
@@ -0,0 +1,33 @@
+(.using
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ ["[0]" static]
+ [math
+ [number
+ ["n" nat]]]]]
+ [\\library
+ ["[0]" /
+ ["/[1]" //]]])
+
+(with_expansions [<nat> (static.random_nat)]
+ (/.export:
+ (def: constant
+ Nat
+ <nat>)
+ (def: shift
+ (-> Nat Nat)
+ (|>> (n.+ <nat>))))
+
+ (//.import: (constant Nat))
+ (//.import: (shift (-> Nat Nat)))
+
+ (def: .public test
+ Test
+ (<| (_.covering /._)
+ ($_ _.and
+ (_.cover [/.export:]
+ (and (n.= <nat> ..constant)
+ (n.= (n.+ <nat> <nat>) (..shift <nat>))))
+ )))
+ )
diff --git a/stdlib/source/test/lux/ffi/export.jvm.lux b/stdlib/source/test/lux/ffi/export.jvm.lux
new file mode 100644
index 000000000..24ef68929
--- /dev/null
+++ b/stdlib/source/test/lux/ffi/export.jvm.lux
@@ -0,0 +1,186 @@
+(.using
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ ["[0]" meta]
+ ["[0]" debug]
+ ["[0]" static]
+ [abstract
+ [monad {"+" do}]]
+ [data
+ ["[0]" bit ("[1]#[0]" equivalence)]
+ ["[0]" text ("[1]#[0]" equivalence)
+ ["%" format]]]
+ [macro
+ ["[0]" code]
+ ["[0]" template]]
+ [math
+ ["[0]" random {"+" Random} ("[1]#[0]" monad)]
+ [number {"+" hex}
+ ["[0]" i64]
+ ["[0]" int ("[1]#[0]" equivalence)]
+ ["[0]" frac ("[1]#[0]" equivalence)]]]]]
+ [\\library
+ ["[0]" /
+ ["/[1]" //]]])
+
+(def: expected_boolean (//.as_boolean (static.random_bit)))
+(def: expected_byte (//.as_byte (static.random_int)))
+(def: expected_short (//.as_short (static.random_int)))
+(def: expected_int (//.as_int (static.random_int)))
+(def: expected_long (//.as_long (static.random_int)))
+(def: expected_char (//.as_char (static.random_int)))
+(def: expected_float (//.as_float (static.random_frac)))
+(def: expected_double (//.as_double (static.random_frac)))
+(def: expected_string (//.as_string (static.random code.text (random.ascii/lower 2))))
+
+(`` (`` (/.export: Primitives
+ ... Constants
+ (actual_boolean boolean ..expected_boolean)
+ (actual_byte byte ..expected_byte)
+ (actual_short short ..expected_short)
+ (actual_int int ..expected_int)
+ (actual_long long ..expected_long)
+ (actual_char char ..expected_char)
+ (actual_float float ..expected_float)
+ (actual_double double ..expected_double)
+
+ ... Methods
+ (~~ (template [<type> <+>]
+ [(((~~ (template.symbol [<type> "_method"]))
+ [left <type>
+ right <type>])
+ <type>
+ ((~~ (template.symbol [//._] ["as_" <type>]))
+ (<+> ((~~ (template.symbol [//._] ["of_" <type>])) left)
+ ((~~ (template.symbol [//._] ["of_" <type>])) right))))]
+
+ [boolean and]
+ [byte int.+]
+ [short int.+]
+ [int int.+]
+ [long int.+]
+ [char int.+]
+ [float frac.+]
+ [double frac.+]
+ ))
+ )))
+
+(`` (`` (//.import: Primitives
+ ["[1]::[0]"
+ ("static" actual_boolean boolean)
+ ("static" actual_byte byte)
+ ("static" actual_short short)
+ ("static" actual_int int)
+ ("static" actual_long long)
+ ("static" actual_char char)
+ ("static" actual_float float)
+ ("static" actual_double double)
+
+ (~~ (template [<type>]
+ [("static" (~~ (template.symbol [<type> "_method"])) [<type> <type>] <type>)]
+
+ [boolean]
+ [byte]
+ [short]
+ [int]
+ [long]
+ [char]
+ [float]
+ [double]
+ ))
+ ])))
+
+(/.export: Objects
+ (actual_string java/lang/String ..expected_string)
+
+ ((string_method [left java/lang/String right java/lang/String])
+ java/lang/String
+ (//.as_string (%.format (//.of_string left) (//.of_string right))))
+
+ (([a] left [left a right a]) a left)
+ (([a] right [left a right a]) a right))
+
+(//.import: Objects
+ ["[1]::[0]"
+ ("static" actual_string java/lang/String)
+
+ ("static" string_method [java/lang/String java/lang/String] java/lang/String)
+
+ ("static" [a] left [a a] a)
+ ("static" [a] right [a a] a)])
+
+(def: tiny_int
+ (Random Int)
+ (random#each (|>> (i64.and (hex "F")) .int)
+ random.nat))
+
+(def: tiny_frac
+ (Random Frac)
+ (random#each (|>> (i64.and (hex "FFFF"))
+ .int
+ int.frac)
+ random.nat))
+
+(`` (`` (def: .public test
+ Test
+ (<| (_.covering /._)
+ (do [! random.monad]
+ [(~~ (template [<type> <as> <random>]
+ [(~~ (template.symbol [left_ <type>])) (# ! each (|>> <as>) <random>)
+ (~~ (template.symbol [right_ <type>])) (# ! each (|>> <as>) <random>)]
+
+ [boolean //.as_boolean random.bit]
+ [byte //.as_byte ..tiny_int]
+ [short //.as_short ..tiny_int]
+ [int //.as_int ..tiny_int]
+ [long //.as_long ..tiny_int]
+ [char //.as_char ..tiny_int]
+ [float //.as_float ..tiny_frac]
+ [double //.as_double ..tiny_frac]
+ [string //.as_string (random.ascii/lower 1)]
+ ))]
+ ($_ _.and
+ (_.cover [/.export:]
+ (and (bit#= (//.of_boolean ..expected_boolean) (//.of_boolean (Primitives::actual_boolean)))
+ (int#= (//.of_byte ..expected_byte) (//.of_byte (Primitives::actual_byte)))
+ (int#= (//.of_short ..expected_short) (//.of_short (Primitives::actual_short)))
+ (int#= (//.of_int ..expected_int) (//.of_int (Primitives::actual_int)))
+ (int#= (//.of_long ..expected_long) (//.of_long (Primitives::actual_long)))
+ (int#= (//.of_char ..expected_char) (//.of_char (Primitives::actual_char)))
+ (frac#= (//.of_float ..expected_float) (//.of_float (Primitives::actual_float)))
+ (frac#= (//.of_double ..expected_double) (//.of_double (Primitives::actual_double)))
+
+ (~~ (template [<=> <+> <type>]
+ [(with_expansions [<left> (template.symbol ["left_" <type>])
+ <right> (template.symbol ["right_" <type>])
+ <of> (template.symbol [//._] ["of_" <type>])
+ <method> (template.symbol ["Primitives::" <type> "_method"])]
+ (<=> (<+> (<of> <left>) (<of> <right>))
+ (<of> (<method> <left> <right>))))]
+
+ [bit#= and boolean]
+ [int#= int.+ byte]
+ [int#= int.+ short]
+ [int#= int.+ int]
+ [int#= int.+ long]
+ [int#= int.+ char]
+ [frac#= frac.+ float]
+ [frac#= frac.+ double]
+ ))
+
+ (text#= (//.of_string ..expected_string) (//.of_string (Objects::actual_string)))
+
+ (text#= (%.format (//.of_string left_string) (//.of_string right_string))
+ (//.of_string (Objects::string_method left_string right_string)))
+
+ (text#= (//.of_string left_string)
+ (//.of_string (Objects::left left_string right_string)))
+ (text#= (//.of_string right_string)
+ (//.of_string (Objects::right left_string right_string)))
+ (int#= (//.of_long left_long)
+ (//.of_long (Objects::left left_long right_long)))
+ (int#= (//.of_long right_long)
+ (//.of_long (Objects::right left_long right_long)))
+ ))
+ ))))))
diff --git a/stdlib/source/test/lux/ffi/export.lua.lux b/stdlib/source/test/lux/ffi/export.lua.lux
new file mode 100644
index 000000000..63cc558ef
--- /dev/null
+++ b/stdlib/source/test/lux/ffi/export.lua.lux
@@ -0,0 +1,33 @@
+(.using
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ ["[0]" static]
+ [math
+ [number
+ ["n" nat]]]]]
+ [\\library
+ ["[0]" /
+ ["/[1]" //]]])
+
+(with_expansions [<nat> (static.random_nat)]
+ (/.export:
+ (def: constant
+ Nat
+ <nat>)
+ (def: shift
+ (-> Nat Nat)
+ (|>> (n.+ <nat>))))
+
+ (//.import: (constant Nat))
+ (//.import: (shift (-> Nat Nat)))
+
+ (def: .public test
+ Test
+ (<| (_.covering /._)
+ ($_ _.and
+ (_.cover [/.export:]
+ (and (n.= <nat> (..constant))
+ (n.= (n.+ <nat> <nat>) ((..shift) <nat>))))
+ )))
+ )
diff --git a/stdlib/source/test/lux/ffi/export.py.lux b/stdlib/source/test/lux/ffi/export.py.lux
new file mode 100644
index 000000000..67e276b8c
--- /dev/null
+++ b/stdlib/source/test/lux/ffi/export.py.lux
@@ -0,0 +1,33 @@
+(.using
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ ["[0]" static]
+ [math
+ [number
+ ["n" nat]]]]]
+ [\\library
+ ["[0]" /
+ ["/[1]" //]]])
+
+(with_expansions [<nat> (static.random_nat)]
+ (/.export:
+ (def: constant
+ Nat
+ <nat>)
+ (def: shift
+ (-> Nat Nat)
+ (|>> (n.+ <nat>))))
+
+ (//.import: (constant Nat))
+ (//.import: (shift (-> Nat Nat)))
+
+ (def: .public test
+ Test
+ (<| (_.covering /._)
+ ($_ _.and
+ (_.cover [/.export:]
+ (and (n.= <nat> ..constant)
+ (n.= (n.+ <nat> <nat>) (..shift <nat>))))
+ )))
+ )
diff --git a/stdlib/source/test/lux/ffi/export.rb.lux b/stdlib/source/test/lux/ffi/export.rb.lux
new file mode 100644
index 000000000..0ceaf7e00
--- /dev/null
+++ b/stdlib/source/test/lux/ffi/export.rb.lux
@@ -0,0 +1,43 @@
+(.using
+ [library
+ [lux "*"
+ ["_" test {"+" Test}]
+ ["[0]" static]
+ [math
+ [number
+ ["n" nat]]]]]
+ [\\library
+ ["[0]" /
+ ["/[1]" //]]])
+
+(with_expansions [<nat> (static.random_nat)]
+ (/.export:
+ (def: nullary
+ Nat
+ <nat>)
+ (def: unary
+ (-> Nat Nat)
+ (|>> (n.+ <nat>)))
+ (def: CONSTANT
+ Nat
+ <nat>)
+ (def: $global
+ (-> Nat Nat)
+ (|>> (n.+ <nat>))))
+
+ (//.import: (nullary [] Nat))
+ (//.import: (unary [Nat] Nat))
+ (//.import: (CONSTANT Nat))
+ (//.import: ($global (-> Nat Nat)))
+
+ (def: .public test
+ Test
+ (<| (_.covering /._)
+ ($_ _.and
+ (_.cover [/.export:]
+ (and (n.= <nat> (..nullary []))
+ (n.= (n.+ <nat> <nat>) (..unary <nat>))
+ (n.= <nat> (..CONSTANT))
+ (n.= (n.+ <nat> <nat>) ((..$global) <nat>))))
+ )))
+ )
diff --git a/stdlib/source/unsafe/lux/data/binary.lux b/stdlib/source/unsafe/lux/data/binary.lux
index f5e4d5b4e..cf25b655f 100644
--- a/stdlib/source/unsafe/lux/data/binary.lux
+++ b/stdlib/source/unsafe/lux/data/binary.lux
@@ -31,8 +31,10 @@
@.jvm (as_is <jvm>)
@.js
- (as_is (ffi.import: ArrayBuffer)
- (ffi.import: Uint8Array)
+ (as_is (ffi.import: ArrayBuffer
+ ["[1]::[0]"])
+ (ffi.import: Uint8Array
+ ["[1]::[0]"])
(type: .public Binary
Uint8Array))