|
|
@@ -158,12 +158,21 @@ checkstate: |
|
|
|
} |
|
|
|
if (memcmp(bufp, "HTTP/1.1 ", 9) == 0 || memcmp(bufp, "HTTP/1.0 ", 9) == 0) { |
|
|
|
// Got some headers; find transfer encoding, content length, and end of headers |
|
|
|
eoh = memmem(bufp, n, "\r\n\r\n", 4); |
|
|
|
m0 = memmem(bufp, n, "\r\n\r\n", 4); |
|
|
|
m1 = memmem(bufp, n, "\n\n", 2); |
|
|
|
if (m0 && m1) { |
|
|
|
eoh = (m0 < m1 ? m0 + 4 : m1 + 2); |
|
|
|
} else if (m0) { |
|
|
|
eoh = m0 + 4; |
|
|
|
} else if (m1) { |
|
|
|
eoh = m1 + 2; |
|
|
|
} else { |
|
|
|
eoh = NULL; |
|
|
|
} |
|
|
|
if (!eoh) { |
|
|
|
fprintf(stderr, "Error: end of headers not found\n"); |
|
|
|
return 1; |
|
|
|
} |
|
|
|
eoh += 4; |
|
|
|
DEBUG_PRINTF("Response body begins at %p (offset %zu)\n", (void*)eoh, eoh - bufp); |
|
|
|
|
|
|
|
if (memcmp(bufp, "HTTP/1.0 ", 9) == 0) { |
|
|
@@ -174,14 +183,15 @@ checkstate: |
|
|
|
} |
|
|
|
length = response_length - (eoh - bufp); |
|
|
|
state = STATE_BODY; |
|
|
|
} else if ((m0 = memcasemem(bufp, eoh - bufp, "\r\ncontent-length:", 17)) && m0 < eoh) { |
|
|
|
} else if ((m0 = memcasemem(bufp, eoh - bufp, "\ncontent-length:", 16)) && m0 < eoh) { |
|
|
|
DEBUG_PRINTF("Found Content-Length header at %p (offset %zu)\n", (void*)(m0 + 2), m0 + 2 - bufp); |
|
|
|
m1 = memmem(m0 + 1, eoh - (m0 + 1), "\r\n", 2); |
|
|
|
m1 = memmem(m0 + 1, eoh - (m0 + 1), "\n", 1); |
|
|
|
if (!m1) { |
|
|
|
fprintf(stderr, "Error: CRLF after Content-Length missing\n"); |
|
|
|
return 1; |
|
|
|
} |
|
|
|
m0 += 17; |
|
|
|
if (*(m1 - 1) == '\r') --m1; |
|
|
|
m0 += 16; |
|
|
|
while (m0 < bufp + n && (*m0 == ' ' || *m0 == '\t')) ++m0; |
|
|
|
if (sscanf(m0, "%zu%ln", &length, &nscan) <= 0) { |
|
|
|
fprintf(stderr, "Error: invalid Content-Length\n"); |
|
|
@@ -205,18 +215,19 @@ checkstate: |
|
|
|
|
|
|
|
state = STATE_BODY; |
|
|
|
} else { |
|
|
|
m0 = memcasemem(bufp, eoh - bufp, "\r\ntransfer-encoding:", 20); |
|
|
|
m0 = memcasemem(bufp, eoh - bufp, "\ntransfer-encoding:", 19); |
|
|
|
if (!m0 || m0 >= eoh) { |
|
|
|
fprintf(stderr, "Error: Content-Length and Transfer-Encoding missing\n"); |
|
|
|
return 1; |
|
|
|
} |
|
|
|
DEBUG_PRINTF("Found Transfer-Encoding header at %p (offset %zu)\n", (void*)(m0 + 2), m0 + 2 - bufp); |
|
|
|
m1 = memmem(m0 + 1, eoh - (m0 + 1), "\r\n", 2); |
|
|
|
if (!m1 || m1 >= eoh - 2) { |
|
|
|
DEBUG_PRINTF("Found Transfer-Encoding header at %p (offset %zu)\n", (void*)(m0 + 1), m0 + 1 - bufp); |
|
|
|
m1 = memmem(m0 + 1, eoh - (m0 + 1), "\n", 1); |
|
|
|
if (!m1 || m1 >= eoh - 1) { |
|
|
|
fprintf(stderr, "Error: CRLF after Transfer-Encoding missing\n"); |
|
|
|
return 1; |
|
|
|
} |
|
|
|
m0 += 20; |
|
|
|
m0 += 19; |
|
|
|
if (*(m1 - 1) == '\r') --m1; |
|
|
|
while (m0 < bufp + n && (*m0 == ' ' || *m0 == '\t')) ++m0; |
|
|
|
if (memcmp(m0, "chunked", 7) != 0) { |
|
|
|
fprintf(stderr, "Error: unsupported Transfer-Encoding\n"); |
|
|
@@ -234,15 +245,15 @@ checkstate: |
|
|
|
} |
|
|
|
|
|
|
|
if (html_fake_base) { |
|
|
|
m0 = memcasemem(bufp, eoh - bufp, "\r\ncontent-type:", 15); |
|
|
|
m0 = memcasemem(bufp, eoh - bufp, "\ncontent-type:", 14); |
|
|
|
if (m0 && m0 < eoh) { |
|
|
|
DEBUG_PRINTF("Found Content-Type header at %p (offset %zu)\n", (void*)(m0 + 2), m0 + 2 - bufp); |
|
|
|
m1 = memmem(m0 + 1, eoh - (m0 + 1), "\r\n", 2); |
|
|
|
DEBUG_PRINTF("Found Content-Type header at %p (offset %zu)\n", (void*)(m0 + 1), m0 + 1 - bufp); |
|
|
|
m1 = memmem(m0 + 1, eoh - (m0 + 1), "\n", 1); |
|
|
|
if (!m1) { |
|
|
|
fprintf(stderr, "Error: CRLF after Content-Type missing\n"); |
|
|
|
return 1; |
|
|
|
} |
|
|
|
m0 += 15; |
|
|
|
m0 += 14; |
|
|
|
while (m0 < bufp + n && (*m0 == ' ' || *m0 == '\t')) ++m0; |
|
|
|
if (memcmp(m0, "text/html", 9) == 0) { |
|
|
|
DEBUG_PRINTF("Is HTML response, inserting fake base tag\n"); |
|
|
|