@@ -3,7 +3,10 @@ use bevy_utils::tracing::{
3
3
span:: { Attributes , Record } ,
4
4
Event , Id , Level , Subscriber ,
5
5
} ;
6
- use std:: fmt:: { Debug , Write } ;
6
+ use std:: {
7
+ ffi:: CString ,
8
+ fmt:: { Debug , Write } ,
9
+ } ;
7
10
use tracing_subscriber:: { field:: Visit , layer:: Context , registry:: LookupSpan , Layer } ;
8
11
9
12
#[ derive( Default ) ]
@@ -37,16 +40,6 @@ impl Visit for StringRecorder {
37
40
}
38
41
}
39
42
40
- impl core:: fmt:: Display for StringRecorder {
41
- fn fmt ( & self , mut f : & mut core:: fmt:: Formatter < ' _ > ) -> core:: fmt:: Result {
42
- if !self . 0 . is_empty ( ) {
43
- write ! ( & mut f, " {}" , self . 0 )
44
- } else {
45
- Ok ( ( ) )
46
- }
47
- }
48
- }
49
-
50
43
impl core:: default:: Default for StringRecorder {
51
44
fn default ( ) -> Self {
52
45
StringRecorder :: new ( )
@@ -75,24 +68,33 @@ impl<S: Subscriber + for<'a> LookupSpan<'a>> Layer<S> for AndroidLayer {
75
68
76
69
#[ allow( unsafe_code) ]
77
70
fn on_event ( & self , event : & Event < ' _ > , _ctx : Context < ' _ , S > ) {
71
+ fn sanitize ( string : & str ) -> CString {
72
+ let mut bytes: Vec < u8 > = string
73
+ . as_bytes ( )
74
+ . into_iter ( )
75
+ . copied ( )
76
+ . filter ( |byte| * byte != 0 )
77
+ . collect ( ) ;
78
+ CString :: new ( bytes) . unwrap ( )
79
+ }
80
+
78
81
let mut recorder = StringRecorder :: new ( ) ;
79
82
event. record ( & mut recorder) ;
80
83
let meta = event. metadata ( ) ;
81
- let level = meta. level ( ) ;
82
- let priority = match * level {
84
+ let priority = match * meta. level ( ) {
83
85
Level :: TRACE => android_log_sys:: LogPriority :: VERBOSE ,
84
86
Level :: DEBUG => android_log_sys:: LogPriority :: DEBUG ,
85
87
Level :: INFO => android_log_sys:: LogPriority :: INFO ,
86
88
Level :: WARN => android_log_sys:: LogPriority :: WARN ,
87
89
Level :: ERROR => android_log_sys:: LogPriority :: ERROR ,
88
90
} ;
89
- let message = format ! ( "{} \0 " , recorder ) ;
90
- let tag = format ! ( "{} \0 " , meta . name ( ) ) ;
91
+ // SAFETY: Called only on Android platforms. priority is guaranteed to be in range of c_int.
92
+ // The provided tag and message are null terminated properly.
91
93
unsafe {
92
94
android_log_sys:: __android_log_write (
93
95
priority as android_log_sys:: c_int ,
94
- tag . as_ptr ( ) as * const android_log_sys :: c_char ,
95
- message . as_ptr ( ) as * const android_log_sys :: c_char ,
96
+ sanitize ( meta . name ( ) ) . as_ptr ( ) ,
97
+ sanitize ( & recorder . 0 ) . as_ptr ( ) ,
96
98
) ;
97
99
}
98
100
}
0 commit comments