├── scripts ├── .gitignore ├── README └── package.json ├── tests ├── pos │ ├── simple │ │ ├── 00-empty.ts │ │ ├── 01-error.ts │ │ ├── 15-string-construction.ts │ │ ├── 54-hex.ts │ │ ├── 03-glob.ts │ │ ├── 07-bool.ts │ │ ├── 64-upcast.ts │ │ ├── 06-bool.ts │ │ ├── 51-bitvector.ts │ │ ├── 23-unification.ts │ │ ├── 36-truthy.ts │ │ ├── 60-ref-in-constructor.ts │ │ ├── 65-bitvectors.ts │ │ ├── 21-conditional-expression.ts │ │ ├── 26-unification.ts │ │ ├── 43-func-invariant.ts │ │ ├── 59-qualgen.ts │ │ ├── 46-contextual.ts │ │ ├── 44-overload.ts │ │ ├── 25-field-update.ts │ │ ├── 12-runtime-tags.ts │ │ ├── 52-bitvector.ts │ │ ├── 57-non-linear.ts │ │ ├── 04-glob.ts │ │ ├── 10-func-expression.ts │ │ ├── 60-opt-args.ts │ │ ├── 62-tvars.ts │ │ ├── 59-opt-args.ts │ │ ├── 27-unification.ts │ │ ├── 17-absolute.ts │ │ ├── 02-glob.ts │ │ ├── 11-runtime-tags.ts │ │ ├── 16-arguments-var.ts │ │ ├── 49-addEntry.ts │ │ ├── 65-variadic.ts │ │ ├── 47-overloads.ts │ │ ├── 14-arithmetic.ts │ │ ├── 28-top-type.ts │ │ ├── 48-field-invariant.ts │ │ ├── 50-adhoc.ts │ │ ├── 55-intersection.ts │ │ ├── 38-overload.ts │ │ ├── 24-unification.ts │ │ ├── 61-string-coercion.ts │ │ ├── 08-func-expression.ts │ │ ├── 58-qualgen-00.ts │ │ └── 13-contextual.ts │ ├── reals │ │ ├── reals-00.ts │ │ ├── reals-01.ts │ │ └── reals-02.ts │ ├── objects │ │ ├── hasOwnProperty.ts │ │ ├── 11-object.ts │ │ ├── 07-object.ts │ │ ├── opt-fields-01.ts │ │ ├── 12-object.ts │ │ ├── 00-object.ts │ │ ├── 20-object.ts │ │ ├── 10-object.ts │ │ ├── 13-object.ts │ │ ├── 22-object.ts │ │ ├── 21-object.ts │ │ ├── 14-object.ts │ │ ├── 19-object.ts │ │ ├── 03-object.ts │ │ ├── 06-object.ts │ │ ├── 09-object.ts │ │ └── 02-object.ts │ ├── typealias │ │ ├── talias-05.ts │ │ ├── talias-08.ts │ │ ├── talias-07.ts │ │ ├── talias-01.ts │ │ ├── talias-03.ts │ │ ├── talias-00.ts │ │ ├── talias-02.ts │ │ └── talias-09.ts │ ├── misc │ │ ├── 47-underscore.ts │ │ ├── 15-inc.ts │ │ ├── 39-poly.ts │ │ ├── 40-poly.ts │ │ ├── 46-underscore.ts │ │ ├── 43-top-level.ts │ │ ├── 06-cousot.ts │ │ ├── 48-unite.ts │ │ ├── 17-init.ts │ │ ├── 29-negate.ts │ │ ├── 28-negate.ts │ │ ├── 27-negate.ts │ │ ├── 05-callable-interface.ts │ │ ├── 34-opt-args.ts │ │ ├── 22-max.ts │ │ ├── 00-abs.ts │ │ ├── 26-negate.ts │ │ ├── 16-init.ts │ │ ├── 41-poly.ts │ │ ├── 53-vararg.ts │ │ ├── 38-poly.ts │ │ ├── 07-cousot.ts │ │ ├── 18-inner.ts │ │ ├── 37-poly.ts │ │ ├── 10-dep.ts │ │ ├── 54-short-circuit.ts │ │ ├── 30-negate.ts │ │ ├── 35-overload.ts │ │ ├── 42-safe-meth-call.ts │ │ ├── 13-incr.ts │ │ └── 59-class-inv.ts │ ├── arrays │ │ ├── 18-array.ts │ │ ├── 19-array.ts │ │ ├── 06-array.ts │ │ ├── 07-array.ts │ │ ├── 22-array.ts │ │ ├── 03-array.ts │ │ ├── 17-array.ts │ │ ├── 13-array.ts │ │ ├── 23-array.ts │ │ ├── 25-array.ts │ │ ├── 08-array.ts │ │ ├── 16-array.ts │ │ ├── 01-array.ts │ │ ├── 20-array.ts │ │ ├── 05-array.ts │ │ ├── 15-array.ts │ │ ├── 12-array.ts │ │ ├── 24-array.ts │ │ ├── 00-array.ts │ │ ├── 21-array.ts │ │ ├── 02-array.ts │ │ ├── 26-array.ts │ │ ├── 11-array.ts │ │ ├── 09-array.ts │ │ └── 10-array.ts │ ├── operators │ │ ├── unary-plus-00.ts │ │ ├── cond-expr-00.ts │ │ ├── str.ts │ │ ├── add-01.ts │ │ ├── lor-05.ts │ │ ├── tags.ts │ │ ├── cond-expr-01.ts │ │ ├── pos.ts │ │ ├── add-02.ts │ │ ├── lor-06.ts │ │ ├── stmt.ts │ │ ├── lor-00.ts │ │ ├── lor-02.ts │ │ ├── lor-04.ts │ │ ├── lor-01.ts │ │ ├── lor-03.ts │ │ ├── add-04.ts │ │ ├── inc-00.ts │ │ ├── inc-02.ts │ │ ├── id-01.ts │ │ ├── sum-01.ts │ │ ├── sum-infer-01.ts │ │ ├── sum-02.ts │ │ ├── sum-00.ts │ │ ├── id-00.ts │ │ ├── id-02.ts │ │ └── sum-infer-00.ts │ ├── bounded-poly │ │ ├── 01-test.ts │ │ ├── 03-test.ts │ │ ├── 04-test.ts │ │ ├── 00-test.ts │ │ └── 02-test.ts │ ├── lists │ │ ├── list-head-01.ts │ │ ├── list-head-02.ts │ │ ├── list-01.ts │ │ ├── emp-01.ts │ │ ├── safehead.ts │ │ ├── emp-00.ts │ │ ├── listsum-03.ts │ │ ├── safemap.ts │ │ ├── list-00.ts │ │ ├── listsum-02.ts │ │ ├── list-03.ts │ │ ├── listsum-01.ts │ │ ├── unfold-list-00.ts │ │ ├── list-02.ts │ │ └── safeappend.ts │ ├── unions │ │ ├── test-10.ts │ │ ├── test-07.ts │ │ ├── test-14.ts │ │ ├── test-13.ts │ │ ├── test-02.ts │ │ ├── test-04.ts │ │ ├── test-08.ts │ │ ├── test-15.ts │ │ ├── test-01.ts │ │ ├── test-09.ts │ │ └── test-05.ts │ ├── loops │ │ ├── while-02.ts │ │ ├── for-07.ts │ │ ├── for-06.ts │ │ ├── double-for.ts │ │ ├── while-01.ts │ │ ├── obj-00.ts │ │ ├── while-03.ts │ │ ├── while-06.ts │ │ ├── for-05.ts │ │ ├── for-03.ts │ │ ├── obj-01.ts │ │ ├── for-02.ts │ │ ├── while-rec.ts │ │ └── while-04.ts │ ├── scope │ │ ├── init-01.ts │ │ ├── 10-initialization.ts │ │ ├── 00-scope.ts │ │ ├── 02-scope.ts │ │ ├── init-05.ts │ │ ├── 12-ssa.ts │ │ ├── init-06.ts │ │ ├── init-02.ts │ │ ├── 13-nested.ts │ │ ├── 10-scope.ts │ │ ├── 01-scope.ts │ │ ├── 11-nested.ts │ │ ├── 06-scope.ts │ │ ├── 05-scope.ts │ │ ├── init-03.ts │ │ ├── init-04.ts │ │ ├── 03-scope.ts │ │ └── 07-scope.ts │ ├── inclusion │ │ ├── 10-inclusion.ts │ │ ├── 00-inclusion.ts │ │ ├── 02-inclusion.ts │ │ ├── 04-inclusion.ts │ │ ├── 06-inclusion.ts │ │ ├── 03-inclusion.ts │ │ ├── 05-inclusion.ts │ │ ├── 08-inclusion.ts │ │ └── 01-inclusion.ts │ ├── enums │ │ ├── 02-enum.ts │ │ └── 00-enum.ts │ ├── classes │ │ ├── 30-implements.ts │ │ ├── 03-class.ts │ │ ├── 37-interface.ts │ │ ├── 11-class.ts │ │ ├── 39-method.ts │ │ ├── 20-ctor.ts │ │ ├── 29-glob-in-method.ts │ │ ├── 28-func-field-ctor.ts │ │ ├── 06-class.ts │ │ ├── 09-class.ts │ │ ├── 10-class.ts │ │ ├── 15-classhierarchy.ts │ │ ├── 08-class.ts │ │ ├── 45-this-meth-scope.ts │ │ ├── 36-init.ts │ │ ├── 38-interface.ts │ │ ├── 23-ctor.ts │ │ ├── 44-subclass.ts │ │ ├── 41-offsets.ts │ │ ├── 12-class.ts │ │ ├── 00-class.ts │ │ ├── 27-eq_val.ts │ │ ├── 17-ctor.ts │ │ ├── 19-ctor.ts │ │ └── 25-ctor.ts │ └── fb │ │ ├── minindex-classic.ts │ │ └── opt-args.ts ├── .gitignore ├── neg │ ├── simple │ │ ├── 01-error.ts │ │ ├── 54-hex.ts │ │ ├── 07-bool.ts │ │ ├── 06-bool.ts │ │ ├── 51-bitvector.ts │ │ ├── 03-glob.ts │ │ ├── 43-func-invariant.ts │ │ ├── 36-truthy.ts │ │ ├── bad-spec-00.ts │ │ ├── 21-conditional-expression.ts │ │ ├── 12-unbound-tvar.ts │ │ ├── 10-func-expression.ts │ │ ├── 48-undead.ts │ │ ├── 67-return-false.ts │ │ ├── 25-field-update.ts │ │ ├── 27-unification.ts │ │ ├── 44-overload.ts │ │ ├── 52-bitvector.ts │ │ ├── 13-contextual.ts │ │ ├── 26-unification.ts │ │ ├── 57-non-linear.ts │ │ ├── 05-glob.ts │ │ ├── 60-opt-args.ts │ │ ├── 35-modules.ts │ │ ├── 04-glob.ts │ │ ├── 02-glob.ts │ │ ├── 11-runtime-tags.ts │ │ ├── 65-variadic.ts │ │ ├── 47-overloads.ts │ │ ├── 40-unbound-symbol.ts │ │ ├── 55-intersection.ts │ │ ├── 42-unbound-symbol.ts │ │ ├── 08-func-expression.ts │ │ ├── 24-unification.ts │ │ ├── 61-string-coercion.ts │ │ ├── 45-immutable-field.ts │ │ └── 22-unification.ts │ ├── arrays │ │ ├── 16-array.ts │ │ ├── 18-array.ts │ │ ├── 01-array.ts │ │ ├── 25-array.ts │ │ ├── 04-array.ts │ │ ├── 14-array.ts │ │ ├── 06-array.ts │ │ ├── 02-array.ts │ │ ├── 23-array.ts │ │ ├── 00-array.ts │ │ ├── 13-array.ts │ │ ├── 20-array.ts │ │ ├── 17-array.ts │ │ ├── 08-array.ts │ │ ├── 11-array.ts │ │ ├── 12-array.ts │ │ ├── 05-array.ts │ │ ├── 22-array.ts │ │ ├── 21-array.ts │ │ ├── 24-array.ts │ │ ├── 03-array.ts │ │ ├── 10-array.ts │ │ └── 09-array.ts │ ├── typealias │ │ ├── talias-00.ts │ │ ├── talias-03.ts │ │ ├── talias-01.ts │ │ ├── talias-04.ts │ │ └── talias-02.ts │ ├── objects │ │ ├── 14-object.ts │ │ ├── 07-object.ts │ │ ├── opt-fields-01.ts │ │ ├── 12-object.ts │ │ ├── 13-object.ts │ │ ├── 00-object.ts │ │ ├── 20-object.ts │ │ ├── 11-object.ts │ │ ├── 10-object.ts │ │ ├── 19-object.ts │ │ ├── 21-object.ts │ │ ├── 04-object.ts │ │ ├── 15-object.ts │ │ ├── 18-object.ts │ │ ├── 03-object.ts │ │ ├── 01-object.ts │ │ ├── 05-object.ts │ │ ├── 06-object.ts │ │ ├── 16-object.ts │ │ └── 17-object.ts │ ├── reals │ │ ├── reals-00.ts │ │ ├── reals-02.ts │ │ └── reals-01.ts │ ├── classes │ │ ├── 35-ctor-args-missing.ts │ │ ├── 05-class.ts │ │ ├── 03-class.ts │ │ ├── 10-ctor.ts │ │ ├── 29-method-mut.ts │ │ ├── 06-class.ts │ │ ├── 00-class.ts │ │ ├── 22-func-field-ctor.ts │ │ ├── 19-ctor.ts │ │ ├── 34-this-meth-scope.ts │ │ ├── 13-ctor.ts │ │ ├── 17-ctor.ts │ │ ├── 27-init.ts │ │ ├── 28-interface.ts │ │ ├── 31-offsets.ts │ │ ├── 21-eq-val.ts │ │ └── 26-init.ts │ ├── inclusion │ │ ├── 05-inclusion.ts │ │ ├── 00-inclusion.ts │ │ ├── 06-inclusion.ts │ │ ├── 07-inclusion.ts │ │ ├── 04-inclusion.ts │ │ └── 03-inclusion.ts │ ├── misc │ │ ├── incr.ts │ │ ├── 56-abs-join.ts │ │ ├── 43-top-level.ts │ │ ├── incr3.ts │ │ ├── 40-poly.ts │ │ ├── 57-unite.ts │ │ ├── 09-fixme.ts │ │ ├── 39-poly.ts │ │ ├── 08-global.ts │ │ ├── abs.ts │ │ ├── 01-abs.ts │ │ ├── 26-negate.ts │ │ ├── 00-abs-sig-bad.ts │ │ ├── 55-abs-join.ts │ │ ├── 18-inner.ts │ │ ├── 53-vararg.ts │ │ ├── 58-unite.ts │ │ ├── 37-poly.ts │ │ ├── 38-poly.ts │ │ ├── 27-negate.ts │ │ ├── 42-unsafe-meth-call.ts │ │ ├── 12-incr.ts │ │ ├── 54-short-circuit.ts │ │ ├── 28-negate.ts │ │ ├── 36-packet.ts │ │ ├── 44-twice.ts │ │ └── 59-class-inv.ts │ ├── operators │ │ ├── test-01.ts │ │ ├── str-00.ts │ │ ├── inc-00.ts │ │ ├── test-00.ts │ │ ├── tags.ts │ │ ├── lor-02.ts │ │ ├── conditional-00.ts │ │ ├── conditional-01.ts │ │ ├── lor-05.ts │ │ ├── test-bad-00.ts │ │ ├── conditional-02.ts │ │ ├── stmt-00.ts │ │ ├── lor-00.ts │ │ ├── lor-06.ts │ │ ├── lor-01.ts │ │ ├── lor-03.ts │ │ ├── cond-expr-00.ts │ │ ├── lor-04.ts │ │ ├── inc-01.ts │ │ ├── id-01.ts │ │ ├── sum-ssa-bad.ts │ │ ├── sum-badder.ts │ │ ├── sum-return-missing.ts │ │ ├── add-03a.ts │ │ ├── id-00.ts │ │ ├── sum-bad.ts │ │ └── choice.ts │ ├── lists │ │ ├── list-07.ts │ │ ├── list-04.ts │ │ ├── list-03.ts │ │ ├── list-00.ts │ │ ├── list-02.ts │ │ ├── emp-00.ts │ │ ├── list-06.ts │ │ ├── list-08.ts │ │ ├── list-05.ts │ │ ├── list-09.ts │ │ ├── list-01.ts │ │ ├── list-10.ts │ │ ├── list-11.ts │ │ ├── list-12.ts │ │ ├── unfold-list-00.ts │ │ ├── unfold-list-01.ts │ │ └── safeappend.ts │ ├── unions │ │ ├── test-00.ts │ │ ├── test-13.ts │ │ ├── test-03.ts │ │ ├── test-14.ts │ │ ├── test-15.ts │ │ ├── test-02.ts │ │ ├── test-04.ts │ │ └── test-01.ts │ ├── loops │ │ ├── while-02.ts │ │ ├── while-01.ts │ │ ├── for-03.ts │ │ ├── obj-01.ts │ │ ├── obj-04.ts │ │ ├── obj-00.ts │ │ ├── while-04.ts │ │ ├── while-05.ts │ │ ├── while-rec.ts │ │ ├── while-06.ts │ │ ├── for-02.ts │ │ ├── for-rec-01.ts │ │ └── while-03.ts │ ├── enums │ │ └── 02-enum.ts │ ├── bounded-poly │ │ ├── 01-test.ts │ │ ├── 03-test.ts │ │ ├── 00-test.ts │ │ └── 02-test.ts │ ├── scope │ │ ├── init-01.ts │ │ ├── 00-scope.ts │ │ ├── init-06.ts │ │ ├── 02-scope.ts │ │ ├── init-02.ts │ │ ├── 01-scope.ts │ │ ├── init-04.ts │ │ ├── init-03.ts │ │ └── 11-nested.ts │ └── fb │ │ └── opt-args.ts ├── cleanup ├── todo │ ├── pos │ │ ├── proto │ │ │ ├── array-proto.ts │ │ │ ├── proto-lookup8.ts │ │ │ ├── proto-lookup1.ts │ │ │ ├── proto-lookup2.ts │ │ │ ├── proto-lookup7.ts │ │ │ ├── proto-lookup4.ts │ │ │ ├── proto-lookup3.ts │ │ │ ├── proto-lookup5.ts │ │ │ └── proto-lookup6.ts │ │ ├── operators │ │ │ ├── void.ts │ │ │ ├── float-00.ts │ │ │ ├── eq.ts │ │ │ ├── lor-07.ts │ │ │ ├── bracketref-00.ts │ │ │ └── bitwise-00.ts │ │ ├── control-flow │ │ │ └── break.ts │ │ ├── loops │ │ │ └── do-while.ts │ │ ├── pemissions │ │ │ ├── test-03.ts │ │ │ ├── test-01.ts │ │ │ ├── test-04.ts │ │ │ └── test-05.ts │ │ ├── objects │ │ │ ├── 04-object.ts │ │ │ └── abs-mut.ts │ │ ├── simple │ │ │ ├── 67-variadic.ts │ │ │ ├── init-01.ts │ │ │ ├── 66-variadic.ts │ │ │ ├── modules.ts │ │ │ ├── 70-opt-args.ts │ │ │ ├── null-undef-literals.ts │ │ │ └── late-init.ts │ │ ├── misc │ │ │ └── missing-qualif.ts │ │ └── unions │ │ │ └── or-undef.ts │ ├── weird │ │ ├── order.ts │ │ ├── slowMul.ts │ │ └── splay-00.ts │ ├── neg │ │ ├── proto │ │ │ ├── proto-lookup1.ts │ │ │ └── proto-lookup7.ts │ │ ├── misc │ │ │ └── circular-logic.ts │ │ └── simple │ │ │ └── 66-variadic.ts │ └── ssa-bug-3.ts ├── demo │ ├── reals.ts │ ├── poly.ts │ ├── cast.ts │ ├── opt-args.ts │ ├── variadic.ts │ ├── while-rec.ts │ ├── string-coercion.ts │ ├── negate.ts │ └── minindex-classic.ts └── benchmarks │ └── todo │ └── pldi16 │ └── d3 │ ├── include │ └── number.ts │ ├── transpose.ts │ └── keys.ts ├── .gitattributes ├── doc ├── talk │ ├── SoCal-05-2015 │ │ ├── ignores.dic │ │ └── images │ │ │ ├── ecoop15.png │ │ │ ├── Screenshot-from-2015-04-30-08-29-12.png │ │ │ └── Screenshot-from-2015-05-01-16-19-23.png │ ├── Dagstuhl-07-2014.pdf │ └── Dagstuhl-07-2014.pptx └── formal │ ├── mathpartir.sty │ └── src │ └── includes.tex ├── include ├── ambient │ ├── boolean.d.ts │ ├── undefined.d.ts │ ├── iarguments.d.ts │ └── error.d.ts └── rsc │ ├── aliases.d.ts │ └── mutability.d.ts ├── ext └── tsc-bin │ └── bin │ └── tsc-refscript ├── .gitmodules ├── src └── Language │ └── Rsc │ ├── AST.hs │ └── Pretty.hs └── stack.yaml /scripts/.gitignore: -------------------------------------------------------------------------------- 1 | *.js 2 | -------------------------------------------------------------------------------- /tests/pos/simple/00-empty.ts: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /tests/.gitignore: -------------------------------------------------------------------------------- 1 | *.js 2 | scratch/ 3 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | ext/* linguist-vendored 2 | -------------------------------------------------------------------------------- /doc/talk/SoCal-05-2015/ignores.dic: -------------------------------------------------------------------------------- 1 | dataflow -------------------------------------------------------------------------------- /tests/neg/simple/01-error.ts: -------------------------------------------------------------------------------- 1 | 2 | throw new Error(2); 3 | -------------------------------------------------------------------------------- /tests/pos/simple/01-error.ts: -------------------------------------------------------------------------------- 1 | 2 | throw new Error(""); 3 | -------------------------------------------------------------------------------- /include/ambient/boolean.d.ts: -------------------------------------------------------------------------------- 1 | 2 | interface Boolean { } 3 | -------------------------------------------------------------------------------- /tests/cleanup: -------------------------------------------------------------------------------- 1 | #! /bin/bash 2 | 3 | node ../scripts/cleanup.js 4 | -------------------------------------------------------------------------------- /tests/pos/simple/15-string-construction.ts: -------------------------------------------------------------------------------- 1 | let s = String(3); 2 | -------------------------------------------------------------------------------- /tests/neg/arrays/16-array.ts: -------------------------------------------------------------------------------- 1 | 2 | let a = [1,2,3,4,5] 3 | 4 | a[5] = 1; 5 | -------------------------------------------------------------------------------- /ext/tsc-bin/bin/tsc-refscript: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | require('./tsc-refscript.js') 3 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/array-proto.ts: -------------------------------------------------------------------------------- 1 | 2 | Array.prototype.slice.call([10,11,12], 0, 2); 3 | -------------------------------------------------------------------------------- /include/ambient/undefined.d.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ undefined :: undefined */ 3 | declare let undefined; 4 | -------------------------------------------------------------------------------- /tests/pos/reals/reals-00.ts: -------------------------------------------------------------------------------- 1 | 2 | let a = 0.5; 3 | let b = 0.5; 4 | 5 | assert(a + b === 1.0); 6 | -------------------------------------------------------------------------------- /doc/formal/mathpartir.sty: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UCSD-PL/refscript/HEAD/doc/formal/mathpartir.sty -------------------------------------------------------------------------------- /tests/pos/simple/54-hex.ts: -------------------------------------------------------------------------------- 1 | let a = 0x00000008; 2 | let b = 0x00000008; 3 | assert(b === (a | a)); 4 | -------------------------------------------------------------------------------- /tests/todo/pos/operators/void.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: () => undefined */ 2 | function foo() { 3 | return void 0; 4 | } -------------------------------------------------------------------------------- /doc/talk/Dagstuhl-07-2014.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UCSD-PL/refscript/HEAD/doc/talk/Dagstuhl-07-2014.pdf -------------------------------------------------------------------------------- /doc/talk/Dagstuhl-07-2014.pptx: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UCSD-PL/refscript/HEAD/doc/talk/Dagstuhl-07-2014.pptx -------------------------------------------------------------------------------- /tests/todo/pos/control-flow/break.ts: -------------------------------------------------------------------------------- 1 | function foo():void { 2 | while (true) { 3 | break; 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /tests/todo/pos/loops/do-while.ts: -------------------------------------------------------------------------------- 1 | function foo() { 2 | var i = 0; 3 | do { 4 | i++; 5 | } while (i < 10) 6 | } -------------------------------------------------------------------------------- /scripts/README: -------------------------------------------------------------------------------- 1 | To get dependencies: 2 | 3 | $ npm install 4 | $ tsd install 5 | 6 | 7 | To build: 8 | 9 | $ tsc -------------------------------------------------------------------------------- /tests/pos/objects/hasOwnProperty.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ x :: { } */ 3 | declare let x; 4 | 5 | x.hasOwnProperty("prop"); 6 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-05.ts: -------------------------------------------------------------------------------- 1 | /*@ type Pos = {number | 0 < v } */ 2 | 3 | /*@ bob :: Pos */ 4 | let bob = 10; 5 | -------------------------------------------------------------------------------- /tests/neg/simple/54-hex.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | let a = 0x00000008; 4 | 5 | let b = 0x00000011; 6 | 7 | assert(b === a + a); 8 | -------------------------------------------------------------------------------- /tests/neg/typealias/talias-00.ts: -------------------------------------------------------------------------------- 1 | /*@ type Nat = {v: number | 1000 <= v } */ 2 | 3 | /*@ z :: Nat */ 4 | let z = 12; 5 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-08.ts: -------------------------------------------------------------------------------- 1 | /*@ type gt = {number | n <= n} */ 2 | 3 | /*@ bog :: gt<7> */ 4 | let bog = 10; 5 | -------------------------------------------------------------------------------- /tests/neg/objects/14-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ({x: number}) => void */ 3 | export function foo(o) { 4 | o.y = 10; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/reals/reals-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ option --real */ 3 | 4 | let a = 0.5; 5 | let b = 0.5; 6 | 7 | assert(a + b === 1.1); 8 | -------------------------------------------------------------------------------- /tests/neg/simple/07-bool.ts: -------------------------------------------------------------------------------- 1 | export function foo() { 2 | if (true || false) { 3 | assert(false); 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/simple/03-glob.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ a :: posint */ 3 | let a = 1; 4 | let b = a + 1; 5 | let c = b; 6 | assert(b === c); 7 | -------------------------------------------------------------------------------- /tests/pos/simple/07-bool.ts: -------------------------------------------------------------------------------- 1 | export function foo() { 2 | if (true && false) { 3 | assert(false); 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/simple/64-upcast.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: () => {v: number + string | 0 < 1} */ 2 | function foo(){ 3 | return 4; 4 | } 5 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "liquid-fixpoint"] 2 | path = liquid-fixpoint 3 | url = git@github.com:ucsd-progsys/liquid-fixpoint.git 4 | -------------------------------------------------------------------------------- /tests/demo/reals.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ option --real */ 3 | 4 | let a = 10; 5 | 6 | let b = 20; 7 | 8 | assert(a * a + b * b > 499); 9 | -------------------------------------------------------------------------------- /tests/neg/classes/35-ctor-args-missing.ts: -------------------------------------------------------------------------------- 1 | class Foo { 2 | constructor() {} 3 | } 4 | 5 | let x = new Foo; 6 | -------------------------------------------------------------------------------- /tests/neg/inclusion/05-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | // Predefined objects 5 | assert("PII" in Math); // returns false 6 | -------------------------------------------------------------------------------- /tests/neg/reals/reals-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ option --real */ 3 | 4 | 5 | let a = 0.5; 6 | let b = 0.5; 7 | 8 | assert(a * b === 2.5); 9 | -------------------------------------------------------------------------------- /tests/pos/misc/47-underscore.ts: -------------------------------------------------------------------------------- 1 | /* foo :: () => number */ 2 | export function foo():number { 3 | let _ = 3; 4 | return _; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/objects/11-object.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(o: { x:number; y: boolean }): { x: number } { 3 | return o; 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/reals/reals-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ option --real */ 3 | 4 | let a = 0.5; 5 | let b = 0.5; 6 | 7 | assert(a * b === 0.25); 8 | -------------------------------------------------------------------------------- /doc/talk/SoCal-05-2015/images/ecoop15.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UCSD-PL/refscript/HEAD/doc/talk/SoCal-05-2015/images/ecoop15.png -------------------------------------------------------------------------------- /tests/neg/objects/07-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ obj :: { (Immutable) x: number; y: { number | v = this.x }; } */ 3 | let obj = { x: 1, y: 2 }; 4 | -------------------------------------------------------------------------------- /tests/neg/reals/reals-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ option --real */ 3 | 4 | let a = 10; 5 | 6 | let b = 19; 7 | 8 | assert(a * a + b * b > 499); 9 | -------------------------------------------------------------------------------- /tests/neg/simple/06-bool.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ simple :: () => { v:boolean | Prop v } */ 3 | function simple() { 4 | return (0 === 1); 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/arrays/18-array.ts: -------------------------------------------------------------------------------- 1 | 2 | export function f1(a1: IArray, a2: MArray) { 3 | return a1.concat(a2); 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/arrays/19-array.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(a: MArray, e: A): MArray { 3 | a.push(e); 4 | return a; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/misc/15-inc.ts: -------------------------------------------------------------------------------- 1 | /*@ incr :: (x:number) => {number|v = x + 1} */ 2 | function incr(x:number):number{ 3 | return x + 1; 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/objects/07-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ obj :: { (Immutable) x: number; y: { number | v = this.x }; } */ 3 | let obj = { x: 1, y: 1 }; 4 | -------------------------------------------------------------------------------- /tests/pos/objects/opt-fields-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ opt :: (Mutable) { f?: posint } */ 3 | let opt: { f?: number } = { } ; 4 | 5 | opt.f = 1; 6 | -------------------------------------------------------------------------------- /tests/pos/reals/reals-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ option --real */ 3 | 4 | let a = 10; 5 | 6 | let b = 20; 7 | 8 | assert(a * a + b * b > 499); 9 | -------------------------------------------------------------------------------- /tests/neg/arrays/18-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ emp :: IArray */ 3 | let emp = []; 4 | 5 | assert(emp === null); 6 | 7 | // assert(false); 8 | -------------------------------------------------------------------------------- /tests/neg/misc/incr.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ nincr :: (x:number) => {number|v = x + 1} */ 3 | function nincr(x:number):number{ 4 | return x++; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/objects/opt-fields-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ opt :: (Mutable) { f?: posint } */ 3 | let opt: { f?: number } = { } ; 4 | 5 | opt.f = -1; 6 | -------------------------------------------------------------------------------- /tests/neg/simple/51-bitvector.ts: -------------------------------------------------------------------------------- 1 | 2 | let a = 0x00000001; 3 | let b = 0x00000002; 4 | let c = 0x00000004; 5 | 6 | assert((a|b) === c); 7 | -------------------------------------------------------------------------------- /tests/pos/objects/12-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ( (Mutable){x: number}) => void */ 3 | export function foo(o):void { 4 | o.x = 10; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/operators/unary-plus-00.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(): number { 3 | let x = 0; 4 | let y = + x; 5 | return y 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/simple/06-bool.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ simple :: () => { v:boolean | Prop v } */ 3 | export function simple() { 4 | return (0 < 1); 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/simple/51-bitvector.ts: -------------------------------------------------------------------------------- 1 | 2 | let a = 0x00000001; 3 | let b = 0x00000002; 4 | let c = 0x00000003; 5 | 6 | assert((a|b) === c); 7 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-07.ts: -------------------------------------------------------------------------------- 1 | /*@ type Pos = {number | 0 < v } */ 2 | 3 | /*@ bob :: IArray */ 4 | let bob = [10, 20, 30]; 5 | -------------------------------------------------------------------------------- /tests/neg/operators/test-01.ts: -------------------------------------------------------------------------------- 1 | function main(){ 2 | let y = 0; 3 | let x = random(); 4 | y = x + y; 5 | assert (0 <= y); 6 | } 7 | 8 | 9 | -------------------------------------------------------------------------------- /tests/neg/simple/03-glob.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ a :: posint */ 3 | let a = 1; 4 | let b = a + 1; 5 | a = a + 1; 6 | let c = a + 1; 7 | assert(b === c); 8 | -------------------------------------------------------------------------------- /tests/pos/misc/39-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | function idp(x: A): A { return x; } 3 | 4 | let f = <(x: number) => number> idp; 5 | 6 | assert(f(5) === 5); 7 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup8.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { string | 0 < 1} */ 3 | function foo() { 4 | return "foo".charAt(0); 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/neg/lists/list-07.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: () => List */ 2 | function foo(){ 3 | return { data: 10, next: null }; 4 | } 5 | 6 | -------------------------------------------------------------------------------- /tests/neg/misc/56-abs-join.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ abs :: ({ } + number) => { boolean | 0 < 1 } */ 3 | function abs(x: any) { 4 | return 0 > x; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/objects/12-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ((ReadOnly) { x: number }) => void */ 3 | export function foo(o: any) { 4 | o.x = "aaa"; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/operators/str-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ baz :: () => {v: string | v = "dog"} */ 3 | function baz(){ 4 | let z = 'cat'; 5 | return z; 6 | } 7 | 8 | -------------------------------------------------------------------------------- /tests/pos/arrays/06-array.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(arr: IArray, f: (x: number) => string): IArray { 3 | return arr.map(f); 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/misc/40-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | function idp(x: A): A { return x; } 3 | 4 | let f : (x: number) => number = idp; 5 | 6 | assert(f(5) === 5) ; 7 | -------------------------------------------------------------------------------- /tests/pos/objects/00-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: posint) => { a: posint } */ 3 | function foo(x: number): Object { 4 | return { a: x }; 5 | } 6 | -------------------------------------------------------------------------------- /tests/todo/pos/operators/float-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:number) => {number | 0 < 1} */ 3 | function foo(x:number):number { 4 | return x + 0.5; 5 | } -------------------------------------------------------------------------------- /tests/todo/weird/order.ts: -------------------------------------------------------------------------------- 1 | /*@ x :: number + string */ 2 | declare var x; 3 | /*@ y :: number */ 4 | declare var y; 5 | var a = x>y; 6 | var b = y>x; 7 | -------------------------------------------------------------------------------- /include/ambient/iarguments.d.ts: -------------------------------------------------------------------------------- 1 | 2 | interface IArguments { 3 | [index: number]: any; 4 | length: number; 5 | callee: Function; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/objects/13-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ( (Mutable){x: { v: number | v > 10 } }) => void */ 3 | export function foo(o) { 4 | o.x = 5; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/operators/inc-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ inc :: ({number | 0 < 1 }) => void */ 3 | function inc(x){ 4 | let y = x + 1; 5 | assert(y > 0); 6 | } 7 | 8 | -------------------------------------------------------------------------------- /tests/neg/objects/00-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: posint) => { (Immutable) a: { number | v > 1 } } */ 3 | function foo(x) { 4 | return { a: x }; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/objects/20-object.ts: -------------------------------------------------------------------------------- 1 | 2 | // Cannot assign Unique object 3 | 4 | let a_unique_obj = { c: 3 }; 5 | 6 | let an_alias_to_a_unique_obj = a_unique_obj; 7 | -------------------------------------------------------------------------------- /tests/neg/operators/test-00.ts: -------------------------------------------------------------------------------- 1 | /*@ main :: () => { void | 0 < 1 } */ 2 | function main(){ 3 | let x = 0; 4 | let y = x - 1; 5 | assert (0 < y); 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/bounded-poly/01-test.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | export function foo(x: V): V { 4 | return x; 5 | } 6 | 7 | assert(foo(1) === 1); 8 | -------------------------------------------------------------------------------- /tests/pos/lists/list-head-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => {v:number | v > 0} */ 3 | 4 | function foo():number{ 5 | return head({data: 1, next: null}); 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/objects/20-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly a_unique_obj :: {} */ 3 | let a_unique_obj = { c: 3 }; 4 | 5 | let an_alias_to_a_unique_obj = a_unique_obj 6 | -------------------------------------------------------------------------------- /tests/pos/simple/23-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | function getX(p: { x: A }): A { 3 | return p.x; 4 | } 5 | 6 | let a = getX({ x: 1 }); 7 | 8 | assert(a === 1); 9 | -------------------------------------------------------------------------------- /tests/neg/arrays/01-array.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (a: { IArray | len v <= 10 } ) => number */ 2 | export function foo(a:number []) : number { 3 | return a[9]; 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/arrays/07-array.ts: -------------------------------------------------------------------------------- 1 | 2 | export function bar(arr: IArray, f: (a: number, b: number) => string): IArray { 3 | return arr.map(f); 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/arrays/22-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ mkArray :: ( ) => { IArray | len v = 5 } */ 3 | export function mkArray( ) { 4 | return new Array(5); 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/lists/list-head-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => {top | (v > 0)}*/ 3 | 4 | function foo():number{ 5 | return head({data: 1, next: null}); 6 | } 7 | 8 | 9 | -------------------------------------------------------------------------------- /tests/pos/simple/36-truthy.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ simple :: (x: number) => { v:number | (v != 0) } */ 3 | function simple(x) { 4 | if (x) return x; 5 | return 1; 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/unions/test-10.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number) => { number + boolean | ttag v = ttag x } */ 3 | function foo(x: number): number { 4 | return x; 5 | } 6 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup1.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ({ __proto__: { x: string }, *: number }) => number */ 3 | function foo(o) { 4 | return o.x; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup2.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: ({ __proto__ : { x: boolean }, x: number}) => { number | 0 < 1 } */ 2 | function foo(o) { 3 | return o.x; 4 | } 5 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup7.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ({ __proto__: { x: string }, y: number }) => string */ 3 | function foo(o) { 4 | return o.x; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/neg/objects/11-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (o: { x:number; }) => { x: number; y: boolean; } */ 3 | export function foo(o: any): any { 4 | 5 | return o; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/operators/tags.ts: -------------------------------------------------------------------------------- 1 | /*@ moo :: (number) => {v:string | v = "string"} */ 2 | function moo(x:number):string { 3 | let z :string= typeof(x); 4 | return z; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/unions/test-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ fails :: (number) => number + undefined */ 3 | export function fails (x:number):any { 4 | return x ? true : undefined; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/arrays/03-array.ts: -------------------------------------------------------------------------------- 1 | 2 | let emp: MArray = []; 3 | 4 | //Needed to infer mutability 5 | emp.push(1); 6 | emp.pop(); 7 | 8 | assert(!(emp === null)); 9 | -------------------------------------------------------------------------------- /tests/pos/objects/10-object.ts: -------------------------------------------------------------------------------- 1 | /*@ foo:: (o: { (Immutable) x: number; }) => { (Immutable) x: number + boolean } */ 2 | export function foo(o) { 3 | return o; 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/objects/13-object.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: ((Mutable){ x: { v: number | v > 10 }; y: string + number }) => void */ 2 | function foo(o):void { 3 | o.x = 20; 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/operators/cond-expr-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ main :: (x: number) => { v:number | v != 0 } */ 3 | function main(x: number): number { 4 | return x ? x : (x + 1); 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/operators/str.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ baz :: () => {v: string | v = "cat"} */ 3 | export function baz(): string { 4 | let z: string = "cat"; 5 | return z; 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/simple/60-ref-in-constructor.ts: -------------------------------------------------------------------------------- 1 | class Foo { 2 | /*@ new (x: number, y: {number | v < x}): Foo */ 3 | constructor(x, y) { } 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/simple/65-bitvectors.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly foo :: bitvector32 */ 3 | let foo = 0x00000000; 4 | 5 | /*@ readonly bar :: bitvector32 */ 6 | let bar = 0x00000001; 7 | -------------------------------------------------------------------------------- /tests/neg/lists/list-04.ts: -------------------------------------------------------------------------------- 1 | /*@ hop :: (LList) => List */ 2 | function hop(xs){ 3 | return xs; 4 | } 5 | 6 | -------------------------------------------------------------------------------- /tests/neg/loops/while-02.ts: -------------------------------------------------------------------------------- 1 | /*@ loop :: () => { number | v = 1 } */ 2 | function loop(){ 3 | let x = 1; 4 | while (x === 1) { 5 | x = 2; 6 | } 7 | return x; 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/misc/43-top-level.ts: -------------------------------------------------------------------------------- 1 | let a = 1; 2 | 3 | module A { 4 | /*@ foo :: () => { number | v < 0 } */ 5 | function foo() { 6 | return a ; 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/simple/43-func-invariant.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (f: () => void) => {number | v > 4 } */ 2 | export function foo(f) { 3 | if (f) return 3; 4 | return undefined; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/misc/46-underscore.ts: -------------------------------------------------------------------------------- 1 | module foo { 2 | 3 | /*@ _ :: number */ 4 | declare let _: number; 5 | 6 | /*@ $ :: string */ 7 | declare let $; 8 | 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/operators/add-01.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(): number { 3 | let x: number = 0; 4 | let y: number = x + 1; 5 | assert(0 < y); 6 | return y 7 | } 8 | -------------------------------------------------------------------------------- /tests/todo/neg/proto/proto-lookup1.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ({ __proto__: { x: string }, *: number }) => { string | 0 < 1 } */ 3 | function foo(o) { 4 | return o.x; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/todo/neg/proto/proto-lookup7.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ({ __proto__: { x: string }, x: number }) => { string | 0 < 1 } */ 3 | function foo(o) { 4 | return o.x; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/neg/arrays/25-array.ts: -------------------------------------------------------------------------------- 1 | 2 | declare function uniqueAlias(x: UArray, y: UArray): void; 3 | 4 | let a = new Array(10); 5 | 6 | uniqueAlias(a, a); 7 | -------------------------------------------------------------------------------- /tests/neg/enums/02-enum.ts: -------------------------------------------------------------------------------- 1 | 2 | enum Operator { 3 | ADD, 4 | DIV, 5 | MUL, 6 | SUB 7 | } 8 | 9 | // Unimplemented 10 | assert(Operator[Operator.ADD] === "SUB"); 11 | -------------------------------------------------------------------------------- /tests/neg/lists/list-03.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ hop :: (LList) => LList */ 4 | function hop(xs){ 5 | return xs; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/misc/incr3.ts: -------------------------------------------------------------------------------- 1 | /*@ incr3 :: (x:number) => {number | v = x + 3} */ 2 | function incr3(x:number):number{ 3 | ++x; 4 | ++x; 5 | x++; 6 | ++x; 7 | return x; 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/operators/lor-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: undefined + number, y: { number | v >= 0 }) => { number | 0 < 1 } */ 3 | function foo(x,y) { 4 | return y || x; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/neg/simple/36-truthy.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ simple :: (x: number) => { v:number | (v != 0) } */ 3 | function simple(x) { 4 | if (!x) 5 | return x; 6 | return 1; 7 | } 8 | -------------------------------------------------------------------------------- /tests/neg/simple/bad-spec-00.ts: -------------------------------------------------------------------------------- 1 | class Blah { 2 | constructor() {} 3 | 4 | /*@ foo() : void */ 5 | foo() {} 6 | 7 | /*@ foo() : void */ 8 | bar() {} 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/arrays/17-array.ts: -------------------------------------------------------------------------------- 1 | /*@ myArray :: { IArray | (len v) = 1 } */ 2 | declare let myArray: string[]; 3 | 4 | 5 | assert(typeof myArray[0] === "string"); 6 | 7 | 8 | -------------------------------------------------------------------------------- /tests/pos/loops/while-02.ts: -------------------------------------------------------------------------------- 1 | /*@ loop :: () => { number | v != 1 } */ 2 | function loop(){ 3 | let x = 1; 4 | while (x === 1) { 5 | x = 2; 6 | } 7 | return x; 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/unions/test-07.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(x: number | boolean): number | string { 3 | if (typeof x === "number") 4 | return x; 5 | return "a"; 6 | } 7 | -------------------------------------------------------------------------------- /tests/todo/pos/operators/eq.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (x:number) => string */ 2 | function foo(x:number):string { 3 | if (x == 3) { 4 | return "three" 5 | } 6 | return "not three" 7 | } 8 | -------------------------------------------------------------------------------- /tests/neg/arrays/04-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ writeIndex :: (a: IArray, i: { number | v < len a }) => void */ 3 | function writeIndex(a, i) { 4 | a[i] = 10; 5 | return; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/arrays/14-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ where :: ( ) => { IArray | len v = 2 } */ 3 | function where() { 4 | let result = new Array(20); 5 | return result; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/bounded-poly/01-test.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | export function foo(x: V): V { 4 | return x; 5 | } 6 | 7 | assert(foo(1) === 2); 8 | assert(foo("") === ""); 9 | -------------------------------------------------------------------------------- /tests/neg/bounded-poly/03-test.ts: -------------------------------------------------------------------------------- 1 | 2 | function foo(x: number): number { 3 | return x; 4 | } 5 | 6 | export function main() { 7 | assert(foo(2) === 3); 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/lists/list-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ hop :: (LList) => LList */ 3 | function hop(xs){ 4 | return tail(xs); 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/misc/40-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | function idp(x: A): A { return x; } 3 | 4 | /*@ f :: (x: number) => number */ 5 | let f = <(x: number) => number> idp; 6 | 7 | assert(f(6) === 5) ; 8 | -------------------------------------------------------------------------------- /tests/pos/arrays/13-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (cat: number) => IArray<{ number | v >= cat }> */ 3 | function bar(cat : number) : number[] { 4 | return [cat, cat + 1, cat + 2]; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/arrays/23-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Length(v: a): len v = 6 */ 3 | /*@ qualif LtN(v: int): v < 7 */ 4 | 5 | let a: IArray = [1,2,3,4,5,6] 6 | 7 | assert(a[5] <= 10); 8 | -------------------------------------------------------------------------------- /tests/pos/bounded-poly/03-test.ts: -------------------------------------------------------------------------------- 1 | 2 | function foo(x: number): number { 3 | return x; 4 | } 5 | 6 | export function main() { 7 | assert(foo(2) === 2); 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/simple/21-conditional-expression.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (f: () => posint) => posint */ 3 | export function bar(f) { 4 | return (typeof f === "function") ? f() : f; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/simple/26-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: A) => A */ 3 | export function foo(x: any): any { 4 | if (0 < 1) { 5 | return x; 6 | } 7 | return 1; 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/simple/43-func-invariant.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (f: () => void) => { number | v > 2 } */ 3 | export function foo(f) { 4 | if (f) return 3; 5 | return undefined; 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/simple/59-qualgen.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => List */ 3 | function foo() { 4 | let obj = { data: 12, next: null }; 5 | 6 | return obj; 7 | } 8 | -------------------------------------------------------------------------------- /tests/todo/pos/pemissions/test-03.ts: -------------------------------------------------------------------------------- 1 | 2 | // Use uniqueness to capture effectful operations 3 | 4 | let a = new Array(); 5 | a.push(1); 6 | a.push(2); 7 | assert(a.length === 2); 8 | -------------------------------------------------------------------------------- /doc/talk/SoCal-05-2015/images/Screenshot-from-2015-04-30-08-29-12.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UCSD-PL/refscript/HEAD/doc/talk/SoCal-05-2015/images/Screenshot-from-2015-04-30-08-29-12.png -------------------------------------------------------------------------------- /doc/talk/SoCal-05-2015/images/Screenshot-from-2015-05-01-16-19-23.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UCSD-PL/refscript/HEAD/doc/talk/SoCal-05-2015/images/Screenshot-from-2015-05-01-16-19-23.png -------------------------------------------------------------------------------- /tests/neg/arrays/06-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (cat: number) => IArray<{ number | v >= cat }> */ 3 | function bar(cat : number) : number[] { 4 | return [cat, cat - 1, cat + 2]; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/neg/operators/conditional-00.ts: -------------------------------------------------------------------------------- 1 | //adapted from transducers 2 | 3 | /*@ foo :: () => {string | 0 < 1} */ 4 | function foo() { 5 | let bar = false ? 3 : null; 6 | return bar; 7 | } 8 | -------------------------------------------------------------------------------- /tests/neg/operators/conditional-01.ts: -------------------------------------------------------------------------------- 1 | //adapted from transducers 2 | 3 | /*@ foo :: () => {string | 0 < 1} */ 4 | function foo() { 5 | let bar = true ? 3 : null; 6 | return bar; 7 | } 8 | -------------------------------------------------------------------------------- /tests/neg/operators/lor-05.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: undefined + { number | v > 1}, y: { number | v > 2}) => { number | v > 2 } */ 3 | export function foo(x, y) { 4 | return x || y; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/operators/test-bad-00.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: () => number */ 2 | function foo() 3 | { 4 | let x = 0; 5 | let y = x + 1; 6 | assert(10 < y); 7 | return y 8 | } 9 | 10 | 11 | -------------------------------------------------------------------------------- /tests/pos/arrays/25-array.ts: -------------------------------------------------------------------------------- 1 | 2 | declare function fromIArray(x: IArray, y: IArray): void; 3 | 4 | let a: IArray = new Array(10); 5 | 6 | fromIArray(a, a); 7 | -------------------------------------------------------------------------------- /tests/pos/operators/lor-05.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: undefined + { number | v > 1}, y: { number | v > 2}) => { number | v > 1 } */ 3 | export function foo(x, y) { 4 | return x || y; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/operators/tags.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ moo :: (number) => {v:string | v = "number"} */ 3 | export function moo(x: number): string { 4 | let z: string = typeof (x); 5 | return z; 6 | } 7 | -------------------------------------------------------------------------------- /tests/todo/ssa-bug-3.ts: -------------------------------------------------------------------------------- 1 | 2 | let j = 5; 3 | let merged = new Array(j); 4 | 5 | while (1 >= 0) { 6 | while (j > 0) { 7 | j--; 8 | merged[j] = 3; 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/lists/list-02.ts: -------------------------------------------------------------------------------- 1 | /*@ hop :: (List) => LList */ 2 | function hop(xs){ 3 | let t = tail(xs); 4 | return t; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /tests/neg/operators/conditional-02.ts: -------------------------------------------------------------------------------- 1 | //adapted from transducers 2 | 3 | /*@ foo :: () => { number | v = 5 } */ 4 | function foo() { 5 | let bar = true ? 3 : null; 6 | return bar + 1; 7 | } 8 | -------------------------------------------------------------------------------- /tests/neg/operators/stmt-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (number, boolean) => {number| 0 < 1} */ 3 | function foo(x, y){ 4 | x = x + 1; 5 | y = y + 1; 6 | assert(x === y); 7 | return x + y; 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/scope/init-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | let r: number = (cnd) ? 1 : -2; 5 | return r; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/simple/21-conditional-expression.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (f: () => posint) => { number | v < 0 } */ 3 | export function bar(f) { 4 | return (typeof f === "function") ? f : f(); 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/objects/22-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ global a_unique_obj :: (Unique) { a: number; b: number }*/ 3 | let a_unique_obj = { a: 0, b: 0 }; 4 | 5 | a_unique_obj.a = 0; 6 | // a_unique_obj.b = 1; 7 | -------------------------------------------------------------------------------- /tests/pos/operators/cond-expr-01.ts: -------------------------------------------------------------------------------- 1 | //adapted from transducers 2 | 3 | /*@ foo :: () => { number | v = 4 } */ 4 | export function foo() { 5 | return ((true ? 3 : null)) + 1; 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/scope/init-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | let r: number = (cnd) ? 1 : 2; 5 | return r; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/arrays/02-array.ts: -------------------------------------------------------------------------------- 1 | /*@ index :: (a: IArray, i: {number| 0 <= v && v <= len a}) => number */ 2 | export function index(a:number[], i:number) : number { 3 | return a[i]; 4 | } 5 | -------------------------------------------------------------------------------- /tests/neg/arrays/23-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (IArray, (number, number, number, number) => string) => { IArray | 0 < 1 } */ 3 | function bar(arr, f) { 4 | return arr.map(f); 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/misc/57-unite.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (A, B) => A */ 2 | export function foo(x: any, y: any) { 3 | if (x === y) { 4 | return x; 5 | } else { 6 | return y; 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/simple/12-unbound-tvar.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (a: IArray) => { v: number | v >= 0 && v = (len a) } */ 3 | export declare function foo(a: IArray): number; 4 | 5 | let a = foo([1,2]); 6 | -------------------------------------------------------------------------------- /tests/neg/typealias/talias-03.ts: -------------------------------------------------------------------------------- 1 | /*@ predicate gt x y = x >= y */ 2 | /*@ type gArray[x] = IArray<{number | gt(v, x)}> */ 3 | 4 | /*@ ga :: #gArray[1] */ 5 | let ga = [0,0,0,0]; 6 | -------------------------------------------------------------------------------- /tests/pos/arrays/08-array.ts: -------------------------------------------------------------------------------- 1 | /*@ index :: (a: IArray, i: {number|(0 <= v && v < (len a))}) => number */ 2 | export function index(a: number[], i: number): number { 3 | return a[i]; 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/bounded-poly/04-test.ts: -------------------------------------------------------------------------------- 1 | 2 | function foo(x: V, y: number, z: V): V { 3 | return x; 4 | } 5 | 6 | export function main() { 7 | assert(foo(2, 2, 2) === 2); 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/operators/pos.ts: -------------------------------------------------------------------------------- 1 | 2 | export function main(): number { 3 | let y: number = 0; 4 | let x: number = _pos(); 5 | assert(0 <= y); 6 | assert(0 <= x); 7 | return y; 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/simple/46-contextual.ts: -------------------------------------------------------------------------------- 1 | 2 | interface IPoint { x: number; y: number } 3 | 4 | export declare function bar(p: IPoint): void; 5 | 6 | bar({ x: 1, y: 2 }); 7 | -------------------------------------------------------------------------------- /tests/todo/neg/misc/circular-logic.ts: -------------------------------------------------------------------------------- 1 | foo(); 2 | /*@ foo :: () => {void | false} */ 3 | function foo() { } // this should fail, but the call on line 1 lets false into the environment so it passes? 4 | -------------------------------------------------------------------------------- /tests/neg/objects/10-object.ts: -------------------------------------------------------------------------------- 1 | /*@ foo:: (o: { (Mutable) x: number; }) => { (Mutable) x: number + boolean } */ 2 | export function foo(o: { x: number; }): { x: number | boolean } { 3 | return o; 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/lists/list-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Gt10(v:number): 10 < v */ 3 | 4 | /*@ foo :: () => List */ 5 | function foo() { 6 | return { data: 12, next: null }; 7 | } 8 | 9 | -------------------------------------------------------------------------------- /tests/neg/loops/while-01.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | /*@ loop :: () => { number | v = 800 } */ 5 | function loop() { 6 | let x = 1; 7 | while (x <= 5) { 8 | x = x + 1; 9 | } 10 | return x; 11 | } 12 | -------------------------------------------------------------------------------- /tests/neg/simple/10-func-expression.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo2 :: () => () => undefined */ 3 | export function foo2() { 4 | assert(false); 5 | return function() { 6 | return undefined; 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/unions/test-13.ts: -------------------------------------------------------------------------------- 1 | /*@ type pos = { number | v > 0 } */ 2 | type pos = number; 3 | 4 | /*@ foo :: (x: boolean + pos) => void */ 5 | declare function foo(x: number | boolean): void; 6 | 7 | foo(-1); 8 | -------------------------------------------------------------------------------- /tests/pos/lists/emp-01.ts: -------------------------------------------------------------------------------- 1 | /*@ boop :: (List) => {v:boolean | 0 < 1} */ 2 | function boop(xs : List) : boolean{ 3 | return emptyPoly(xs) 4 | } 5 | -------------------------------------------------------------------------------- /tests/pos/unions/test-14.ts: -------------------------------------------------------------------------------- 1 | 2 | declare function ofNumber(x: number): void; 3 | 4 | export function foo(x: number | boolean) { 5 | if (typeof x === "number") { 6 | ofNumber(x); 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /tests/todo/pos/objects/04-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { v: number | v = 5 } */ 3 | function foo () { 4 | var obj = {f1: {f11: 1} }; 5 | return obj["f1"].f11 + obj.f1["f11"] + obj["f1"]["f11"]; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/misc/09-fixme.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ work :: () => void */ 3 | function work(){ 4 | return; 5 | } 6 | 7 | /*@ bar :: () => {v:number | v = 0} */ 8 | function bar(){ 9 | work(); 10 | return 6; 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/loops/for-07.ts: -------------------------------------------------------------------------------- 1 | //adapted from navier-stokes-typed-octane.ts 2 | 3 | for (let j = 1; j <= 3; j++) { 4 | let i = 7; 5 | } 6 | 7 | for (let k = 1; k <= 3; k++) { 8 | let i = 8; 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/simple/44-overload.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (f: () => posint) => posint */ 3 | /*@ bar :: (f: number) => number */ 4 | export function bar(f) { 5 | return (typeof f === "function") ? f() : f; 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/unions/test-13.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ type pos = { number | v > 0 } */ 3 | type pos = number; 4 | 5 | /*@ foo :: (x: boolean + pos) => void */ 6 | declare function foo(x: number | boolean): void; 7 | 8 | foo(1); 9 | -------------------------------------------------------------------------------- /tests/neg/arrays/00-array.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (IArray) => number */ 2 | function foo(a) { 3 | return a[0]; 4 | } 5 | 6 | foo([]); 7 | foo([1]); 8 | foo([1,2]); 9 | foo([1,2,3]); 10 | foo([1,2,3,4]); 11 | -------------------------------------------------------------------------------- /tests/neg/operators/lor-00.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | /*@ foo :: (x:null, y: { number | v > 1 } ) => { number | v > 11 } */ 5 | function foo(x,y) { 6 | return x || y; // works due to contextual type "nunber" 7 | } 8 | 9 | -------------------------------------------------------------------------------- /tests/neg/unions/test-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ negate :: (x: {v: number | v > 0} + boolean) => { v: number | v > 0 } + boolean */ 3 | function negate(x): any { 4 | return (typeof (x) === "number") ? (0 - x) : (!x); 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/inclusion/10-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(o: IArray): number { 3 | let ret = 0; 4 | 5 | for (let k in o) { 6 | ret += o[k]; 7 | } 8 | 9 | return ret; 10 | }; 11 | -------------------------------------------------------------------------------- /tests/pos/lists/safehead.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ getHead :: (LList) => { number | 0 < 1 } */ 3 | function getHead(xs){ 4 | if (empty(xs)) { 5 | return 1; 6 | } 7 | return safehead(xs); 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/operators/add-02.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(x: number): number { 3 | let y: number = 0; 4 | if (0 < x) { 5 | y = x + y; 6 | assert(0 <= y); 7 | } 8 | return y; 9 | } 10 | -------------------------------------------------------------------------------- /tests/neg/arrays/13-array.ts: -------------------------------------------------------------------------------- 1 | 2 | export function revInc(a: MArray): IArray { 3 | a.reverse(); 4 | for (let i = 0; i < a.length; i++) { 5 | a[i] = a[i] + 1; 6 | } 7 | return a; 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/lists/emp-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ boop :: (List) => {v:boolean | Prop v} */ 3 | function boop(xs : List) : boolean{ 4 | let r = empty(xs); 5 | return r; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/simple/48-undead.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ noop :: (u: top) => void */ 3 | function noop(u) { } 4 | 5 | /*@ foo :: (u : boolean) => void */ 6 | export function foo(u) { 7 | noop(u); 8 | assert(false); 9 | } 10 | -------------------------------------------------------------------------------- /tests/neg/simple/67-return-false.ts: -------------------------------------------------------------------------------- 1 | 2 | foo(); 3 | 4 | /*@ foo :: () => {void | false} */ 5 | export function foo() { } 6 | 7 | // this should fail, but the call on line 1 lets false into the environment so it passes? 8 | -------------------------------------------------------------------------------- /tests/pos/lists/emp-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ boop :: (List) => {v:boolean | 0 < 1} */ 3 | function boop(xs : List) : boolean{ 4 | let r = empty(xs); 5 | return r; 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/scope/10-initialization.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | /*@ r :: number */ 5 | let r = (cnd) ? 1 : 2; 6 | return r; 7 | } 8 | -------------------------------------------------------------------------------- /tests/pos/simple/25-field-update.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly x_25 :: (Mutable) { f: posint } */ 3 | let x_25 = { f: 1 }; 4 | 5 | module A { 6 | export function foo(): void { 7 | x_25.f = 2; 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /tests/todo/pos/pemissions/test-01.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ g :: (a: { int | v = b.x }, b: { @IM x: int; @MU y: int }) => void */ 4 | declare function g(a: number, b: { x: number; y: number }): void; 5 | 6 | g(1, { x: 1, y: 1 }); 7 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup4.ts: -------------------------------------------------------------------------------- 1 | function foo(o, s) 2 | /*: { __proto__: {y: Bool, __proto__: Object, z: _ }, y: _, z: _, x: Num} 3 | * /(x|(y|z))/ 4 | -> Num + Bool + Undef */ { 5 | return o[s]; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/objects/19-object.ts: -------------------------------------------------------------------------------- 1 | 2 | // Cannot reference unique object in the context of 3 | // an object literal member 4 | 5 | let uniqueInnerObj = { n: 6 }; 6 | 7 | let uniqueObj = { a: 5, b: "String", c: uniqueInnerObj }; 8 | -------------------------------------------------------------------------------- /tests/neg/scope/00-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | let a = 1; 3 | 4 | 5 | 6 | module A { 7 | 8 | 9 | export function foo(): void { 10 | assert(a === 1); 11 | } 12 | 13 | a++; 14 | 15 | foo(); 16 | 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/lists/listsum-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ listsum :: (List) => number */ 3 | function listsum(xs:List):number { 4 | let t = tail(xs); 5 | return listsum(t); 6 | } 7 | 8 | -------------------------------------------------------------------------------- /tests/pos/simple/12-runtime-tags.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(f: () => number): number; 3 | export function foo(f: number): number 4 | export function foo(f: any): number { 5 | return (typeof f === "function") ? f() : f; 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/unions/test-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ check_undefined :: (x: T + undefined) => T */ 3 | export function check_undefined(x: any): T { 4 | if (typeof x === "undefined") 5 | return crash(); 6 | return x; 7 | } 8 | -------------------------------------------------------------------------------- /tests/todo/pos/objects/abs-mut.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif G10(v: int): v > 10 */ 2 | 3 | /*@ hop :: (x: List) => List */ 4 | export function hop(x) { 5 | return { data: 15, next: null }; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/loops/for-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { number | v = 10 } */ 3 | 4 | function foo() { 5 | 6 | let x = 1; 7 | 8 | for (let i = 0; i < 5; i ++) { 9 | x = i; 10 | } 11 | 12 | return x; 13 | 14 | } 15 | -------------------------------------------------------------------------------- /tests/neg/operators/lor-06.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:null, y: number) => posint */ 3 | export function foo(x,y) { 4 | return x || y; // no contextual type here -- hence using 5 | // the explicit cast 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/simple/25-field-update.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly x_25 :: (Mutable) { f: posint } */ 3 | let x_25 = { f: 1 }; 4 | 5 | module A { 6 | 7 | export function foo(): void { 8 | x_25.f = 0; 9 | } 10 | 11 | } 12 | -------------------------------------------------------------------------------- /tests/neg/simple/27-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | export declare function bar(): boolean; 3 | 4 | export function foo(x: A): A { 5 | let a = undefined; 6 | if (bar()) { 7 | a = x; 8 | } 9 | return a; 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/simple/44-overload.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ bar :: (() => number) => { number | v > 0 } */ 4 | /*@ bar :: (number) => number */ 5 | export function bar(f) { 6 | return (typeof f === "function") ? f : f(); 7 | } 8 | -------------------------------------------------------------------------------- /tests/neg/simple/52-bitvector.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ a :: { v: bitvector32 | v = lit "#x00000001" (BitVec Size32) } */ 3 | let a = 0x00000001; 4 | 5 | 6 | if (a) { 7 | assert(false); 8 | } 9 | else { 10 | assert(true); 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/inclusion/00-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif HasP (p: Str, x: a): hasProperty x p */ 3 | 4 | export function values(m: { [k: string]: T }): void { 5 | for (let k in m) { 6 | let b = (m[k]); 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/misc/43-top-level.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly */ 3 | let a = 1; 4 | 5 | 6 | module A { 7 | 8 | 9 | /*@ foo :: () => { number | v > 0 } */ 10 | function foo():number { 11 | return a ; 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/objects/21-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ global a_unique_obj :: { c: posint } */ 3 | let a_unique_obj = { c: 3 }; 4 | 5 | /*@ global another_obj :: { c: number } */ 6 | let another_obj = { c: 10 }; 7 | 8 | another_obj = a_unique_obj; 9 | -------------------------------------------------------------------------------- /tests/pos/operators/lor-06.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:null, y: posint) => posint */ 3 | export function foo(x,y) { 4 | return x || y; // no contextual type here -- hence using 5 | // the explicit cast 6 | } 7 | -------------------------------------------------------------------------------- /tests/pos/simple/52-bitvector.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ a :: { v: bitvector32 | v = lit "#x00000001" (BitVec Size32) } */ 3 | let a = 0x00000001; 4 | 5 | 6 | if (a) { 7 | assert(true); 8 | } 9 | else { 10 | assert(false); 11 | } 12 | -------------------------------------------------------------------------------- /tests/todo/pos/pemissions/test-04.ts: -------------------------------------------------------------------------------- 1 | 2 | // Use uniqueness to capture effectful operations 3 | 4 | let a = new Array(); 5 | 6 | for (let i = 0; i < 10; i ++) { 7 | a.push(i); 8 | } 9 | 10 | assert(a.length === 10); 11 | -------------------------------------------------------------------------------- /tests/neg/misc/39-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Bot(v: number): v = 5 */ 3 | /*@ qualif Bot(v: number): v = 6 */ 4 | 5 | function idp(x: A): A { return x; } 6 | 7 | let f = <(x: number) => number> idp; 8 | 9 | assert(f(5) === 6); 10 | -------------------------------------------------------------------------------- /tests/neg/scope/init-06.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(n: number): number { 3 | /*@ local r :: number + undefined */ 4 | let r; 5 | while (n < 10) { 6 | r = 1; 7 | n++; 8 | } 9 | return r; 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/simple/13-contextual.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (a: IArray, is: IArray>) => { IArray | len v = len is } */ 3 | declare function foo(array: T[], is:number[]) : T[]; 4 | 5 | assert(foo([1,2,3],[2,1,0]).length === 2); 6 | -------------------------------------------------------------------------------- /tests/pos/loops/for-06.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(): void { 3 | for (let x = 1; x < 3; x++) { } 4 | } 5 | 6 | export function bar(): void { 7 | let x; 8 | for (x = 1; x < 3; x++) { } 9 | assert(x >= 3); 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/operators/stmt.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number, { number | v = x }) => number */ 3 | export function foo(x: number, y: number): number { 4 | x = x + 1; 5 | y = y + 1; 6 | assert(x === y); 7 | return x + y; 8 | } 9 | -------------------------------------------------------------------------------- /tests/todo/neg/simple/66-variadic.ts: -------------------------------------------------------------------------------- 1 | /*@ bar :: (this: Array) => number */ 2 | function bar () { 3 | this.push(1); 4 | return this.length; 5 | } 6 | 7 | var a = bar.call([1,2,3,4]); 8 | assert(a === 4); 9 | 10 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup3.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: ( { __proto__: {y: boolean}, x: number}, 2 | {string | ((v = "x") || (v = "y")) }) 3 | => number + { boolean | 0 < 1 } */ 4 | function foo(o, s) { 5 | return o[s]; 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/lists/list-06.ts: -------------------------------------------------------------------------------- 1 | /*@ hop :: (List) => LList */ 2 | function hop(xs){ 3 | if (! empty(xs)) { 4 | return xs; 5 | } 6 | return { data: 15, next: null }; 7 | } 8 | 9 | -------------------------------------------------------------------------------- /tests/neg/lists/list-08.ts: -------------------------------------------------------------------------------- 1 | /*@ hop :: (LList) => List */ 2 | function hop(xs){ 3 | if (! empty(xs)) { 4 | return xs; 5 | } 6 | return { data: 15, next: null }; 7 | } 8 | 9 | -------------------------------------------------------------------------------- /tests/neg/misc/08-global.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ({v:number|v>0}) => {v:number|v<0} */ 3 | function foo(a) { 4 | 5 | /*@ bar :: () => void */ 6 | function bar() { 7 | a = -a; 8 | } 9 | bar(); 10 | 11 | return a; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/scope/02-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ g :: number */ 3 | let g = 1; 4 | 5 | /*@ inc :: (xxx: number) => { number | v = xxx + 1 } */ 6 | function inc(xxx: number): number { 7 | return xxx + 1; 8 | } 9 | 10 | assert(inc(g) === 3); 11 | -------------------------------------------------------------------------------- /tests/neg/typealias/talias-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ type Nat = {v: number | 10 <= v } */ 3 | 4 | /*@ ab :: (number) => Nat */ 5 | export function ab(x:number): number { 6 | if (x > 0){ 7 | return x; 8 | } 9 | return (0 - x); 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/inclusion/02-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ d3_vendorSymbol :: (object: {}, name: string) => { boolean | ((Prop v) <=> hasProperty(object, name)) } */ 3 | function d3_vendorSymbol(object:any, name:string) { 4 | return name in object; 5 | } 6 | -------------------------------------------------------------------------------- /tests/pos/inclusion/04-inclusion.ts: -------------------------------------------------------------------------------- 1 | /*@ option --extrainvs */ 2 | 3 | // Arrays 4 | let trees: IArray = ["redwood", "bay", "cedar", "oak", "maple"]; 5 | 6 | assert("length" in trees); // returns true (length is an assert property) 7 | -------------------------------------------------------------------------------- /tests/pos/inclusion/06-inclusion.ts: -------------------------------------------------------------------------------- 1 | /*@ option --extrainvs */ 2 | 3 | // Custom objects 4 | let mycar = {make: "Honda", model: "Accord", year: 1998}; 5 | assert("make" in mycar); // returns true 6 | assert("model" in mycar); // returns true 7 | -------------------------------------------------------------------------------- /tests/pos/loops/double-for.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo() { 3 | let a = 0; 4 | 5 | for (let j = 1; j <= 3; j++) { 6 | for (let i = 1; i <= 3; i++) { 7 | ++a; 8 | } 9 | } 10 | ++a; 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/misc/06-cousot.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ loop :: (n:number, {m:number | m = n}) => void */ 3 | function loop(n: number, m: number) { 4 | 5 | n = n + 1; 6 | m = m + 1; 7 | 8 | assert(m === n); 9 | 10 | return; 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/misc/48-unite.ts: -------------------------------------------------------------------------------- 1 | 2 | function foo(x: A, y: A): A { 3 | if (x === y) { 4 | return x; 5 | } else { 6 | return y; 7 | } 8 | } 9 | 10 | export function bar(x: A,y: A): A { 11 | return foo(x,y); 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ type Nat = {v: number | 0 <= v } */ 3 | 4 | /*@ ab :: (number) => Nat */ 5 | export function ab(x:number): number { 6 | if (x > 0){ 7 | return x; 8 | } 9 | return (0 - x); 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/inclusion/00-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif HasP (p: Str, x: a): hasProperty x p */ 3 | 4 | 5 | export function values(m: { [k: string]: T }): void { 6 | for (let k in m) { 7 | let b = (m["k"]); 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /tests/neg/lists/list-05.ts: -------------------------------------------------------------------------------- 1 | /*@ hop :: (LList) => LList */ 2 | function hop(xs){ 3 | if (! empty(xs)) { 4 | return xs; 5 | } 6 | return { data: 15, next: null }; 7 | } 8 | 9 | -------------------------------------------------------------------------------- /tests/neg/loops/obj-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { a: { number | v = 1 } } */ 3 | function foo(): Object { 4 | let x = { a: 1 }; 5 | for (let i = 0; i < 5; i++) { 6 | x = { a: 2 }; 7 | } 8 | return x; 9 | 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/simple/26-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | export declare function ff(): number; 3 | 4 | /*@ foo :: (x: A) => A */ 5 | export function foo(x: any): any { 6 | if (0 < ff()) { 7 | return x; 8 | } 9 | return 1; 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/simple/57-non-linear.ts: -------------------------------------------------------------------------------- 1 | /*@ option --real */ 2 | 3 | /*@ type nat = {number | v >= 0} */ 4 | 5 | /*@ foo :: (x:nat, y:nat) => void */ 6 | export function foo(x, y) { 7 | assert((x + 1) + (y + 3) * (x + 2) < (x + 2) * (y + 2)); 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/loops/while-01.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Ineq(v : int ): (v <= 6) */ 2 | 3 | /*@ loop :: () => { number | v = 6 } */ 4 | function loop() { 5 | let x = 1; 6 | while (x <= 5) { 7 | x = x + 1; 8 | } 9 | return x; 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/misc/17-init.ts: -------------------------------------------------------------------------------- 1 | 2 | // crash is from the prelude.ts 3 | // crash :: forall A. () => A 4 | // declare function crash(): A; 5 | 6 | 7 | export function init(n:number):T{ 8 | let x:T = crash(); 9 | return x; 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/operators/lor-00.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(): void { 3 | let a = _pos(); 4 | let b = random() 5 | 6 | if (a || b) { 7 | assert(true); 8 | } 9 | else { 10 | assert(false); 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/scope/00-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ b :: { number | v >= 2 } */ 3 | let b = 2; 4 | 5 | 6 | module A { 7 | 8 | 9 | export function foo(): void { 10 | assert(++b >= 2); 11 | } 12 | 13 | foo(); 14 | 15 | 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/simple/57-non-linear.ts: -------------------------------------------------------------------------------- 1 | /*@ option --real */ 2 | 3 | /*@ type nat = {number | v >= 0} */ 4 | 5 | /*@ foo :: (x:nat, y:nat) => void */ 6 | export function foo(x, y) { 7 | assert((x + 1) + (y + 1) * (x + 2) < (x + 2) * (y + 2)); 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/inclusion/06-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ option --extrainvs */ 3 | 4 | // Custom objects 5 | let mycar = {make: "Honda", model: "Accord", year: 1998}; 6 | assert("make?" in mycar); // returns false 7 | assert("model_" in mycar); // returns false 8 | -------------------------------------------------------------------------------- /tests/neg/loops/obj-04.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { a: { number | 40 = v } } */ 3 | 4 | function foo() { 5 | 6 | let x = { a: 1 }; 7 | 8 | for (let i = 0; i < 5; i++) { 9 | x = { a: i }; 10 | } 11 | 12 | return x; 13 | 14 | } 15 | -------------------------------------------------------------------------------- /tests/neg/misc/abs.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ abs :: (x:number) => {v:number | 0 < 1} */ 3 | function abs(x){ 4 | let res = 0; 5 | if (x > 0) { 6 | res = x; 7 | } else { 8 | res = -x; 9 | }; 10 | assert(res >= 10); 11 | return res; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/operators/lor-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: undefined + number, y:number) => { number | v = 1 } */ 3 | export function foo(x,y) { 4 | if (x || y) { 5 | return 0; 6 | } 7 | else { 8 | return 1; 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/operators/lor-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: posint, y: { string | v = "" }, z: boolean) => posint */ 3 | export function foo(x: number, y: string, z: boolean) { 4 | if (x && (y || z)) { 5 | return 1; 6 | } 7 | return 0; 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/unions/test-14.ts: -------------------------------------------------------------------------------- 1 | 2 | declare function ofBoolean(x: boolean): void; 3 | 4 | export function foo(x: number | boolean) { 5 | let tag = typeof x; 6 | if (tag === "number") { 7 | ofBoolean(x); 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/arrays/16-array.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Length(v: a): len v = 3 */ 2 | 3 | /*@ a :: IArray */ 4 | let a = [1,2,3]; 5 | 6 | /*@ b :: { IArray | len v = 4 } */ 7 | let b = [1,2,3,4]; 8 | 9 | assert(a.length + b.length === 7); 10 | -------------------------------------------------------------------------------- /tests/pos/misc/29-negate.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ negate :: (x: {number | v > 0} + boolean) => { v: number | v > 0 } */ 3 | 4 | function negate(x):any { 5 | if (typeof(x) === "number") { 6 | return x; 7 | } 8 | return 1; 9 | 10 | } 11 | 12 | -------------------------------------------------------------------------------- /tests/pos/operators/lor-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: undefined + number, y: { number | v > 0 }) => number */ 3 | export function foo(x,y) { 4 | if (y || x) { 5 | return 1; 6 | } 7 | else { 8 | return 0; 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/operators/lor-04.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:null, y:number, z: posint) => posint */ 3 | export function foo(x, y, z): number { 4 | if (x || y || z) { 5 | return 1; 6 | } 7 | else { 8 | return 0; 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /src/Language/Rsc/AST.hs: -------------------------------------------------------------------------------- 1 | module Language.Rsc.AST ( 2 | module AST 3 | ) where 4 | 5 | import Language.Rsc.AST.Annotations as AST 6 | import Language.Rsc.AST.Check as AST 7 | import Language.Rsc.AST.Syntax as AST 8 | 9 | -------------------------------------------------------------------------------- /tests/neg/loops/obj-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: (Mutable) { a: number; b: string }) => { number | v > 5 } */ 3 | 4 | function foo(x) { 5 | 6 | for (let i = 0; i < 5; i++) { 7 | x.b = i; 8 | } 9 | 10 | return x.a; 11 | 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/loops/while-04.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: () => { number | 0 < 1 } */ 2 | function foo() { 3 | /*@ local i :: number */ 4 | let i: any = 0; 5 | while (i < 5) { 6 | i = "dog"; // whoops, should be same as outside. 7 | } 8 | return i; 9 | } 10 | -------------------------------------------------------------------------------- /tests/neg/objects/21-object.ts: -------------------------------------------------------------------------------- 1 | 2 | // Cannot re-assign a reference to a unique object 3 | 4 | let a_unique_obj = { c: 3 }; 5 | 6 | /*@ global another_obj :: { c: number } */ 7 | let another_obj = { c: 10 }; 8 | 9 | another_obj = a_unique_obj; 10 | -------------------------------------------------------------------------------- /tests/pos/enums/02-enum.ts: -------------------------------------------------------------------------------- 1 | 2 | enum Operator { ADD, DIV, MUL, SUB } 3 | 4 | assert(Operator.ADD === 0); 5 | 6 | // PV: Disabling support for now 7 | 8 | // assert(Operator[Operator.ADD] === "ADD"); 9 | 10 | // assert(Operator[0] === "ADD") ; 11 | -------------------------------------------------------------------------------- /tests/pos/misc/28-negate.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ negate :: (x: {number | v > 0} + boolean) => { v: number | v < 0 } */ 3 | 4 | function negate(x):any { 5 | if (typeof(x) === "number") { 6 | return 0 - x; 7 | } 8 | return -1 ; 9 | 10 | } 11 | 12 | -------------------------------------------------------------------------------- /tests/pos/scope/02-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ g :: number */ 3 | let g = 1; 4 | 5 | /*@ inc :: (xxx: number) => { number | v = xxx + 1 } */ 6 | export function inc(xxx: number): number { 7 | return xxx + 1; 8 | } 9 | 10 | assert(inc(g) === inc(g)); 11 | -------------------------------------------------------------------------------- /tests/pos/unions/test-04.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ check_undefined :: (T + undefined) => T */ 3 | function check_undefined(x:any) : T { 4 | if (typeof x === "undefined") 5 | return crash(); 6 | return x; 7 | } 8 | 9 | check_undefined(1); 10 | -------------------------------------------------------------------------------- /tests/benchmarks/todo/pldi16/d3/include/number.ts: -------------------------------------------------------------------------------- 1 | /// 2 | 3 | /*@ d3_number :: (x:number + undefined) => {v:boolean | Prop(v) => ttag(x) == "number"} */ 4 | function d3_number(x:any):any{ 5 | return x !== null && !isNaN(x); 6 | } 7 | -------------------------------------------------------------------------------- /tests/neg/lists/list-09.ts: -------------------------------------------------------------------------------- 1 | /*@ hop :: (LList) => List */ 2 | function hop(xs){ 3 | if (empty(xs)) 4 | return { data: 15, next: null }; 5 | else 6 | return xs; 7 | 8 | } 9 | 10 | -------------------------------------------------------------------------------- /tests/neg/misc/01-abs.ts: -------------------------------------------------------------------------------- 1 | export function abs(x: number): number { 2 | let y = x; 3 | if (x > 0) { 4 | y = x; 5 | } else { 6 | y = 10 + x; 7 | }; 8 | assert(y > 10); 9 | assert(y >= 100); 10 | return y; 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/arrays/01-array.ts: -------------------------------------------------------------------------------- 1 | //adapted from tsc 2 | 3 | /*@ filter :: (x: boolean) => IArray + number */ 4 | export function filter(x):any { 5 | if (x) { 6 | return 42; 7 | } 8 | return >new Array(3); 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/arrays/20-array.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Length(v: a): len v = 3 */ 2 | /*@ qualif Length(v: a): len v = 6 */ 3 | 4 | let a1: IArray = [1,2,3]; 5 | let a2: IArray = [4,5,6]; 6 | let a3: IArray = a1.concat(a2); 7 | assert(a3.length === 6); 8 | -------------------------------------------------------------------------------- /tests/pos/misc/27-negate.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ negate :: (xxx: {number | v > 0} + boolean) => { v: number | v < 0 } + boolean */ 3 | function negate(xxx): any { 4 | if (typeof(xxx) === "number") { 5 | return 0 - xxx; 6 | } 7 | return 0 - 1; 8 | 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/simple/04-glob.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif CmpZ(v:int): v = 20 */ 2 | 3 | /*@ global */ let glob = 20; 4 | 5 | 6 | module A { 7 | 8 | function zog() { 9 | glob = 20; 10 | } 11 | zog(); 12 | 13 | assert(glob === 20); 14 | 15 | } 16 | -------------------------------------------------------------------------------- /tests/todo/pos/operators/lor-07.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: posint, y: { string | v = "0" }, z: boolean) => posint */ 3 | export function foo(x: number, y: string, z: boolean) { 4 | if (x && (y || z)) { 5 | return 1; 6 | } 7 | return 0; 8 | } 9 | -------------------------------------------------------------------------------- /tests/todo/pos/simple/67-variadic.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: forall T. (this: { IArray | (len v) = 4 }) => { number | v = (len this) } */ 3 | function bar () { 4 | return this.length; 5 | } 6 | 7 | var a = bar.call([1,2,3,4]); 8 | assert(a === 4); 9 | 10 | -------------------------------------------------------------------------------- /tests/neg/arrays/20-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Length(v: a): len v = 3 */ 3 | /*@ qualif Length(v: a): len v = 8 */ 4 | 5 | let a1: IArray = [1,2,3]; 6 | let a2: IArray = [4,5,6]; 7 | let a3: IArray = a1.concat(a2); 8 | assert(a3.length === 8); 9 | -------------------------------------------------------------------------------- /tests/neg/misc/26-negate.ts: -------------------------------------------------------------------------------- 1 | /*@ negate :: (x: number + boolean) => 2 | { v: number + boolean | (ttag(v) = ttag(x)) } */ 3 | function negate(x): any { 4 | if (typeof(x) === "number") { 5 | return !x; 6 | } else { 7 | return 0 - x; 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /tests/neg/objects/04-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly */ 3 | let x = { 4 | a: 5, 5 | b: "String", 6 | }; 7 | 8 | /*@ foo :: () => { v: number | v = 4 } */ 9 | export function foo() { 10 | let y = { a: 4 } 11 | y = x; 12 | return y.a; 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/typealias/talias-04.ts: -------------------------------------------------------------------------------- 1 | /*@ predicate gt x y = x >= y */ 2 | /*@ type Nat = {number | gt(v, 0) } */ 3 | /*@ type IArrayN = {v:IArray | len v = n} */ 4 | 5 | /*@ ga :: IArrayN */ 6 | let ga = [0,10,20,30]; 7 | -------------------------------------------------------------------------------- /tests/pos/inclusion/03-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Len(v: a): len v = 5 */ 3 | 4 | // Arrays 5 | let trees: IArray = ["redwood", "bay", "cedar", "oak", "maple"]; 6 | assert(0 in trees); // returns true 7 | assert(3 in trees); // returns true 8 | -------------------------------------------------------------------------------- /tests/pos/loops/obj-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Ineq3(v : number ): (5 <= v) */ 3 | 4 | /*@ foo :: (x: (Mutable) { a: number }) => number */ 5 | export function foo(x) : number { 6 | for (let i = 0; i < 5; i ++) { 7 | x.a = i; 8 | } 9 | return x.a; 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/loops/while-03.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Ineq1(v : int ): (v <= 5) */ 2 | 3 | /*@ foo :: () => { number | v = 5 } */ 4 | function foo() : number { 5 | let x = 0; 6 | let i = 1; 7 | while (i < 5) { 8 | x = i; 9 | i = i + 1; 10 | } 11 | return i; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/misc/05-callable-interface.ts: -------------------------------------------------------------------------------- 1 | 2 | interface Foo { 3 | (): number; 4 | (x: string): string; 5 | } 6 | 7 | declare let a: Foo; 8 | 9 | assert(typeof a() === "number"); 10 | assert(typeof a("aa") === "string"); 11 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-03.ts: -------------------------------------------------------------------------------- 1 | /*@ predicate gt x y = x >= y */ 2 | /*@ type Nat = {number | 0 <= v} */ 3 | /*@ type iArrayN = {v: IArray | len v = n } */ 4 | 5 | /*@ ga :: IArray */ 6 | let ga = [0,10,20,30]; 7 | -------------------------------------------------------------------------------- /tests/todo/pos/simple/init-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ init :: (number) => {v: number | 0 <= v} */ 3 | function init(n:number):number{ 4 | let i; 5 | let sum = 0; 6 | while (n > 0) { 7 | i = n; 8 | sum += i; 9 | } 10 | return sum; 11 | } 12 | -------------------------------------------------------------------------------- /tests/neg/operators/cond-expr-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif CmpZ (x: int, v: int): v = x + 1 */ 3 | /*@ qualif CmpZ (v: int): v != 0 */ 4 | 5 | /*@ main :: (x: number) => { v:number | v != 0 } */ 6 | function main(x: number): number { 7 | return x ? (x - 1) : (x + 1); 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/simple/05-glob.ts: -------------------------------------------------------------------------------- 1 | 2 | // Globals are not allowed to apper in refinements 3 | 4 | /*@ a :: posint */ 5 | let a = 1; 6 | 7 | /*@ c :: posint */ 8 | let c = 1; 9 | 10 | a = a - 5; 11 | 12 | /*@ b :: { v: number | v > a && v >= c } */ 13 | let b = 2; 14 | -------------------------------------------------------------------------------- /tests/pos/misc/34-opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => {void | true} */ 3 | /*@ foo :: (l: {number | 0 <= v}) => {void | true} */ 4 | function foo(l?: number) { 5 | /*@ local l1 :: number */ 6 | let l1 = (arguments.length < 1) ? 0 : l; 7 | assert(0 <= l1); 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/operators/lor-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: undefined + number, y:number, z: posint) => { number | v = 1 } */ 3 | export function foo(x, y, z) { 4 | if (x || y || z) { 5 | return 1; 6 | } 7 | else { 8 | return 0; 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/scope/init-05.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => number + undefined */ 3 | export function foo(cnd: boolean): number { 4 | /*@ local r :: number + undefined */ 5 | let r; 6 | if (cnd) { 7 | r = 1; 8 | } 9 | return r; 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/simple/10-func-expression.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number) => () => undefined */ 3 | export function foo(x: number) { 4 | /*@ readonly f :: () => undefined */ 5 | let f = function() { 6 | return undefined; 7 | } 8 | return f; 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-00.ts: -------------------------------------------------------------------------------- 1 | /*@ type Nat = {v: number | 0 <= v } */ 2 | type Nat = number; 3 | 4 | /*@ z :: Nat */ 5 | let z = 12; 6 | 7 | /*@ foo :: (Nat) => void */ 8 | function foo(a) { } 9 | 10 | /*@ bar :: (Nat) => void */ 11 | function bar(a) { } 12 | -------------------------------------------------------------------------------- /tests/neg/arrays/17-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (IArray) => void */ 3 | function bar(a) { 4 | 5 | a[0] = -1; 6 | } 7 | 8 | /*@ foo :: ({ IArray | len v > 0 }) => void */ 9 | function foo(a) { 10 | bar(a); 11 | assert(a[0] > 0); 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/simple/60-opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | function foo(l?: number) { 3 | let lo = l; 4 | 5 | if (arguments.length < 1) { 6 | lo = 0; 7 | } 8 | let lo1 = lo; 9 | assert(0 < lo1); 10 | } 11 | 12 | 13 | foo(); 14 | foo(0); 15 | foo(1); 16 | -------------------------------------------------------------------------------- /tests/pos/classes/30-implements.ts: -------------------------------------------------------------------------------- 1 | //adapted from transducers 2 | 3 | interface Foo {} 4 | 5 | class FooImpl implements Foo { 6 | constructor() { } 7 | } 8 | 9 | /*@ x :: Foo */ 10 | let x = new FooImpl(); 11 | -------------------------------------------------------------------------------- /tests/pos/simple/60-opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | function foo(l?: number) { 3 | let lo = l; 4 | 5 | if (arguments.length < 1) { 6 | lo = 0; 7 | } 8 | let lo1 = lo; 9 | assert(0 <= lo1); 10 | } 11 | 12 | 13 | foo(); 14 | foo(0); 15 | foo(1); 16 | -------------------------------------------------------------------------------- /tests/pos/simple/62-tvars.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: IArray) => T + undefined */ 3 | export function foo(x: IArray): T { 4 | /*@ b :: T + undefined */ 5 | let b: T; 6 | if (x.length > 0) { 7 | b = x[0]; 8 | } 9 | return b; 10 | } 11 | -------------------------------------------------------------------------------- /tests/demo/poly.ts: -------------------------------------------------------------------------------- 1 | 2 | function idd(x:A):A { 3 | return x; 4 | } 5 | 6 | function bar(x: A, f: (x: A) => A): A { 7 | return f(x); 8 | } 9 | 10 | export function main(x: number): number { 11 | return bar(x, idd); // this is actually (idd @ number) 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/simple/35-modules.ts: -------------------------------------------------------------------------------- 1 | module M { 2 | 3 | /*@ s :: { string | v = "hello" } */ 4 | export let s = "hello"; 5 | 6 | /*@ f :: () => { string | v = "aaa" } */ 7 | export function f() { 8 | return s; 9 | } 10 | } 11 | 12 | M.f(); -------------------------------------------------------------------------------- /tests/pos/lists/safemap.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ map :: ((A) => B, xs: LList) => {v: LList | (LLlen v) = (LLlen xs)} */ 3 | function map(f, xs){ 4 | if (empty(xs)) { 5 | return nil(); 6 | } 7 | return cons(f(safehead(xs)), map(f, safetail(xs))); 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/misc/22-max.ts: -------------------------------------------------------------------------------- 1 | /*@ max :: (number, number) => number */ 2 | export function max(x:number, y:number):number{ 3 | let r :number= 0; 4 | if (x > y) { 5 | r = x; 6 | } else { 7 | r = y; 8 | } 9 | assert(r >= x); 10 | assert(r >= y); 11 | return r; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/simple/59-opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | class Foo { 4 | public x:number; 5 | 6 | constructor(x?: number) { 7 | if (x) this.x = x; 8 | else this.x = 0; 9 | } 10 | } 11 | 12 | let f = new Foo(1); 13 | let h = new Foo(); 14 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-02.ts: -------------------------------------------------------------------------------- 1 | /*@ predicate gt x y = x >= y */ 2 | /*@ type gnat[A,x] = {A | gt(v, x)} */ 3 | /*@ type nat = gnat[number, 0] */ 4 | 5 | // thus `nat` is just an alias for: {number | gt(v, 0)} 6 | 7 | /*@ z :: nat */ 8 | let z : number = 12; 9 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup5.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: ({ __proto__: {y: boolean, __proto__: {}, *: _}, *: string, x: number }, 2 | { string | (v = "x" || v = "y" || v = "z")}) => number + boolean + string + undefined */ 3 | function foo(o, s) { 4 | return o[s]; 5 | } 6 | -------------------------------------------------------------------------------- /tests/neg/arrays/08-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Length(v: a): len v = 3 */ 3 | /*@ qualif Length(v: a): len v = 4 */ 4 | 5 | let a: IArray = [1,2,3]; 6 | 7 | /*@ b :: { IArray | len v = 4 } */ 8 | let b = [1,2,3,4]; 9 | 10 | assert(a.length + b.length === 8); 11 | -------------------------------------------------------------------------------- /tests/neg/classes/05-class.ts: -------------------------------------------------------------------------------- 1 | 2 | class Foo { 3 | public f: A; 4 | 5 | constructor(x: A) { 6 | this.f = x; 7 | } 8 | } 9 | 10 | let p: number = 0; 11 | 12 | let a: Foo = new Foo(p); 13 | 14 | assert(a.f > 0); 15 | -------------------------------------------------------------------------------- /tests/neg/lists/list-01.ts: -------------------------------------------------------------------------------- 1 | /*@ listsum :: (LList) => {v:number | 0 < v} */ 2 | function listsum(xs){ 3 | if (empty(xs)) { 4 | return 0; 5 | } 6 | let h = head(xs); 7 | let t = tail(xs); 8 | return h + listsum(t); 9 | } 10 | -------------------------------------------------------------------------------- /tests/neg/lists/list-10.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif G11(v:number): v > 10 */ 2 | /*@ qualif G11(v:number): v > 9 */ 3 | 4 | /*@ hop :: (List) => LList */ 5 | function hop(xs){ 6 | let t = tail(xs); 7 | return t; 8 | } 9 | 10 | -------------------------------------------------------------------------------- /tests/neg/loops/while-05.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (n: number) => { boolean | 0 < 1} */ 2 | function foo(n: number) { 3 | let b; 4 | let i; 5 | let j = 0; 6 | while (j < n) { 7 | b = i < 10; 8 | i = j; 9 | j++; 10 | } 11 | return b; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/loops/while-rec.ts: -------------------------------------------------------------------------------- 1 | 2 | function loop(x: number): number { 3 | if (x <= 4) { 4 | let r = loop(x + 1); 5 | return r; 6 | } 7 | return x; 8 | } 9 | 10 | export function main(): void { 11 | let x = loop(0); 12 | assert(x === 6); 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/misc/00-abs-sig-bad.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ abs :: ({ x: number }) => { number | v > x } */ 3 | function abs(y) { 4 | let res = 0; 5 | if (y > 0) { 6 | res = y; 7 | } else { 8 | res = -y; 9 | }; 10 | assert(res >= 0); 11 | return res; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/typealias/talias-02.ts: -------------------------------------------------------------------------------- 1 | /*@ predicate gt x y = x < y */ 2 | /*@ type gnat[A,x] = {A | gt(v, x)} */ 3 | /*@ type nat = #gnat[number, 0] */ 4 | 5 | // thus `nat` is just an alias for: {number | gt(v, 0)} 6 | 7 | /*@ z :: nat */ 8 | let z : number = 12; 9 | -------------------------------------------------------------------------------- /tests/pos/bounded-poly/00-test.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | export function foo(x: V): V { 4 | return x; 5 | } 6 | 7 | let a_18_0 = foo(1); 8 | let a_18_1 = foo(""); 9 | 10 | assert(typeof foo(a_18_0) === "number"); 11 | assert(typeof foo(a_18_1) === "string"); 12 | -------------------------------------------------------------------------------- /tests/pos/classes/03-class.ts: -------------------------------------------------------------------------------- 1 | 2 | class Foo { 3 | 4 | /*@ (Mutable) ffffff: A */ 5 | public ffffff: A; 6 | 7 | constructor(x: A) { 8 | this.ffffff = x; 9 | } 10 | 11 | } 12 | 13 | let aaa = new Foo(1); 14 | 15 | assert(aaa.ffffff === 1); 16 | -------------------------------------------------------------------------------- /tests/pos/classes/37-interface.ts: -------------------------------------------------------------------------------- 1 | 2 | interface A { 3 | f: T; 4 | } 5 | 6 | 7 | interface C extends A { 8 | minChar: number; 9 | limChar: number; 10 | trailingTriviaWidth: number; 11 | g: T; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/simple/27-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | export declare function bar(): boolean; 3 | 4 | export function foo(x: A, y: A): A { 5 | let a = undefined; 6 | if (bar()) { 7 | a = x; 8 | } 9 | else { 10 | a = y; 11 | } 12 | return a; 13 | } 14 | -------------------------------------------------------------------------------- /tests/todo/pos/simple/66-variadic.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Length(v:number): (len v) = 4 */ 3 | 4 | var a = 5 | (function () 6 | /*@ forall A . (this: A) => A */ 7 | { 8 | return this; 9 | 10 | }).call([1,2,3,4]); 11 | 12 | assert(a.length === 4); 13 | 14 | -------------------------------------------------------------------------------- /tests/demo/cast.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => number + undefined */ 3 | declare function foo(): any; 4 | 5 | export function bar(): number { 6 | let x = foo(); 7 | if (x) { // Try removing this undefined check 8 | return 1 + x; 9 | } 10 | return 0; 11 | } 12 | -------------------------------------------------------------------------------- /tests/neg/arrays/11-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ is_num :: (x:number) => boolean */ 3 | function is_num(x:any) { 4 | return !isNaN(x); 5 | } 6 | 7 | /*@ foo :: (IArray) => IArray */ 8 | export function foo(arr:any) { 9 | return arr.filter(is_num); 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/classes/03-class.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | class Foo { 4 | 5 | /*@ (Mutable) ffffff: A */ 6 | public ffffff: A; 7 | 8 | constructor(x: A) { 9 | this.ffffff = x; 10 | } 11 | 12 | } 13 | 14 | let aaa = new Foo(1); 15 | 16 | assert(aaa.ffffff === 2); 17 | -------------------------------------------------------------------------------- /tests/neg/lists/list-11.ts: -------------------------------------------------------------------------------- 1 | /*@ listsum :: (List) => {v:number| 0 <= v} */ 2 | function listsum(xs){ 3 | if (empty(xs)) { 4 | return 0; 5 | } 6 | let h = head(xs); 7 | let t = tail(xs); 8 | return h + listsum(t); 9 | } 10 | 11 | -------------------------------------------------------------------------------- /tests/neg/lists/list-12.ts: -------------------------------------------------------------------------------- 1 | /*@ listsum :: (List) => {v:number| 0 <= v} */ 2 | function listsum(xs){ 3 | if (empty(xs)) { 4 | return 0; 5 | } 6 | let h = head(xs); 7 | let t = tail(xs); 8 | return h + listsum(t); 9 | } 10 | 11 | -------------------------------------------------------------------------------- /tests/neg/loops/while-06.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => number */ 3 | export function foo() { 4 | let i = 0; 5 | let z: number | string = 10; 6 | 7 | while (i < 5) { 8 | i = i + 1; 9 | z = "dog"; // whoops, should be same as outside. 10 | } 11 | 12 | return z; 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/misc/55-abs-join.ts: -------------------------------------------------------------------------------- 1 | 2 | export function abs(x: number): number { 3 | let res: number | boolean = 0; 4 | if (x > 0) { 5 | res = x; 6 | } else { 7 | res = (x > 99); 8 | }; 9 | 10 | assert(res >= 0); 11 | return res; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/objects/15-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (x: (Mutable){ f: number} ) => void */ 3 | function bar(a: any) { 4 | a.f = -1; 5 | } 6 | 7 | /*@ foo :: (x: (Mutable) { f: { number | v > 0 } }) => void */ 8 | function foo(x: any) { 9 | bar(x); 10 | assert(x.f > 0); 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/arrays/05-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ is_num :: (x: number + undefined) => boolean */ 3 | function is_num(x:any) { 4 | return !isNaN(x); 5 | } 6 | 7 | /*@ foo :: (IArray) => IArray */ 8 | export function foo(arr:any) { 9 | return arr.filter(is_num); 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/loops/while-06.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => number */ 3 | export function foo() { 4 | let i = 10; 5 | let z: number | string = 10; 6 | 7 | while (i < 5) { 8 | i = i + 1; 9 | z = "dog"; // whoops, should be same as outside. 10 | } 11 | 12 | return z; 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/misc/00-abs.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ abs :: (x: number) => { number | v >= x } */ 3 | function abs(x: number): number { 4 | let res = 0; 5 | if (x > 0) { 6 | res = x; 7 | } else { 8 | res = -x; 9 | }; 10 | assert(res >= 0); 11 | return res; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/misc/26-negate.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ negate :: (x: {v: number | v > 0} + boolean) => { v: number | v < 0 } + boolean */ 3 | export function negate(x): any { 4 | if (typeof(x) === "number") { 5 | return 0-x; 6 | } 7 | else { 8 | return !x 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/objects/14-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (a: (Mutable) { f: number }) => void */ 3 | function bar(a: { f: number }) { 4 | a.f = 1; 5 | } 6 | 7 | /*@ foo :: (x: (Mutable){ f: posint }) => void */ 8 | function foo(x: any) { 9 | bar(x); 10 | assert(x.f > 0); 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/operators/lor-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: posint, y: { string | v = "0" }, z: boolean) => posint */ 3 | export function foo(x: number, y: string, z: boolean) { 4 | if (x && (y || z)) { 5 | return 1; 6 | } 7 | else { 8 | return 0; 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/simple/17-absolute.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ abs :: (x: number) => {res: number | res >= 0} */ 3 | export function abs(x: number): number { 4 | let r = x; 5 | if (x > 0) { 6 | r = x; 7 | } 8 | else { 9 | r = (0 - x); 10 | } 11 | return r; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/typealias/talias-09.ts: -------------------------------------------------------------------------------- 1 | /*@ type eq[s] = {number | v = s} */ 2 | 3 | class Foo { 4 | 5 | /*@ (Immutable) x: number */ 6 | private x = 3; 7 | 8 | /*@ (Immutable) y: eq */ 9 | private y = 3; 10 | 11 | constructor() { } 12 | } 13 | -------------------------------------------------------------------------------- /tests/todo/pos/proto/proto-lookup6.ts: -------------------------------------------------------------------------------- 1 | function foo(o, s) 2 | /*: 3 | (rec o . { __proto__: Object, *: Num + 'o, /___(.*)_/: Any}) 4 | * /([^_])(.*)([^_])/ 5 | -> Undef + Num + (rec o . { __proto__: Object, *: Num + 'o, /___(.*)_/: Any}) 6 | */ 7 | { 8 | return o[s]; 9 | } 10 | -------------------------------------------------------------------------------- /tests/todo/pos/simple/modules.ts: -------------------------------------------------------------------------------- 1 | module K.L { 2 | export module Z { 3 | export class A { 4 | constructor () {} 5 | } 6 | } 7 | } 8 | 9 | module M { 10 | class B extends K.L.Z.A { 11 | constructor () { 12 | super(); 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /include/rsc/aliases.d.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ type idx = { v: number | 0 <= v && v < len x } */ 3 | declare type idx = number; 4 | 5 | /*@ type posint = { v: number | 0 < v } */ 6 | declare type posint = number; 7 | 8 | /*@ type negint = { v: number | v < 0 } */ 9 | declare type negint = number; 10 | -------------------------------------------------------------------------------- /tests/neg/arrays/12-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ revInc :: (a: IArray) => { IArray | len v = len a } */ 3 | export function revInc(a: number[]) { 4 | a.reverse(); 5 | for (let i = 0; i < a.length; i++) { 6 | a[i] = a[i] + 1; 7 | } 8 | a.push(1); 9 | return a; 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/inclusion/07-inclusion.ts: -------------------------------------------------------------------------------- 1 | /*@ option --extrainvs */ 2 | 3 | 4 | class Point { 5 | x: number = 1; 6 | y: number = 2; 7 | constructor () {} 8 | } 9 | 10 | assert("x" in new Point()); // returns true 11 | assert("z" in new Point()); // returns false 12 | -------------------------------------------------------------------------------- /tests/neg/lists/unfold-list-00.ts: -------------------------------------------------------------------------------- 1 | 2 | interface MyList { 3 | d: A; 4 | /*@ n: MyList + null */ 5 | n: MyList; 6 | } 7 | 8 | let inner = { d: 2, n: null }; 9 | 10 | /*@ readonly a :: MyList */ 11 | let a = { d: 1, n: inner }; 12 | -------------------------------------------------------------------------------- /tests/neg/simple/04-glob.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif CmpZ(v:int): v = 20 */ 3 | 4 | // This is a local variable 5 | let glob = 20; 6 | 7 | 8 | module A { 9 | 10 | 11 | function zog(){ 12 | glob = 3; 13 | } 14 | 15 | zog(); 16 | 17 | assert(glob === 20); 18 | 19 | } 20 | -------------------------------------------------------------------------------- /tests/pos/loops/for-05.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Poo(v: int, i: int): v = i - 1 */ 3 | /*@ qualif Poo(v: int): v < 5 */ 4 | 5 | /*@ bar :: () => { number | 4 = v } */ 6 | function bar(): number { 7 | let z = -1; 8 | for (let i = 0; i < 5; i++) { 9 | z = i; 10 | } 11 | return z; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/scope/12-ssa.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Cmp(v: int): v = 3 */ 3 | 4 | export function bar() { 5 | let x = 1; 6 | if (true) { 7 | x = 3; 8 | } 9 | assert(x === 3); 10 | 11 | let y = 1; 12 | if (true) { 13 | 14 | } 15 | assert(y === 1); 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/unions/test-08.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number) => { number | v = 1 } + boolean */ 3 | function foo(x) { 4 | /*@ global */ let r: number | boolean = 1; 5 | if (x > 0) { 6 | r = 1; 7 | } 8 | else { 9 | r = true; 10 | } 11 | return r; 12 | } 13 | -------------------------------------------------------------------------------- /tests/todo/pos/pemissions/test-05.ts: -------------------------------------------------------------------------------- 1 | 2 | // Use uniqueness to capture effectful operations 3 | 4 | 5 | function addRand(a: Array): void { 6 | a.push(random()); 7 | } 8 | 9 | let a = new Array(); 10 | 11 | addRand(a); 12 | addRand(a); 13 | 14 | assert(a.length === 2); 15 | -------------------------------------------------------------------------------- /tests/neg/arrays/05-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:number) => IArray<{ number | v = x }> */ 3 | function foo(x : number) : number[] { 4 | return [x]; 5 | } 6 | 7 | /*@ bar :: (y:number) => IArray<{ number | v > y }> */ 8 | function bar(y : number) : number[] { 9 | return foo(y); 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/loops/for-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Ineq(v : int ): (v <= 6) */ 3 | /*@ qualif Ineq(v : int ): (v <= 7) */ 4 | 5 | /*@ loop :: () => { number | v = 7 } */ 6 | function loop() : number{ 7 | 8 | let x = 0; 9 | 10 | for(x = 1; x <= 5; x ++) { 11 | } 12 | 13 | return x; 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/arrays/15-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Length(v: a): len v = 1 */ 3 | 4 | 5 | /*@ readonly arr :: IArray */ 6 | let arr = ["a"]; 7 | 8 | 9 | module A { 10 | 11 | export function baz(): string { 12 | return arr[0]; 13 | } 14 | 15 | baz(); 16 | 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/classes/11-class.ts: -------------------------------------------------------------------------------- 1 | //adapted from navier-stokes octane 2 | class FluidField { 3 | 4 | private size = 6; 5 | 6 | constructor() { } 7 | 8 | /*@ foo(x: {number | v = this.size}) : void */ 9 | foo(x) { 10 | this.foo(x); 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/objects/19-object.ts: -------------------------------------------------------------------------------- 1 | 2 | // We can reference an object in the context of 3 | // an object literal member after making it mutable. 4 | 5 | /*@ readonly uniqueInnerObj :: { n : number } */ 6 | let uniqueInnerObj = { n: 6 }; 7 | 8 | let uniqueObj = { a: 5, b: "String", c: uniqueInnerObj }; 9 | -------------------------------------------------------------------------------- /tests/pos/operators/add-04.ts: -------------------------------------------------------------------------------- 1 | /*@ bog :: (x: number) => { number | v = x } */ 2 | /*@ bog :: (x: { string | false } ) => string */ 3 | export function bog(x) { 4 | return x; 5 | } 6 | 7 | export function gloop(y: number): number { 8 | let z: number = bog(y); 9 | return z; 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/operators/inc-00.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif PlusOne(v: int, x: int) : v = x + 1 */ 2 | 3 | function inc(x: number) { 4 | return x + 1; 5 | } 6 | 7 | export function main() { 8 | let a = _pos(); 9 | let b = inc(a); 10 | assert(b === a + 1); 11 | assert(b > 0); 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/scope/init-06.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (n: number) => { number | true } + undefined */ 3 | export function foo(n: number): number { 4 | /*@ local r :: number + undefined */ 5 | let r; 6 | while (n < 10) { 7 | r = 1; 8 | n++; 9 | } 10 | return r; 11 | } 12 | -------------------------------------------------------------------------------- /tests/neg/misc/18-inner.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ main :: (xx: number) => { v: number | v > xx } */ 3 | function main(xx: number): number { 4 | /*@ readonly */ 5 | let x = xx; 6 | let plus: (a: number) => number = function (a) { 7 | return a + x; 8 | }; 9 | return plus(xx); 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/misc/53-vararg.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number, y: (number) => number) => {number + undefined | 0 < 1 } */ 3 | /*@ foo :: (x: number) => {number + undefined | 0 < 1 } */ 4 | function foo(x: any, y?: any): any { 5 | let bobZooo = arguments.length; 6 | assert (bobZooo <= 1); 7 | return 1; 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/simple/02-glob.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ global glob :: posint */ 3 | let glob = 4; 4 | 5 | 6 | module A { 7 | 8 | function bar() { 9 | glob = 7; 10 | return; 11 | } 12 | 13 | export function zoo() { 14 | bar(); 15 | assert(glob > 10); 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /tests/neg/unions/test-15.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ check_undefined :: (x: { T + undefined | v ~~ y}, y: { T + undefined | v ~~ x }) => T */ 3 | function check_undefined(x:any, y: any) : T { 4 | if (typeof x === "undefined") 5 | return crash(); 6 | return x; 7 | } 8 | 9 | check_undefined(1,2); 10 | -------------------------------------------------------------------------------- /tests/pos/arrays/12-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:number) => IArray<{ number | v = x }> */ 3 | function foo(x: number): number[] { 4 | return [x]; 5 | } 6 | 7 | /*@ bar :: (y:number) => IArray<{ number | v = y }> */ 8 | export function bar(y: number): number[] { 9 | return foo(y); 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/classes/39-method.ts: -------------------------------------------------------------------------------- 1 | class Foo { 2 | public x: number; 3 | constructor() { 4 | this.x = 3; 5 | } 6 | 7 | /*@ @Mutable bar(): void */ 8 | bar() { 9 | this.x = 4; 10 | } 11 | } 12 | 13 | let f = new Foo(); 14 | f.bar(); 15 | -------------------------------------------------------------------------------- /tests/pos/loops/for-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Ineq(v : number ): (v <= 6) */ 3 | 4 | // related: while-05.js 5 | 6 | /*@ loop :: () => { number | v > 0 } */ 7 | function loop() : number{ 8 | let x = 1; 9 | 10 | for(let i = 1; i <= 5; i ++) { 11 | x = x + x; 12 | } 13 | 14 | return x; 15 | } 16 | -------------------------------------------------------------------------------- /tests/pos/loops/obj-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { a: { number | v = 1 } } */ 3 | function foo() : Object { 4 | 5 | /*@ local x :: (ReadOnly) { a: number } */ 6 | let x = { a: 1 }; 7 | 8 | for (let i = 0; i < 5; i ++) { 9 | x = { a: 1 }; 10 | } 11 | 12 | return x; 13 | 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/misc/16-init.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ init :: (number) => {v: number | v > 0} */ 3 | function init(n: number): number { 4 | /*@ local i :: number + undefined */ 5 | let i: number; 6 | if (n > 0) { 7 | i = 1; 8 | } else { 9 | i = 2; 10 | } 11 | return i; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/scope/init-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => posint */ 3 | export function foo(cnd: boolean): number { 4 | /*@ local r :: number + undefined */ 5 | let r; 6 | if (cnd) { 7 | r = 1; 8 | } 9 | else { 10 | r = 2; 11 | } 12 | return r; 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/simple/02-glob.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ global glob :: posint */ 3 | let glob = 12; 4 | 5 | module A { 6 | 7 | function bar() { 8 | glob = 7; 9 | return; 10 | } 11 | 12 | export function zoo() { 13 | bar(); 14 | assert(glob > 0); 15 | } 16 | 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/unions/test-15.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ check_undefined :: (x: { T + undefined | v ~~ y}, y: { T + undefined | v ~~ x }) => T */ 3 | function check_undefined(x:any, y: any) : T { 4 | if (typeof x === "undefined") 5 | return crash(); 6 | return x; 7 | } 8 | 9 | check_undefined(1,1); 10 | -------------------------------------------------------------------------------- /tests/neg/classes/10-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class AA { 3 | /*@ (Immutable) x: number */ 4 | public x = 0; 5 | 6 | /*@ (Immutable) y: { number | v = this.x } */ 7 | public y = 0; 8 | 9 | constructor() { } 10 | 11 | } 12 | 13 | let aa = new AA(); 14 | assert(aa.x === aa.y + 1); 15 | -------------------------------------------------------------------------------- /tests/neg/loops/for-rec-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ forloop :: (number, number, (number, A) => A, A) => A */ 3 | export function forloop(lo, hi, body, acc) { 4 | if (lo < hi) { 5 | let newAcc = body(acc, lo); 6 | return forloop(lo + 1, hi, body, newAcc); 7 | } 8 | return acc; 9 | } 10 | -------------------------------------------------------------------------------- /tests/neg/misc/58-unite.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (A, A) => A*/ 3 | export function foo(x, y) { 4 | if (x === y) { 5 | return x; 6 | } else { 7 | return y; 8 | } 9 | } 10 | 11 | /*@ bar :: (A, B) => {v:A | 0 < 1} */ 12 | function bar(x, y) { 13 | return foo(x, y); 14 | } 15 | -------------------------------------------------------------------------------- /tests/neg/objects/18-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ gobj :: (Mutable) { a: posint } */ 3 | let gobj = { a: 5, b: "glorp" }; 4 | 5 | function foo() { 6 | gobj.a = gobj.a - 1; 7 | } 8 | 9 | export function moo(): void { 10 | foo(); 11 | let z = gobj.a; 12 | assert(z > 0); 13 | return; 14 | } 15 | -------------------------------------------------------------------------------- /tests/neg/scope/init-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | /*@ local r :: number */ 5 | let r = 0; 6 | if (cnd) { 7 | r = 1; 8 | } 9 | else { 10 | r = -2; 11 | } 12 | return r; 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/classes/20-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class AA { 3 | /*@ (Immutable) x : number */ 4 | public x = 0; 5 | 6 | /*@ (Immutable) y: { number | v = this.x } */ 7 | public y = 0; 8 | 9 | constructor() { } 10 | } 11 | 12 | let aa = new AA(); 13 | assert(aa.x === aa.y); 14 | -------------------------------------------------------------------------------- /tests/pos/misc/41-poly.ts: -------------------------------------------------------------------------------- 1 | function id(x: A): A { 2 | return x; 3 | } 4 | 5 | export function foo(y: number): number; 6 | export function foo(y: boolean): boolean; 7 | export function foo(y: string): string; 8 | export function foo(y: any): any { 9 | let z = id(y); 10 | return z; 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/misc/53-vararg.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number, y: (number) => number) => {number + undefined | 0 < 1} */ 3 | /*@ foo :: (x: number) => {number + undefined | 0 < 1} */ 4 | function foo(x: any, y?: any): any { 5 | let bobZooo = arguments.length; 6 | assert (bobZooo > 0); 7 | return 1; 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/scope/13-nested.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif AddTrhree(v:int, w: int): v = w + 3 */ 3 | 4 | /*@ foo :: () => { number | v = 4 } */ 5 | export function foo() { 6 | let u = 1; 7 | 8 | function addThree(u: number) { 9 | return u + 3; 10 | } 11 | 12 | return addThree(u); 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/simple/11-runtime-tags.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(f: () => number): number; 3 | export function foo(f: number): number 4 | export function foo(f: any): number { 5 | if (typeof f === "function") { 6 | return f(); 7 | } 8 | else { 9 | return f + 1; 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /tests/demo/opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | function buildName(firstName: string, lastName?: string) { 3 | if (arguments.length === 2) 4 | return firstName + " " + lastName; 5 | else 6 | return firstName; 7 | } 8 | 9 | let result1 = buildName("Bob"); 10 | let result3 = buildName("Bob", "Adams"); 11 | -------------------------------------------------------------------------------- /tests/demo/variadic.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (x: string) => { string | v = x } */ 3 | declare function bar(x: string): string; 4 | 5 | function foo(x: V, f: (v: U) => W, a: U): W { 6 | return f.call(x, a); 7 | } 8 | 9 | 10 | let a: IArray = ["a"]; 11 | 12 | assert(foo(a, bar, "b") === "b"); 13 | -------------------------------------------------------------------------------- /tests/neg/operators/lor-04.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:null, y:number, z: number) => posint */ 3 | export function foo(x, y, z): number { 4 | 5 | let a = 1 || true; 6 | 7 | 8 | if (x || y || z) { 9 | return 1; 10 | } 11 | else { 12 | return 0; 13 | } 14 | 15 | 16 | 17 | } 18 | -------------------------------------------------------------------------------- /tests/neg/unions/test-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bob :: (number) => number + undefined */ 3 | function bob(x:number):any { 4 | if (x > 0) return x; 5 | return undefined; 6 | } 7 | 8 | /*@ bar :: (number) => number */ 9 | export function bar(x: number) : any { 10 | let z = bob(x); 11 | return z; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/unions/test-04.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ({number | 0 < 1}) => { number | v = 2 } + boolean */ 3 | function foo(x) { 4 | /*@ r :: number + boolean */ 5 | let r: any = 1; 6 | if (x > 0) { 7 | r = 1; 8 | } 9 | else { 10 | r = true; 11 | } 12 | return r; 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/classes/29-glob-in-method.ts: -------------------------------------------------------------------------------- 1 | class Blah { 2 | constructor() { } 3 | 4 | public state = 3; 5 | 6 | public foo(): void { 7 | /*@ val :: number + null */ 8 | let val = null; 9 | if (this.state === 42) 10 | val = 7; 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/misc/38-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | function idd(x:A):A { 4 | return x; 5 | } 6 | 7 | function bar(x: A, f: (y: A) => A): A { 8 | return f(x); 9 | } 10 | 11 | /*@ main :: () => { number | v > 5 } */ 12 | function main() { 13 | return bar(10, idd); // this is actually (idd @ number) 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/simple/16-arguments-var.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo() { 3 | /*@ bar :: (x:top) => number */ 4 | /*@ bar :: () => number */ 5 | let bar = function(x?) { 6 | if (arguments.length === 0) 7 | return 0; 8 | return 1; 9 | } 10 | return bar(); 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/simple/49-addEntry.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ type MMap = (Mutable) {[x:string]: T} */ 3 | type MMap = { [x: string]: T }; 4 | 5 | /*@ addEntry :: (ob: MMap, entry: { f0: string; f1: T }) => MMap */ 6 | export function addEntry(ob, entry) { 7 | ob[entry.f0] = entry.f1; 8 | return ob; 9 | } 10 | -------------------------------------------------------------------------------- /tests/todo/pos/misc/missing-qualif.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Add(v: number, n: number, m: number): v < m + n */ 3 | 4 | /*@ lin_solve :: () => void */ 5 | function lin_solve() { 6 | var x = 6; 7 | // ++x; 8 | for (var i = 1; i <= 1; i++) { 9 | ++x; 10 | assert(x < 9); 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/classes/29-method-mut.ts: -------------------------------------------------------------------------------- 1 | class Foo { 2 | public x:number; 3 | constructor() { 4 | this.x = 3; 5 | } 6 | 7 | /*@ @Mutable bar(): void */ 8 | bar() { 9 | this.x = 4; 10 | } 11 | } 12 | 13 | let f: Foo = new Foo(); 14 | 15 | f.bar(); 16 | -------------------------------------------------------------------------------- /tests/neg/misc/37-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | function idd(x:A):A { 4 | return x; 5 | } 6 | 7 | function bar(x: A, f: (y: A) => A): A { 8 | return f(x); 9 | } 10 | 11 | /*@ main :: (number) => {string | 0 < 1} */ 12 | function main(x){ 13 | return bar(x, idd); // this is actually (idd @ number) 14 | } 15 | -------------------------------------------------------------------------------- /tests/neg/operators/inc-01.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif PlusOne(v: int,x: int): v = x + 1 */ 2 | 3 | function inc(x: number) { 4 | let res = x + 1; 5 | return res; 6 | } 7 | 8 | export function main(): void { 9 | let a = pos(); 10 | let b = inc(a); 11 | assert (b > (a + 1)); 12 | assert(b > 0); 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/simple/11-runtime-tags.ts: -------------------------------------------------------------------------------- 1 | 2 | /* foo :: (f: () => number) => number */ 3 | /*@ foo :: (f: number) => number */ 4 | export function foo(f) { 5 | if (typeof f === "function") { 6 | return f + 1; 7 | } 8 | else { 9 | // assert(false); 10 | return f(); 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/simple/65-variadic.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (x: string) => { string | v = x } */ 3 | declare function bar(x: string): string; 4 | 5 | function foo(x: V, f: (v: U) => U, a: U): U { 6 | return f.call(x, a); 7 | } 8 | 9 | let a: IArray = ["a"]; 10 | 11 | assert(foo(a, bar, "b") === "a"); 12 | -------------------------------------------------------------------------------- /tests/pos/enums/00-enum.ts: -------------------------------------------------------------------------------- 1 | let zzz = 111 2 | 3 | enum A1 { 4 | a1 = 777, 5 | b1 = zzz 6 | } 7 | 8 | enum A2 { 9 | a2 = 0x00000001, 10 | b2 = 0x00000010, 11 | c2 = 0x00000100, 12 | d2 = 0x00001000, 13 | e2 = 0x00010000, 14 | f2 = 0x00100000, 15 | g2 = 0x01000000, 16 | h2 = 0x10000000, 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/lists/list-00.ts: -------------------------------------------------------------------------------- 1 | /*@ hop :: (LList= 0}>) => void */ 2 | function hop(as? : List) : void { 3 | if (empty(as)) { 4 | return; 5 | } 6 | let h = head(as); 7 | assert(0 <= h); 8 | let t = tail(as); 9 | return hop(t); 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/misc/07-cousot.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ loop :: (n:number, {m:number | m = n}) => void */ 3 | function loop(n:number, m:number) :void{ 4 | 5 | if (random() > 0){ 6 | n = n + 1; 7 | m = m + 1; 8 | } 9 | else { 10 | n = 0; 11 | m = 0; 12 | } 13 | 14 | assert(m === n); 15 | 16 | return; 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/misc/18-inner.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ main :: (xx: posint) => { v: number | v > xx } */ 3 | function main(xx: number): number { 4 | 5 | /*@ global */ 6 | let x_ = xx; 7 | 8 | let plus: (a: number) => number = function (a) { 9 | return a + x_; 10 | }; 11 | 12 | return plus(xx); 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/scope/10-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo1(): string { 3 | 4 | /*@ a1 :: string */ 5 | let a1 = "1"; 6 | a1 = a1 + "2"; 7 | 8 | let bar1: () => string = function() { 9 | a1 = a1 + "3"; 10 | return a1; 11 | } 12 | 13 | return bar1(); 14 | } 15 | 16 | foo1(); 17 | -------------------------------------------------------------------------------- /tests/todo/weird/slowMul.ts: -------------------------------------------------------------------------------- 1 | // This is SAFE but takes insanely long to check. 2 | // Removing the refinement on x speeds it up to normal speeds. 3 | /*@ foo :: ({number | v > 0 && v*v < 1000000}) => void */ 4 | function foo(w) { 5 | var x = new Array(w); 6 | for (var i=0; i { number | v = x + 1 } */ 3 | function inc(x: number): number { 4 | return x + 1; 5 | } 6 | 7 | export function main(): void { 8 | let a: number = _pos(); 9 | let b: number = inc(a); 10 | assert(b === a + 1); 11 | assert(b > 0); 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/simple/65-variadic.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ bar :: (x: string) => { string | v = x } */ 3 | declare function bar(x: string): string; 4 | 5 | function foo(x: V, f: (v: U) => W, a: U): W { 6 | return f.call(x, a); 7 | } 8 | 9 | 10 | let a: IArray = ["a"]; 11 | 12 | assert(foo(a, bar, "b") === "b"); 13 | -------------------------------------------------------------------------------- /tests/neg/arrays/22-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly */ let aaa: IArray = [1, 2, 3, 4]; 3 | 4 | /*@ foo :: () => void */ 5 | function foo(): void { 6 | aaa[2] = 0; 7 | } 8 | 9 | /*@ bar :: (n: idx) => posint */ 10 | export function bar(n: number): number { 11 | let z = aaa[n]; 12 | return z; 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/simple/47-overloads.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number) => { number | v > 100 } */ 3 | /*@ foo :: (x: string) => { number | v > 100 } */ 4 | export function foo(x: any): any { 5 | if (typeof x === "number") { 6 | if (x > 99) { 7 | return x; 8 | } 9 | } 10 | return 200; 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/loops/for-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Poo(v: int, i: int): v = i - 1 */ 3 | /*@ qualif Poo(v: int): v < 6 */ 4 | 5 | 6 | /*@ loop :: () => { number | v = 5 } */ 7 | function loop() : number{ 8 | 9 | let y = 0; 10 | 11 | for(let x = 1 ;x <= 5; x ++) { 12 | y = x; 13 | } 14 | 15 | return y; 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/simple/47-overloads.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: number) => { number | v > 100 } */ 3 | /*@ foo :: (x: string) => { number | v > 100 } */ 4 | export function foo(x: any): any { 5 | if (typeof x === "number") { 6 | if (x > 100) { 7 | return x; 8 | } 9 | } 10 | return 200; 11 | } 12 | -------------------------------------------------------------------------------- /tests/neg/arrays/21-array.ts: -------------------------------------------------------------------------------- 1 | /*@ readonly */ let a: number[] = [1, 2, 3, 4]; 2 | 3 | /*@ foo :: () => void */ 4 | function foo(): void { 5 | a[2] = 10; 6 | } 7 | 8 | /*@ bar :: ({ number | 0 <= v && v <= 4 }) => posint */ 9 | export function bar(n: number): number { 10 | let z: number = a[n]; 11 | return z; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/bounded-poly/00-test.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | export function foo(x: V): V; 4 | export function foo(x: V): V; 5 | export function foo(x: any): any { 6 | return x; 7 | } 8 | 9 | let a = foo(""); 10 | 11 | 12 | assert(typeof foo(1) === "string"); 13 | assert(typeof foo("") === "number"); 14 | -------------------------------------------------------------------------------- /tests/neg/misc/38-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | function idd(x:A):A { 4 | return x; 5 | } 6 | 7 | function bar(x: A, f: (z:A) => A): A { 8 | return f(x); 9 | } 10 | 11 | /*@ main :: (x: { number | v > 5 }) => { number | v > 10 } */ 12 | function main(x){ 13 | return bar(x, idd); // this is actually (idd @ number) 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/arrays/24-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Length(v: a): len v > 0 */ 3 | 4 | function bar(a: IArray) { 5 | // a[0] = 1; // We do not allow updates on immutable arrays 6 | } 7 | 8 | /*@ foo :: ({ IArray | len v > 0 }) => void */ 9 | function foo(a) { 10 | bar(a); 11 | assert(a[0] > 0); 12 | } 13 | -------------------------------------------------------------------------------- /scripts/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "refscript-tests", 3 | "version": "0.1.0", 4 | "dependencies": { 5 | "bluebird": "^2.10.2", 6 | "colors": "^1.1.2", 7 | "glob": "^5.0.15", 8 | "glob-promise": "^1.0.4", 9 | "microtime": "^2.0.0", 10 | "promise": "^7.0.4", 11 | "underscore": "^1.8.3" 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/classes/06-class.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (x: Node + undefined) => void */ 2 | export function foo(x: Node) { 3 | if (x) { 4 | x.field = 2; 5 | } 6 | } 7 | 8 | class Node { 9 | constructor() { } 10 | 11 | /*@ (Immutable) field: number */ 12 | public field = 0; 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/operators/id-01.ts: -------------------------------------------------------------------------------- 1 | /*@ id2 :: forall A B. (A, B) => A */ 2 | function id2(x, y) { return x;} 3 | 4 | /*@ main :: (x:number, boolean) => {v:number|v > x} */ 5 | function main(x, y){ 6 | let yr = id2(y, x); 7 | let xr = id2(x, y); 8 | let z = 0; 9 | if (yr) { 10 | z = 10; 11 | } 12 | return xr + z; 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/scope/01-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ( ) => { number | v = 123 }*/ 3 | export function foo(): number { 4 | /*@ a :: number */ 5 | let a = 1; 6 | a = a + 1; 7 | 8 | let bar: () => number = function() { 9 | a = a + 1; 10 | return a; 11 | } 12 | return bar(); 13 | } 14 | 15 | foo(); 16 | -------------------------------------------------------------------------------- /tests/pos/inclusion/05-inclusion.ts: -------------------------------------------------------------------------------- 1 | /*@ option --extrainvs */ 2 | 3 | // Predefined objects 4 | // assert("PI" in Math); // returns true 5 | 6 | // Custom objects 7 | 8 | let mycar = {make: "Honda", model: "Accord", year: 1998}; 9 | assert("make" in mycar); // returns true 10 | assert("model" in mycar); // returns true 11 | -------------------------------------------------------------------------------- /tests/demo/while-rec.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Ineq(v : int): (v <= 6) */ 3 | /*@ qualif Eq1(v: int): v = 6 */ 4 | 5 | function loop(x: number): number { 6 | if (x <= 5) { 7 | return loop(x + 1); 8 | } 9 | return x; 10 | } 11 | 12 | export function main(): void { 13 | let x = loop(0); 14 | assert(x === 6); 15 | } 16 | -------------------------------------------------------------------------------- /tests/neg/classes/00-class.ts: -------------------------------------------------------------------------------- 1 | 2 | class BankAccount { 3 | /*@ f: posint */ 4 | public f = 1; 5 | /*@ g: { string | v = "a" } */ 6 | public g = "a"; 7 | 8 | /*@ new (x: any): BankAccount */ 9 | constructor(x) { 10 | this.g = x; 11 | } 12 | } 13 | 14 | let ba = new BankAccount("a"); 15 | ba.g = "b"; 16 | -------------------------------------------------------------------------------- /tests/neg/classes/22-func-field-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class Foo { 3 | /*@ bar : () => posint */ 4 | public bar: () => number 5 | 6 | constructor() { 7 | /*@ _bar :: () => number */ 8 | function _bar() { 9 | return -3; 10 | } 11 | 12 | this.bar = _bar; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/arrays/00-array.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(a: IArray) { 3 | if (a.length > 0) { 4 | return a[0]; 5 | } 6 | return 0; 7 | } 8 | 9 | foo(>[]); 10 | foo(>[1]); 11 | foo(>[1, 2]); 12 | foo(>[1, 2, 3]); 13 | foo(>[1, 2, 3, 4]); 14 | -------------------------------------------------------------------------------- /tests/pos/arrays/21-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ revInc :: (a: IArray) => { IArray | len v = len a } */ 3 | export function revInc(a: number[]) { 4 | // a.reverse(); // currently not allowed on non-mutable arrays 5 | for (let i = 0; i < a.length; i++) { 6 | let b = a[i] + 1; 7 | } 8 | return a; 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/classes/28-func-field-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class Foo { 3 | /*@ bar : () => posint */ 4 | public bar: () => number 5 | 6 | constructor() { 7 | /*@ _bar :: () => number */ 8 | function _bar() { 9 | return 3; 10 | } 11 | 12 | this.bar = _bar; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/lists/listsum-02.ts: -------------------------------------------------------------------------------- 1 | /*@ listsum :: (LList) => { number | 0 <= v } */ 2 | function listsum(xs : List) : number{ 3 | if (empty(xs)) { 4 | return 0; 5 | } 6 | let h :number = head(xs); 7 | let t = tail(xs); 8 | return h + listsum(t); 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/objects/03-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly */ 3 | let innerObj = { n: 6 } 4 | 5 | /*@ readonly */ 6 | let gobj = { a: 5, b: "String", oo: innerObj }; 7 | 8 | 9 | 10 | module A { 11 | 12 | /*@ foo :: () => { n: posint } */ 13 | export function foo (): { n: number } { 14 | return gobj.oo; 15 | } 16 | 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/scope/01-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: ( ) => posint */ 3 | export function foo(): number { 4 | 5 | /*@ a :: posint */ 6 | let a = 1; 7 | a = a + 123; 8 | 9 | let bar: () => number = function(): number { 10 | a = a + 1; 11 | return a; 12 | } 13 | 14 | return bar(); 15 | } 16 | 17 | foo(); 18 | -------------------------------------------------------------------------------- /tests/benchmarks/todo/pldi16/d3/transpose.ts: -------------------------------------------------------------------------------- 1 | /// 2 | /// 3 | 4 | d3.transpose = function(matrix) 5 | /*@ (matrix:IArray>) => {IArray> | 0 < 1} */ 6 | { 7 | //ORIG: return d3.zip.apply(d3, matrix); 8 | return d3.zip(matrix); 9 | }; 10 | -------------------------------------------------------------------------------- /tests/neg/misc/27-negate.ts: -------------------------------------------------------------------------------- 1 | /*@ negate :: (x: number + boolean) 2 | => { v: number + boolean | (ttag(v) = ttag(x)) } */ 3 | function negate(x: any): any { 4 | if (typeof(x) === "number") { 5 | if (x > 100) 6 | return 0 - x; 7 | else 8 | return false; 9 | } else { 10 | return !x; 11 | } 12 | } 13 | 14 | -------------------------------------------------------------------------------- /tests/neg/misc/42-unsafe-meth-call.ts: -------------------------------------------------------------------------------- 1 | class Tree { 2 | constructor() {} 3 | 4 | /*@ root : TreeNode + null */ 5 | root = null; 6 | 7 | foo(): void { 8 | this.root.bar(); 9 | } 10 | } 11 | 12 | class TreeNode { 13 | bar(): void {}; 14 | constructor() {} 15 | 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/arrays/02-array.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: ({ IArray | len v >= 10 } ) => number */ 2 | export function foo(a: number[]): number { 3 | return a[9]; 4 | } 5 | 6 | /*@ bar :: (a: IArray, i: { number | 0 <= i && i+1 < len a}) => number */ 7 | export function bar(a: number[], i: number): number { 8 | return a[i + 1]; 9 | } 10 | -------------------------------------------------------------------------------- /tests/pos/classes/06-class.ts: -------------------------------------------------------------------------------- 1 | 2 | class A { 3 | constructor (x:T) { } 4 | 5 | /*@ n : { number | v > 0 } */ 6 | public n : number = 5; 7 | /*@ m : string */ 8 | private m : string = "a"; 9 | } 10 | 11 | /*@ a :: A */ 12 | let a : A = new A(1); 13 | 14 | assert(a.n > 0); 15 | -------------------------------------------------------------------------------- /tests/pos/classes/09-class.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x: Node + undefined) => void */ 3 | export function foo(x: Node) { 4 | if (x) { 5 | (>x).field = 2; 6 | } 7 | } 8 | 9 | class Node { 10 | constructor() { } 11 | 12 | /*@ (Mutable) field: number */ 13 | public field = 0; 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/fb/minindex-classic.ts: -------------------------------------------------------------------------------- 1 | 2 | export function minIndex(arr: IArray): number { 3 | if (arr.length <= 0) return -1; 4 | let min = 0; 5 | for (let i = 0; i < arr.length; i++) { 6 | let cur = arr[i]; 7 | if (cur < arr[min]) { 8 | min = i; 9 | } 10 | } 11 | return min; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/loops/while-rec.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Ineq(v : int): (v <= 6) */ 3 | /*@ qualif Eq1(v: int): v = 6 */ 4 | 5 | function loop(x: number): number { 6 | if (x <= 5) { 7 | return loop(x + 1); 8 | } 9 | return x; 10 | } 11 | 12 | export function main(): void { 13 | let x = loop(0); 14 | assert(x === 6); 15 | } 16 | -------------------------------------------------------------------------------- /tests/pos/scope/11-nested.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif AddTrhree(v:int, w: int): v = w + 3 */ 3 | 4 | let w = 1; 5 | 6 | class ABC { 7 | constructor() { } 8 | 9 | public addThree(u: number) { 10 | return u + 3; 11 | } 12 | } 13 | 14 | let a: ABC = new ABC(); 15 | 16 | assert(a.addThree(w) === 4); 17 | -------------------------------------------------------------------------------- /tests/pos/simple/14-arithmetic.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (x: number) => {number | v = x + 2} */ 2 | export function foo(x: number): number { 3 | let a = zogbert(x); 4 | let b = zogbert(a); 5 | return b; 6 | } 7 | 8 | /*@ zogbert :: (x: number) => {number | v = x + 1} */ 9 | function zogbert(x: number): number { 10 | return x + 1; 11 | } 12 | -------------------------------------------------------------------------------- /tests/todo/pos/simple/70-opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => {void | 0 < 1} */ 3 | /*@ foo :: (l: {number | 0 <= v}) => {void | 0 < 1} */ 4 | function foo(l?: number) 5 | { 6 | 7 | /*@ local loc :: number */ 8 | let loc = 0; 9 | 10 | if (arguments.length === 1) { 11 | loc = l; 12 | } 13 | 14 | assert(0 <= loc); 15 | } 16 | -------------------------------------------------------------------------------- /doc/formal/src/includes.tex: -------------------------------------------------------------------------------- 1 | \usepackage[usenames,dvipsnames]{color} 2 | \usepackage{amsmath} 3 | \usepackage{amssymb} 4 | \usepackage{stmaryrd} 5 | \usepackage{caption} 6 | \usepackage{listings} 7 | \usepackage{ottalt} 8 | 9 | \inputott{typing.ott} 10 | \input{src/ott-local} 11 | 12 | \newcommand\panos[1]{{\color{Red}{\textit{Panos: #1}}}} 13 | 14 | -------------------------------------------------------------------------------- /tests/pos/lists/list-03.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif G10(v:number): v > 10 */ 2 | 3 | /*@ hop :: (List) => List */ 4 | /*@ hop :: (null) => List */ 5 | function hop(xs) { 6 | if (!empty(xs)) { 7 | return xs; 8 | } 9 | return { data: 15, next: null }; 10 | } 11 | 12 | -------------------------------------------------------------------------------- /tests/pos/misc/37-poly.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ idd :: (x:T) => T */ 4 | function idd(x:A):A { 5 | return x; 6 | } 7 | 8 | /*@ bar :: (A, (x:A) => A) => A */ 9 | function bar(x:any, f:any){ 10 | return f(x); 11 | } 12 | 13 | export function main(x: number): number { 14 | return bar(x, idd); // this is actually (idd @ number) 15 | } 16 | -------------------------------------------------------------------------------- /tests/pos/scope/06-scope.ts: -------------------------------------------------------------------------------- 1 | //adapted from navier-stokes 2 | 3 | /*@ u :: string */ 4 | let u = "hi"; 5 | 6 | module A { 7 | 8 | export function bar(u: number): void { 9 | u = 3; 10 | u = 3; 11 | } 12 | 13 | /*@ blah :: () => {void | true} */ 14 | function blah() { 15 | u = u + " there" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/simple/28-top-type.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ resistance :: number */ 3 | let resistance = 1000; 4 | 5 | /*@ makeNum :: (x: number) => number */ 6 | /*@ makeNum :: (x: A) => number */ 7 | function makeNum(x: any) { 8 | return 1; 9 | } 10 | 11 | 12 | export function doCalculateResistance() { 13 | resistance = makeNum("1"); 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/simple/48-field-invariant.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif PP(v: int): v > 1 */ 2 | 3 | /*@ type TT = (Mutable) { 4 | f: { number | v > 1 }; 5 | g: boolean; 6 | } */ 7 | type TT = { f: number; g: boolean }; 8 | 9 | /*@ local bb :: TT */ 10 | let bb: TT = { f: 2, g: true }; 11 | 12 | bb.g = false; 13 | 14 | let dd = bb; 15 | assert(dd.f > 1); 16 | -------------------------------------------------------------------------------- /tests/pos/simple/50-adhoc.ts: -------------------------------------------------------------------------------- 1 | 2 | // OBJECT LITERAL METHODS VS FUNCTION FIELDS 3 | 4 | interface NumberGenerator { 5 | generate: () => number; 6 | } 7 | 8 | export function foo(): NumberGenerator { 9 | return { 10 | generate: function() { 11 | return 3; 12 | } 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/unions/test-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ negate :: (x: { number | v > 0 } + boolean) => { number | v < 0 } + boolean */ 3 | function negate(x): any { 4 | // return (typeof (x) === "number") ? (0 - x) : (!x); 5 | 6 | if (typeof (x) === "number") { 7 | return (0 - x); 8 | } 9 | else { 10 | return (!x); 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/classes/10-class.ts: -------------------------------------------------------------------------------- 1 | class Foo{ 2 | constructor() { } 3 | } 4 | 5 | export declare function bar(): void; 6 | 7 | export function foo(f: Foo): () => void; 8 | export function foo(f: () => void): () => void; 9 | export function foo(f: any): () => void { 10 | return (typeof f === "function") ? f : bar 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/classes/15-classhierarchy.ts: -------------------------------------------------------------------------------- 1 | //adapted from transducers 2 | 3 | class Super { 4 | constructor() { } 5 | } 6 | 7 | class Sub extends Super { 8 | constructor() { 9 | super(); 10 | } 11 | } 12 | 13 | /*@ x :: {Sub | extends_class (v,"Super")} */ 14 | let x = new Sub(); 15 | -------------------------------------------------------------------------------- /include/ambient/error.d.ts: -------------------------------------------------------------------------------- 1 | 2 | interface Error { 3 | name: string; 4 | message: string; 5 | } 6 | 7 | interface ErrorConstructor { 8 | new (message?: string): Error; 9 | (message?: string): Error; 10 | prototype: Error; 11 | } 12 | 13 | declare let Error: ErrorConstructor; 14 | -------------------------------------------------------------------------------- /stack.yaml: -------------------------------------------------------------------------------- 1 | # GHC 7.10.2 2 | # resolver: nightly-2015-09-24 3 | 4 | # GHC 7.10.3 5 | resolver: nightly-2016-01-06 6 | 7 | 8 | packages: 9 | - ./liquid-fixpoint 10 | - . 11 | 12 | 13 | extra-deps: 14 | - intern-0.9.1.4 15 | - located-base-0.1.0.0 16 | - ascii-progress-0.3.2.0 17 | - concurrent-output-1.7.1 18 | - fgl-visualize-0.1.0.1 19 | - dotgen-0.4.2 20 | -------------------------------------------------------------------------------- /tests/neg/arrays/24-array.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Eq5(v: int): v > 0 */ 2 | 3 | /*@ mkArray :: (n: number) => MArray */ 4 | export function mkArray(n: number): MArray { 5 | let i = 1; 6 | 7 | /*@ a :: MArray */ 8 | let a: MArray = []; 9 | 10 | while (-10 < i) { 11 | a.push(i); 12 | i = i - 1; 13 | } 14 | return a; 15 | } 16 | -------------------------------------------------------------------------------- /tests/neg/fb/opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | function buildName(firstName: string, lastName?: string) { 3 | if (arguments.length === 1) 4 | return firstName + " " + lastName; 5 | else 6 | return firstName; 7 | } 8 | 9 | let result1 = buildName("Bob"); //works correctly now 10 | let result3 = buildName("Bob", "Adams"); //ah, just right 11 | -------------------------------------------------------------------------------- /tests/neg/lists/unfold-list-01.ts: -------------------------------------------------------------------------------- 1 | 2 | interface NumList { 3 | d: number; 4 | /*@ n : NumList + null */ 5 | n: NumList; 6 | } 7 | 8 | /*@ foo :: () => number */ 9 | function foo() { 10 | /*@ a :: NumList */ 11 | let a = { d: 1, n: { d: 2, n: null } }; 12 | return a.n; 13 | } 14 | 15 | let aa = foo(); 16 | -------------------------------------------------------------------------------- /tests/pos/fb/opt-args.ts: -------------------------------------------------------------------------------- 1 | 2 | function buildName(firstName: string, lastName?: string) { 3 | if (arguments.length === 2) 4 | return firstName + " " + lastName; 5 | else 6 | return firstName; 7 | } 8 | 9 | let result1 = buildName("Bob"); //works correctly now 10 | let result3 = buildName("Bob", "Adams"); //ah, just right 11 | -------------------------------------------------------------------------------- /tests/pos/lists/listsum-01.ts: -------------------------------------------------------------------------------- 1 | /*@ sum :: (LList) => number */ 2 | function sum(xs : List) : number{ 3 | if (empty(xs)) { 4 | return 0; 5 | } 6 | let h : number = head(xs); 7 | let t = tail(xs); 8 | let z : number = sum(xs); 9 | 10 | return 10; // h + sum(t); 11 | } 12 | -------------------------------------------------------------------------------- /tests/pos/lists/unfold-list-00.ts: -------------------------------------------------------------------------------- 1 | 2 | interface MyList { 3 | d: A; 4 | 5 | /*@ n : MyList + null */ 6 | n: MyList; 7 | } 8 | 9 | let inner: MyList = { d: 2, n: null } 10 | 11 | /*@ a :: MyList */ 12 | let a = { d: 1, n: inner }; 13 | 14 | let b = a; 15 | assert(a.d > 0); 16 | -------------------------------------------------------------------------------- /tests/pos/misc/10-dep.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:number, {y:number | x < y}) => number */ 3 | function foo(x:number, y:number) : number{ 4 | return 10; 5 | } 6 | 7 | /*@ baz :: ({a:number|0 < 1}, {b:number | 0 < 1}) => number */ 8 | function baz(a :number, b:number){ 9 | let r :number= 0; 10 | if (a < b){ 11 | r = foo(a, b); 12 | } 13 | return r; 14 | } 15 | -------------------------------------------------------------------------------- /tests/pos/operators/id-01.ts: -------------------------------------------------------------------------------- 1 | /*@ id2 :: (A, B) => A */ 2 | function id2(x, y) { 3 | return x; 4 | } 5 | 6 | /*@ main :: (x:number, boolean) => {v:number|v >= x} */ 7 | function main(x, y) { 8 | let yr = id2(y, x); 9 | let xr = id2(x, y); 10 | let z = 0; 11 | if (yr) { 12 | z = 10; 13 | } 14 | return xr + z; 15 | } 16 | -------------------------------------------------------------------------------- /tests/demo/string-coercion.ts: -------------------------------------------------------------------------------- 1 | 2 | declare function bar(x: string): void; 3 | declare function foo(x: {}): void; 4 | 5 | export function reduce(x: string): void; 6 | export function reduce(x: {}): void; 7 | export function reduce(x: any): void { 8 | if (typeof x === "string") { 9 | bar(x); 10 | } else { 11 | foo(x); 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/operators/sum-ssa-bad.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ sumLoop :: (number, number) => number */ 3 | function sumLoop(acc, i){ 4 | let r = 0; 5 | if (0 < i){ 6 | r = sumLoop(acc + 1, i - 1); 7 | } 8 | return r; 9 | } 10 | 11 | /*@ main :: () => void */ 12 | function main(){ 13 | let n = pos(); 14 | let m = sumLoop(0, n); 15 | assert(m === n); 16 | } 17 | -------------------------------------------------------------------------------- /tests/neg/arrays/03-array.ts: -------------------------------------------------------------------------------- 1 | /*@ indirectIndex :: ( dataArr: IArray 2 | , idxArr : IArray> 3 | , i: { number | 0 <= v && v <= len idxArr}) 4 | => number */ 5 | function indirectIndex(dataArr : number[], idxArr:number[], i:number) : number { 6 | let j = idxArr[i]; 7 | return dataArr[j]; 8 | } 9 | -------------------------------------------------------------------------------- /tests/neg/classes/19-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class AA { 3 | 4 | /*@ (Mutable) x: number */ 5 | public x = 0; 6 | 7 | // Refinement CANNOT refer to mutable fields 8 | 9 | /*@ (Immutable) y: { number | v = this.x } */ 10 | public y = 0; 11 | 12 | constructor() { } 13 | } 14 | 15 | let aa = new AA(); 16 | aa.x = 1; 17 | assert(aa.x === aa.y); 18 | -------------------------------------------------------------------------------- /tests/todo/pos/operators/bracketref-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { v: number | v = 3 } */ 3 | function foo ():number { 4 | var obj = {f1: {f11: 1} }; 5 | 6 | // OK 7 | return obj.f1.f11 + obj.f1.f11 + obj.f1.f11; 8 | 9 | // BAD: 10 | // return obj["f1"].f11 + obj.f1["f11"] + obj["f1"]["f11"]; 11 | } 12 | 13 | var objNoAnnot = { f: 1, g: "str" } 14 | 15 | -------------------------------------------------------------------------------- /tests/neg/lists/safeappend.ts: -------------------------------------------------------------------------------- 1 | /*@ append :: (xs: LList, ys: LList) => {v : LList | (LLlen v) = (LLlen xs) + (LLlen ys)} */ 2 | function append(xs, ys){ 3 | if (empty(xs)) { 4 | return ys; 5 | } else { 6 | let x = safehead(xs); 7 | let xs_ = safetail(xs); 8 | return cons(x, append(xs, ys)); 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/neg/unions/test-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (x:number) => number + undefined */ 3 | declare function foo(x:number): number; 4 | 5 | /*@ bar :: (y: number) => number */ 6 | export function bar(y:number):number { 7 | let z = foo(y); 8 | if (typeof z === "undefined"){ 9 | let a = new Array(z); 10 | return z; 11 | } 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/lists/list-02.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif G10(v:number): v > 10 */ 2 | 3 | /*@ hop :: (List) => List */ 4 | /*@ hop :: (null) => List */ 5 | function hop(xs){ 6 | if (empty(xs)) { 7 | } 8 | else { 9 | return xs; 10 | } 11 | return { data: 15, next: null }; 12 | } 13 | 14 | -------------------------------------------------------------------------------- /tests/pos/lists/safeappend.ts: -------------------------------------------------------------------------------- 1 | /*@ append :: (xs: LList, ys: LList) => {v : LList | (LLlen v) = (LLlen xs) + (LLlen ys)} */ 2 | function append(xs, ys){ 3 | if (empty(xs)) { 4 | return ys; 5 | } else { 6 | let x = safehead(xs); 7 | let xs_ = safetail(xs); 8 | return cons(x, append(xs_, ys)); 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /tests/pos/scope/05-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | module M { 3 | let a = 1; 4 | export let b = 2; 5 | b = 3; 6 | function foo() { 7 | let b = 1; 8 | b = 2; 9 | } 10 | } 11 | 12 | module N { 13 | /*@ a :: number */ 14 | let a = 2; 15 | function foo() { 16 | M.b = 2; 17 | M.b = M.b + 2; 18 | } 19 | } 20 | 21 | M.b = 1; 22 | -------------------------------------------------------------------------------- /tests/pos/simple/55-intersection.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (f: (Immutable) { f: (s: { string | v = "aaa" }) => string }) => void */ 3 | declare function foo(f: { f: any }); 4 | 5 | /*@ x :: (Immutable) { 6 | f: ({ string | v = "aaa" || v = "bbb" }) => string; 7 | f: ({ number | v > 0 }) => number; 8 | } */ 9 | declare let x; 10 | 11 | foo(x); 12 | -------------------------------------------------------------------------------- /tests/neg/simple/40-unbound-symbol.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ outer :: (xxxx: number) => { void | 0 < 1 } */ 3 | function outer(xxxx: number) { 4 | 5 | /*@ obj :: { 6 | x: [Mutable] number; 7 | y: { number | v = x }; 8 | z: { number | v = xxxx }; 9 | } 10 | */ 11 | let obj = { x: 1, y: 2, z: 3 }; 12 | 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/inclusion/08-inclusion.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif HasP (p: Str, x: a): hasProperty x p */ 2 | /*@ qualif EnumP (p: Str, x: a): enumProp x p */ 3 | 4 | /*@ values :: (mp: (Immutable) { [k: string]: T }, key: string) => void */ 5 | export function values(mp: { [k: string]: T }, key: string): void { 6 | if (key in mp) { 7 | let a = (mp[key]); 8 | } 9 | }; 10 | -------------------------------------------------------------------------------- /tests/pos/scope/init-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | /*@ local r :: number + undefined */ 5 | let r; 6 | if (cnd) { 7 | r = 1; 8 | } 9 | else { 10 | if (r > 5) { 11 | r = 10; 12 | } 13 | r = 2; 14 | } 15 | return r; 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/scope/init-04.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | /*@ local r :: number + undefined */ 5 | let r; 6 | if (cnd) { 7 | r = 1; 8 | } 9 | else { 10 | if (r > 5) { 11 | r = -10; 12 | } 13 | r = 1; 14 | } 15 | return r; 16 | } 17 | -------------------------------------------------------------------------------- /tests/neg/loops/while-03.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Ineq2(v : number ): (v < 5) */ 2 | 3 | /*@ foo :: () => { number | v = 10 } */ 4 | 5 | function foo() { 6 | 7 | let x = 1; 8 | let i = 0; 9 | 10 | while (i < 5) { 11 | // What is the invariant here ? 12 | // is x == to which i (the invariant?) 13 | x = i; 14 | i = i + 1; 15 | } 16 | 17 | return x; 18 | 19 | } 20 | -------------------------------------------------------------------------------- /tests/neg/misc/12-incr.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ option --real */ 4 | 5 | /*@ qualif Add1(v: int, y: int): v = y + 1 */ 6 | 7 | 8 | /*@ incr :: (x:number) => {number|v = x + 1} */ 9 | function incr(x:number):number{ 10 | return ++x; 11 | } 12 | 13 | /*@ foo :: (x:number) => {number|v = 3*x + 4} */ 14 | function foo(x:number):number{ 15 | return x += incr(x++) + incr(x++); 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/bounded-poly/02-test.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif EqM1(v: int): v = -1 */ 3 | 4 | /*@ foo :: (x: W, y: V, z: V, w: V) => W */ 5 | export function foo(x: W, y: V, z: V, w: V): W { 6 | return x; 7 | } 8 | 9 | let negone = -1; 10 | 11 | let a_20_0 = foo(negone,2, 2, 2); 12 | 13 | assert(a_20_0 === negone); 14 | -------------------------------------------------------------------------------- /tests/pos/objects/06-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly innerObj :: (Mutable) { c: posint } */ 3 | let innerObj = { c: 3 }; 4 | 5 | /*@ a06 :: { b: (Mutable) { c: number } } */ 6 | let a06 = { b: innerObj }; 7 | 8 | /*@ foo :: ({ (Mutable) c: number }) => void */ 9 | function foo(o: { c: number }): void { 10 | o.c = 2; 11 | } 12 | 13 | foo(a06.b); 14 | 15 | assert(a06.b.c > 0); 16 | -------------------------------------------------------------------------------- /tests/pos/scope/03-scope.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(): void { 3 | /*@ gggg :: { number | v > 0 } */ 4 | let gggg = 1; 5 | gggg = gggg + 1; 6 | } 7 | 8 | /*@ bar :: () => { number | v = 2 } */ 9 | function bar() { 10 | let s = 1; 11 | /*@ gggg :: { string | v = "a" } */ 12 | let gggg = "a"; 13 | s = s + 1; 14 | gggg = "a"; 15 | return s; 16 | } 17 | -------------------------------------------------------------------------------- /tests/neg/classes/34-this-meth-scope.ts: -------------------------------------------------------------------------------- 1 | //adapted from navier-stokes 2 | class Foo { 3 | /*@ (Immutable) a: {number | v = 5} */ 4 | a = 5; 5 | 6 | constructor() {} 7 | 8 | /*@ bar({number | v = this.a }): {number | v = 0} */ 9 | bar(x) { 10 | return this.a - x; 11 | } 12 | } 13 | 14 | let z: Foo = new Foo(); 15 | z.bar(4); 16 | -------------------------------------------------------------------------------- /tests/neg/inclusion/04-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ qualif Len(v: a): len v = 3 */ 4 | /*@ qualif Len(v: a): len v = 4 */ 5 | /*@ qualif Len(v: a): len v = 5 */ 6 | /*@ qualif Len(v: a): len v = 6 */ 7 | 8 | // Arrays 9 | let trees: IArray = ["redwood", "bay", "cedar", "oak", "maple"]; 10 | 11 | 12 | assert("mylength" in trees); // returns true (length is an assert property) 13 | -------------------------------------------------------------------------------- /tests/neg/misc/54-short-circuit.ts: -------------------------------------------------------------------------------- 1 | export function foo(arr: IArray): boolean { 2 | if (arr.length > 0) { 3 | if (arr[0] === "blah") { 4 | return true; 5 | } 6 | } 7 | return false; 8 | } 9 | 10 | export function bar(arr: IArray): boolean { 11 | if ((arr.length > 0) && (arr[1] === "blah")) { 12 | return true; 13 | } 14 | return false; 15 | } 16 | -------------------------------------------------------------------------------- /tests/neg/operators/sum-badder.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ sumLoop :: (number, number) => number */ 3 | function sumLoop(acc, i){ 4 | let r = 0; 5 | if (0 < i){ 6 | r = sumLoop(acc, i - 1); 7 | } else { 8 | r = acc; 9 | } 10 | return r; 11 | } 12 | 13 | /*@ main :: () => void */ 14 | function main(){ 15 | let n = pos(); 16 | let m = sumLoop(0, n); 17 | assert(m === n); 18 | } 19 | -------------------------------------------------------------------------------- /tests/neg/simple/55-intersection.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | /*@ foo :: (f: (Immutable) { f: (s: { string | v = "aaa" }) => string }) => void */ 5 | declare function foo(f: { f: any }); 6 | 7 | /*@ x :: (Immutable) { 8 | f: ({ string | v = "aa" || v = "bbb" }) => string; 9 | f: ({ number | v > 0 }) => number; 10 | } */ 11 | declare let x; 12 | 13 | foo(x); 14 | -------------------------------------------------------------------------------- /tests/pos/misc/54-short-circuit.ts: -------------------------------------------------------------------------------- 1 | export function foo(arr: IArray): boolean { 2 | if (arr.length > 0) { 3 | if (arr[0] === "blah") { 4 | return true; 5 | } 6 | } 7 | return false; 8 | } 9 | 10 | export function bar(arr: IArray): boolean { 11 | if ((arr.length > 0) && (arr[0] === "blah")) { 12 | return true; 13 | } 14 | return false; 15 | } 16 | -------------------------------------------------------------------------------- /tests/demo/negate.ts: -------------------------------------------------------------------------------- 1 | /*@ negate :: (x: number) => { number | v > 0 <=> x < 0 } */ 2 | /*@ negate :: (x: boolean) => { boolean | Prop v <=> not (Prop x) } */ 3 | export function negate(x): any { 4 | if (typeof(x) === "number") { 5 | return 0 - x; 6 | } else { 7 | return !x; 8 | } 9 | } 10 | 11 | let a: number = negate(10); 12 | let b: boolean = negate(true); 13 | -------------------------------------------------------------------------------- /tests/neg/arrays/10-array.ts: -------------------------------------------------------------------------------- 1 | //XXX: WORKS with this line - some qualifier scraping is missing... 2 | /*@ qualif Length(v:number): (len v) = 3 */ 3 | 4 | /*@ foo :: () => {void | 0 < 1} */ 5 | export function foo(){ 6 | let a: IArray = [1,2,3]; 7 | /*@ b :: { IArray | len v = 4 } */ 8 | let b = [1,2,3,4]; 9 | assert(a.length + b.length === 7); 10 | return; 11 | } 12 | -------------------------------------------------------------------------------- /tests/neg/classes/13-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class AA { 3 | 4 | /*@ (Immutable) k: number */ 5 | public k: number; 6 | 7 | /*@ (Immutable) l: { number | v = this.k } */ 8 | public l: number; 9 | 10 | constructor() { 11 | this.k = random(); 12 | this.l = random(); 13 | } 14 | 15 | } 16 | 17 | let n = new AA(); 18 | assert(n.k === n.l); 19 | -------------------------------------------------------------------------------- /tests/neg/objects/03-object.ts: -------------------------------------------------------------------------------- 1 | 2 | // `innerObj` will be a unique reference so should not be 3 | // cast to the type of `outerObj` 4 | 5 | let innerObj = { n: 6 } 6 | 7 | /*@ readonly */ 8 | let outerObj = { a: 5, b: "String", oo: innerObj }; 9 | 10 | 11 | 12 | module A { 13 | 14 | export function foo (): { n: number } { 15 | return outerObj.oo; 16 | } 17 | 18 | } 19 | -------------------------------------------------------------------------------- /tests/neg/operators/sum-return-missing.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ sumLoop :: (number, number) => number */ 3 | function sumLoop(acc, i){ 4 | let r = 0; 5 | if (0 < i){ 6 | let r = sumLoop(acc + 1, i - 1); 7 | return r; 8 | } 9 | // return r; 10 | } 11 | 12 | /*@ main :: () => void */ 13 | function main(){ 14 | let n = pos(); 15 | let m = sumLoop(0, n); 16 | assert(m === n); 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/classes/08-class.ts: -------------------------------------------------------------------------------- 1 | 2 | export function ext(x: number) { } 3 | 4 | class Foo { 5 | 6 | // Static method 7 | static s(x: number) {} 8 | 9 | // Method 10 | m(x: number, y: number) {} 11 | 12 | // Function field 13 | f = ext; 14 | 15 | constructor() {} 16 | } 17 | 18 | let a: Foo = new Foo(); 19 | Foo.s(1); 20 | a.m(1,2); 21 | a.f(1); 22 | -------------------------------------------------------------------------------- /tests/pos/misc/30-negate.ts: -------------------------------------------------------------------------------- 1 | /*@ negate :: (x: number) => { number | v > 0 <=> x < 0 } */ 2 | /*@ negate :: (x: boolean) => { boolean | Prop v <=> not (Prop x) } */ 3 | export function negate(x): any { 4 | if (typeof(x) === "number") { 5 | return 0 - x; 6 | } 7 | else { 8 | return !x; 9 | } 10 | } 11 | 12 | let a: number = negate(10); 13 | let b: boolean = negate(true); 14 | -------------------------------------------------------------------------------- /tests/pos/simple/38-overload.ts: -------------------------------------------------------------------------------- 1 | 2 | export function foo(x: string): string; 3 | export function foo(x: number): number; 4 | export function foo(x: any): any { 5 | if (typeof x === "string") { 6 | return "-" + x; 7 | } 8 | else { 9 | return - x; 10 | } 11 | } 12 | 13 | declare function bak(yyyy: A): string; 14 | declare function bak(xxxx: number): number; 15 | -------------------------------------------------------------------------------- /tests/neg/classes/17-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | class AA { 4 | /*@ (Immutable) a: { string | v = "OLD" } */ 5 | public a = "OLD"; 6 | 7 | constructor() { } 8 | } 9 | 10 | class BB extends AA { 11 | 12 | public b = 0; 13 | 14 | constructor() { 15 | super(); 16 | this.a = "NEW"; 17 | } 18 | } 19 | 20 | let n = new BB(); 21 | -------------------------------------------------------------------------------- /tests/neg/simple/42-unbound-symbol.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ outer :: (xxxx: number) => void */ 3 | export function outer(xxxx: number) { 4 | 5 | /*@ foo :: (a: { number | v = xxxx }) => void */ 6 | function foo(a: number) { 7 | 8 | }; 9 | 10 | /*@ bar :: (weird: number) => { number | v = zzzz } */ 11 | function bar(weird: number) { 12 | return weird; 13 | }; 14 | 15 | } 16 | -------------------------------------------------------------------------------- /tests/pos/arrays/26-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ where :: (values: IArray, f: (T) => boolean) => UArray */ 3 | export function where(values: T[], f: (v: T) => boolean): T[] { 4 | let global: IArray = []; 5 | 6 | let result = new Array(5); 7 | for (let i = 0; i < values.length; i++) { 8 | if (f(values[i])) { 9 | result.push(values[i]); 10 | } 11 | } 12 | return result; 13 | } 14 | -------------------------------------------------------------------------------- /tests/pos/classes/45-this-meth-scope.ts: -------------------------------------------------------------------------------- 1 | //adapted from navier-stokes 2 | 3 | 4 | class Foo { 5 | 6 | /*@ (Immutable) a: { number | v = 5 } */ 7 | a = 5; 8 | 9 | constructor() { } 10 | 11 | /*@ bar({number | v = this.a}) : {number | v = 0} */ 12 | bar(x) { 13 | return this.a - x; 14 | } 15 | } 16 | 17 | let z = new Foo(); 18 | z.bar(5); 19 | -------------------------------------------------------------------------------- /tests/pos/objects/09-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ global gobj :: (Mutable) { a: number; b: string } */ 3 | let gobj = {a: 1, b: "glorp" }; 4 | 5 | module A { 6 | export function foo(): void { 7 | gobj.a = gobj.a + 1; 8 | return; 9 | } 10 | 11 | export function moo(): void{ 12 | foo(); 13 | let z = gobj.a; 14 | assert(z > -11); 15 | return; 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/operators/sum-01.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Plus(v: int, x: int, y:int): v = x + y */ 3 | 4 | function sumLoop(acc: number, i: number): number { 5 | if (0 < i) { 6 | return sumLoop(acc + 1, i - 1); 7 | } 8 | return acc; 9 | } 10 | 11 | export function main(): void { 12 | let n: number = _pos(); 13 | let m: number = sumLoop(0, n); 14 | assert(m === n); 15 | } 16 | -------------------------------------------------------------------------------- /tests/pos/operators/sum-infer-01.ts: -------------------------------------------------------------------------------- 1 | 2 | // Ha ha. Why is this safe? :) 3 | 4 | function sumLoop(acc: number, i: number) { 5 | let r: number = acc; 6 | 7 | if (0 < i) { 8 | r = sumLoop(acc + 1, i); 9 | } 10 | 11 | return r; 12 | } 13 | 14 | export function main() { 15 | let n: number = _pos(); 16 | let m: number = sumLoop(0, n); 17 | assert(m === n); 18 | } 19 | -------------------------------------------------------------------------------- /tests/neg/arrays/09-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ toNumber :: (x: string) => { number | 0 <= v } */ 3 | function toNumber(x) { 4 | let n = Number(x); 5 | if (n >= 0) { 6 | return n; 7 | } 8 | else { 9 | return 0; 10 | } 11 | } 12 | 13 | 14 | /*@ foo :: (IArray) => IArray<{ number | 0 < v }> */ 15 | export function foo(arr) { 16 | return arr.map(toNumber); 17 | } 18 | -------------------------------------------------------------------------------- /tests/neg/objects/01-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif PLusOne(v:int, w: int): v = w + 1 */ 3 | /*@ qualif Six(v:int): v = 6 */ 4 | 5 | function inc1(n: number) { return n + 1; } 6 | function inc2(n: number) { return n + 2; } 7 | 8 | /*@ x :: { @Final f: (n: number) => number } */ 9 | let x = { f: inc2 }; 10 | 11 | function foo() :number { 12 | return x.f(5); 13 | } 14 | 15 | assert(foo() === 6); 16 | -------------------------------------------------------------------------------- /tests/neg/simple/08-func-expression.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly bar :: (x:number) => {number | v = x + 1} */ 3 | let bar = function(x: number) { 4 | return x + 1; 5 | } 6 | 7 | /*@ readonly foo :: (x:number) => {number | v = x + 2} */ 8 | let foo = function(x: number) { 9 | let a = bar(x); 10 | let b = bar(a); 11 | return b; 12 | } 13 | 14 | let baz = foo; 15 | assert(foo(1) === baz(2)); 16 | -------------------------------------------------------------------------------- /tests/pos/arrays/11-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ toNumber :: (x: string) => { number | 0 <= v } */ 3 | function toNumber(x) { 4 | let n = Number(x); 5 | if (n >= 0) { 6 | return n; 7 | } 8 | else { 9 | return 0; 10 | } 11 | } 12 | 13 | 14 | /*@ foo :: (IArray) => IArray<{ number | 0 <= v }> */ 15 | export function foo(arr) { 16 | return arr.map(toNumber); 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/classes/36-init.ts: -------------------------------------------------------------------------------- 1 | 2 | class Foo { 3 | 4 | /*@ f : { number | v = 4 } */ 5 | public f: number; 6 | 7 | /*@ new (id: { number | v = 4 }): Foo */ 8 | constructor(a: number) { 9 | this.f = a; 10 | } 11 | } 12 | 13 | export function createFoo(): Foo { 14 | let foo = new Foo(4); 15 | foo.f = 4; 16 | return foo; 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/classes/38-interface.ts: -------------------------------------------------------------------------------- 1 | 2 | interface A { 3 | f: T; 4 | 5 | /*@ g : { number | v > 0 } */ 6 | g: number; 7 | } 8 | 9 | /*@ interface C extends A */ 10 | interface C extends A { 11 | minChar: number; 12 | limChar: number; 13 | trailingTriviaWidth: number; 14 | } 15 | -------------------------------------------------------------------------------- /tests/todo/pos/simple/null-undef-literals.ts: -------------------------------------------------------------------------------- 1 | //adapted from underscore 2 | 3 | /*@ isNull :: (ob:T) => {boolean | ((Prop v) <=> (ob ~~ null))} */ 4 | function isNull(ob) { 5 | return ob === null; 6 | } 7 | 8 | // (this one already works:) 9 | /*@ isUndefined :: (ob:T) => {boolean | ((Prop v) <=> (ob ~~ undefined))} */ 10 | function isUndefined(ob) { 11 | return ob === undefined; 12 | } 13 | -------------------------------------------------------------------------------- /tests/neg/bounded-poly/02-test.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ qualif EqM1(v: int): v = -1 */ 4 | /*@ qualif EqM1(v: int): v = -2 */ 5 | 6 | // posint get translated to number before being passed to RSC 7 | 8 | /*@ foo :: (x: W, y: V) => W */ 9 | export function foo(x: W, y: V): W { 10 | return x; 11 | } 12 | 13 | assert(foo(-1, -2) === -1); 14 | -------------------------------------------------------------------------------- /tests/neg/classes/27-init.ts: -------------------------------------------------------------------------------- 1 | 2 | class Foo { 3 | 4 | /*@ f : { number | v = 4 } */ 5 | public f: number; 6 | 7 | /*@ new (id: { number | v = 4 }): Foo */ 8 | constructor(a: number) { 9 | this.f = a; 10 | } 11 | 12 | } 13 | 14 | export function createFoo() { 15 | let foo: Foo = new Foo(4); 16 | foo.f = 10; 17 | return foo; 18 | } 19 | -------------------------------------------------------------------------------- /tests/neg/objects/05-object.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif PLusOne(v:number, w: number) : v = w + 1 */ 2 | 3 | /*@ inc :: (number) => number */ 4 | function inc(n) { return n + 1; } 5 | 6 | /*@ readonly */ let obj = { 7 | a: 5, 8 | b: "String", 9 | oo: { n: 6 } 10 | }; 11 | 12 | /*@ foo :: (number) => { b: boolean } */ 13 | export function foo (n) { 14 | return obj.oo; 15 | } 16 | -------------------------------------------------------------------------------- /tests/neg/objects/06-object.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ innerObj :: (Mutable) { c: posint } */ 3 | let innerObj = { c: 3 }; 4 | 5 | /*@ outerObj :: (Mutable) { b: (Mutable) { c: number } } */ 6 | let outerObj = { b: innerObj }; 7 | 8 | /*@ foo :: (o: (Mutable) { c: number }) => void */ 9 | function foo(o: { c: number }): void { 10 | o.c = 0; 11 | } 12 | 13 | foo(outerObj.b); 14 | 15 | assert(outerObj.b.c > 0); 16 | -------------------------------------------------------------------------------- /tests/neg/operators/add-03a.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ myPlusOk :: /\ (x: number, y: number) => { number | v = x + y } 4 | /\ (x: string, y: string) => { string | true } */ 5 | function myPlusOk(x, y){ 6 | return myPlusOk(x,y); 7 | } 8 | 9 | /*@ num_num :: (a:number, b:number) => {number | v = a + 1 } */ 10 | function num_num(a, b){ 11 | let d = myPlusOk(a, b); 12 | return d; 13 | } 14 | -------------------------------------------------------------------------------- /tests/neg/operators/id-00.ts: -------------------------------------------------------------------------------- 1 | function idt(x: A): A { return x; } 2 | 3 | 4 | /*@ idbool :: (boolean) => boolean */ 5 | function idbool(x) { return idt(x); } 6 | 7 | /*@ main :: (x:number, boolean) => { number | v = x } */ 8 | function main(x, y) { 9 | let yr = idt(y); 10 | let xr = idt(x); 11 | let z = 0; 12 | if (yr) { 13 | z = 10; 14 | } 15 | return xr + z; 16 | } 17 | -------------------------------------------------------------------------------- /tests/neg/scope/init-04.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | /*@ local r :: number */ 5 | let r = 0; 6 | if (cnd) { 7 | r = 1; 8 | } 9 | else { 10 | if (r > 5) { 11 | r = 10; 12 | } 13 | else { 14 | r = -2; 15 | } 16 | } 17 | return r; 18 | } 19 | -------------------------------------------------------------------------------- /tests/pos/arrays/09-array.ts: -------------------------------------------------------------------------------- 1 | /*@ indirectIndex :: ( dataArr: IArray 2 | , idxArr : IArray<{number|(0 <= v && v < (len dataArr))}> 3 | , i: { number | ((0 <= v) && (v < (len idxArr)))}) 4 | => number */ 5 | export function indirectIndex(dataArr : number[], idxArr:number[], i:number) : number { 6 | let j = idxArr[i]; 7 | return dataArr[j]; 8 | } 9 | -------------------------------------------------------------------------------- /tests/pos/classes/23-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class AA { 3 | 4 | /*@ (Immutable) k: number */ 5 | public k: number; 6 | 7 | /*@ (Immutable) l: { number | v = this.k } */ 8 | public l: number; 9 | 10 | constructor() { 11 | let n = random(); 12 | this.k = n; 13 | this.l = n; 14 | } 15 | 16 | } 17 | 18 | let n = new AA(); 19 | assert(n.k === n.l); 20 | -------------------------------------------------------------------------------- /tests/todo/weird/splay-00.ts: -------------------------------------------------------------------------------- 1 | class SplayTreeNode { 2 | 3 | /*@ right : [Mutable] SplayTreeNode + undefined */ 4 | public right; 5 | 6 | /*@ traverse_ : (this: SplayTreeNode) : { void | 0 < 1 } */ 7 | public traverse_() { 8 | var current = this; 9 | while (current) { 10 | var peek = current; 11 | current = peek.right; 12 | } 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /tests/neg/objects/16-object.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif PLusOne(v:number, w: number): v = w + 1 */ 2 | /*@ qualif Eq5(v:number): v = 5 */ 3 | 4 | function inc(n: number) { return n + 1; } 5 | 6 | /*@ readonly */ 7 | let gobj = { a: 5, b: "String", f: inc }; 8 | 9 | /*@ foo :: () => { number | v = 6 } */ 10 | function foo () { 11 | gobj.a = 120; 12 | let ff = gobj.f; 13 | return ff(gobj.a); 14 | } 15 | -------------------------------------------------------------------------------- /tests/neg/simple/24-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | interface Pair1 { 3 | x: A; 4 | y: A; 5 | } 6 | 7 | interface ColorPair1 extends Pair1 { 8 | b: B; 9 | } 10 | 11 | export function foo(p: Pair1) { } 12 | 13 | declare let p: ColorPair1; 14 | 15 | foo(p); 16 | 17 | assert(typeof p.x === "string"); 18 | -------------------------------------------------------------------------------- /tests/pos/loops/while-04.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Ineq1(v : int ): (v <= 5) */ 2 | /*@ qualif Eq1(v: int, i: int): v = i - 1 */ 3 | 4 | /*@ foo :: () => { number | v = 4 } */ 5 | function foo() : number{ 6 | let x = 0; 7 | let i = 1; 8 | assert(x === i - 1); 9 | while (i < 5) { 10 | x = i; 11 | i = i + 1; 12 | } 13 | assert(i === 5); 14 | assert(x < i); 15 | assert(x === i - 1); 16 | return x; 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/misc/35-overload.ts: -------------------------------------------------------------------------------- 1 | /*@ plus :: (number, number) => number */ 2 | /*@ plus :: (string, string) => string */ 3 | function plus(x, y) { 4 | let z = x + y; 5 | return z; 6 | } 7 | 8 | /*@ foo :: (number) => number */ 9 | /*@ foo :: (string) => string */ 10 | 11 | export function foo(a){ 12 | if (typeof(a) === "number") 13 | return plus(a, 1); 14 | 15 | return plus(a, "cat"); 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/simple/24-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | interface Pair1 { 3 | x: A; 4 | y: A; 5 | } 6 | 7 | interface ColorPair1 extends Pair1 { 8 | b: B; 9 | } 10 | 11 | export function foo(p: Pair1) { } 12 | 13 | declare let p: ColorPair1; 14 | 15 | foo(p); 16 | 17 | assert(typeof p.x === "number"); 18 | -------------------------------------------------------------------------------- /tests/todo/pos/operators/bitwise-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ randomN :: (n:{number | 0 <= n}) => {v:number | 0 <= v && v <= n} */ 3 | function randomN(n:number){ 4 | 5 | var r = Math.random() * n; 6 | 7 | // We just SUPPORT the operator with no fancy semantics; 8 | // the assume ensures that typechecking passes. 9 | r = r | 0; 10 | 11 | assume (0 <= r && r <= n); 12 | 13 | return r; 14 | 15 | } 16 | -------------------------------------------------------------------------------- /tests/neg/misc/28-negate.ts: -------------------------------------------------------------------------------- 1 | /*@ negate :: (x:number) => {number | v > x} */ 2 | /*@ negate :: (x:boolean) => {boolean | 0 < 1 } */ 3 | function negate(x): any { 4 | if (typeof(x) === "number") { 5 | return !x; 6 | } 7 | else { 8 | return x + 1; 9 | } 10 | } 11 | 12 | /*@ main :: () => boolean */ 13 | function main() { 14 | let a = negate(10); 15 | let b = negate(true); 16 | return b; 17 | } 18 | -------------------------------------------------------------------------------- /tests/neg/misc/36-packet.ts: -------------------------------------------------------------------------------- 1 | class Packet { 2 | /*@ (Mutable) link: Packet + undefined */ 3 | public link: Packet; 4 | 5 | constructor() { } 6 | } 7 | 8 | /*@ foo :: (curr: Packet) => { Packet | 0 < 1 } */ 9 | function foo(curr) { 10 | let next = curr.link; 11 | 12 | if (next) 13 | curr = next; 14 | 15 | return next; 16 | } 17 | -------------------------------------------------------------------------------- /tests/neg/objects/17-object.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif PLusOne(v:number, w: number): v = w + 1 */ 2 | /*@ qualif Eq5(v:number): v = 5 */ 3 | 4 | function inc(n: number) { return n + 2; } 5 | 6 | /*@ readonly */ 7 | let gobj = { 8 | a: 5, 9 | b: "String", 10 | f: inc 11 | }; 12 | 13 | /*@ foo :: () => { number | v = 6 } */ 14 | function foo () { 15 | let ff = gobj.f; 16 | return ff(gobj.a); 17 | } 18 | -------------------------------------------------------------------------------- /tests/neg/simple/61-string-coercion.ts: -------------------------------------------------------------------------------- 1 | 2 | //adapted from transducers 3 | 4 | declare function bar(x: string): void; 5 | declare function foo(x: {}): void; 6 | 7 | export function reduce(x: string): void; 8 | export function reduce(x: {}): void; 9 | export function reduce(x: any): void { 10 | if (typeof x === "string") { 11 | foo(x); 12 | } 13 | else { 14 | foo(x); 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/classes/44-subclass.ts: -------------------------------------------------------------------------------- 1 | //adapted from transducers 2 | 3 | class Foo { 4 | constructor() {} 5 | } 6 | class Super { 7 | constructor() { } 8 | } 9 | 10 | class Sub extends Super> { 11 | constructor() { 12 | super(); 13 | } 14 | } 15 | 16 | /*@ x :: Super> */ 17 | let x = new Sub(); 18 | -------------------------------------------------------------------------------- /tests/pos/simple/61-string-coercion.ts: -------------------------------------------------------------------------------- 1 | 2 | //adapted from transducers 3 | 4 | declare function bar(x: string): void; 5 | declare function foo(x: {}): void; 6 | 7 | export function reduce(x: string): void; 8 | export function reduce(x: {}): void; 9 | export function reduce(x: any): void { 10 | if (typeof x === "string") { 11 | bar(x); 12 | } 13 | else { 14 | foo(x); 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /tests/neg/classes/28-interface.ts: -------------------------------------------------------------------------------- 1 | 2 | interface Point { 3 | x: number; 4 | y: number; 5 | } 6 | 7 | interface ColorPoint extends Point { 8 | c: string; 9 | } 10 | 11 | interface RedPoint extends ColorPoint { 12 | /*@ c : { string | v = "red" } */ 13 | c: string; 14 | } 15 | 16 | let a: RedPoint = { x: 1, y: 2, c: "blue" }; 17 | -------------------------------------------------------------------------------- /tests/neg/misc/44-twice.ts: -------------------------------------------------------------------------------- 1 | 2 | function twice(f: (x: A) => A, x0: A): A { 3 | let x1 = f(x0); 4 | x1 = f(x1); 5 | return x1; 6 | } 7 | 8 | function foo(x: number): number { 9 | let z = 0; 10 | if (random() > 0) { 11 | z = 10; 12 | } 13 | return x + z; 14 | } 15 | 16 | /*@ main :: (n: number) => {v:number |v > n} */ 17 | function main(x) { 18 | return twice(foo, x); 19 | } 20 | -------------------------------------------------------------------------------- /tests/neg/scope/init-03.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (cnd: boolean) => { number | v > 0 } */ 3 | export function foo(cnd: boolean): number { 4 | /*@ local r :: number + undefined */ 5 | let r; 6 | if (cnd) { 7 | r = 1; 8 | } 9 | else { 10 | if (r > 5) { 11 | r = 10; 12 | } 13 | if (r > 7) { 14 | r = -2; 15 | } 16 | } 17 | return r; 18 | } 19 | -------------------------------------------------------------------------------- /tests/pos/classes/41-offsets.ts: -------------------------------------------------------------------------------- 1 | 2 | //adapted from navier-stokes 3 | 4 | class Foo { 5 | /*@ (Immutable) x: number */ 6 | x; 7 | /*@ new (x:number): { Foo | offset(v,"x") = x } */ 8 | constructor(x) { 9 | this.x = x; 10 | } 11 | } 12 | 13 | /*@ foo :: ({Foo | offset(v,"x") = 5}) => {number | v = 0} */ 14 | function foo(z) { 15 | return z.x - 5; 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/unions/test-09.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ a :: { number | 0 < 1 } */ 3 | let a : number = 1; 4 | 5 | /*@ b :: string */ 6 | let b : string = "a"; 7 | 8 | /*@ c :: number + boolean */ 9 | let c = 1; 10 | 11 | /*@ d :: { v: number | v = 1 } + { v: string | v = "" } */ 12 | let d = 1; 13 | 14 | /*@ e :: { { } | 0 < 1 } */ 15 | let e = { } ; 16 | 17 | /*@ local f :: { d: number + boolean } */ 18 | let f = { d: 1 }; 19 | -------------------------------------------------------------------------------- /tests/todo/pos/simple/late-init.ts: -------------------------------------------------------------------------------- 1 | /*@ foo :: (x:Node, y:Node + null) => { void | 0 < 1 } */ 2 | function foo(x, y) { 3 | var right, noOp; 4 | /*@ current :: Node */ 5 | var current = x; 6 | if (!y) { 7 | noOp = 0; 8 | } else { 9 | right = current; 10 | current = y; 11 | } 12 | 13 | var a = right; 14 | 15 | } 16 | 17 | class Node { 18 | constructor() { } 19 | } 20 | -------------------------------------------------------------------------------- /tests/demo/minindex-classic.ts: -------------------------------------------------------------------------------- 1 | 2 | export function minIndex(arr: IArray): number { 3 | if (arr.length <= 0) return -1; 4 | let min = 0; 5 | 6 | // Try making the array accesses unsafe, e.g. by changing < to <= 7 | 8 | for (let i = 0; i < arr.length; i++) { 9 | let cur = arr[i]; 10 | if (cur < arr[min]) { 11 | min = i; 12 | } 13 | } 14 | return min; 15 | } 16 | -------------------------------------------------------------------------------- /tests/neg/classes/31-offsets.ts: -------------------------------------------------------------------------------- 1 | 2 | //adapted from navier-stokes 3 | 4 | class Foo { 5 | /*@ (Immutable) x: number */ 6 | x; 7 | 8 | /*@ new (x: number): {Foo | offset(v,"x") = x} */ 9 | constructor(x) { 10 | this.x = x 11 | } 12 | } 13 | 14 | /*@ foo :: ({Foo | offset(v,"x") = 5}) => {number | v = 1} */ 15 | function foo(z) { 16 | return z.x - 5; 17 | } 18 | -------------------------------------------------------------------------------- /tests/neg/operators/sum-bad.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ sumLoop :: ({acc:number | 0 < 1}, {i:number| 0 <= i}) => {v:number|v = acc + i} */ 3 | function sumLoop(acc, i){ 4 | let r = 0; 5 | if (0 < i){ 6 | r = sumLoop(acc + 1, i); 7 | } else { 8 | r = acc; 9 | } 10 | return r; 11 | } 12 | 13 | /*@ main :: () => void */ 14 | function main(){ 15 | let n = pos(); 16 | let m = sumLoop(0, n); 17 | assert(m === n); 18 | } 19 | -------------------------------------------------------------------------------- /tests/pos/classes/12-class.ts: -------------------------------------------------------------------------------- 1 | //adapted from navier-stokes octane 2 | /*@ qualif Cmp (v: int, x: a): v < len x */ 3 | 4 | 5 | class FluidField { 6 | 7 | /*@ (Immutable) size : posint */ 8 | private size = 5; 9 | 10 | constructor() { } 11 | 12 | /*@ foo({ IArray | len v = this.size }) : void */ 13 | public foo(x) { 14 | let y = x[this.size - 1]; 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/objects/02-object.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif PLusOne(v: int, w: int): v = w + 1 */ 2 | 3 | /*@ local innerObj :: { n: number } */ 4 | let innerObj = { n: 6 }; 5 | 6 | /*@ outerObj :: { a: number; b: string; c: { n : number } } */ 7 | let outerObj = { a: 5, b: "String", c: innerObj }; 8 | 9 | 10 | module A { 11 | 12 | export function foo (n: number): { n: number } { 13 | return outerObj.c; 14 | } 15 | 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/operators/sum-02.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Plus(v: int, x: int, y: int) : v = x + y */ 3 | 4 | function sumLoop(acc: number, i: number): number { 5 | let r: number = acc; 6 | if (0 < i) { 7 | r = sumLoop(acc + 1, i - 1); 8 | } 9 | return r; 10 | } 11 | 12 | export function main(): void { 13 | let n: number = _pos(); 14 | let m: number = sumLoop(0, n); 15 | assert(m === n); 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/unions/test-05.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: (T, {v:number | v > 0}) => T + undefined */ 3 | function foo(x: T, n: number) { 4 | let i = n; 5 | 6 | /*@ a :: T + undefined */ 7 | let a = undefined; 8 | 9 | while (0 < i) { 10 | if (i > 100) { 11 | a = x; 12 | } else { 13 | a = undefined; 14 | } 15 | i--; 16 | } 17 | 18 | return a; 19 | } 20 | -------------------------------------------------------------------------------- /tests/pos/classes/00-class.ts: -------------------------------------------------------------------------------- 1 | class BankAccount { 2 | 3 | /*@ f: posint */ 4 | public f : number = 1; 5 | 6 | /*@ g : { string | v = "a" } */ 7 | public g: string = "a"; 8 | 9 | /*@ new (x: posint): BankAccount */ 10 | constructor(x : number) { 11 | assert( x > 0 ); 12 | // assert(this.g === "a"); 13 | } 14 | 15 | } 16 | 17 | let ba = new BankAccount(1); 18 | 19 | assert(ba.g === "a"); 20 | -------------------------------------------------------------------------------- /tests/pos/misc/42-safe-meth-call.ts: -------------------------------------------------------------------------------- 1 | class Tree { 2 | 3 | constructor() {} 4 | 5 | /*@ root : TreeNode + null */ 6 | root = null 7 | 8 | foo() { 9 | let _root = this.root; 10 | if (_root) { 11 | _root.bar(); 12 | } 13 | } 14 | } 15 | 16 | class TreeNode { 17 | bar(): void {} ; 18 | 19 | constructor() {} 20 | } 21 | -------------------------------------------------------------------------------- /tests/pos/scope/07-scope.ts: -------------------------------------------------------------------------------- 1 | //adapted from underscore 2 | export class Foo { 3 | constructor() { } 4 | 5 | map(): void { 6 | /*@ results :: Array */ 7 | let results = []; 8 | } 9 | } 10 | 11 | // Note that it works outside of a class context: 12 | 13 | export function map(): void { 14 | /*@ results :: Array */ 15 | let results = []; 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/simple/08-func-expression.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ readonly bar :: (x: number) => {number | v = x + 1} */ 3 | let bar = function(x: number) { 4 | return x + 1; 5 | } 6 | 7 | /*@ readonly foo :: (x: number) => {number | v = x + 2} */ 8 | let foo = function(x: number) { 9 | let a = bar(x); 10 | let b = bar(a); 11 | return b; 12 | } 13 | 14 | let baz = foo; 15 | assert(bar(1) === 2); 16 | assert(foo(1) === baz(1)); 17 | -------------------------------------------------------------------------------- /tests/pos/classes/27-eq_val.ts: -------------------------------------------------------------------------------- 1 | // This currently works 2 | 3 | /*@ qualif CmpZ(v:number): v = 1 */ 4 | 5 | class A { 6 | /*@ x : { number | v = 1 } */ 7 | public x = 1; 8 | /*@ y : { number | v = 1 } */ 9 | public y = 1; 10 | constructor() { } 11 | } 12 | 13 | export function foo(): void { 14 | let r = new A(); 15 | let p = r.x; 16 | let q = r.y; 17 | assert(p === q); 18 | } 19 | -------------------------------------------------------------------------------- /tests/pos/misc/13-incr.ts: -------------------------------------------------------------------------------- 1 | /*@ sincr :: (x:number) => {number | v = x + 1} */ 2 | function sincr(x:number):number{ 3 | ++x; 4 | return x; 5 | } 6 | 7 | /*@ incr3 :: (x:number) => {number | v = x + 3} */ 8 | function incr3(x:number):number{ 9 | ++x; 10 | x++; 11 | ++x; 12 | return x; 13 | } 14 | 15 | 16 | /*@ pincr :: (x:number) => {number | v = x + 1} */ 17 | function pincr(x:number):number{ 18 | x++; 19 | return x; 20 | } -------------------------------------------------------------------------------- /tests/pos/operators/sum-00.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Plus(v: int, x: int, y: int): v = x + y */ 2 | 3 | function sumLoop(acc: number, i: number): number { 4 | let r: number = 0; 5 | if (0 < i) { 6 | r = sumLoop(acc + 1, i - 1); 7 | } else { 8 | r = acc; 9 | } 10 | return r; 11 | } 12 | 13 | export function main(): void { 14 | let n = _pos(); 15 | let m = sumLoop(0, n); 16 | assert(m === n); 17 | } 18 | -------------------------------------------------------------------------------- /tests/pos/simple/58-qualgen-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif AA (v: int): (v < 3) */ 3 | /*@ qualif AA (v: a): (len v = 2) */ 4 | 5 | let junk = 0; 6 | 7 | /*@ readonly arr :: IArray */ 8 | let arr = [1, 2]; 9 | 10 | 11 | module A { 12 | 13 | /*@ foo :: () => { number | v < 4 } */ 14 | export function foo(): number { 15 | // arr[0] = 2; 16 | let v = arr[0]; 17 | return v + 1; 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /tests/neg/classes/21-eq-val.ts: -------------------------------------------------------------------------------- 1 | // This currently works 2 | 3 | /*@ qualif CmpZ(v:number): v = 1 */ 4 | 5 | class A { 6 | /*@ x : { number | v = 1 } */ 7 | public x = 1; 8 | /*@ y : { number | v = 1 } */ 9 | public y = 12; 10 | 11 | constructor() { } 12 | } 13 | 14 | export function foo(): void { 15 | let r = new A(); 16 | let p = r.x; 17 | let q = r.y; 18 | assert(p === q); 19 | } 20 | -------------------------------------------------------------------------------- /tests/neg/classes/26-init.ts: -------------------------------------------------------------------------------- 1 | 2 | class Foo { 3 | public f: number; 4 | 5 | constructor(a: number) { 6 | this.f = a; 7 | } 8 | } 9 | 10 | function createFoo(): Foo { 11 | /*@ foo :: Foo */ 12 | let foo = new Foo(5); 13 | 14 | foo.f = 10; 15 | return foo; 16 | } 17 | 18 | let foo = createFoo(); 19 | 20 | if (foo.f === 10) { 21 | assert(foo.f === 100); 22 | } 23 | -------------------------------------------------------------------------------- /tests/neg/operators/choice.ts: -------------------------------------------------------------------------------- 1 | //THIS IS FINE 2 | 3 | /*@ bob :: (x:number) => {v:number | v != 0} */ 4 | function bob(x:number):number { 5 | if (x) { 6 | return x; 7 | } else { 8 | return (x + 1); 9 | } 10 | } 11 | 12 | // BUT this is not -- and should be treated like the above... 13 | 14 | /*@ main :: (x:number) => {v:number | v != 0} */ 15 | function main(x:number): number { 16 | return x ? x : 0; 17 | } 18 | 19 | -------------------------------------------------------------------------------- /tests/todo/pos/unions/or-undef.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | // PV: needs sort-checking at RSC, when dropping the refinement from 4 | // then top-level to parts of then union. 5 | 6 | 7 | /*@ check_undefined :: (x: { T + undefined | v = y}, y: { T + undefined | v = x }) => T */ 8 | function check_undefined(x:any, y: any) : T { 9 | if (typeof x === "undefined") 10 | return crash(); 11 | return x; 12 | } 13 | 14 | check_undefined(1,1); 15 | -------------------------------------------------------------------------------- /tests/benchmarks/todo/pldi16/d3/keys.ts: -------------------------------------------------------------------------------- 1 | /// 2 | 3 | // d3.keys = function(map: {}): string[] 4 | 5 | /*@ keys :: (map: (Immutable){ }) => MArray<{string | hasProperty(v, map) && enumProp(v, map)}> */ 6 | function keys(map: any): any[] { 7 | /*@ keys :: MArray */ 8 | let keys: string[] = []; 9 | for (let key in map) { 10 | keys.push(key); 11 | } 12 | return keys; 13 | }; 14 | -------------------------------------------------------------------------------- /tests/neg/scope/11-nested.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ foo :: () => { number | v = 5 } */ 3 | export function foo() { 4 | 5 | // { k__ 2 } => { k__4 } 6 | function addThree(xxxx: number) { 7 | return xxxx + 1; 8 | } 9 | 10 | return addThree(1); 11 | } 12 | 13 | 14 | 15 | // 1. { k__4 } <: { v = 5 } 16 | // 2. { v = 1 } <: { k__2 } 17 | // 3. x: { k__2 } |- { v = x + 1 } <: { k__4 } 18 | -------------------------------------------------------------------------------- /tests/pos/simple/13-contextual.ts: -------------------------------------------------------------------------------- 1 | /*@ qualif Lt3(v: a): len v = 3 */ 2 | 3 | /*@ foo :: (a: IArray, i: IArray>) => { IArray | len v = len i } */ 4 | declare function foo_13(a: IArray, i: IArray): IArray; 5 | 6 | let a_123: IArray = [1, 2, 3]; 7 | let a_012: IArray = [0, 1, 2]; 8 | 9 | assert(a_012.length === 3); 10 | 11 | let f_13 = foo_13(a_123, a_012); 12 | 13 | assert(f_13.length === 3); 14 | -------------------------------------------------------------------------------- /tests/neg/simple/45-immutable-field.ts: -------------------------------------------------------------------------------- 1 | //adapted from navier-stokes octane 2 | 3 | class FluidField { 4 | 5 | //this should work even if we don't label the field as immutable 6 | 7 | /*@ size: {number | v > 0} */ 8 | private size = 5; 9 | 10 | constructor() { } 11 | 12 | /*@ foo(x: { IArray | len v = this.size }) : void */ 13 | public foo(x) { 14 | x[this.size] = -1 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/classes/17-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | class A { 4 | 5 | /*@ (Immutable) x: posint */ 6 | public x: number; 7 | 8 | /*@ (Immutable) y: string */ 9 | public y: string; 10 | 11 | public c = "aaa"; 12 | 13 | constructor() { 14 | if (random()) 15 | this.y = "a"; 16 | else 17 | this.y = "b"; 18 | 19 | if (random()) 20 | this.x = 2; 21 | else 22 | this.x = 3; 23 | 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /tests/pos/operators/id-00.ts: -------------------------------------------------------------------------------- 1 | /*@ idt :: (A) => A */ 2 | function idt(x) { return x; } 3 | 4 | 5 | /*@ idbool :: (boolean) => boolean */ 6 | function idbool(x) { 7 | return idt(x); 8 | } 9 | 10 | /*@ main :: (x:number, boolean) => { number | v >= x } */ 11 | export function main(x, y) { 12 | let yr = idt(y); 13 | let xr = idt(x); 14 | let z = 0; 15 | if (yr) { 16 | z = 10; 17 | } 18 | return xr + z; 19 | } 20 | -------------------------------------------------------------------------------- /tests/neg/misc/59-class-inv.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ inv (this.rowSize = this.width + 2) */ 3 | class FluidField { 4 | /*@ (Immutable) width : number */ 5 | private width; 6 | /*@ (Immutable) rowSize : number */ 7 | private rowSize; 8 | 9 | /*@ new () : {v:FluidField | 0 < 1} */ 10 | constructor() { 11 | let width = 3; 12 | 13 | this.width = width; 14 | this.rowSize = width + 1; 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /tests/neg/simple/22-unification.ts: -------------------------------------------------------------------------------- 1 | 2 | interface Pair { x: A; y: B; } 3 | export function fst(p: Pair): A { return p.x; } 4 | export function snd(p: Pair): B { return p.y; } 5 | 6 | /*@ neg_o_22_0 :: { @final z: string } */ 7 | let neg_o_22_0 = { z: "ASDFGHJKL" } 8 | let neg_o_22_1 = snd({ x: 1, y: neg_o_22_0 }); 9 | 10 | assert(neg_o_22_1.z === "ASDFGHJK"); 11 | -------------------------------------------------------------------------------- /tests/pos/inclusion/01-inclusion.ts: -------------------------------------------------------------------------------- 1 | // Taken from strobe 2 | 3 | /*@ qualif HasP (p: Str, x: a): hasProperty x p */ 4 | /*@ qualif EnumP (p: Str, x: a): enumProp x p */ 5 | 6 | /*@ foo :: (o: { [x:string]: string + number }) => string */ 7 | export function foo(o) { 8 | for (let x in o) { 9 | let r = o[x]; 10 | if (typeof r === "string") { 11 | return r; 12 | } 13 | } 14 | return "no string found"; 15 | }; 16 | -------------------------------------------------------------------------------- /tests/pos/misc/59-class-inv.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ inv (this.rowSize = this.width + 2) */ 3 | class FluidField { 4 | /*@ (Immutable) width : number */ 5 | private width; 6 | /*@ (Immutable) rowSize : number */ 7 | private rowSize; 8 | 9 | /*@ new () : {v:FluidField | 0 < 1} */ 10 | constructor() { 11 | let width = 3; 12 | 13 | this.width = width; 14 | this.rowSize = width + 2; 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /tests/pos/operators/id-02.ts: -------------------------------------------------------------------------------- 1 | /*@ idt :: (A) => A */ 2 | function idt(x) { return x; } 3 | 4 | 5 | /*@ idbool :: (boolean) => boolean */ 6 | function idbool(x) { return idt(x); } 7 | 8 | /*@ main :: (x:number, boolean) => {v:number|v = x} */ 9 | export function main(x, y) { 10 | let yr = idt(y); 11 | let xr = idt(x); 12 | let z = 0; 13 | if (yr) { 14 | z = 10; 15 | return xr; 16 | } 17 | return xr + z; 18 | } 19 | -------------------------------------------------------------------------------- /src/Language/Rsc/Pretty.hs: -------------------------------------------------------------------------------- 1 | {-# LANGUAGE FlexibleInstances #-} 2 | 3 | -- | Pretty-printing JavaScript. 4 | module Language.Rsc.Pretty (module P) where 5 | 6 | import Language.Rsc.Pretty.Annotations () 7 | import Language.Rsc.Pretty.ClassHierarchy () 8 | import Language.Rsc.Pretty.Common as P 9 | import Language.Rsc.Pretty.Errors as P 10 | import Language.Rsc.Pretty.Syntax as P 11 | 12 | -------------------------------------------------------------------------------- /tests/neg/inclusion/03-inclusion.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | /*@ qualif Len(v: a): len v = 3 */ 4 | /*@ qualif Len(v: a): len v = 4 */ 5 | /*@ qualif Len(v: a): len v = 5 */ 6 | /*@ qualif Len(v: a): len v = 6 */ 7 | 8 | 9 | 10 | // Arrays 11 | 12 | let trees: IArray = ["redwood", "bay", "cedar", "oak", "maple"]; 13 | assert(0 in trees); // returns true 14 | assert(3 in trees); // returns true 15 | 16 | assert(6 in trees); // returns false 17 | -------------------------------------------------------------------------------- /tests/pos/arrays/10-array.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ indirectIndex :: (x: IArray, b: IArray>, i: idx) => number */ 3 | function indirectIndex(x: number[], b: number[], i: number) : number { 4 | let bi = b[i]; 5 | return x[bi]; 6 | } 7 | 8 | /*@ writeIndex :: (x: IArray, i: idx, v : number) => void */ 9 | function writeIndex(x : number[], i : number, v: number) : void { 10 | // x[i] = v; // Not supported 11 | return; 12 | } 13 | -------------------------------------------------------------------------------- /tests/pos/classes/19-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | 3 | class A { 4 | /*@ (Mutable) x: { number | v > 2 } */ 5 | public x: number; 6 | 7 | /*@ (Mutable) y: string */ 8 | public y: string; 9 | 10 | public c = "aaa"; 11 | 12 | public foo() { return 1; } 13 | 14 | constructor() { 15 | if (random()) { this.y = "a"; } else { this.y = "b"; } 16 | if (random()) { this.x = 3; } else { this.x = 4; } 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /tests/pos/classes/25-ctor.ts: -------------------------------------------------------------------------------- 1 | 2 | class AA { 3 | /*@ (Immutable) a: string */ 4 | public a = "OLD"; 5 | 6 | constructor() { } 7 | } 8 | 9 | class BB extends AA { 10 | 11 | /*@ (Immutable) a: { string | v = "NEW" } */ 12 | public a: string; 13 | 14 | public b = 0; 15 | 16 | constructor() { 17 | super(); 18 | this.a = "NEW"; 19 | } 20 | } 21 | 22 | let n = new BB(); 23 | -------------------------------------------------------------------------------- /tests/pos/operators/sum-infer-00.ts: -------------------------------------------------------------------------------- 1 | 2 | /*@ qualif Plus(v: int, x: int, y: int): v = x + y */ 3 | 4 | function sumLoop(acc: number, i: number): number { 5 | let r: number = 0; 6 | if (0 < i) { 7 | r = sumLoop(acc + 1, i - 1); 8 | } else { 9 | r = acc; 10 | } 11 | return r; 12 | } 13 | 14 | export function main() { 15 | let n: number = _pos(); 16 | let m: number = sumLoop(0, n); 17 | assert(m === n); 18 | } 19 | -------------------------------------------------------------------------------- /include/rsc/mutability.d.ts: -------------------------------------------------------------------------------- 1 | 2 | interface ReadOnly { 3 | _readOnnlyBrand: any; 4 | } 5 | 6 | interface AssignsFields extends ReadOnly { 7 | _assignsFieldsBrand: any; 8 | } 9 | 10 | interface Mutable extends AssignsFields { 11 | _mutableBrand: any; 12 | } 13 | 14 | interface Immutable extends ReadOnly { 15 | _immutableBrand: any; 16 | } 17 | 18 | interface Unique extends Immutable, Mutable { 19 | _uniqueBrand: any; 20 | } 21 | --------------------------------------------------------------------------------