//===-- sanitizer_common_interceptors_format.inc ----------------*- C++ -*-===// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // Scanf/printf implementation for use in *Sanitizer interceptors. // Follows http://pubs.opengroup.org/onlinepubs/9699919799/functions/fscanf.html // and http://pubs.opengroup.org/onlinepubs/9699919799/functions/fprintf.html // with a few common GNU extensions. // //===----------------------------------------------------------------------===// #include <stdarg.h> static const char *parse_number(const char *p, int *out) { … } static const char *maybe_parse_param_index(const char *p, int *out) { … } static bool char_is_one_of(char c, const char *s) { … } static const char *maybe_parse_length_modifier(const char *p, char ll[2]) { … } // Returns true if the character is an integer conversion specifier. static bool format_is_integer_conv(char c) { … } // Returns true if the character is an floating point conversion specifier. static bool format_is_float_conv(char c) { … } // Returns string output character size for string-like conversions, // or 0 if the conversion is invalid. static int format_get_char_size(char convSpecifier, const char lengthModifier[2]) { … } enum FormatStoreSize { … }; // Returns the memory size of a format directive (if >0), or a value of // FormatStoreSize. static int format_get_value_size(char convSpecifier, const char lengthModifier[2], bool promote_float) { … } struct ScanfDirective { … }; // Parse scanf format string. If a valid directive in encountered, it is // returned in dir. This function returns the pointer to the first // unprocessed character, or 0 in case of error. // In case of the end-of-string, a pointer to the closing \0 is returned. static const char *scanf_parse_next(const char *p, bool allowGnuMalloc, ScanfDirective *dir) { … } static int scanf_get_value_size(ScanfDirective *dir) { … } // Common part of *scanf interceptors. // Process format string and va_list, and report all store ranges. // Stops when "consuming" n_inputs input items. static void scanf_common(void *ctx, int n_inputs, bool allowGnuMalloc, const char *format, va_list aq) { … } #if SANITIZER_INTERCEPT_PRINTF struct PrintfDirective { … }; static const char *maybe_parse_number(const char *p, int *out) { … } static const char *maybe_parse_number_or_star(const char *p, int *out, bool *star) { … } // Parse printf format string. Same as scanf_parse_next. static const char *printf_parse_next(const char *p, PrintfDirective *dir) { … } static int printf_get_value_size(PrintfDirective *dir) { … } #define SKIP_SCALAR_ARG(aq, convSpecifier, size) … // Common part of *printf interceptors. // Process format string and va_list, and report all load ranges. static void printf_common(void *ctx, const char *format, va_list aq) { … } #endif // SANITIZER_INTERCEPT_PRINTF