From 4dae120015e8ad6ab4fbf9903d3b440ca1e5b31f Mon Sep 17 00:00:00 2001 From: Ben Noordhuis Date: Mon, 29 Oct 2018 18:33:14 +0100 Subject: [PATCH] Support ICE/1.x for SOURCE requests. Normal clients sends "GET / HTTP/1.0" but Shoutcast clients send "SOURCE / ICE/1.0". Accept that as an alternative but only for SOURCE requests. Fixes: https://github.com/nodejs/http-parser/issues/410 PR-URL: https://github.com/nodejs/http-parser/pull/431 Reviewed-By: Fedor Indutny Reviewed-By: Pierce Lopez --- http_parser.c | 22 ++++++++++++++++++++-- test.c | 22 ++++++++++++++++++++++ 2 files changed, 42 insertions(+), 2 deletions(-) diff --git a/http_parser.c b/http_parser.c index 9941b7e..ba1374e 100644 --- a/http_parser.c +++ b/http_parser.c @@ -314,6 +314,8 @@ enum state , s_req_http_HT , s_req_http_HTT , s_req_http_HTTP + , s_req_http_I + , s_req_http_IC , s_req_http_major , s_req_http_dot , s_req_http_minor @@ -1084,11 +1086,17 @@ reexecute: case s_req_http_start: switch (ch) { + case ' ': + break; case 'H': UPDATE_STATE(s_req_http_H); break; - case ' ': - break; + case 'I': + if (parser->method == HTTP_SOURCE) { + UPDATE_STATE(s_req_http_I); + break; + } + /* fall through */ default: SET_ERRNO(HPE_INVALID_CONSTANT); goto error; @@ -1110,6 +1118,16 @@ reexecute: UPDATE_STATE(s_req_http_HTTP); break; + case s_req_http_I: + STRICT_CHECK(ch != 'C'); + UPDATE_STATE(s_req_http_IC); + break; + + case s_req_http_IC: + STRICT_CHECK(ch != 'E'); + UPDATE_STATE(s_req_http_HTTP); /* Treat "ICE" as "HTTP". */ + break; + case s_req_http_HTTP: STRICT_CHECK(ch != '/'); UPDATE_STATE(s_req_http_major); diff --git a/test.c b/test.c index 681cc88..115ddca 100644 --- a/test.c +++ b/test.c @@ -1173,6 +1173,26 @@ const struct message requests[] = ,.headers= { { "Host", "example.com" } } ,.body= "" } + +#define SOURCE_ICE_REQUEST 42 +, {.name = "source request" + ,.type= HTTP_REQUEST + ,.raw= "SOURCE /music/sweet/music ICE/1.0\r\n" + "Host: example.com\r\n" + "\r\n" + ,.should_keep_alive= FALSE + ,.message_complete_on_eof= FALSE + ,.http_major= 1 + ,.http_minor= 0 + ,.method= HTTP_SOURCE + ,.request_path= "/music/sweet/music" + ,.request_url= "/music/sweet/music" + ,.query_string= "" + ,.fragment= "" + ,.num_headers= 1 + ,.headers= { { "Host", "example.com" } } + ,.body= "" + } }; /* * R E S P O N S E S * */ @@ -4268,6 +4288,8 @@ main (void) /// REQUESTS + test_simple("GET / IHTTP/1.0\r\n\r\n", HPE_INVALID_CONSTANT); + test_simple("GET / ICE/1.0\r\n\r\n", HPE_INVALID_CONSTANT); test_simple("GET / HTP/1.1\r\n\r\n", HPE_INVALID_VERSION); test_simple("GET / HTTP/01.1\r\n\r\n", HPE_INVALID_VERSION); test_simple("GET / HTTP/11.1\r\n\r\n", HPE_INVALID_VERSION);