use std::collections::HashMap;
use std::sync::Weak;
use serde::{Deserialize, Serialize};
use smol_str::SmolStr;
use crate::Extension;
use crate::extension::{OpDef, SignatureFunc};
use crate::ops::OpName;
use crate::types::type_param::TypeParam;
use super::signature::SignatureDeclaration;
use super::{DeclarationContext, ExtensionDeclarationError};
#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
pub(super) struct OperationDeclaration {
name: OpName,
#[serde(default)]
#[serde(skip_serializing_if = "crate::utils::is_default")]
description: String,
#[serde(default)]
#[serde(skip_serializing_if = "crate::utils::is_default")]
signature: Option<SignatureDeclaration>,
#[serde(default)]
#[serde(skip_serializing_if = "crate::utils::is_default")]
params: HashMap<SmolStr, ParamDeclaration>,
#[serde(default)]
#[serde(skip_serializing_if = "crate::utils::is_default")]
misc: HashMap<String, serde_json::Value>,
#[serde(default)]
#[serde(skip_serializing_if = "crate::utils::is_default")]
lowering: Option<String>,
}
impl OperationDeclaration {
pub fn register<'ext>(
&self,
ext: &'ext mut Extension,
ctx: DeclarationContext<'_>,
extension_ref: &Weak<Extension>,
) -> Result<&'ext mut OpDef, ExtensionDeclarationError> {
let Some(signature) = &self.signature else {
return Err(ExtensionDeclarationError::MissingSignature {
ext: ext.name().clone(),
op: self.name.clone(),
});
};
if !self.params.is_empty() {
return Err(ExtensionDeclarationError::ParametricOperation {
ext: ext.name().clone(),
op: self.name.clone(),
});
}
let params: Vec<TypeParam> = vec![];
if self.lowering.is_some() {
return Err(ExtensionDeclarationError::LoweringNotSupported {
ext: ext.name().clone(),
op: self.name.clone(),
});
}
let signature_func: SignatureFunc = signature.make_signature(ext, ctx, ¶ms)?;
let op_def = ext.add_op(
self.name.clone(),
self.description.clone(),
signature_func,
extension_ref,
)?;
for (k, v) in &self.misc {
op_def.add_misc(k, v.clone());
}
Ok(op_def)
}
}
#[derive(Debug, Clone, Hash, PartialEq, Eq, Serialize, Deserialize)]
pub(super) struct ParamDeclaration(
String,
);