diff options
Diffstat (limited to 'stdlib/source/test/lux/compiler/default/phase/analysis/reference.lux')
-rw-r--r-- | stdlib/source/test/lux/compiler/default/phase/analysis/reference.lux | 107 |
1 files changed, 107 insertions, 0 deletions
diff --git a/stdlib/source/test/lux/compiler/default/phase/analysis/reference.lux b/stdlib/source/test/lux/compiler/default/phase/analysis/reference.lux new file mode 100644 index 000000000..18ab58fa9 --- /dev/null +++ b/stdlib/source/test/lux/compiler/default/phase/analysis/reference.lux @@ -0,0 +1,107 @@ +(.module: + [lux #* + [control + [monad (#+ do)] + pipe] + [data + ["." error (#+ Error)] + [name ("name/." equivalence)] + [text ("text/." equivalence)]] + [math + ["r" random]] + [type ("type/." equivalence)] + [macro + ["." code]] + [compiler + [default + ["." reference] + ["." init] + ["." phase + ["." analysis + ["." scope] + ["." module] + [".A" type] + ["." expression]] + [extension + [".E" analysis]]]]] + test] + [// + ["_." primitive]]) + +(type: Check (-> (Error Any) Bit)) + +(do-template [<name> <on-success> <on-failure>] + [(def: <name> + Check + (|>> (case> (#error.Success _) + <on-success> + + (#error.Failure _) + <on-failure>)))] + + [success? #1 #0] + [failure? #0 #1] + ) + +(def: (reach-test var-name [export? def-module] [import? dependent-module] check!) + (-> Text [Bit Text] [Bit Text] Check Bit) + (|> (do phase.monad + [_ (module.with-module 0 def-module + (module.define var-name [Any + (if export? + (' {#.export? #1}) + (' {})) + []]))] + (module.with-module 0 dependent-module + (do @ + [_ (if import? + (module.import def-module) + (wrap []))] + (typeA.with-inference + (_primitive.phase (code.identifier [def-module var-name])))))) + (phase.run _primitive.state) + check!)) + +(context: "References" + (<| (times 100) + (do @ + [[expectedT _] _primitive.primitive + def-module (r.unicode 5) + scope-name (r.unicode 5) + var-name (r.unicode 5) + dependent-module (|> (r.unicode 5) + (r.filter (|>> (text/= def-module) not)))] + ($_ seq + (test "Can analyse variable." + (|> (scope.with-scope scope-name + (scope.with-local [var-name expectedT] + (typeA.with-inference + (_primitive.phase (code.local-identifier var-name))))) + (phase.run _primitive.state) + (case> (^ (#error.Success [inferredT (#analysis.Reference (reference.local var))])) + (and (type/= expectedT inferredT) + (n/= 0 var)) + + _ + #0))) + (test "Can analyse definition (in the same module)." + (let [def-name [def-module var-name]] + (|> (do phase.monad + [_ (module.define var-name [expectedT (' {}) []])] + (typeA.with-inference + (_primitive.phase (code.identifier def-name)))) + (module.with-module 0 def-module) + (phase.run _primitive.state) + (case> (^ (#error.Success [_ inferredT (#analysis.Reference (reference.constant constant-name))])) + (and (type/= expectedT inferredT) + (name/= def-name constant-name)) + + _ + #0)))) + (test "Can analyse definition (if exported from imported module)." + (reach-test var-name [#1 def-module] [#1 dependent-module] success?)) + (test "Cannot analyse definition (if not exported from imported module)." + (reach-test var-name [#0 def-module] [#1 dependent-module] failure?)) + (test "Cannot analyse definition (if exported from non-imported module)." + (reach-test var-name [#1 def-module] [#0 dependent-module] failure?)) + )))) |