| 6721 | } |
| 6722 | |
| 6723 | static bool cli_checksum_line_digest(const unsigned char *line, size_t line_length, |
| 6724 | const char *archive_name, size_t archive_name_length, |
| 6725 | char digest[SHA256_BUF_SIZE]) { |
| 6726 | if (!line || line_length <= SHA256_HEX_LEN || |
| 6727 | (line[SHA256_HEX_LEN] != (unsigned char)' ' && |
| 6728 | line[SHA256_HEX_LEN] != (unsigned char)'\t')) { |
| 6729 | return false; |
| 6730 | } |
| 6731 | size_t filename_offset = SHA256_HEX_LEN; |
| 6732 | while (filename_offset < line_length && (line[filename_offset] == (unsigned char)' ' || |
| 6733 | line[filename_offset] == (unsigned char)'\t')) { |
| 6734 | filename_offset++; |
| 6735 | } |
| 6736 | if (filename_offset < line_length && line[filename_offset] == (unsigned char)'*') { |
| 6737 | filename_offset++; |
| 6738 | } |
| 6739 | if (line_length - filename_offset != archive_name_length || |
| 6740 | memcmp(line + filename_offset, archive_name, archive_name_length) != 0) { |
| 6741 | return false; |
| 6742 | } |
| 6743 | |
| 6744 | static const char lower_hex[] = "0123456789abcdef"; |
| 6745 | for (size_t i = 0; i < SHA256_HEX_LEN; i++) { |
| 6746 | int nibble = cli_checksum_hex_nibble(line[i]); |
| 6747 | if (nibble < 0) { |
| 6748 | return false; |
| 6749 | } |
| 6750 | digest[i] = lower_hex[nibble]; |
| 6751 | } |
| 6752 | digest[SHA256_HEX_LEN] = '\0'; |
| 6753 | return true; |
| 6754 | } |
| 6755 | |
| 6756 | /* Parse one downloaded checksum manifest without trusting line truncation or |
| 6757 | * substring matches. This non-header symbol is intentionally exercised by the |
no test coverage detected