From 6c8fb0bf44f74e9fc82f64949aba0bae8309fc88 Mon Sep 17 00:00:00 2001 From: Micael Karlberg Date: Fri, 30 Apr 2010 12:00:00 +0200 Subject: inets: Patch 1115 OTP-8542 [httpc] Memory leak plugged. The profile manager never cleaned up in its handler database. This meant that with each new request handler, another entry was created that was never deleted. Eventually the request id counter (used as a key) would wrap, but the machine would most likely run out of memory before that happened. OTP-8607 [httpc] https requests with default port not handled properly. Jebu Ittiachen. --- lib/inets/doc/src/notes.xml | 52 +++++++++++++++++++++++++++++ lib/inets/src/http_client/httpc.erl | 8 +++-- lib/inets/src/http_client/httpc_handler.erl | 10 +++--- lib/inets/src/http_client/httpc_manager.erl | 18 ++++++++++ lib/inets/src/inets_app/inets.appup.src | 22 ++++++++++-- lib/inets/vsn.mk | 8 +++-- 6 files changed, 107 insertions(+), 11 deletions(-) (limited to 'lib') diff --git a/lib/inets/doc/src/notes.xml b/lib/inets/doc/src/notes.xml index 762c2c84c5..3216b0c2cd 100644 --- a/lib/inets/doc/src/notes.xml +++ b/lib/inets/doc/src/notes.xml @@ -32,6 +32,58 @@ notes.xml +
Inets 5.3.2 + +
Improvements and New Features +

-

+ + +
+ +
Fixed Bugs and Malfunctions + + + + + +

[httpc] - Memory leak plugged. + The profile manager never cleaned up in its handler database. + This meant that with each new request handler, another entry + was created that was never deleted. Eventually the request + id counter (used as a key) would wrap, but the machine would + most likely run out of memory before that happened.

+

Own Id: OTP-8542

+

Lev Walkin

+
+ + +

[httpc] - https requests with default port (443) not handled + properly.

+

Own Id: OTP-8607

+

jebu ittiachen

