From 14d42be21aacb1b3d67cf4e1532f0afaee342f9a Mon Sep 17 00:00:00 2001 From: Ben Noordhuis Date: Thu, 29 Nov 2012 01:21:40 +0100 Subject: [PATCH] test: use error-checking strncat/strncpy replacements --- test.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 86 insertions(+), 7 deletions(-) diff --git a/test.c b/test.c index 0caea24..987c652 100644 --- a/test.c +++ b/test.c @@ -1413,11 +1413,81 @@ const struct message responses[] = , {.name= NULL } /* sentinel */ }; +/* strnlen() is a POSIX.2008 addition. Can't rely on it being available so + * define it ourselves. + */ +size_t +strnlen(const char *s, size_t maxlen) +{ + const char *p; + + p = memchr(s, '\0', maxlen); + if (p == NULL) + return maxlen; + + return p - s; +} + +size_t +strlncat(char *dst, size_t len, const char *src, size_t n) +{ + size_t slen; + size_t dlen; + size_t rlen; + size_t ncpy; + + slen = strnlen(src, n); + dlen = strnlen(dst, len); + + if (dlen < len) { + rlen = len - dlen; + ncpy = slen < rlen ? slen : (rlen - 1); + memcpy(dst + dlen, src, ncpy); + dst[dlen + ncpy] = '\0'; + } + + assert(len > slen + dlen); + return slen + dlen; +} + +size_t +strlcat(char *dst, const char *src, size_t len) +{ + return strlncat(dst, len, src, (size_t) -1); +} + +size_t +strlncpy(char *dst, size_t len, const char *src, size_t n) +{ + size_t slen; + size_t ncpy; + + slen = strnlen(src, n); + + if (len > 0) { + ncpy = slen < len ? slen : (len - 1); + memcpy(dst, src, ncpy); + dst[ncpy] = '\0'; + } + + assert(len > slen); + return slen; +} + +size_t +strlcpy(char *dst, const char *src, size_t len) +{ + return strlncpy(dst, len, src, (size_t) -1); +} + int request_url_cb (http_parser *p, const char *buf, size_t len) { assert(p == parser); - strncat(messages[num_messages].request_url, buf, len); + strlncat(messages[num_messages].request_url, + sizeof(messages[num_messages].request_url), + buf, + len); return 0; } @@ -1430,7 +1500,10 @@ header_field_cb (http_parser *p, const char *buf, size_t len) if (m->last_header_element != FIELD) m->num_headers++; - strncat(m->headers[m->num_headers-1][0], buf, len); + strlncat(m->headers[m->num_headers-1][0], + sizeof(m->headers[m->num_headers-1][0]), + buf, + len); m->last_header_element = FIELD; @@ -1443,7 +1516,10 @@ header_value_cb (http_parser *p, const char *buf, size_t len) assert(p == parser); struct message *m = &messages[num_messages]; - strncat(m->headers[m->num_headers-1][1], buf, len); + strlncat(m->headers[m->num_headers-1][1], + sizeof(m->headers[m->num_headers-1][1]), + buf, + len); m->last_header_element = VALUE; @@ -1467,7 +1543,10 @@ int body_cb (http_parser *p, const char *buf, size_t len) { assert(p == parser); - strncat(messages[num_messages].body, buf, len); + strlncat(messages[num_messages].body, + sizeof(messages[num_messages].body), + buf, + len); messages[num_messages].body_size += len; check_body_is_final(p); // printf("body_cb: '%s'\n", requests[num_messages].body); @@ -2879,15 +2958,15 @@ test_scan (const struct message *r1, const struct message *r2, const struct mess parser_init(type_both ? HTTP_BOTH : r1->type); buf1_len = i; - strncpy(buf1, total, buf1_len); + strlncpy(buf1, sizeof(buf1), total, buf1_len); buf1[buf1_len] = 0; buf2_len = j - i; - strncpy(buf2, total+i, buf2_len); + strlncpy(buf2, sizeof(buf1), total+i, buf2_len); buf2[buf2_len] = 0; buf3_len = total_len - j; - strncpy(buf3, total+j, buf3_len); + strlncpy(buf3, sizeof(buf1), total+j, buf3_len); buf3[buf3_len] = 0; read = parse(buf1, buf1_len);