use std::{fmt, hash::Hash};
use serde::*;
use crate::{CodeSpan, Ident, Primitive, Signature};
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
pub struct DynamicFunction {
pub(crate) index: usize,
pub(crate) sig: Signature,
}
impl From<(usize, Signature)> for DynamicFunction {
fn from((index, sig): (usize, Signature)) -> Self {
Self { index, sig }
}
}
impl From<DynamicFunction> for (usize, Signature) {
fn from(func: DynamicFunction) -> Self {
(func.index, func.sig)
}
}
impl DynamicFunction {
pub fn signature(&self) -> Signature {
self.sig
}
}
impl fmt::Debug for DynamicFunction {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "<dynamic#{:x}>", self.index)
}
}
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
#[serde(untagged)]
pub enum FunctionId {
Primitive(Primitive),
Named(Ident),
Macro(Option<Ident>, CodeSpan),
Main,
#[doc(hidden)]
Unnamed,
}
impl PartialEq<&str> for FunctionId {
fn eq(&self, other: &&str) -> bool {
match self {
FunctionId::Named(name) => &&**name == other,
_ => false,
}
}
}
impl From<Ident> for FunctionId {
fn from(name: Ident) -> Self {
Self::Named(name)
}
}
impl From<Primitive> for FunctionId {
fn from(op: Primitive) -> Self {
Self::Primitive(op)
}
}
impl fmt::Display for FunctionId {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
match self {
FunctionId::Named(name) => write!(f, "{name}"),
FunctionId::Primitive(prim) => write!(f, "{prim}"),
FunctionId::Macro(Some(name), span) => write!(f, "macro expansion of {name} at {span}"),
FunctionId::Macro(None, span) => write!(f, "macro expansion of at {span}"),
FunctionId::Main => write!(f, "main"),
FunctionId::Unnamed => write!(f, "unnamed"),
}
}
}