@@ -59,6 +59,37 @@ static_assert(
59
59
kLevelToPal [size_t (LogLevel::Fatal)] == et_pal_log_level_t ::kFatal ,
60
60
" " );
61
61
62
+ /* *
63
+ * Returns the length of the longest valid UTF-8 prefix in a byte buffer.
64
+ */
65
+ static inline size_t get_valid_utf8_prefix_length (const char * bytes, size_t length) {
66
+ if (!bytes || length == 0 ) {
67
+ return 0 ;
68
+ }
69
+ const auto * data = reinterpret_cast <const unsigned char *>(bytes);
70
+ auto index = size_t {0 };
71
+ auto last_valid_length = size_t {0 };
72
+ while (index < length) {
73
+ const auto lead_byte = data[index];
74
+ const size_t sequence_length =
75
+ (lead_byte < 0x80 ) ? 1 :
76
+ ((lead_byte & 0xE0 ) == 0xC0 ) ? 2 :
77
+ ((lead_byte & 0xF0 ) == 0xE0 ) ? 3 :
78
+ ((lead_byte & 0xF8 ) == 0xF0 ) ? 4 : 0 ;
79
+ if (!sequence_length || index + sequence_length > length) {
80
+ return last_valid_length;
81
+ }
82
+ for (size_t continuation_index = 1 ; continuation_index < sequence_length; ++continuation_index) {
83
+ if ((data[index + continuation_index] & 0xC0 ) != 0x80 ) {
84
+ return last_valid_length;
85
+ }
86
+ }
87
+ index += sequence_length;
88
+ last_valid_length = index;
89
+ }
90
+ return last_valid_length;
91
+ }
92
+
62
93
/* *
63
94
* Log a string message.
64
95
*
@@ -84,20 +115,23 @@ void vlogf(
84
115
85
116
// Maximum length of a log message.
86
117
static constexpr size_t kMaxLogMessageLength = 256 ;
87
- char buf[kMaxLogMessageLength ];
88
- size_t len = vsnprintf (buf, kMaxLogMessageLength , format, args);
89
- if (len >= kMaxLogMessageLength - 1 ) {
90
- buf[kMaxLogMessageLength - 2 ] = ' $' ;
91
- len = kMaxLogMessageLength - 1 ;
92
- }
93
- buf[kMaxLogMessageLength - 1 ] = 0 ;
118
+ char buffer[kMaxLogMessageLength ];
119
+
120
+ const auto write_count = vsnprintf (buffer, kMaxLogMessageLength , format, args);
121
+ const size_t used_length = (write_count < 0 )
122
+ ? 0
123
+ : (write_count >= static_cast <int >(kMaxLogMessageLength )
124
+ ? kMaxLogMessageLength - 1
125
+ : static_cast <size_t >(write_count));
126
+ const auto valid_length = get_valid_utf8_prefix_length (buffer, used_length);
127
+ buffer[valid_length] = ' \0 ' ;
94
128
95
- et_pal_log_level_t pal_level = (level < LogLevel::NumLevels)
129
+ const auto pal_level = (level < LogLevel::NumLevels)
96
130
? kLevelToPal [size_t (level)]
97
131
: et_pal_log_level_t ::kUnknown ;
98
132
99
133
pal_emit_log_message (
100
- timestamp, pal_level, filename, function, line, buf, len );
134
+ timestamp, pal_level, filename, function, line, buffer, valid_length );
101
135
102
136
#endif // ET_LOG_ENABLED
103
137
}
0 commit comments