feat: wrap up adding uplc builtins for now
This commit is contained in:
parent
d5d2ba9cd7
commit
819256df99
|
@ -6,6 +6,7 @@
|
|||
|
||||
**aiken**: Fancy errors using [miette](https://github.com/zkat/miette)
|
||||
**aiken**: Typechecking
|
||||
**aiken**: Inject `aiken/builtin` module with some functions from `DefaultFunction` in UPLC directly exposed
|
||||
**aiken-lang**: add `infer` method to `UntypedModule` which returns a `TypedModule`
|
||||
|
||||
### Changed
|
||||
|
|
|
@ -80,6 +80,7 @@ dependencies = [
|
|||
"itertools",
|
||||
"miette",
|
||||
"pretty_assertions",
|
||||
"strum",
|
||||
"thiserror",
|
||||
"uplc",
|
||||
"vec1",
|
||||
|
@ -928,6 +929,12 @@ version = "0.1.21"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7ef03e0a2b150c7a90d01faf6254c9c48a41e95fb2a8c2ac1c6f0d2b9aefc342"
|
||||
|
||||
[[package]]
|
||||
name = "rustversion"
|
||||
version = "1.0.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "97477e48b4cf8603ad5f7aaf897467cf42ab4218a38ef76fb14c2d6773a6d6a8"
|
||||
|
||||
[[package]]
|
||||
name = "rusty-fork"
|
||||
version = "0.3.0"
|
||||
|
@ -1010,6 +1017,25 @@ version = "0.10.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623"
|
||||
|
||||
[[package]]
|
||||
name = "strum"
|
||||
version = "0.24.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "063e6045c0e62079840579a7e47a355ae92f60eb74daaf156fb1e84ba164e63f"
|
||||
|
||||
[[package]]
|
||||
name = "strum_macros"
|
||||
version = "0.24.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1e385be0d24f186b4ce2f9982191e7101bb737312ad61c1f2f984f34bcf85d59"
|
||||
dependencies = [
|
||||
"heck",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"rustversion",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "supports-color"
|
||||
version = "1.3.0"
|
||||
|
@ -1192,6 +1218,8 @@ dependencies = [
|
|||
"proptest",
|
||||
"serde",
|
||||
"serde_json",
|
||||
"strum",
|
||||
"strum_macros",
|
||||
"thiserror",
|
||||
]
|
||||
|
||||
|
|
|
@ -37,7 +37,7 @@ impl Project {
|
|||
let mut module_types = HashMap::new();
|
||||
|
||||
module_types.insert("aiken".to_string(), builtins::prelude(&id_gen));
|
||||
module_types.insert("aiken/builtin".to_string(), builtins::plutus());
|
||||
module_types.insert("aiken/builtin".to_string(), builtins::plutus(&id_gen));
|
||||
|
||||
Project {
|
||||
config,
|
||||
|
|
|
@ -15,6 +15,7 @@ chumsky = "0.8.0"
|
|||
internment = "0.7.0"
|
||||
itertools = "0.10.5"
|
||||
miette = "5.2.0"
|
||||
strum = "0.24.1"
|
||||
thiserror = "1.0.37"
|
||||
uplc = { path = '../uplc', version = "0.0.21" }
|
||||
vec1 = "1.8.0"
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
use std::{cell::RefCell, collections::HashMap, sync::Arc};
|
||||
|
||||
use strum::IntoEnumIterator;
|
||||
|
||||
use uplc::builtins::DefaultFunction;
|
||||
|
||||
use crate::{
|
||||
|
@ -212,7 +214,7 @@ pub fn prelude(id_gen: &IdGenerator) -> TypeInfo {
|
|||
prelude
|
||||
}
|
||||
|
||||
pub fn plutus() -> TypeInfo {
|
||||
pub fn plutus(id_gen: &IdGenerator) -> TypeInfo {
|
||||
let mut plutus = TypeInfo {
|
||||
name: "aiken/builtin".to_string(),
|
||||
package: "".to_string(),
|
||||
|
@ -223,101 +225,174 @@ pub fn plutus() -> TypeInfo {
|
|||
accessors: HashMap::new(),
|
||||
};
|
||||
|
||||
plutus.values.insert(
|
||||
DefaultFunction::AddInteger.to_string(),
|
||||
DefaultFunction::AddInteger.into(),
|
||||
);
|
||||
|
||||
plutus.values.insert(
|
||||
DefaultFunction::SubtractInteger.to_string(),
|
||||
DefaultFunction::SubtractInteger.into(),
|
||||
);
|
||||
|
||||
plutus.values.insert(
|
||||
DefaultFunction::MultiplyInteger.to_string(),
|
||||
DefaultFunction::MultiplyInteger.into(),
|
||||
);
|
||||
|
||||
plutus.values.insert(
|
||||
DefaultFunction::DivideInteger.to_string(),
|
||||
DefaultFunction::DivideInteger.into(),
|
||||
);
|
||||
for builtin in DefaultFunction::iter() {
|
||||
if let Some(value) = from_default_function(builtin, id_gen) {
|
||||
plutus.values.insert(
|
||||
builtin.to_string().replace("ByteString", "ByteArray"),
|
||||
value,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
plutus
|
||||
}
|
||||
|
||||
impl From<DefaultFunction> for ValueConstructor {
|
||||
fn from(builtin: DefaultFunction) -> Self {
|
||||
let (tipo, arity) = match builtin {
|
||||
DefaultFunction::AddInteger
|
||||
| DefaultFunction::SubtractInteger
|
||||
| DefaultFunction::MultiplyInteger
|
||||
| DefaultFunction::DivideInteger
|
||||
| DefaultFunction::QuotientInteger
|
||||
| DefaultFunction::RemainderInteger
|
||||
| DefaultFunction::ModInteger => {
|
||||
let tipo = function(vec![int(), int()], int());
|
||||
pub fn from_default_function(
|
||||
builtin: DefaultFunction,
|
||||
id_gen: &IdGenerator,
|
||||
) -> Option<ValueConstructor> {
|
||||
let info = match builtin {
|
||||
DefaultFunction::AddInteger
|
||||
| DefaultFunction::SubtractInteger
|
||||
| DefaultFunction::MultiplyInteger
|
||||
| DefaultFunction::DivideInteger
|
||||
| DefaultFunction::QuotientInteger
|
||||
| DefaultFunction::RemainderInteger
|
||||
| DefaultFunction::ModInteger => {
|
||||
let tipo = function(vec![int(), int()], int());
|
||||
|
||||
(tipo, 2)
|
||||
}
|
||||
Some((tipo, 2))
|
||||
}
|
||||
|
||||
DefaultFunction::EqualsInteger
|
||||
| DefaultFunction::LessThanInteger
|
||||
| DefaultFunction::LessThanEqualsInteger => {
|
||||
let tipo = function(vec![int(), int()], bool());
|
||||
DefaultFunction::EqualsInteger
|
||||
| DefaultFunction::LessThanInteger
|
||||
| DefaultFunction::LessThanEqualsInteger => {
|
||||
let tipo = function(vec![int(), int()], bool());
|
||||
|
||||
(tipo, 2)
|
||||
}
|
||||
DefaultFunction::AppendByteString => todo!(),
|
||||
DefaultFunction::ConsByteString => todo!(),
|
||||
DefaultFunction::SliceByteString => todo!(),
|
||||
DefaultFunction::LengthOfByteString => todo!(),
|
||||
DefaultFunction::IndexByteString => todo!(),
|
||||
DefaultFunction::EqualsByteString => todo!(),
|
||||
DefaultFunction::LessThanByteString => todo!(),
|
||||
DefaultFunction::LessThanEqualsByteString => todo!(),
|
||||
DefaultFunction::Sha2_256 => todo!(),
|
||||
DefaultFunction::Sha3_256 => todo!(),
|
||||
DefaultFunction::Blake2b_256 => todo!(),
|
||||
DefaultFunction::VerifyEd25519Signature => todo!(),
|
||||
DefaultFunction::VerifyEcdsaSecp256k1Signature => todo!(),
|
||||
DefaultFunction::VerifySchnorrSecp256k1Signature => todo!(),
|
||||
DefaultFunction::AppendString => todo!(),
|
||||
DefaultFunction::EqualsString => todo!(),
|
||||
DefaultFunction::EncodeUtf8 => todo!(),
|
||||
DefaultFunction::DecodeUtf8 => todo!(),
|
||||
DefaultFunction::IfThenElse => todo!(),
|
||||
DefaultFunction::ChooseUnit => todo!(),
|
||||
DefaultFunction::Trace => todo!(),
|
||||
DefaultFunction::FstPair => todo!(),
|
||||
DefaultFunction::SndPair => todo!(),
|
||||
DefaultFunction::ChooseList => todo!(),
|
||||
DefaultFunction::MkCons => todo!(),
|
||||
DefaultFunction::HeadList => todo!(),
|
||||
DefaultFunction::TailList => todo!(),
|
||||
DefaultFunction::NullList => todo!(),
|
||||
DefaultFunction::ChooseData => todo!(),
|
||||
DefaultFunction::ConstrData => todo!(),
|
||||
DefaultFunction::MapData => todo!(),
|
||||
DefaultFunction::ListData => todo!(),
|
||||
DefaultFunction::IData => todo!(),
|
||||
DefaultFunction::BData => todo!(),
|
||||
DefaultFunction::UnConstrData => todo!(),
|
||||
DefaultFunction::UnMapData => todo!(),
|
||||
DefaultFunction::UnListData => todo!(),
|
||||
DefaultFunction::UnIData => todo!(),
|
||||
DefaultFunction::UnBData => todo!(),
|
||||
DefaultFunction::EqualsData => todo!(),
|
||||
DefaultFunction::SerialiseData => todo!(),
|
||||
DefaultFunction::MkPairData => todo!(),
|
||||
DefaultFunction::MkNilData => todo!(),
|
||||
DefaultFunction::MkNilPairData => todo!(),
|
||||
};
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::AppendByteString => {
|
||||
let tipo = function(vec![byte_array(), byte_array()], byte_array());
|
||||
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::ConsByteString => {
|
||||
let tipo = function(vec![int(), byte_array()], byte_array());
|
||||
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::SliceByteString => {
|
||||
let tipo = function(vec![int(), int(), byte_array()], byte_array());
|
||||
|
||||
Some((tipo, 3))
|
||||
}
|
||||
DefaultFunction::LengthOfByteString => {
|
||||
let tipo = function(vec![byte_array()], int());
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::IndexByteString => {
|
||||
let tipo = function(vec![byte_array(), int()], int());
|
||||
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::EqualsByteString
|
||||
| DefaultFunction::LessThanByteString
|
||||
| DefaultFunction::LessThanEqualsByteString => {
|
||||
let tipo = function(vec![byte_array(), byte_array()], bool());
|
||||
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::Sha2_256 | DefaultFunction::Sha3_256 | DefaultFunction::Blake2b_256 => {
|
||||
let tipo = function(vec![byte_array()], byte_array());
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
|
||||
DefaultFunction::VerifyEd25519Signature => {
|
||||
let tipo = function(vec![byte_array(), byte_array(), byte_array()], bool());
|
||||
|
||||
Some((tipo, 3))
|
||||
}
|
||||
DefaultFunction::VerifyEcdsaSecp256k1Signature => None,
|
||||
DefaultFunction::VerifySchnorrSecp256k1Signature => None,
|
||||
DefaultFunction::AppendString => {
|
||||
let tipo = function(vec![string(), string()], string());
|
||||
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::EqualsString => {
|
||||
let tipo = function(vec![string(), string()], bool());
|
||||
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::EncodeUtf8 => {
|
||||
let tipo = function(vec![string()], byte_array());
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::DecodeUtf8 => {
|
||||
let tipo = function(vec![byte_array()], string());
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::IfThenElse => None,
|
||||
DefaultFunction::ChooseUnit => None,
|
||||
DefaultFunction::Trace => {
|
||||
let ret = generic_var(id_gen.next());
|
||||
|
||||
let tipo = function(vec![string(), ret.clone()], ret);
|
||||
|
||||
Some((tipo, 2))
|
||||
}
|
||||
DefaultFunction::FstPair => None,
|
||||
DefaultFunction::SndPair => None,
|
||||
DefaultFunction::ChooseList => None,
|
||||
DefaultFunction::MkCons => None,
|
||||
DefaultFunction::HeadList => {
|
||||
let ret = generic_var(id_gen.next());
|
||||
|
||||
let tipo = function(vec![list(ret.clone())], ret);
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::TailList => {
|
||||
let ret = list(generic_var(id_gen.next()));
|
||||
|
||||
let tipo = function(vec![ret.clone()], ret);
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::NullList => {
|
||||
let ret = list(generic_var(id_gen.next()));
|
||||
|
||||
let tipo = function(vec![ret], bool());
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::ChooseData => None,
|
||||
DefaultFunction::ConstrData => None,
|
||||
DefaultFunction::MapData => None,
|
||||
DefaultFunction::ListData => None,
|
||||
DefaultFunction::IData => None,
|
||||
DefaultFunction::BData => None,
|
||||
DefaultFunction::UnConstrData => None,
|
||||
DefaultFunction::UnMapData => None,
|
||||
DefaultFunction::UnListData => None,
|
||||
DefaultFunction::UnIData => None,
|
||||
DefaultFunction::UnBData => None,
|
||||
DefaultFunction::EqualsData => {
|
||||
let arg = generic_var(id_gen.next());
|
||||
|
||||
let tipo = function(vec![arg.clone(), arg], bool());
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::SerialiseData => {
|
||||
let tipo = function(vec![generic_var(id_gen.next())], byte_array());
|
||||
|
||||
Some((tipo, 1))
|
||||
}
|
||||
DefaultFunction::MkPairData => None,
|
||||
DefaultFunction::MkNilData => None,
|
||||
DefaultFunction::MkNilPairData => None,
|
||||
};
|
||||
|
||||
info.map(|(tipo, arity)| {
|
||||
ValueConstructor::public(
|
||||
tipo,
|
||||
ValueConstructorVariant::ModuleFn {
|
||||
name: builtin.to_string(),
|
||||
name: builtin.to_string().replace("ByteString", "ByteArray"),
|
||||
field_map: None,
|
||||
module: "".to_string(),
|
||||
arity,
|
||||
|
@ -325,7 +400,7 @@ impl From<DefaultFunction> for ValueConstructor {
|
|||
builtin: Some(builtin),
|
||||
},
|
||||
)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
pub fn int() -> Arc<Type> {
|
||||
|
|
|
@ -27,6 +27,8 @@ thiserror = "1.0.31"
|
|||
anyhow = "1.0.57"
|
||||
serde = { version = "1.0.144", features = ["derive"] }
|
||||
serde_json = "1.0.85"
|
||||
strum = "0.24.1"
|
||||
strum_macros = "0.24.3"
|
||||
|
||||
[dev-dependencies]
|
||||
hex = "0.4.3"
|
||||
|
|
|
@ -1,11 +1,13 @@
|
|||
use std::{fmt::Display, str::FromStr};
|
||||
|
||||
use strum_macros::EnumIter;
|
||||
|
||||
use flat_rs::de;
|
||||
|
||||
/// All the possible builtin functions in Untyped Plutus Core.
|
||||
#[repr(u8)]
|
||||
#[allow(non_camel_case_types)]
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Copy)]
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Copy, EnumIter)]
|
||||
pub enum DefaultFunction {
|
||||
// Integer functions
|
||||
AddInteger = 0,
|
||||
|
|
|
@ -0,0 +1,8 @@
|
|||
pub type ScriptContext(purpose) {
|
||||
tx_info: TxInfo,
|
||||
script_purpose: purpose
|
||||
}
|
||||
|
||||
pub type TxInfo {
|
||||
idk: Int
|
||||
}
|
|
@ -0,0 +1,7 @@
|
|||
use sample/context
|
||||
|
||||
pub type Mint {
|
||||
currency_symbol: ByteArray
|
||||
}
|
||||
|
||||
pub type ScriptContext = context.ScriptContext(Mint)
|
|
@ -0,0 +1,7 @@
|
|||
use sample/context
|
||||
|
||||
pub type Spend {
|
||||
idk: Int
|
||||
}
|
||||
|
||||
pub type ScriptContext = context.ScriptContext(Spend)
|
|
@ -1,13 +0,0 @@
|
|||
use aiken/builtin.{addInteger}
|
||||
|
||||
pub type ScriptContext {
|
||||
idk: Int
|
||||
}
|
||||
|
||||
pub fn append(a: ByteArray, b: ByteArray) -> ByteArray {
|
||||
todo
|
||||
}
|
||||
|
||||
pub fn add(a, b) {
|
||||
addInteger(a, b)
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
use sample
|
||||
use sample/syntax.{append}
|
||||
use sample/mint
|
||||
use sample/spend
|
||||
|
||||
pub type Datum {
|
||||
something: String,
|
||||
|
@ -10,13 +10,7 @@ pub type Redeemer {
|
|||
Sell
|
||||
}
|
||||
|
||||
pub fn validate(datum: Datum, rdmr: Redeemer, ctx: sample.ScriptContext) -> Bool {
|
||||
let thing = if True {
|
||||
3
|
||||
} else {
|
||||
"thing"
|
||||
}
|
||||
|
||||
pub fn spend(datum: Datum, rdmr: Redeemer, ctx: spend.ScriptContext) -> Bool {
|
||||
when rdmr is {
|
||||
Buy -> True
|
||||
Sell -> datum.something == "Aiken"
|
||||
|
|
Loading…
Reference in New Issue