UNPKG

@helios-lang/compiler

Version:

Helios is a Domain Specific Language that compiles to Plutus-Core (i.e. Cardano on-chain validator scripts). Helios is a non-Haskell alternative to Plutus. With this library you can compile Helios scripts and build Cardano transactions, all you need to bu

426 lines (408 loc) 14.2 kB
import { expectDefined } from "@helios-lang/type-utils" import { FTPP } from "../codegen/ParametricName.js" import { FuncType, GenericEnumMemberType, GenericType, makeListType, makeMapType } from "./common.js" import { Parameter } from "./Parameter.js" import { ParametricData } from "./ParametricData.js" import { DefaultTypeClass } from "./parametric.js" /** * @typedef {import("./common.js").DataType} DataType * @typedef {import("./common.js").Type} Type * @typedef {import("./common.js").InstanceMembers} InstanceMembers * @typedef {import("./common.js").TypeMembers} TypeMembers */ /** * @param {Type} type * @returns {InstanceMembers} */ export function genCommonInstanceMembers(type) { return { serialize: new FuncType([], ByteArrayType), show: new FuncType([], StringType) } } /** * @param {Type} type * @returns {TypeMembers} */ export function genCommonTypeMembers(type) { return { __eq: new FuncType([type, type], BoolType), __neq: new FuncType([type, type], BoolType), from_data: new FuncType([RawDataType], type), __to_data: new FuncType([type], RawDataType), is_valid_data: new FuncType([RawDataType], BoolType) } } /** * @internal * @param {Type} type * @param {Type} parentType * @returns {TypeMembers} */ export function genCommonEnumTypeMembers(type, parentType) { return { __eq: new FuncType([type, parentType], BoolType), __neq: new FuncType([type, parentType], BoolType), from_data: new FuncType([RawDataType], type), __to_data: new FuncType([type], RawDataType), is_valid_data: new FuncType([RawDataType], BoolType), __is: new FuncType([parentType], BoolType) } } /** * Builtin bool type * @type {DataType} */ export const BoolType = new GenericType({ name: "Bool", genTypeSchema: (self, parents) => ({ kind: "internal", name: "Bool" }), genInstanceMembers: (self) => ({ ...genCommonInstanceMembers(self), to_int: new FuncType([], IntType), trace: new FuncType([StringType], self), trace_if_false: new FuncType([StringType], self), trace_if_true: new FuncType([StringType], self) }), genTypeMembers: (self) => ({ ...genCommonTypeMembers(self), __and: new FuncType([self, self], self), __neq: new FuncType([self, self], self), __not: new FuncType([self], self), __or: new FuncType([self, self], self), and: new FuncType( [new FuncType([], self), new FuncType([], self)], self ), or: new FuncType([new FuncType([], self), new FuncType([], self)], self) }) }) /** * Builtin bytearray type * @type {DataType} */ export const ByteArrayType = new GenericType({ name: "ByteArray", genTypeSchema: (self, parents) => ({ kind: "internal", name: "ByteArray" }), genInstanceMembers: (self) => ({ ...genCommonInstanceMembers(self), blake2b: new FuncType([], self), decode_utf8: new FuncType([], StringType), decode_utf8_safe: new FuncType([], StringType), ends_with: new FuncType([self], BoolType), length: IntType, prepend: new FuncType([IntType], self), sha2: new FuncType([], self), sha3: new FuncType([], self), slice: new FuncType([IntType, IntType], self), starts_with: new FuncType([self], BoolType) }), genTypeMembers: (self) => ({ ...genCommonTypeMembers(self), __add: new FuncType([self, self], self), __geq: new FuncType([self, self], BoolType), __gt: new FuncType([self, self], BoolType), __leq: new FuncType([self, self], BoolType), __lt: new FuncType([self, self], BoolType), parse: new FuncType([StringType], self) }) }) /** * @type {DataType} */ export const IntType = new GenericType({ name: "Int", genTypeSchema: (self, parents) => ({ kind: "internal", name: "Int" }), genInstanceMembers: (self) => ({ ...genCommonInstanceMembers(self), abs: new FuncType([], self), bound: new FuncType([self, self], self), bound_max: new FuncType([self], self), bound_min: new FuncType([self], self), decode_zigzag: new FuncType([], self), encode_zigzag: new FuncType([], self), to_base58: new FuncType([], StringType), to_big_endian: new FuncType([], ByteArrayType), to_bool: new FuncType([], BoolType), to_hex: new FuncType([], StringType), to_little_endian: new FuncType([], ByteArrayType), to_ratio: new FuncType([], RatioType), to_real: new FuncType([], RealType) }), genTypeMembers: (self) => ({ ...genCommonTypeMembers(self), __add: new FuncType([self, self], self), __add1: new FuncType([self, RealType], RealType), __div: new FuncType([self, self], self), __div1: new FuncType([self, RealType], RealType), __div2: new FuncType([self, RatioType], RatioType), __geq: new FuncType([self, self], BoolType), __geq1: new FuncType([self, RealType], BoolType), __geq2: new FuncType([self, RatioType], BoolType), __gt: new FuncType([self, self], BoolType), __gt1: new FuncType([self, RealType], BoolType), __gt2: new FuncType([self, RatioType], BoolType), __leq: new FuncType([self, self], BoolType), __leq1: new FuncType([self, RealType], BoolType), __leq2: new FuncType([self, RatioType], BoolType), __lt: new FuncType([self, self], BoolType), __lt1: new FuncType([self, RealType], BoolType), __lt2: new FuncType([self, RatioType], BoolType), __mod: new FuncType([self, self], self), __mul: new FuncType([self, self], self), __mul1: new FuncType([self, RealType], RealType), __neg: new FuncType([self], self), __pos: new FuncType([self], self), __sub: new FuncType([self, self], self), __sub1: new FuncType([self, RealType], RealType), __sub2: new FuncType([self, RatioType], RatioType), from_base58: new FuncType([StringType], self), from_big_endian: new FuncType([ByteArrayType], self), from_little_endian: new FuncType([ByteArrayType], self), max: new FuncType([self, self], self), min: new FuncType([self, self], self), parse: new FuncType([StringType], self), sqrt: new FuncType([self], self) }) }) /** * Type of external data that must be cast/type-checked before using * Not named 'Data' in Js because that would be too generic * @type {DataType} */ export const RawDataType = new GenericType({ name: "Data", genTypeSchema: (self, parents) => ({ kind: "internal", name: "Data" }), genInstanceMembers: (self) => ({ ...genCommonInstanceMembers(self), tag: IntType, as: (() => { const a = new Parameter("a", `${FTPP}0`, new DefaultTypeClass()) return new ParametricData([a], a.ref) })(), as_strictly: (() => { const a = new Parameter("a", `${FTPP}0`, new DefaultTypeClass()) return new ParametricData([a], a.ref) })() }), genTypeMembers: (self) => ({ ...genCommonTypeMembers(self), ConstrData: RawConstrDataType, MapData: RawMapDataType, ListData: RawListDataType, IntData: RawIntDataType, ByteArrayData: RawByteArrayDataType }) }) const RawConstrDataType = new GenericEnumMemberType({ name: "ConstrData", constrIndex: -1, parentType: RawDataType, genTypeSchema: (self, parents) => ({ kind: "internal", name: "Data" }), fieldNames: ["tag", "fields"], genInstanceMembers: (self) => ({ tag: IntType, fields: expectDefined(makeListType)(RawDataType) }), genTypeMembers: (self) => ({ __is: new FuncType([RawDataType], BoolType) }) }) const RawMapDataType = new GenericEnumMemberType({ name: "MapData", constrIndex: -1, parentType: RawDataType, fieldNames: ["entries"], genTypeSchema: (self, parents) => ({ kind: "internal", name: "Data" }), genInstanceMembers: (self) => ({ entries: expectDefined(makeMapType)(RawDataType, RawDataType) }), genTypeMembers: (self) => ({ __is: new FuncType([RawDataType], BoolType) }) }) const RawListDataType = new GenericEnumMemberType({ name: "ListData", constrIndex: -1, parentType: RawDataType, fieldNames: ["items"], genTypeSchema: (self, parents) => ({ kind: "internal", name: "Data" }), genInstanceMembers: (self) => ({ items: expectDefined(makeListType)(RawDataType) }), genTypeMembers: (self) => ({ __is: new FuncType([RawDataType], BoolType) }) }) const RawIntDataType = new GenericEnumMemberType({ name: "IntData", constrIndex: -1, parentType: RawDataType, fieldNames: ["value"], genTypeSchema: (self, parents) => ({ kind: "internal", name: "Data" }), genInstanceMembers: (self) => ({ value: IntType }), genTypeMembers: (self) => ({ __is: new FuncType([RawDataType], BoolType) }) }) const RawByteArrayDataType = new GenericEnumMemberType({ name: "ByteArrayData", constrIndex: -1, parentType: RawDataType, fieldNames: ["value"], genTypeSchema: (self, parents) => ({ kind: "internal", name: "Data" }), genInstanceMembers: (self) => ({ value: ByteArrayType }), genTypeMembers: (self) => ({ __is: new FuncType([RawDataType], BoolType) }) }) /** * Builtin top/bottom Ratio */ export const RatioType = new GenericType({ name: "Ratio", genTypeSchema: (self, parents) => ({ kind: /** @type {const} */ ("internal"), name: "Ratio" }), genInstanceMembers: (self) => ({ ...genCommonInstanceMembers(self), bottom: IntType, top: IntType, ceil: new FuncType([], IntType), floor: new FuncType([], IntType), to_real: new FuncType([], RealType), trunc: new FuncType([], IntType), round: new FuncType([], IntType), equals: new FuncType([self], BoolType) }), genTypeMembers: (self) => ({ ...genCommonTypeMembers(self), new: new FuncType([IntType, IntType], self), __add: new FuncType([self, self], self), __add1: new FuncType([self, IntType], self), __sub: new FuncType([self, self], self), __sub1: new FuncType([self, IntType], self), __mul: new FuncType([self, self], self), __mul1: new FuncType([self, IntType], self), __div: new FuncType([self, self], self), __div1: new FuncType([self, IntType], self), __lt: new FuncType([self, self], BoolType), __lt1: new FuncType([self, IntType], BoolType), __leq: new FuncType([self, self], BoolType), __leq1: new FuncType([self, IntType], BoolType), __gt: new FuncType([self, self], BoolType), __gt1: new FuncType([self, IntType], BoolType), __geq: new FuncType([self, self], BoolType), __geq1: new FuncType([self, IntType], BoolType) }) }) /** * Builtin Real fixed point number type * @type {DataType} */ export const RealType = new GenericType({ name: "Real", genTypeSchema: (self, parents) => ({ kind: "internal", name: "Real" }), genInstanceMembers: (self) => ({ ...genCommonInstanceMembers(self), abs: new FuncType([], self), ceil: new FuncType([], IntType), floor: new FuncType([], IntType), round: new FuncType([], IntType), trunc: new FuncType([], IntType), to_ratio: new FuncType([], RatioType) }), genTypeMembers: (self) => ({ ...genCommonTypeMembers(self), __add: new FuncType([self, self], self), __add1: new FuncType([self, IntType], self), __div: new FuncType([self, self], self), __div1: new FuncType([self, IntType], self), __eq1: new FuncType([self, IntType], BoolType), __geq: new FuncType([self, self], BoolType), __geq1: new FuncType([self, IntType], BoolType), __gt: new FuncType([self, self], BoolType), __gt1: new FuncType([self, IntType], BoolType), __leq: new FuncType([self, self], BoolType), __leq1: new FuncType([self, IntType], BoolType), __lt: new FuncType([self, self], BoolType), __lt1: new FuncType([self, IntType], BoolType), __mul: new FuncType([self, self], self), __mul1: new FuncType([self, IntType], self), __neg: new FuncType([self], self), __neq1: new FuncType([self, IntType], BoolType), __pos: new FuncType([self], self), __sub: new FuncType([self, self], self), __sub1: new FuncType([self, IntType], self), divf: new FuncType([self, self], self), // log: new FuncType([self], self), // TODO: make this accurate to 6 decimal places at a reasonable cost logf: new FuncType([self], self), max: new FuncType([self, self], self), min: new FuncType([self, self], self), mulf: new FuncType([self, self], self), sqrt: new FuncType([self], self), sqrtf: new FuncType([self], self) }) }) /** * Builtin string type * @type {DataType} */ export const StringType = new GenericType({ name: "String", genTypeSchema: (self, parents) => ({ kind: "internal", name: "String" }), genInstanceMembers: (self) => ({ ...genCommonInstanceMembers(self), encode_utf8: new FuncType([], ByteArrayType), ends_with: new FuncType([self], BoolType), starts_with: new FuncType([self], BoolType) }), genTypeMembers: (self) => ({ ...genCommonTypeMembers(self), __add: new FuncType([self, self], self), is_valid_utf8: new FuncType([ByteArrayType], BoolType) }) })