From f9060599aeab81cb9282ddf51cc057bf1353208f Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Tue, 25 Oct 2011 12:34:56 +0200 Subject: The XSS prevention methods used was confused if the URL was encoded (hex-encoded). OTP-9655 --- lib/inets/src/http_lib/http_util.erl | 5 ++--- lib/inets/src/http_server/httpd_file.erl | 4 ++-- lib/inets/src/http_server/httpd_util.erl | 25 ++++++++++++++----------- 3 files changed, 18 insertions(+), 16 deletions(-) (limited to 'lib/inets/src') diff --git a/lib/inets/src/http_lib/http_util.erl b/lib/inets/src/http_lib/http_util.erl index be0602ff6e..5d8cb9365d 100644 --- a/lib/inets/src/http_lib/http_util.erl +++ b/lib/inets/src/http_lib/http_util.erl @@ -190,9 +190,8 @@ timeout(Timeout, Started) -> html_encode(Chars) -> Reserved = sets:from_list([$&, $<, $>, $\", $', $/]), - lists:append(lists:map(fun(Char) -> - char_to_html_entity(Char, Reserved) - end, Chars)). + lists:append([char_to_html_entity(Char, Reserved) || Char <- Chars]). + %%%======================================================================== diff --git a/lib/inets/src/http_server/httpd_file.erl b/lib/inets/src/http_server/httpd_file.erl index fbe713ecd1..4490a6356a 100644 --- a/lib/inets/src/http_server/httpd_file.erl +++ b/lib/inets/src/http_server/httpd_file.erl @@ -39,8 +39,8 @@ handle_error(_Reason, Op, _ModData, Path) -> handle_error(500, Op, none, Path, ""). handle_error(StatusCode, Op, none, Path, Reason) -> - {StatusCode, none, ?NICE("Can't " ++ Op ++ Path ++ Reason)}; + {StatusCode, none, ?NICE("Can't " ++ Op ++ " " ++ Path ++ Reason)}; handle_error(StatusCode, Op, ModData, Path, Reason) -> {StatusCode, ModData#mod.request_uri, - ?NICE("Can't " ++ Op ++ Path ++ Reason)}. + ?NICE("Can't " ++ Op ++ " " ++ Path ++ Reason)}. diff --git a/lib/inets/src/http_server/httpd_util.erl b/lib/inets/src/http_server/httpd_util.erl index 7fe5d6d152..2e0752bcc0 100644 --- a/lib/inets/src/http_server/httpd_util.erl +++ b/lib/inets/src/http_server/httpd_util.erl @@ -180,10 +180,10 @@ message(301,URL,_) -> message(304, _URL,_) -> "The document has not been changed."; message(400, none, _) -> - "Your browser sent a query that this server could not understand."; + "Your browser sent a query that this server could not understand. "; message(400, Msg, _) -> "Your browser sent a query that this server could not understand. " ++ - http_util:html_encode(Msg); + html_encode(http_uri:decode(Msg)); message(401, none, _) -> "This server could not verify that you are authorized to access the document you @@ -193,29 +193,29 @@ browser doesn't understand how to supply the credentials required."; message(403,RequestURI,_) -> "You don't have permission to access " ++ - http_util:html_encode(RequestURI) ++ + html_encode(RequestURI) ++ " on this server."; message(404,RequestURI,_) -> "The requested URL " ++ - http_util:html_encode(RequestURI) ++ + html_encode(RequestURI) ++ " was not found on this server."; message(408, Timeout, _) -> Timeout; message(412,none,_) -> "The requested preconditions where false"; message(413, Reason,_) -> - "Entity: " ++ http_util:html_encode(Reason); + "Entity: " ++ html_encode(Reason); message(414,ReasonPhrase,_) -> - "Message " ++ http_util:html_encode(ReasonPhrase) ++ "."; + "Message " ++ html_encode(ReasonPhrase) ++ "."; message(416,ReasonPhrase,_) -> - http_util:html_encode(ReasonPhrase); + html_encode(ReasonPhrase); message(500,_,ConfigDB) -> ServerAdmin = lookup(ConfigDB, server_admin, "unknown@unknown"), "The server encountered an internal error or " "misconfiguration and was unable to complete " "your request.

Please contact the server administrator " - ++ http_util:html_encode(ServerAdmin) ++ + ++ html_encode(ServerAdmin) ++ ", and inform them of the time the error occurred " "and anything you might have done that may have caused the error."; @@ -224,17 +224,17 @@ message(501,{Method, RequestURI, HTTPVersion}, _ConfigDB) -> is_atom(Method) -> atom_to_list(Method)++ " to " ++ - http_util:html_encode(RequestURI) ++ + html_encode(RequestURI) ++ " (" ++ HTTPVersion ++ ") not supported."; is_list(Method) -> Method++ " to " ++ - http_util:html_encode(RequestURI) ++ + html_encode(RequestURI) ++ " (" ++ HTTPVersion ++ ") not supported." end; message(503, String, _ConfigDB) -> - "This service in unavailable due to: " ++ http_util:html_encode(String). + "This service in unavailable due to: " ++ html_encode(String). maybe_encode(URI) -> case lists:member($%, URI) of @@ -244,6 +244,9 @@ maybe_encode(URI) -> http_uri:encode(URI) end. +html_encode(String) -> + http_util:html_encode(http_uri:decode(String)). + %%convert_rfc_date(Date)->{{YYYY,MM,DD},{HH,MIN,SEC}} convert_request_date([D,A,Y,DateType| Rest])-> -- cgit v1.2.3 From be97727709814ca6e872806f30933b267c6f700b Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Tue, 25 Oct 2011 12:48:03 +0200 Subject: Added release notes, appup and correct version. OTP-9655 --- lib/inets/src/inets_app/inets.appup.src | 44 +++++++++++---------------------- 1 file changed, 14 insertions(+), 30 deletions(-) (limited to 'lib/inets/src') diff --git a/lib/inets/src/inets_app/inets.appup.src b/lib/inets/src/inets_app/inets.appup.src index c31b0deb30..ea696b9155 100644 --- a/lib/inets/src/inets_app/inets.appup.src +++ b/lib/inets/src/inets_app/inets.appup.src @@ -18,6 +18,13 @@ {"%VSN%", [ + {"5.3.5", + [ + {load_module, http_util, soft_purge, soft_purge, []}, + {load_module, httpd_util, soft_purge, soft_purge, [http_util]}, + {load_module, httpd_file, soft_purge, soft_purge, []} + ] + }, {"5.3.4", [ {restart_application, inets} @@ -42,24 +49,16 @@ [ {restart_application, inets} ] - }, - {"5.2", - [ - {restart_application, inets} - ] - }, - {"5.1.3", - [ - {restart_application, inets} - ] - }, - {"5.1.2", - [ - {restart_application, inets} - ] } ], [ + {"5.3.5", + [ + {load_module, http_util, soft_purge, soft_purge, []}, + {load_module, httpd_util, soft_purge, soft_purge, [http_util]}, + {load_module, httpd_file, soft_purge, soft_purge, []} + ] + }, {"5.3.4", [ {restart_application, inets} @@ -84,21 +83,6 @@ [ {restart_application, inets} ] - }, - {"5.2", - [ - {restart_application, inets} - ] - }, - {"5.1.3", - [ - {restart_application, inets} - ] - }, - {"5.1.2", - [ - {restart_application, inets} - ] } ] }. -- cgit v1.2.3 From 1577983b9b3883b74e3e460ed4f8f6916ffaa3a5 Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Wed, 26 Oct 2011 12:20:29 +0200 Subject: Fixed hex-decoding. OTP-9655 --- lib/inets/src/http_lib/http_uri.erl | 33 +++++++++++++++++----- .../src/http_server/httpd_request_handler.erl | 4 +-- lib/inets/src/http_server/httpd_response.erl | 16 ++++++++--- lib/inets/src/http_server/httpd_util.erl | 2 +- lib/inets/src/inets_app/inets.appup.src | 14 +++++---- 5 files changed, 49 insertions(+), 20 deletions(-) (limited to 'lib/inets/src') diff --git a/lib/inets/src/http_lib/http_uri.erl b/lib/inets/src/http_lib/http_uri.erl index 3804af60f4..b470fd0b46 100644 --- a/lib/inets/src/http_lib/http_uri.erl +++ b/lib/inets/src/http_lib/http_uri.erl @@ -21,7 +21,8 @@ -module(http_uri). -export([parse/1]). --export([parse/1, encode/1, decode/1]). +-export([encode/1, decode/1]). + %%%========================================================================= %%% API @@ -45,16 +46,33 @@ encode(URI) -> $\\, $', $^, $%, $ ]), lists:append(lists:map(fun(Char) -> uri_encode(Char, Reserved) end, URI)). -decode([$%,Hex1,Hex2|Rest]) -> - [hex2dec(Hex1)*16+hex2dec(Hex2)|decode(Rest)]; -decode([First|Rest]) -> - [First|decode(Rest)]; -decode([]) -> +decode(String) -> + try + begin + do_decode(String) + end + catch + throw:{bad_hex_value, _BadChar} -> + %% The string is either badly encoded or a string + %% containing a % followed by a non-hex char. + %% In any case, return as-is since there is nothing + %% we can do... + %% Note that the valid hex-chars are: 0-9, a-f and A-F. + String + end. + +do_decode([$%,Hex1,Hex2|Rest]) -> + [hex2dec(Hex1)*16+hex2dec(Hex2)|do_decode(Rest)]; +do_decode([First|Rest]) -> + [First|do_decode(Rest)]; +do_decode([]) -> []. + %%%======================================================================== %%% Internal functions %%%======================================================================== + parse_scheme(AbsURI) -> case split_uri(AbsURI, ":", {error, no_scheme}, 1, 1) of {error, no_scheme} -> @@ -138,4 +156,5 @@ uri_encode(Char, Reserved) -> hex2dec(X) when (X>=$0) andalso (X=<$9) -> X-$0; hex2dec(X) when (X>=$A) andalso (X=<$F) -> X-$A+10; -hex2dec(X) when (X>=$a) andalso (X=<$f) -> X-$a+10. +hex2dec(X) when (X>=$a) andalso (X=<$f) -> X-$a+10; +hex2dec(X) -> throw({bad_hex_value, X}). diff --git a/lib/inets/src/http_server/httpd_request_handler.erl b/lib/inets/src/http_server/httpd_request_handler.erl index fa832cba3f..1bf1b20b5b 100644 --- a/lib/inets/src/http_server/httpd_request_handler.erl +++ b/lib/inets/src/http_server/httpd_request_handler.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1997-2009. All Rights Reserved. +%% Copyright Ericsson AB 1997-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -343,7 +343,7 @@ handle_http_msg({Method, Uri, Version, {RecordHeaders, Headers}, Body}, Reason = io_lib:format("Forbidden URI: ~p~n", [URI]), error_log(Reason, ModData), {stop, normal, State#state{response_sent = true}}; - {error,{bad_request, {malformed_syntax, URI}}} -> + {error, {bad_request, {malformed_syntax, URI}}} -> ?hdrd("validation failed: bad request - malformed syntax", [{uri, URI}]), httpd_response:send_status(ModData#mod{http_version = Version}, diff --git a/lib/inets/src/http_server/httpd_response.erl b/lib/inets/src/http_server/httpd_response.erl index ea9cfbf4f2..1301f27081 100644 --- a/lib/inets/src/http_server/httpd_response.erl +++ b/lib/inets/src/http_server/httpd_response.erl @@ -1,7 +1,7 @@ %% %% %CopyrightBegin% %% -%% Copyright Ericsson AB 1997-2009. All Rights Reserved. +%% Copyright Ericsson AB 1997-2011. All Rights Reserved. %% %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in @@ -100,12 +100,19 @@ send_status(#mod{socket_type = SocketType, socket = Socket, config_db = ConfigDB} = ModData, StatusCode, PhraseArgs) -> + ?hdrd("send status", [{status_code, StatusCode}, + {phrase_args, PhraseArgs}]), + ReasonPhrase = httpd_util:reason_phrase(StatusCode), Message = httpd_util:message(StatusCode, PhraseArgs, ConfigDB), Body = get_body(ReasonPhrase, Message), - send_header(ModData, StatusCode, [{content_type, "text/html"}, - {content_length, integer_to_list(length(Body))}]), + ?hdrt("send status - header", [{reason_phrase, ReasonPhrase}, + {message, Message}]), + send_header(ModData, StatusCode, + [{content_type, "text/html"}, + {content_length, integer_to_list(length(Body))}]), + httpd_socket:deliver(SocketType, Socket, Body). @@ -345,8 +352,9 @@ transform({Field, Value}) when is_list(Field) -> %% Leave this method and go on to the newer form of response %% OTP-4408 %%---------------------------------------------------------------------- -send_response_old(#mod{method = "HEAD"} = ModData, +send_response_old(#mod{method = "HEAD"} = ModData, StatusCode, Response) -> + NewResponse = lists:flatten(Response), case httpd_util:split(NewResponse, [?CR, ?LF, ?CR, ?LF],2) of diff --git a/lib/inets/src/http_server/httpd_util.erl b/lib/inets/src/http_server/httpd_util.erl index 2e0752bcc0..366843354e 100644 --- a/lib/inets/src/http_server/httpd_util.erl +++ b/lib/inets/src/http_server/httpd_util.erl @@ -183,7 +183,7 @@ message(400, none, _) -> "Your browser sent a query that this server could not understand. "; message(400, Msg, _) -> "Your browser sent a query that this server could not understand. " ++ - html_encode(http_uri:decode(Msg)); + html_encode(Msg); message(401, none, _) -> "This server could not verify that you are authorized to access the document you diff --git a/lib/inets/src/inets_app/inets.appup.src b/lib/inets/src/inets_app/inets.appup.src index ea696b9155..528a3601a4 100644 --- a/lib/inets/src/inets_app/inets.appup.src +++ b/lib/inets/src/inets_app/inets.appup.src @@ -20,9 +20,10 @@ [ {"5.3.5", [ - {load_module, http_util, soft_purge, soft_purge, []}, - {load_module, httpd_util, soft_purge, soft_purge, [http_util]}, - {load_module, httpd_file, soft_purge, soft_purge, []} + {load_module, http_util, soft_purge, soft_purge, []}, + {load_module, httpd_util, soft_purge, soft_purge, [http_util]}, + {load_module, httpd_file, soft_purge, soft_purge, []}, + {load_module, httpd_response, soft_purge, soft_purge, []} ] }, {"5.3.4", @@ -54,9 +55,10 @@ [ {"5.3.5", [ - {load_module, http_util, soft_purge, soft_purge, []}, - {load_module, httpd_util, soft_purge, soft_purge, [http_util]}, - {load_module, httpd_file, soft_purge, soft_purge, []} + {load_module, http_util, soft_purge, soft_purge, []}, + {load_module, httpd_util, soft_purge, soft_purge, [http_util]}, + {load_module, httpd_file, soft_purge, soft_purge, []}, + {load_module, httpd_response, soft_purge, soft_purge, []} ] }, {"5.3.4", -- cgit v1.2.3 From 9b6f04a6dfb955a6615f632197f3d70487a97d26 Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Wed, 26 Oct 2011 13:53:45 +0200 Subject: Skip catching hex decode failure. OTP-9655 --- lib/inets/src/http_lib/http_uri.erl | 17 ++--------------- 1 file changed, 2 insertions(+), 15 deletions(-) (limited to 'lib/inets/src') diff --git a/lib/inets/src/http_lib/http_uri.erl b/lib/inets/src/http_lib/http_uri.erl index b470fd0b46..d03acff3a9 100644 --- a/lib/inets/src/http_lib/http_uri.erl +++ b/lib/inets/src/http_lib/http_uri.erl @@ -47,19 +47,7 @@ encode(URI) -> lists:append(lists:map(fun(Char) -> uri_encode(Char, Reserved) end, URI)). decode(String) -> - try - begin - do_decode(String) - end - catch - throw:{bad_hex_value, _BadChar} -> - %% The string is either badly encoded or a string - %% containing a % followed by a non-hex char. - %% In any case, return as-is since there is nothing - %% we can do... - %% Note that the valid hex-chars are: 0-9, a-f and A-F. - String - end. + do_decode(String). do_decode([$%,Hex1,Hex2|Rest]) -> [hex2dec(Hex1)*16+hex2dec(Hex2)|do_decode(Rest)]; @@ -156,5 +144,4 @@ uri_encode(Char, Reserved) -> hex2dec(X) when (X>=$0) andalso (X=<$9) -> X-$0; hex2dec(X) when (X>=$A) andalso (X=<$F) -> X-$A+10; -hex2dec(X) when (X>=$a) andalso (X=<$f) -> X-$a+10; -hex2dec(X) -> throw({bad_hex_value, X}). +hex2dec(X) when (X>=$a) andalso (X=<$f) -> X-$a+10. -- cgit v1.2.3 From 37650c5ab7d286cdf4a4afa0d6eff1d915f57cff Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Wed, 26 Oct 2011 13:56:09 +0200 Subject: Fixed HTML encode. First *try* to hex decode uri, and then do the actual html encode. OTP-9655 --- lib/inets/src/http_server/httpd_request.erl | 8 ++++---- lib/inets/src/http_server/httpd_util.erl | 10 ++++++++-- 2 files changed, 12 insertions(+), 6 deletions(-) (limited to 'lib/inets/src') diff --git a/lib/inets/src/http_server/httpd_request.erl b/lib/inets/src/http_server/httpd_request.erl index 75f03c4fc2..1c23316ecb 100644 --- a/lib/inets/src/http_server/httpd_request.erl +++ b/lib/inets/src/http_server/httpd_request.erl @@ -261,12 +261,12 @@ validate_uri(RequestURI) -> (catch http_uri:decode(string:left(RequestURI, Ndx))) end, case UriNoQueryNoHex of - {'EXIT',_Reason} -> + {'EXIT', _Reason} -> {error, {bad_request, {malformed_syntax, RequestURI}}}; _ -> - Path = format_request_uri(UriNoQueryNoHex), - Path2=[X||X<-string:tokens(Path, "/"),X=/="."], %% OTP-5938 - validate_path( Path2,0, RequestURI) + Path = format_request_uri(UriNoQueryNoHex), + Path2 = [X||X<-string:tokens(Path, "/"),X=/="."], %% OTP-5938 + validate_path(Path2, 0, RequestURI) end. validate_path([], _, _) -> diff --git a/lib/inets/src/http_server/httpd_util.erl b/lib/inets/src/http_server/httpd_util.erl index 366843354e..15bfe9c621 100644 --- a/lib/inets/src/http_server/httpd_util.erl +++ b/lib/inets/src/http_server/httpd_util.erl @@ -245,7 +245,13 @@ maybe_encode(URI) -> end. html_encode(String) -> - http_util:html_encode(http_uri:decode(String)). + try http_uri:decode(String) of + Decoded when is_list(Decoded) -> + http_util:html_encode(Decoded) + catch + _:_ -> + http_util:html_encode(String) + end. %%convert_rfc_date(Date)->{{YYYY,MM,DD},{HH,MIN,SEC}} @@ -259,7 +265,7 @@ convert_request_date([D,A,Y,DateType| Rest])-> fun convert_rfc850_date/1 end, case catch Func([D,A,Y,DateType| Rest]) of - {ok,Date} -> + {ok, Date} -> Date; _Error-> bad_date -- cgit v1.2.3 From b6719f7943cbaeb10d5121f360f9540db494b639 Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Tue, 1 Nov 2011 14:56:38 +0100 Subject: Added versions 5.2, 5.1.3 and 5.1.2 again. OTP-9655 --- lib/inets/src/inets_app/inets.appup.src | 32 +++++++++++++++++++++++++++++++- 1 file changed, 31 insertions(+), 1 deletion(-) (limited to 'lib/inets/src') diff --git a/lib/inets/src/inets_app/inets.appup.src b/lib/inets/src/inets_app/inets.appup.src index 528a3601a4..5b04c7ed93 100644 --- a/lib/inets/src/inets_app/inets.appup.src +++ b/lib/inets/src/inets_app/inets.appup.src @@ -50,7 +50,22 @@ [ {restart_application, inets} ] - } + }, + {"5.2", + [ + {restart_application, inets} + ] + }, + {"5.1.3", + [ + {restart_application, inets} + ] + }, + {"5.1.2", + [ + {restart_application, inets} + ] + } ], [ {"5.3.5", @@ -85,6 +100,21 @@ [ {restart_application, inets} ] + }, + {"5.2", + [ + {restart_application, inets} + ] + }, + {"5.1.3", + [ + {restart_application, inets} + ] + }, + {"5.1.2", + [ + {restart_application, inets} + ] } ] }. -- cgit v1.2.3 From 53b434e40047fc4e085f57412b4e2227faddf23b Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Wed, 9 Nov 2011 17:30:56 +0100 Subject: Aftermerge cleanup. --- lib/inets/src/http_server/httpd_request_handler.erl | 6 ------ 1 file changed, 6 deletions(-) (limited to 'lib/inets/src') diff --git a/lib/inets/src/http_server/httpd_request_handler.erl b/lib/inets/src/http_server/httpd_request_handler.erl index e07c7b0cd4..d2f22fce93 100644 --- a/lib/inets/src/http_server/httpd_request_handler.erl +++ b/lib/inets/src/http_server/httpd_request_handler.erl @@ -1,14 +1,8 @@ %% %% %CopyrightBegin% -<<<<<<< HEAD -%% -%% Copyright Ericsson AB 1997-2011. All Rights Reserved. -%% -======= %% %% Copyright Ericsson AB 1997-2011. All Rights Reserved. %% ->>>>>>> bmk/inets/httpd/xss_when_erl_encoded/r13/OTP-9655 %% The contents of this file are subject to the Erlang Public License, %% Version 1.1, (the "License"); you may not use this file except in %% compliance with the License. You should have received a copy of the -- cgit v1.2.3