1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
use std::fmt::Display;
pub struct Trace {
title : String,
info: String,
backtrace : String,
}
impl Trace {
pub fn new<T : Display>(title: T) -> Trace {
Trace {
title: title.to_string(),
info: String::new(),
backtrace : String::new(),
}
}
pub fn trace_filter<T: Display>(&mut self, traces_of: T) -> &mut Trace {
let mut count = 0;
backtrace::trace(|frame| {
backtrace::resolve(frame.ip(), |symbol| {
let name = if let Some(name) = symbol.name() {
name.to_string()
} else {
" - <unknown caller name>".to_string()
};
let filename = if let Some(filename) = symbol.filename() {
filename.display().to_string()
} else {
" - <unknown file name>".to_string()
};
let line = if let Some(line) = symbol.lineno() {
line
} else {
0
};
let output = format!("{:<2} -- {} \n {:10} {}:{} ", count, name, "", filename, line);
let matches = traces_of.to_string();
let matches = matches.split("|");
for text_match in matches {
if output.contains(text_match) {
self.backtrace = format!("{}\n{}", self.backtrace, output);
break;
}
}
});
count += 1;
true
});
self
}
pub fn info<T: Display>(&mut self, info: T) -> &mut Trace {
self.info = info.to_string();
self
}
pub fn emit(&self){
let output = format!("----------------------------------------------------------------------- BEGIN ------ {} \n", self.title);
let output = if self.info.len() > 0 {
format!("{}{} \n",output, self.info)
} else { output };
let output = if self.backtrace.len() > 0 {
format!("{}{} \n\n",output, self.backtrace)
} else { output };
let output = format!("{}----------------------------------------------------------------------- END -------- {} \n\n", output, self.title);
println!("{}", output);
}
pub fn log<T: Display, U: Display, V: Display> (title: T, info: U, trace_filter: V){
Self::new(title).info(info).trace_filter(trace_filter).emit();
}
}