| 220 | #define MI_NEXTC() c = *in; if (c==0) break; in++; |
| 221 | |
| 222 | int _mi_vsnprintf(char* buf, size_t bufsize, const char* fmt, va_list args) { |
| 223 | if (buf == NULL || bufsize == 0 || fmt == NULL) return 0; |
| 224 | buf[bufsize - 1] = 0; |
| 225 | char* const end = buf + (bufsize - 1); |
| 226 | const char* in = fmt; |
| 227 | char* out = buf; |
| 228 | while (true) { |
| 229 | if (out >= end) break; |
| 230 | char c; |
| 231 | MI_NEXTC(); |
| 232 | if (c != '%') { |
| 233 | if (c == '\\') { |
| 234 | MI_NEXTC(); |
| 235 | switch (c) { |
| 236 | case 'e': mi_outc('\x1B', &out, end); break; |
| 237 | case 't': mi_outc('\t', &out, end); break; |
| 238 | case 'n': mi_outc('\n', &out, end); break; |
| 239 | case 'r': mi_outc('\r', &out, end); break; |
| 240 | case '\\': mi_outc('\\', &out, end); break; |
| 241 | default: /* ignore */ break; |
| 242 | } |
| 243 | } |
| 244 | else if ((c >= ' ' && c <= '~') || c=='\n' || c=='\r' || c=='\t' || c=='\x1b') { // output visible ascii or standard control only |
| 245 | mi_outc(c, &out, end); |
| 246 | } |
| 247 | } |
| 248 | else { |
| 249 | MI_NEXTC(); |
| 250 | char fill = ' '; |
| 251 | size_t width = 0; |
| 252 | char numtype = 'd'; |
| 253 | char numplus = 0; |
| 254 | bool alignright = true; |
| 255 | if (c == '+' || c == ' ') { numplus = c; MI_NEXTC(); } |
| 256 | if (c == '-') { alignright = false; MI_NEXTC(); } |
| 257 | if (c == '0') { fill = '0'; MI_NEXTC(); } |
| 258 | if (c >= '1' && c <= '9') { |
| 259 | width = (c - '0'); MI_NEXTC(); |
| 260 | while (c >= '0' && c <= '9') { |
| 261 | width = (10 * width) + (c - '0'); MI_NEXTC(); |
| 262 | } |
| 263 | if (c == 0) break; // extra check due to while |
| 264 | } |
| 265 | if (c == 'z' || c == 't' || c == 'L') { numtype = c; MI_NEXTC(); } |
| 266 | else if (c == 'l') { |
| 267 | numtype = c; MI_NEXTC(); |
| 268 | if (c == 'l') { numtype = 'L'; MI_NEXTC(); } |
| 269 | } |
| 270 | |
| 271 | char* start = out; |
| 272 | if (c == '%') { |
| 273 | mi_outc('%', &out, end); |
| 274 | } |
| 275 | else if (c == 's') { |
| 276 | // string |
| 277 | const char* s = va_arg(args, const char*); |
| 278 | mi_outs(s, &out, end); |
| 279 | } |
no test coverage detected