use super::super::*;
use super::enums::*;
#[cfg(not(feature = "std"))]
use alloc::string::String;
#[cfg(not(feature = "std"))]
use alloc::vec::Vec;
pub trait SymbolResolver {
fn symbol(
&mut self, instruction: &Instruction, operand: u32, instruction_operand: Option<u32>, address: u64, address_size: u32,
) -> Option<SymbolResult>;
}
#[derive(Debug, Clone, Eq, PartialEq, Hash)]
pub enum SymResString<'a> {
Str(&'a str),
String(String),
}
impl<'a> Default for SymResString<'a> {
#[cfg_attr(has_must_use, must_use)]
#[inline]
fn default() -> Self {
SymResString::Str("")
}
}
impl<'a> SymResString<'a> {
#[cfg_attr(feature = "cargo-clippy", allow(clippy::wrong_self_convention))]
pub(crate) fn to_owned<'b>(self) -> SymResString<'b> {
match self {
SymResString::Str(s) => SymResString::String(String::from(s)),
SymResString::String(s) => SymResString::String(s),
}
}
pub(crate) fn to_owned2<'b>(&self) -> SymResString<'b> {
match self {
&SymResString::Str(s) => SymResString::String(String::from(s)),
&SymResString::String(ref s) => SymResString::String(s.clone()),
}
}
}
#[derive(Debug, Default, Clone, Eq, PartialEq, Hash)]
pub struct SymResTextPart<'a> {
pub text: SymResString<'a>,
pub color: FormatterTextKind,
}
impl<'a> SymResTextPart<'a> {
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn new(text: &'a str, color: FormatterTextKind) -> Self {
Self { text: SymResString::Str(text), color }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_string(text: String, color: FormatterTextKind) -> Self {
Self { text: SymResString::String(text), color }
}
#[cfg_attr(feature = "cargo-clippy", allow(clippy::wrong_self_convention))]
pub(crate) fn to_owned<'b>(self) -> SymResTextPart<'b> {
SymResTextPart { text: self.text.to_owned(), color: self.color }
}
pub(crate) fn to_owned2<'b>(&self) -> SymResTextPart<'b> {
SymResTextPart { text: self.text.to_owned2(), color: self.color }
}
}
#[derive(Debug, Clone, Eq, PartialEq, Hash)]
pub enum SymResTextInfo<'a> {
Text(SymResTextPart<'a>),
TextVec(&'a [SymResTextPart<'a>]),
}
impl<'a> SymResTextInfo<'a> {
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn new(text: &'a str, color: FormatterTextKind) -> Self {
SymResTextInfo::Text(SymResTextPart::new(text, color))
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_string(text: String, color: FormatterTextKind) -> Self {
SymResTextInfo::Text(SymResTextPart::with_string(text, color))
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_text(text: SymResTextPart<'a>) -> Self {
SymResTextInfo::Text(text)
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_vec(text: &'a [SymResTextPart<'a>]) -> Self {
SymResTextInfo::TextVec(text)
}
#[cfg_attr(feature = "cargo-clippy", allow(clippy::wrong_self_convention))]
pub(crate) fn to_owned<'b>(self, vec: &'b mut Vec<SymResTextPart<'b>>) -> SymResTextInfo<'b> {
match self {
SymResTextInfo::Text(part) => SymResTextInfo::Text(part.to_owned()),
SymResTextInfo::TextVec(parts) => {
vec.clear();
vec.extend(parts.iter().map(|a| a.to_owned2()));
SymResTextInfo::TextVec(vec)
}
}
}
}
#[derive(Debug, Clone, Eq, PartialEq, Hash)]
pub struct SymbolResult<'a> {
pub address: u64,
pub text: SymResTextInfo<'a>,
pub flags: u32,
pub symbol_size: Option<MemorySize>,
}
impl<'a> SymbolResult<'a> {
const DEFAULT_KIND: FormatterTextKind = FormatterTextKind::Label;
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_str(address: u64, text: &'a str) -> Self {
Self { address, text: SymResTextInfo::new(text, SymbolResult::DEFAULT_KIND), flags: SymbolFlags::NONE, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_str_size(address: u64, text: &'a str, size: MemorySize) -> Self {
Self { address, text: SymResTextInfo::new(text, SymbolResult::DEFAULT_KIND), flags: SymbolFlags::NONE, symbol_size: Some(size) }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_str_kind(address: u64, text: &'a str, color: FormatterTextKind) -> Self {
Self { address, text: SymResTextInfo::new(text, color), flags: SymbolFlags::NONE, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_str_kind_flags(address: u64, text: &'a str, color: FormatterTextKind, flags: u32) -> Self {
Self { address, text: SymResTextInfo::new(text, color), flags, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_string(address: u64, text: String) -> Self {
Self { address, text: SymResTextInfo::with_string(text, SymbolResult::DEFAULT_KIND), flags: SymbolFlags::NONE, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_string_size(address: u64, text: String, size: MemorySize) -> Self {
Self { address, text: SymResTextInfo::with_string(text, SymbolResult::DEFAULT_KIND), flags: SymbolFlags::NONE, symbol_size: Some(size) }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_string_kind(address: u64, text: String, color: FormatterTextKind) -> Self {
Self { address, text: SymResTextInfo::with_string(text, color), flags: SymbolFlags::NONE, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_string_kind_flags(address: u64, text: String, color: FormatterTextKind, flags: u32) -> Self {
Self { address, text: SymResTextInfo::with_string(text, color), flags, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_text(address: u64, text: SymResTextInfo<'a>) -> Self {
Self { address, text, flags: SymbolFlags::NONE, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_text_size(address: u64, text: SymResTextInfo<'a>, size: MemorySize) -> Self {
Self { address, text, flags: SymbolFlags::NONE, symbol_size: Some(size) }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_text_flags(address: u64, text: SymResTextInfo<'a>, flags: u32) -> Self {
Self { address, text, flags, symbol_size: None }
}
#[cfg_attr(has_must_use, must_use)]
#[inline]
pub fn with_text_flags_size(address: u64, text: SymResTextInfo<'a>, flags: u32, size: MemorySize) -> Self {
Self { address, text, flags, symbol_size: Some(size) }
}
#[cfg_attr(feature = "cargo-clippy", allow(clippy::wrong_self_convention))]
pub(crate) fn to_owned<'b>(self, vec: &'b mut Vec<SymResTextPart<'b>>) -> SymbolResult<'b> {
SymbolResult { address: self.address, text: self.text.to_owned(vec), flags: self.flags, symbol_size: self.symbol_size }
}
}