| 126 | } |
| 127 | |
| 128 | static timestamp_t parse_commit_date(const char *buf, const char *tail) |
| 129 | { |
| 130 | const char *dateptr; |
| 131 | const char *eol; |
| 132 | |
| 133 | if (buf + 6 >= tail) |
| 134 | return 0; |
| 135 | if (memcmp(buf, "author", 6)) |
| 136 | return 0; |
| 137 | while (buf < tail && *buf++ != '\n') |
| 138 | /* nada */; |
| 139 | if (buf + 9 >= tail) |
| 140 | return 0; |
| 141 | if (memcmp(buf, "committer", 9)) |
| 142 | return 0; |
| 143 | |
| 144 | /* |
| 145 | * Jump to end-of-line so that we can walk backwards to find the |
| 146 | * end-of-email ">". This is more forgiving of malformed cases |
| 147 | * because unexpected characters tend to be in the name and email |
| 148 | * fields. |
| 149 | */ |
| 150 | eol = memchr(buf, '\n', tail - buf); |
| 151 | if (!eol) |
| 152 | return 0; |
| 153 | dateptr = eol; |
| 154 | while (dateptr > buf && dateptr[-1] != '>') |
| 155 | dateptr--; |
| 156 | if (dateptr == buf) |
| 157 | return 0; |
| 158 | |
| 159 | /* |
| 160 | * Trim leading whitespace, but make sure we have at least one |
| 161 | * non-whitespace character, as parse_timestamp() will otherwise walk |
| 162 | * right past the newline we found in "eol" when skipping whitespace |
| 163 | * itself. |
| 164 | * |
| 165 | * In theory it would be sufficient to allow any character not matched |
| 166 | * by isspace(), but there's a catch: our isspace() does not |
| 167 | * necessarily match the behavior of parse_timestamp(), as the latter |
| 168 | * is implemented by system routines which match more exotic control |
| 169 | * codes, or even locale-dependent sequences. |
| 170 | * |
| 171 | * Since we expect the timestamp to be a number, we can check for that. |
| 172 | * Anything else (e.g., a non-numeric token like "foo") would just |
| 173 | * cause parse_timestamp() to return 0 anyway. |
| 174 | */ |
| 175 | while (dateptr < eol && isspace(*dateptr)) |
| 176 | dateptr++; |
| 177 | if (!isdigit(*dateptr) && *dateptr != '-') |
| 178 | return 0; |
| 179 | |
| 180 | /* |
| 181 | * We know there is at least one digit (or dash), so we'll begin |
| 182 | * parsing there and stop at worst case at eol. |
| 183 | * |
| 184 | * Note that we may feed parse_timestamp() extra characters here if the |
| 185 | * commit is malformed, and it will parse as far as it can. For |
no outgoing calls
no test coverage detected