ecsimple/
logger.rs

1
2use std::env;
3use std::io::{Write};
4use std::fs;
5//use std::io::prelude::*;
6use lazy_static::lazy_static;
7use chrono::{Local,Timelike,Datelike};
8use std::sync::RwLock;
9
10
11
12fn _ecsimple_get_environ_var(envname :&str) -> String {
13	match env::var(envname) {
14		Ok(v) => {
15			format!("{}",v)
16		},
17		Err(_e) => {
18			String::from("")
19		}
20	}
21}
22
23#[allow(dead_code)]
24struct LogVar {
25	level :i32,
26	nostderr : bool,
27	wfile : Option<fs::File>,
28	wfilename :String,
29	baklevel :i32,
30	baknostderr :bool,
31}
32
33
34fn ecsimple_proc_log_init(prefix :&str) -> LogVar {
35	let mut getv :String;
36	let mut retv :i32 = 0;
37	let mut nostderr :bool = false;
38	let mut coptfile :Option<fs::File> = None;
39	let mut key :String;
40	let mut fname :String = "".to_string();
41
42	key = format!("{}_LEVEL", prefix);
43	getv = _ecsimple_get_environ_var(&key);
44	if getv.len() > 0 {
45		match getv.parse::<i32>() {
46			Ok(v) => {
47				retv = v;
48			},
49			Err(e) => {
50				retv = 0;
51				eprintln!("can not parse [{}] error[{}]", getv,e);
52			}
53		}
54	}
55
56	key = format!("{}_NOSTDERR",prefix);
57	getv = _ecsimple_get_environ_var(&key);
58	if getv.len() > 0 {
59		nostderr = true;
60	}
61
62
63
64	key = format!("{}_LOGFILE",prefix);
65	getv = _ecsimple_get_environ_var(&key);
66	if getv.len() > 0 {
67		fname = format!("{}",getv);
68		let fo = fs::File::create(&getv);
69		if fo.is_err() {
70			eprintln!("can not open [{}]", getv);
71		} else {
72			coptfile = Some(fo.unwrap());
73		}
74	}
75
76	return LogVar {
77		level : retv,
78		nostderr : nostderr,
79		wfile : coptfile,
80		wfilename : fname,
81		baklevel : 0,
82		baknostderr : true,
83	};
84}
85
86
87lazy_static! {
88	static ref ECSIMPLE_LOG_LEVEL : RwLock<LogVar> = {
89	 	RwLock::new(ecsimple_proc_log_init("ECSIMPLE"))
90	};
91}
92
93pub fn set_ecsimple_logger_disable() {
94	let mut ecsimpleref = ECSIMPLE_LOG_LEVEL.write().unwrap();
95	ecsimpleref.baknostderr = ecsimpleref.nostderr;
96	ecsimpleref.baklevel = ecsimpleref.level;
97	ecsimpleref.wfile = None;
98	ecsimpleref.level = 0;
99	ecsimpleref.nostderr = true;
100	return;
101}
102
103pub fn set_ecsimple_logger_enable() {
104	let mut ecsimpleref = ECSIMPLE_LOG_LEVEL.write().unwrap();
105	ecsimpleref.level = ecsimpleref.baklevel;
106	ecsimpleref.nostderr = ecsimpleref.baknostderr;	
107	if ecsimpleref.wfilename.len() > 0 {
108		let fo = fs::File::create(&ecsimpleref.wfilename);
109		if fo.is_ok() {
110			ecsimpleref.wfile = Some(fo.unwrap());
111		}
112	}
113	return ;
114}
115
116
117#[allow(dead_code)]
118pub (crate)  fn ecsimple_debug_out(level :i32, outs :&str) {
119	let refecsimple = ECSIMPLE_LOG_LEVEL.write().unwrap();
120	if refecsimple.level >= level {
121		let c = format!("{}\n",outs);
122		if !refecsimple.nostderr {
123			let _ = std::io::stderr().write_all(c.as_bytes());
124		}
125
126		if refecsimple.wfile.is_some() {
127			let mut wf = refecsimple.wfile.as_ref().unwrap();
128			let _ = wf.write(c.as_bytes());
129		}
130	}
131	return;
132}
133
134pub (crate) fn ecsimple_log_get_timestamp() -> String {
135	let now = Local::now();
136	return format!("{}/{}/{} {}:{}:{}",now.year(),now.month(),now.day(),now.hour(),now.minute(),now.second());
137}
138
139#[macro_export]
140macro_rules! ecsimple_log_error {
141	($($arg:tt)+) => {
142		let mut c :String= format!("[ECSIMPLE]<ERROR>{}[{}:{}]  ",ecsimple_log_get_timestamp(),file!(),line!());
143		c.push_str(&(format!($($arg)+)[..]));
144		ecsimple_debug_out(0,&c);
145	}
146}
147
148#[macro_export]
149macro_rules! ecsimple_log_warn {
150	($($arg:tt)+) => {
151		let mut c :String= format!("[ECSIMPLE]<WARN>{}[{}:{}]  ",ecsimple_log_get_timestamp(),file!(),line!());
152		c.push_str(&(format!($($arg)+)[..]));
153		ecsimple_debug_out(10,&c);
154	}
155}
156
157
158#[macro_export]
159macro_rules! ecsimple_log_info {
160	($($arg:tt)+) => {
161		let mut c :String= format!("[ECSIMPLE]<INFO>{}[{}:{}]  ",ecsimple_log_get_timestamp(),file!(),line!());
162		c.push_str(&(format!($($arg)+)[..]));
163		ecsimple_debug_out(20,&c);
164	}
165}
166
167#[cfg(feature="debug_mode")]
168#[macro_export]
169macro_rules! ecsimple_log_trace {
170	($($arg:tt)+) => {
171		let mut _c :String= format!("[ECSIMPLE]<TRACE>{}[{}:{}]  ",ecsimple_log_get_timestamp(),file!(),line!());
172		_c.push_str(&(format!($($arg)+)[..]));
173		ecsimple_debug_out(40, &_c);
174	}
175}
176
177#[cfg(not(feature="debug_mode"))]
178#[macro_export]
179macro_rules! ecsimple_log_trace {
180	($($arg:tt)+) => {}
181}
182
183
184#[macro_export]
185macro_rules! ecsimple_assert {
186	($v:expr , $($arg:tt)+) => {
187		if !($v) {
188			let mut _c :String= format!("[ECSIMPLE][{}:{}] ",file!(),line!());
189			_c.push_str(&(format!($($arg)+)[..]));
190			panic!("{}", _c);
191		}
192	}
193}
194
195
196#[macro_export]
197macro_rules! ecsimple_format_buffer_log {
198	($buf:expr,$len:expr,$info:tt,$iv:expr,$($arg:tt)+) => {
199		let mut c :String = format!("[ECSIMPLE][{}:{}]",file!(),line!());
200		c.push_str(&format!("{} ",$info));
201		c.push_str(&ecsimple_log_get_timestamp());
202		c.push_str(": ");
203		c.push_str(&(format!($($arg)+)[..]));
204		let _ptr :*const u8 = $buf as *const u8;
205		let  mut _ci :usize;
206		let _totallen: usize = $len as usize;
207		let mut _lasti :usize = 0;
208		let mut _nb :u8;
209		c.push_str(&format!(" buffer [{:?}][{}]",_ptr,_totallen));
210		_ci = 0;
211		while _ci < _totallen {
212			if (_ci % 16) == 0 {
213				if _ci > 0 {
214					c.push_str("    ");
215					while _lasti < _ci {
216						unsafe{
217							_nb = *_ptr.offset(_lasti as isize);	
218						}
219						
220						if _nb >= 0x20 && _nb <= 0x7e {
221							c.push(_nb as char);
222						} else {
223							c.push_str(".");
224						}
225						_lasti += 1;
226					}
227				}
228				c.push_str(&format!("\n0x{:08x}:", _ci));
229			}
230			unsafe {_nb = *_ptr.offset(_ci as isize);}			
231			c.push_str(&format!(" 0x{:02x}",_nb));
232			_ci += 1;
233		}
234
235		if _lasti < _ci {
236			while (_ci % 16) != 0 {
237				c.push_str("     ");
238				_ci += 1;
239			}
240
241			c.push_str("    ");
242
243			while _lasti < _totallen {
244				unsafe {_nb = *_ptr.offset(_lasti as isize);}				
245				if _nb >= 0x20 && _nb <= 0x7e {
246					c.push(_nb as char);
247				} else {
248					c.push_str(".");
249				}
250				_lasti += 1;
251			}
252			//c.push_str("\n");
253		}
254		ecsimple_debug_out($iv,&c);
255	}
256}
257
258#[macro_export]
259macro_rules! ecsimple_debug_buffer_error {
260	($buf:expr,$len:expr,$($arg:tt)+) => {
261		ecsimple_format_buffer_log!($buf,$len,"<ERROR>",0,$($arg)+);
262	}
263}
264
265#[macro_export]
266macro_rules! ecsimple_debug_buffer_warn {
267	($buf:expr,$len:expr,$($arg:tt)+) => {
268		ecsimple_format_buffer_log!($buf,$len,"<WARN>",10,$($arg)+);
269	}
270}
271
272#[macro_export]
273macro_rules! ecsimple_debug_buffer_info {
274	($buf:expr,$len:expr,$($arg:tt)+) => {
275		ecsimple_format_buffer_log!($buf,$len,"<INFO>",20,$($arg)+);
276	}
277}
278
279#[macro_export]
280macro_rules! ecsimple_debug_buffer_debug {
281	($buf:expr,$len:expr,$($arg:tt)+) => {
282		ecsimple_format_buffer_log!($buf,$len,"<DEBUG>",30,$($arg)+);
283	}
284}
285
286#[cfg(feature="debug_mode")]
287#[macro_export]
288macro_rules! ecsimple_debug_buffer_trace {
289	($buf:expr,$len:expr,$($arg:tt)+) => {
290		ecsimple_format_buffer_log!($buf,$len,"<TRACE>",40,$($arg)+);
291	}
292}
293
294#[cfg(not(feature="debug_mode"))]
295#[macro_export]
296macro_rules! ecsimple_debug_buffer_trace {
297	($buf:expr,$len:expr,$($arg:tt)+) => {}
298}