diff --git a/crates/lang/src/builtins.rs b/crates/lang/src/builtins.rs index 193aaab2..c2d084c8 100644 --- a/crates/lang/src/builtins.rs +++ b/crates/lang/src/builtins.rs @@ -21,6 +21,7 @@ pub const LIST: &str = "List"; pub const NIL: &str = "Nil"; pub const RESULT: &str = "Result"; pub const STRING: &str = "String"; +pub const OPTION: &str = "Option"; /// Build a prelude that can be injected /// into a compiler pipeline @@ -224,6 +225,60 @@ pub fn prelude(id_gen: &IdGenerator) -> TypeInfo { ), ); + // Option(value, none) + let option_value = generic_var(id_gen.next()); + let option_none = generic_var(id_gen.next()); + + prelude.types.insert( + OPTION.to_string(), + TypeConstructor { + location: Span::empty(), + parameters: vec![option_value.clone(), option_none.clone()], + tipo: option(option_value, option_none), + module: "".to_string(), + public: true, + }, + ); + + prelude.types_constructors.insert( + OPTION.to_string(), + vec!["Some".to_string(), "None".to_string()], + ); + + let some = generic_var(id_gen.next()); + let none = generic_var(id_gen.next()); + let _ = prelude.values.insert( + "Some".to_string(), + ValueConstructor::public( + function(vec![some.clone()], option(some, none)), + ValueConstructorVariant::Record { + module: "".into(), + name: "Some".to_string(), + field_map: None::, + arity: 1, + location: Span::empty(), + constructors_count: 2, + }, + ), + ); + + let some = generic_var(id_gen.next()); + let none = generic_var(id_gen.next()); + let _ = prelude.values.insert( + "None".to_string(), + ValueConstructor::public( + function(vec![none.clone()], option(some, none)), + ValueConstructorVariant::Record { + module: "".into(), + name: "None".to_string(), + field_map: None::, + arity: 0, + location: Span::empty(), + constructors_count: 2, + }, + ), + ); + prelude } @@ -486,6 +541,15 @@ pub fn result(a: Arc, e: Arc) -> Arc { }) } +pub fn option(a: Arc, e: Arc) -> Arc { + Arc::new(Type::App { + public: true, + name: OPTION.to_string(), + module: "".to_string(), + args: vec![a, e], + }) +} + pub fn function(args: Vec>, ret: Arc) -> Arc { Arc::new(Type::Fn { ret, args }) } diff --git a/examples/aiken_std/lib/aiken/context.ak b/examples/aiken_std/lib/aiken/context.ak index 70a234bc..24cef8af 100644 --- a/examples/aiken_std/lib/aiken/context.ak +++ b/examples/aiken_std/lib/aiken/context.ak @@ -13,6 +13,9 @@ pub type ScriptPurpose { Certify(Certificate) } +pub type Redeemer = + Data + pub type BoundValue(value) { NegativeInfinity Finite(value) @@ -32,20 +35,21 @@ pub type Interval(value) { pub type Transaction { inputs: List(Input), reference_inputs: List(Input), - outputs: List(Nil), + outputs: List(Output), fee: Value, mint: Value, certificates: List(Certificate), withdrawals: List(Pair(StakeCredential, Int)), validity_range: Interval(Int), - extra_signatories: Nil, - redeemers: List(Nil), + extra_signatories: List(PublicKeyHash), + redeemers: List(Pair(ScriptPurpose, Redeemer)), datums: List(Pair(Hash(Data), Data)), id: TransactionId, } -pub type TransactionId = - Hash(Transaction) +pub type TransactionId = { + hash: Hash(Transaction) +} pub type Input { output_reference: OutputReference, @@ -60,17 +64,45 @@ pub type OutputReference { pub type PolicyId = ByteArray -pub type StakeCredential = - Nil +pub type StakeCredential = { + StakeHash(Credential) + StakePointer(Int, Int, Int) +} + +pub type Credential = { + PublicKeyCredential(PublicKeyHash) + ScriptCredential(ScriptHash) +} pub type VerificationKey = Nil +pub type ScriptHash = + ByteArray + +pub type PublicKeyHash = + Hash(VerificationKey) + pub type PoolId = Hash(VerificationKey) -pub type Output = - Nil +pub type Output = { + address: Address, + value: Value, + datum: DatumOption, + reference_script: Option(ScriptHash), +} + +pub type Address = { + payment_credential: Credential, + stake_credential: Option(StakeCredential), +} + +pub type DatumOption = { + NoDatum + DatumHash(Hash(Data)) + Datum(Data) +} pub type AssetName = ByteArray