This behaves slightly different than mime_parse_int(), int that we actually return a "bool" for success / failure on "reasonable" parsing. This kinda dumb, because we have two interfaces, where one does not move along the buf pointer, but this one does (and the ones using this function do).
| 3622 | // dumb, because we have two interfaces, where one does not move along the |
| 3623 | // buf pointer, but this one does (and the ones using this function do). |
| 3624 | bool |
| 3625 | mime_parse_integer(const char *&buf, const char *end, int *integer) |
| 3626 | { |
| 3627 | while ((buf != end) && *buf && !is_digit(*buf) && (*buf != '-')) { |
| 3628 | buf += 1; |
| 3629 | } |
| 3630 | |
| 3631 | if ((buf == end) || (*buf == '\0')) { |
| 3632 | return false; |
| 3633 | } |
| 3634 | |
| 3635 | int32_t num; |
| 3636 | bool negative; |
| 3637 | |
| 3638 | // This code is copied verbatim from mime_parse_int ... Sigh. Maybe amc is right, and |
| 3639 | // we really need to clean this up. But, as such, we should redo all these interfaces, |
| 3640 | // and that's a big undertaking (and we'd want to move these strings all to string_view's). |
| 3641 | if (is_digit(*buf)) { // fast case |
| 3642 | num = *buf++ - '0'; |
| 3643 | while ((buf != end) && is_digit(*buf)) { |
| 3644 | if (num != INT_MAX) { |
| 3645 | int new_num = (num * 10) + (*buf++ - '0'); |
| 3646 | |
| 3647 | num = (new_num < num ? INT_MAX : new_num); // Check for overflow |
| 3648 | } else { |
| 3649 | ++buf; // Skip the remaining (valid) digits since we reached MAX/MIN_INT |
| 3650 | } |
| 3651 | } |
| 3652 | } else { |
| 3653 | num = 0; |
| 3654 | negative = false; |
| 3655 | |
| 3656 | while ((buf != end) && ParseRules::is_space(*buf)) { |
| 3657 | buf += 1; |
| 3658 | } |
| 3659 | |
| 3660 | if ((buf != end) && (*buf == '-')) { |
| 3661 | negative = true; |
| 3662 | buf += 1; |
| 3663 | } |
| 3664 | // NOTE: we first compute the value as negative then correct the |
| 3665 | // sign back to positive. This enables us to correctly parse MININT. |
| 3666 | while ((buf != end) && is_digit(*buf)) { |
| 3667 | if (num != INT_MIN) { |
| 3668 | int new_num = (num * 10) - (*buf++ - '0'); |
| 3669 | |
| 3670 | num = (new_num > num ? INT_MIN : new_num); // Check for overflow, so to speak, see above re: negative |
| 3671 | } else { |
| 3672 | ++buf; // Skip the remaining (valid) digits since we reached MAX/MIN_INT |
| 3673 | } |
| 3674 | } |
| 3675 | |
| 3676 | if (!negative) { |
| 3677 | num = -num; |
| 3678 | } |
| 3679 | } |
| 3680 | |
| 3681 | *integer = num; |
no test coverage detected