+
+ +
+
+ +
+ +
Inets 5.3.1
Improvements and New Features diff --git a/lib/inets/src/http_client/httpc.erl b/lib/inets/src/http_client/httpc.erl index 5205605e0a..6deeab6948 100644 --- a/lib/inets/src/http_client/httpc.erl +++ b/lib/inets/src/http_client/httpc.erl @@ -432,7 +432,7 @@ handle_request(Method, Url, Options = request_options(Options0), Sync = proplists:get_value(sync, Options), Stream = proplists:get_value(stream, Options), - Host2 = header_host(Host, Port), + Host2 = header_host(Scheme, Host, Port), HeadersRecord = header_record(NewHeaders, Host2, HTTPOptions), Receiver = proplists:get_value(receiver, Options), SocketOpts = proplists:get_value(socket_opts, Options), @@ -895,9 +895,11 @@ bad_option(Option, BadValue) -> throw({error, {bad_option, Option, BadValue}}). -header_host(Host, 80 = _Port) -> +header_host(https, Host, 443 = _Port) -> Host; -header_host(Host, Port) -> +header_host(http, Host, 80 = _Port) -> + Host; +header_host(_Scheme, Host, Port) -> Host ++ ":" ++ integer_to_list(Port). diff --git a/lib/inets/src/http_client/httpc_handler.erl b/lib/inets/src/http_client/httpc_handler.erl index 695ff9cf82..5e79d874fb 100644 --- a/lib/inets/src/http_client/httpc_handler.erl +++ b/lib/inets/src/http_client/httpc_handler.erl @@ -1424,14 +1424,16 @@ try_to_enable_pipeline_or_keep_alive( State#state{status = close} end. -answer_request(Request, Msg, #state{timers = Timers} = State) -> +answer_request(#request{id = RequestId, from = From} = Request, Msg, + #state{timers = Timers, profile_name = ProfileName} = State) -> ?hcrt("answer request", [{request, Request}]), - httpc_response:send(Request#request.from, Msg), + httpc_response:send(From, Msg), RequestTimers = Timers#timers.request_timers, TimerRef = - proplists:get_value(Request#request.id, RequestTimers, undefined), - Timer = {Request#request.id, TimerRef}, + proplists:get_value(RequestId, RequestTimers, undefined), + Timer = {RequestId, TimerRef}, cancel_timer(TimerRef, {timeout, Request#request.id}), + httpc_manager:request_done(RequestId, ProfileName), State#state{request = Request#request{from = answer_sent}, timers = Timers#timers{request_timers = diff --git a/lib/inets/src/http_client/httpc_manager.erl b/lib/inets/src/http_client/httpc_manager.erl index f3cd81f4a7..b278077a66 100644 --- a/lib/inets/src/http_client/httpc_manager.erl +++ b/lib/inets/src/http_client/httpc_manager.erl @@ -30,6 +30,7 @@ request/2, cancel_request/2, request_canceled/2, + request_done/2, retry_request/2, redirect_request/2, insert_session/2, @@ -170,6 +171,18 @@ request_canceled(RequestId, ProfileName) -> cast(ProfileName, {request_canceled, RequestId}). +%%-------------------------------------------------------------------- +%% Function: request_done(RequestId, ProfileName) -> ok +%% RequestId - ref() +%% ProfileName = atom() +%% +%% Description: Inform tha manager that a request has been completed. +%%-------------------------------------------------------------------- + +request_done(RequestId, ProfileName) -> + cast(ProfileName, {request_done, RequestId}). + + %%-------------------------------------------------------------------- %% Function: insert_session(Session, ProfileName) -> _ %% Session - #tcp_session{} @@ -486,6 +499,11 @@ handle_cast({request_canceled, RequestId}, State) -> {noreply, State} end; +handle_cast({request_done, RequestId}, State) -> + ?hcrv("request done", [{request_id, RequestId}]), + ets:delete(State#state.handler_db, RequestId), + {noreply, State}; + handle_cast({set_options, Options}, State = #state{options = OldOptions}) -> ?hcrv("set options", [{options, Options}, {old_options, OldOptions}]), NewOptions = diff --git a/lib/inets/src/inets_app/inets.appup.src b/lib/inets/src/inets_app/inets.appup.src index ba1dc8ccdb..dfdfb41373 100644 --- a/lib/inets/src/inets_app/inets.appup.src +++ b/lib/inets/src/inets_app/inets.appup.src @@ -18,9 +18,18 @@ {"%VSN%", [ + {"5.3.1", + [ + {load_module, httpc, soft_purge, soft_purge, []}, + {update, httpc_handler, soft, soft_purge, soft_purge, [httpc_manager]}, + {update, httpc_manager, soft, soft_purge, soft_purge, []} + ] + }, {"5.3", [ - {update, httpc_handler, soft, soft_purge, soft_purge, [mod_esi]}, + {load_module, httpc, soft_purge, soft_purge, []}, + {update, httpc_handler, soft, soft_purge, soft_purge, [httpc_manager]}, + {update, httpc_manager, soft, soft_purge, soft_purge, []}, {load_module, mod_esi, soft_purge, soft_purge, []} ] }, @@ -41,9 +50,18 @@ } ], [ + {"5.3.1", + [ + {load_module, httpc, soft_purge, soft_purge, []}, + {update, httpc_handler, soft, soft_purge, soft_purge, [httpc_manager]}, + {update, httpc_manager, soft, soft_purge, soft_purge, []} + ] + }, {"5.3", [ - {update, httpc_handler, soft, soft_purge, soft_purge, [mod_esi]}, + {load_module, httpc, soft_purge, soft_purge, []}, + {update, httpc_handler, soft, soft_purge, soft_purge, [httpc_manager]}, + {update, httpc_manager, soft, soft_purge, soft_purge, []}, {load_module, mod_esi, soft_purge, soft_purge, []} ] }, diff --git a/lib/inets/vsn.mk b/lib/inets/vsn.mk index 401bf4d37d..7776bef0a5 100644 --- a/lib/inets/vsn.mk +++ b/lib/inets/vsn.mk @@ -18,11 +18,15 @@ # %CopyrightEnd% APPLICATION = inets -INETS_VSN = 5.3.1 +INETS_VSN = 5.3.2 PRE_VSN = APP_VSN = "$(APPLICATION)-$(INETS_VSN)$(PRE_VSN)" -TICKETS = OTP-8508 OTP-8509 +TICKETS = OTP-8542 OTP-8607 + +TICKETS_5_3_1 = \ + OTP-8508 \ + OTP-8509 TICKETS_5_3 = \ OTP-8016 \ -- cgit v1.2.3