diff options
author | Loïc Hoguin <[email protected]> | 2017-01-20 15:16:50 +0100 |
---|---|---|
committer | Loïc Hoguin <[email protected]> | 2017-01-20 15:16:50 +0100 |
commit | 353dc29d8f7e9aed7a35426f680f39a975a4cbcb (patch) | |
tree | 0afab7e097390bbb0333ce2f61c4b707f2c9dbdd /src/cowboy_http.erl | |
parent | 0f8452cafaa27aeffb103019564c086eacfd34f9 (diff) | |
download | cowboy-353dc29d8f7e9aed7a35426f680f39a975a4cbcb.tar.gz cowboy-353dc29d8f7e9aed7a35426f680f39a975a4cbcb.tar.bz2 cowboy-353dc29d8f7e9aed7a35426f680f39a975a4cbcb.zip |
Fix protocol breaking when user tries to send empty chunk
The {data, IsFin, Data} uses IsFin to indicate whether this
is the last chunk, while chunked transfer-encoding uses the
length of Data, and ends when it is 0. We must therefore not
send chunks with empty data.
Diffstat (limited to 'src/cowboy_http.erl')
-rw-r--r-- | src/cowboy_http.erl | 24 |
1 files changed, 14 insertions, 10 deletions
diff --git a/src/cowboy_http.erl b/src/cowboy_http.erl index dcda3fb..1f32b6a 100644 --- a/src/cowboy_http.erl +++ b/src/cowboy_http.erl @@ -842,16 +842,20 @@ commands(State0=#state{socket=Socket, transport=Transport, streams=Streams}, Str %% @todo We probably want to allow Data to be the {sendfile, ...} tuple also. commands(State=#state{socket=Socket, transport=Transport, streams=Streams}, StreamID, [{data, IsFin, Data}|Tail]) -> - - %% @todo We need to kill the stream if it tries to send data before headers. - - %% @todo Same as above. - case lists:keyfind(StreamID, #stream.id, Streams) of - #stream{version='HTTP/1.1'} -> - Size = iolist_size(Data), - Transport:send(Socket, [integer_to_binary(Size, 16), <<"\r\n">>, Data, <<"\r\n">>]); - #stream{version='HTTP/1.0'} -> - Transport:send(Socket, Data) + %% Do not send anything when the user asks to send an empty + %% data frame, as that would break the protocol. + Size = iolist_size(Data), + case Size of + 0 -> ok; + _ -> + %% @todo We need to kill the stream if it tries to send data before headers. + %% @todo Same as above. + case lists:keyfind(StreamID, #stream.id, Streams) of + #stream{version='HTTP/1.1'} -> + Transport:send(Socket, [integer_to_binary(Size, 16), <<"\r\n">>, Data, <<"\r\n">>]); + #stream{version='HTTP/1.0'} -> + Transport:send(Socket, Data) + end end, maybe_terminate(State, StreamID, Tail, IsFin); %% Send a file. |