Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Custom const for ERROR_TYPE #756

Merged
merged 1 commit into from
Dec 22, 2023
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
feat: Custom const for ERROR_TYPE
  • Loading branch information
ss2165 committed Dec 22, 2023
commit 123b7f478a3d887071116b245d68be1f58feb347
66 changes: 60 additions & 6 deletions src/extension/prelude.rs
Original file line number Diff line number Diff line change
Expand Up @@ -137,12 +137,11 @@ pub fn new_array_op(element_ty: Type, size: u64) -> LeafOp {
.into()
}

/// The custom type for Errors.
pub const ERROR_CUSTOM_TYPE: CustomType =
CustomType::new_simple(ERROR_TYPE_NAME, PRELUDE_ID, TypeBound::Eq);
/// Unspecified opaque error type.
pub const ERROR_TYPE: Type = Type::new_extension(CustomType::new_simple(
ERROR_TYPE_NAME,
PRELUDE_ID,
TypeBound::Eq,
));
pub const ERROR_TYPE: Type = Type::new_extension(ERROR_CUSTOM_TYPE);

/// The string name of the error type.
pub const ERROR_TYPE_NAME: SmolStr = SmolStr::new_inline("error");
Expand Down Expand Up @@ -191,6 +190,48 @@ impl KnownTypeConst for ConstUsize {
const TYPE: CustomType = USIZE_CUSTOM_T;
}

#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
/// Structure for holding constant usize values.
pub struct ConstError {
/// Integer tag/signal for the error.
pub signal: u32,
/// Error message.
pub message: String,
}

impl ConstError {
/// Define a new error value.
pub fn new(signal: u32, message: impl ToString) -> Self {
Self {
signal,
message: message.to_string(),
}
}
}

#[typetag::serde]
impl CustomConst for ConstError {
fn name(&self) -> SmolStr {
format!("ConstError({:?}, {:?})", self.signal, self.message).into()
}

fn check_custom_type(&self, typ: &CustomType) -> Result<(), CustomCheckFailure> {
self.check_known_type(typ)
}

fn equal_consts(&self, other: &dyn CustomConst) -> bool {
crate::values::downcast_equal_consts(self, other)
}

fn extension_reqs(&self) -> ExtensionSet {
ExtensionSet::singleton(&PRELUDE_ID)
}
}

impl KnownTypeConst for ConstError {
const TYPE: CustomType = ERROR_CUSTOM_TYPE;
}

#[cfg(test)]
mod test {
use crate::{
Expand Down Expand Up @@ -219,7 +260,7 @@ mod test {
}

#[test]
/// Test building a HUGR involving a new_array operation.
/// test the prelude error type.
fn test_error_type() {
let ext_def = PRELUDE
.get_type(&ERROR_TYPE_NAME)
Expand All @@ -229,5 +270,18 @@ mod test {

let ext_type = Type::new_extension(ext_def);
assert_eq!(ext_type, ERROR_TYPE);

let error_val = ConstError::new(2, "my message");

assert_eq!(error_val.name(), "ConstError(2, \"my message\")");

assert!(error_val.check_custom_type(&ERROR_CUSTOM_TYPE).is_ok());

assert_eq!(
error_val.extension_reqs(),
ExtensionSet::singleton(&PRELUDE_ID)
);
assert!(error_val.equal_consts(&ConstError::new(2, "my message")));
assert!(!error_val.equal_consts(&ConstError::new(3, "my message")));
}
}