type variable = string let globalIdentifier = ref 1 module VariableMap = Map.Make(String) module VariableSet = Set.Make(String) type ftype = IntegerType | BooleanType | PolimorphicType of string | FunctionType of ftype list * ftype type fsubstitution = (* goes from polimorphic types to types *) ftype VariableMap.t type fenvironment = (* goes from variables to types *) ftype VariableMap.t type typingshape = (* tuple of a simple type environment and a simple type *) fenvironment * ftype type t_exp = Integer of int (* x := a *) | Boolean of bool (* v *) | Variable of variable (* x *) | Function of variable list * ftype * t_exp (* lambda x: t. x *) | Application of t_exp * t_exp list (* x x *) | Plus of t_exp * t_exp (* x + x *) | Minus of t_exp * t_exp (* x - x *) | Times of t_exp * t_exp (* x * x *) | Division of t_exp * t_exp (* x / x *) | Modulo of t_exp * t_exp (* x % x *) | Power of t_exp * t_exp (* x ^ x *) | PowerMod of t_exp * t_exp * t_exp (* (x ^ x) % x *) | Rand of t_exp (* rand(0, x) *) | BAnd of t_exp * t_exp (* x and x *) | BOr of t_exp * t_exp (* x or x *) | BNot of t_exp (* not x *) | Cmp of t_exp * t_exp (* x == x *) | CmpLess of t_exp * t_exp (* x < x *) | CmpLessEq of t_exp * t_exp (* x <= x *) | CmpGreater of t_exp * t_exp (* x > x *) | CmpGreaterEq of t_exp * t_exp (* x >= x *) | IfThenElse of t_exp * t_exp * t_exp (* if b then c else c *) | LetIn of variable * t_exp * t_exp (* let x = x in x *) | LetFun of variable * variable list * ftype * t_exp * t_exp (* let rec x: t. x in x *) type permittedValues = IntegerPermitted of int | BooleanPermitted of bool | FunctionPermitted of closure and closure = { inputList: variable list; body: t_exp; assignments: permittedValues VariableMap.t; recursiveness: variable option } type memory = { assignments: permittedValues VariableMap.t } type error = [ `AbsentAssignment of string | `WrongType of string | `DivisionByZero of string | `WrongArity of string | `WrongTypeSpecification of string ]