| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | #ifndef UTIL_STRTONUM_H | ||
| 2 | #define UTIL_STRTONUM_H | ||
| 3 | |||
| 4 | #include <limits.h> | ||
| 5 | #include <stdbool.h> | ||
| 6 | #include <stddef.h> | ||
| 7 | #include <stdint.h> | ||
| 8 | #include "macros.h" | ||
| 9 | #include "string-view.h" | ||
| 10 | |||
| 11 | extern const uint8_t hex_decode_table[64]; | ||
| 12 | |||
| 13 | enum { | ||
| 14 | HEX_INVALID = 0xF0, | ||
| 15 | }; | ||
| 16 | |||
| 17 | // Decodes a single, hexadecimal digit and returns a numerical value | ||
| 18 | // between 0-15, or HEX_INVALID for invalid digits | ||
| 19 | 1068 | static inline unsigned int hex_decode(unsigned char c) | |
| 20 | { | ||
| 21 | 1068 | c -= '0'; // Lookup table starts at '0' | |
| 22 | 1068 | return hex_decode_table[(c < sizeof(hex_decode_table)) ? c : 63]; | |
| 23 | } | ||
| 24 | |||
| 25 | 419 | static inline bool ascii_isxdigit(unsigned char c) | |
| 26 | { | ||
| 27 | 419 | return hex_decode(c) <= 0xF; | |
| 28 | } | ||
| 29 | |||
| 30 | 4 | static inline size_t ascii_hex_prefix_length(const char *str, size_t len) | |
| 31 | { | ||
| 32 | 4 | size_t i = 0; | |
| 33 |
4/4✓ Branch 0 (4→5) taken 162 times.
✓ Branch 1 (4→6) taken 1 times.
✓ Branch 2 (5→3) taken 159 times.
✓ Branch 3 (5→6) taken 3 times.
|
163 | while (i < len && ascii_isxdigit(str[i])) { |
| 34 | 159 | i++; | |
| 35 | } | ||
| 36 | 4 | return i; | |
| 37 | } | ||
| 38 | |||
| 39 | WARN_UNUSED_RESULT | ||
| 40 | 59 | static inline size_t buf_parse_hex_uint(const char *str, size_t len, unsigned int *valp) | |
| 41 | { | ||
| 42 | 59 | unsigned int val = 0; | |
| 43 | 59 | size_t i; | |
| 44 |
2/2✓ Branch 0 (6→3) taken 184 times.
✓ Branch 1 (6→7) taken 50 times.
|
234 | for (i = 0; i < len; i++) { |
| 45 | 184 | unsigned int x = hex_decode(str[i]); | |
| 46 |
2/2✓ Branch 0 (3→4) taken 177 times.
✓ Branch 1 (3→7) taken 7 times.
|
184 | if (unlikely(x > 0xF)) { |
| 47 | break; | ||
| 48 | } | ||
| 49 |
2/2✓ Branch 0 (4→5) taken 175 times.
✓ Branch 1 (4→8) taken 2 times.
|
177 | if (unlikely(val > (UINT_MAX >> 4))) { |
| 50 | return 0; // Overflow | ||
| 51 | } | ||
| 52 | 175 | val = val << 4 | x; | |
| 53 | } | ||
| 54 | 57 | *valp = val; | |
| 55 | 57 | return i; | |
| 56 | } | ||
| 57 | |||
| 58 | size_t size_str_width(size_t x) CONST_FN WARN_UNUSED_RESULT; | ||
| 59 | size_t buf_parse_uintmax(const char *str, size_t len, uintmax_t *valp) WARN_UNUSED_RESULT WRITEONLY(3); | ||
| 60 | size_t buf_parse_ulong(const char *str, size_t len, unsigned long *valp) WARN_UNUSED_RESULT WRITEONLY(3); | ||
| 61 | size_t buf_parse_uint(const char *str, size_t len, unsigned int *valp) WARN_UNUSED_RESULT WRITEONLY(3); | ||
| 62 | size_t buf_parse_size(const char *str, size_t len, size_t *valp) WARN_UNUSED_RESULT WRITEONLY(3); | ||
| 63 | bool str_to_int(const char *str, int *valp) NONNULL_ARGS WARN_UNUSED_RESULT WRITEONLY(2); | ||
| 64 | bool str_to_uint(const char *str, unsigned int *valp) NONNULL_ARGS WARN_UNUSED_RESULT WRITEONLY(2); | ||
| 65 | bool str_to_size(const char *str, size_t *valp) NONNULL_ARGS WARN_UNUSED_RESULT WRITEONLY(2); | ||
| 66 | bool str_to_ulong(const char *str, unsigned long *valp) NONNULL_ARGS WARN_UNUSED_RESULT WRITEONLY(2); | ||
| 67 | bool str_to_filepos(const char *str, size_t *linep, size_t *colp) NONNULL_ARGS WARN_UNUSED_RESULT WRITEONLY(2) WRITEONLY(3); | ||
| 68 | bool str_to_xfilepos(const char *str, size_t *linep, size_t *colp) NONNULL_ARGS WARN_UNUSED_RESULT WRITEONLY(2) WRITEONLY(3); | ||
| 69 | StringView parse_file_line_col(const char *str, size_t *linep, size_t *colp) NONNULL_ARGS WARN_UNUSED_RESULT WRITEONLY(2) WRITEONLY(3); | ||
| 70 | intmax_t parse_filesize(const char *str) NONNULL_ARGS WARN_UNUSED_RESULT; | ||
| 71 | |||
| 72 | #endif | ||
| 73 |