1use core::fmt::{Debug, Formatter, Result as FmtResult};
2
3use crate::{AnsiColorScheme, AnsiColored, DebugAnsiColored, UnwindContextArgs};
4
5#[derive(Clone, Eq, PartialEq, Ord, PartialOrd, Hash)]
13pub struct UnwindContextFunc<Args> {
14 pub name: &'static str,
16 pub args: Args,
18}
19
20impl<Args> UnwindContextFunc<Args> {
21 #[inline]
44 pub fn new(name: &'static str, args: Args) -> Self {
45 Self { name, args }
46 }
47}
48
49impl<Args> Debug for UnwindContextFunc<Args>
50where
51 for<'a> UnwindContextArgs<&'a Args>: Debug,
52{
53 #[inline]
54 fn fmt(&self, f: &mut Formatter<'_>) -> FmtResult {
55 write!(
56 f,
57 "fn {}({:?})",
58 self.name,
59 UnwindContextArgs::new(&self.args)
60 )?;
61 Ok(())
62 }
63}
64
65impl<Args> DebugAnsiColored for UnwindContextFunc<Args>
66where
67 for<'a> UnwindContextArgs<&'a Args>: DebugAnsiColored,
68{
69 #[inline]
70 fn fmt_colored(
71 &self,
72 f: &mut Formatter<'_>,
73 color_scheme: &'static AnsiColorScheme,
74 ) -> FmtResult {
75 write!(
76 f,
77 "{}fn {}{}{}({}{:?}{}){}",
78 color_scheme.fn_keyword,
79 color_scheme.func_name,
80 self.name,
81 color_scheme.func_braces,
82 color_scheme.default,
83 AnsiColored::new(UnwindContextArgs::new(&self.args), color_scheme),
84 color_scheme.func_braces,
85 color_scheme.default,
86 )?;
87 Ok(())
88 }
89}
90
91#[cfg(test)]
92mod tests {
93 use core::fmt::Error as FmtError;
94
95 use crate::test_common::{arg, TEST_COLOR_SCHEME};
96 use crate::test_util::debug_fmt;
97 use crate::{AnsiColored, UnwindContextFunc};
98
99 #[test]
100 fn test_func_fmt() {
101 let mut buffer = [0; 64];
102
103 assert_eq!(
104 debug_fmt(&mut buffer, &UnwindContextFunc::new("foo", ())),
105 Ok("fn foo()")
106 );
107 assert_eq!(
108 debug_fmt(
109 &mut buffer,
110 &UnwindContextFunc::new("foo", (arg(Some("bar"), 1), ()))
111 ),
112 Ok("fn foo(bar: 1)")
113 );
114 assert_eq!(
115 debug_fmt(
116 &mut buffer,
117 &UnwindContextFunc::new("foo", (arg(Some("bar"), 1), (arg(Some("baz"), 2), ())))
118 ),
119 Ok("fn foo(bar: 1, baz: 2)")
120 );
121 }
122
123 #[test]
124 fn test_func_colored_fmt() {
125 let mut buffer = [0; 128];
126
127 assert_eq!(
128 debug_fmt(
129 &mut buffer,
130 &AnsiColored::new(
131 UnwindContextFunc::new("foo", (arg(Some("bar"), 1), (arg(Some("baz"), 2), ()))),
132 &TEST_COLOR_SCHEME
133 )
134 ),
135 Ok(concat!(
136 "{FN}fn ",
137 "{FN_NAME}foo",
138 "{FN_BRACE}(",
139 "{DEF}bar: ",
140 "{NUM}1",
141 "{DEF}, baz: ",
142 "{NUM}2",
143 "{DEF}",
144 "{FN_BRACE}",
145 ")",
146 "{DEF}"
147 ))
148 );
149 }
150
151 #[test]
152 fn test_func_failed_fmt() {
153 let func = UnwindContextFunc::new("foo", (arg(Some("foo"), 1), (arg(Some("bar"), 2), ())));
154
155 let mut buffer = [0; 64];
156 let len = debug_fmt(&mut buffer, &func).unwrap().len();
157 for len in 0..len {
158 assert_eq!(debug_fmt(&mut buffer[0..len], &func), Err(FmtError));
159 }
160 }
161
162 #[test]
163 fn test_func_failed_colored_fmt() {
164 let func = AnsiColored::new(
165 UnwindContextFunc::new("foo", (arg(Some("foo"), 1), (arg(Some("bar"), 2), ()))),
166 &TEST_COLOR_SCHEME,
167 );
168
169 let mut buffer = [0; 128];
170 let len = debug_fmt(&mut buffer, &func).unwrap().len();
171 for len in 0..len {
172 assert_eq!(debug_fmt(&mut buffer[0..len], &func), Err(FmtError));
173 }
174 }
175}