Recent

Author Topic: memleak in fphttpclient?  (Read 5486 times)

billyb123

  • New Member
  • *
  • Posts: 26
memleak in fphttpclient?
« on: January 24, 2017, 05:51:36 pm »
valgrind says this prog leaks memory (about 80kb).
BUT i noticed when i put 'http' (for example, http://www.example.com/) instead of 'https' it doesnt leak memory.

can someone explain this to me? why do i have memleak here?

Code: [Select]
{$MODE DELPHI}
program test;
uses
  fphttpclient;

const
  url = 'https://api.darksky.net/';

var
  page: ansistring;
  http: tfphttpclient;

begin
  http := tfphttpclient.create (nil);
  try
    page := http.get (url);
  finally
    http.free;
  end;
  writeln (page);
end.

Thaddy

  • Hero Member
  • *****
  • Posts: 14393
  • Sensorship about opinions does not belong here.
Re: memleak in fphttpclient?
« Reply #1 on: January 24, 2017, 06:01:27 pm »
fphttpclient uses sslsockets for https.(in the implementation uses clause)
80Kb looks like a context not being free'd by sslsockets.
I would not worry too much unless the leak is progressive (increases when doing multiple https visits).
Will have a look.
Object Pascal programmers should get rid of their "component fetish" especially with the non-visuals.

molly

  • Hero Member
  • *****
  • Posts: 2330
Re: memleak in fphttpclient?
« Reply #2 on: January 24, 2017, 06:06:00 pm »
Would be great if you could have a look Thaddy. Secure or not, heaptrc keeps telling me there is leakage (3.0, win32)

rvk

  • Hero Member
  • *****
  • Posts: 6171
Re: memleak in fphttpclient?
« Reply #3 on: January 24, 2017, 06:27:56 pm »
I'm getting an 404 exception with your program (with that page).

Try the following:
Code: Pascal  [Select][+][-]
  1. {$MODE DELPHI}
  2. program project1;
  3. uses
  4.   fphttpclient;
  5.  
  6. const
  7.   url = 'https://api.darksky.net/';
  8.  
  9. var
  10.   page: ansistring;
  11.   http: tfphttpclient;
  12.  
  13. begin
  14.   http := tfphttpclient.create (nil);
  15.   try
  16.     try
  17.       page := http.get (url);
  18.     except
  19.       writeln('woops, exception');
  20.     end;
  21.   finally
  22.     http.free;
  23.   end;
  24.   writeln (page);
  25. end.

So without proper exception handling it seems not everything is freed. With above example I don't get a leak.

molly

  • Hero Member
  • *****
  • Posts: 2330
Re: memleak in fphttpclient?
« Reply #4 on: January 24, 2017, 06:32:26 pm »
Thanks rvk, i can confirm.

Strange.

rvk

  • Hero Member
  • *****
  • Posts: 6171
Re: memleak in fphttpclient?
« Reply #5 on: January 24, 2017, 06:39:44 pm »
Yes. Without the exception handling this is what I get.
So the page returns a 404.
Get only expects a 200 and otherwise throws an exception.

Internally there is a leak that with throwing an exception something is not freed.
But then it's weird that if I handle the exception at a higher level that block does get freed.

Code: [Select]
An unhandled exception occurred at $00414579:
EHTTPClient: Unexpected response status code: 404
  $00414579  TFPCUSTOMHTTPCLIENT__READRESPONSE,  line 1089 of ./fcl-web/src/base/fphttpclient.pp
  $00414E75  TFPCUSTOMHTTPCLIENT__DONORMALREQUEST,  line 1179 of ./fcl-web/src/base/fphttpclient.pp
  $00415133  TFPCUSTOMHTTPCLIENT__DOMETHOD,  line 1232 of ./fcl-web/src/base/fphttpclient.pp
  $004156A9  TFPCUSTOMHTTPCLIENT__HTTPMETHOD,  line 1331 of ./fcl-web/src/base/fphttpclient.pp
  $00415867  TFPCUSTOMHTTPCLIENT__GET,  line 1367 of ./fcl-web/src/base/fphttpclient.pp
  $004158BC  TFPCUSTOMHTTPCLIENT__GET,  line 1398 of ./fcl-web/src/base/fphttpclient.pp
  $0040180A  main,  line 16 of project1.lpr

Heap dump by heaptrc unit
376 memory blocks allocated : 17237/18384
372 memory blocks freed     : 17080/18216
4 unfreed memory blocks : 157
True heap size : 491520 (96 used in System startup)
True free heap : 490960
Should be : 491000
Call trace for block $01814660 size 64
  $00409D6C  fpc_raiseexception,  line 165 of C:/dev/fpc/rtl/inc/except.inc
  $004145B3  TFPCUSTOMHTTPCLIENT__READRESPONSE,  line 1090 of ./fcl-web/src/base/fphttpclient.pp
  $00414E75  TFPCUSTOMHTTPCLIENT__DONORMALREQUEST,  line 1179 of ./fcl-web/src/base/fphttpclient.pp
  $00415133  TFPCUSTOMHTTPCLIENT__DOMETHOD,  line 1232 of ./fcl-web/src/base/fphttpclient.pp
  $004156A9  TFPCUSTOMHTTPCLIENT__HTTPMETHOD,  line 1331 of ./fcl-web/src/base/fphttpclient.pp
  $00415867  TFPCUSTOMHTTPCLIENT__GET,  line 1367 of ./fcl-web/src/base/fphttpclient.pp
  $004158BC  TFPCUSTOMHTTPCLIENT__GET,  line 1398 of ./fcl-web/src/base/fphttpclient.pp
  $0040180A  main,  line 16 of project1.lpr
Call trace for block $0174D9D8 size 24
  $00409D6C  fpc_raiseexception,  line 165 of C:/dev/fpc/rtl/inc/except.inc
  $004145B3  TFPCUSTOMHTTPCLIENT__READRESPONSE,  line 1090 of ./fcl-web/src/base/fphttpclient.pp
  $00414E75  TFPCUSTOMHTTPCLIENT__DONORMALREQUEST,  line 1179 of ./fcl-web/src/base/fphttpclient.pp
  $00415133  TFPCUSTOMHTTPCLIENT__DOMETHOD,  line 1232 of ./fcl-web/src/base/fphttpclient.pp
  $004156A9  TFPCUSTOMHTTPCLIENT__HTTPMETHOD,  line 1331 of ./fcl-web/src/base/fphttpclient.pp
  $00415867  TFPCUSTOMHTTPCLIENT__GET,  line 1367 of ./fcl-web/src/base/fphttpclient.pp
  $004158BC  TFPCUSTOMHTTPCLIENT__GET,  line 1398 of ./fcl-web/src/base/fphttpclient.pp
  $0040180A  main,  line 16 of project1.lpr
Call trace for block $0178CA60 size 49
  $0042434B  FORMAT,  line 403 of C:/dev/fpc/rtl/objpas/sysutils/sysformt.inc
  $00424822  FORMAT,  line 1066 of C:/dev/fpc/rtl/objpas/sysutils/sysstr.inc
  $00427D9E  EXCEPTION__CREATEFMT,  line 190 of C:/dev/fpc/rtl/objpas/sysutils/sysutils.inc
  $004145A7  TFPCUSTOMHTTPCLIENT__READRESPONSE,  line 1090 of ./fcl-web/src/base/fphttpclient.pp
  $00414E75  TFPCUSTOMHTTPCLIENT__DONORMALREQUEST,  line 1179 of ./fcl-web/src/base/fphttpclient.pp
  $00415133  TFPCUSTOMHTTPCLIENT__DOMETHOD,  line 1232 of ./fcl-web/src/base/fphttpclient.pp
  $004156A9  TFPCUSTOMHTTPCLIENT__HTTPMETHOD,  line 1331 of ./fcl-web/src/base/fphttpclient.pp
  $00415867  TFPCUSTOMHTTPCLIENT__GET,  line 1367 of ./fcl-web/src/base/fphttpclient.pp
Call trace for block $0174D978 size 20
  $004145A7  TFPCUSTOMHTTPCLIENT__READRESPONSE,  line 1090 of ./fcl-web/src/base/fphttpclient.pp
  $00414E75  TFPCUSTOMHTTPCLIENT__DONORMALREQUEST,  line 1179 of ./fcl-web/src/base/fphttpclient.pp
  $00415133  TFPCUSTOMHTTPCLIENT__DOMETHOD,  line 1232 of ./fcl-web/src/base/fphttpclient.pp
  $004156A9  TFPCUSTOMHTTPCLIENT__HTTPMETHOD,  line 1331 of ./fcl-web/src/base/fphttpclient.pp
  $00415867  TFPCUSTOMHTTPCLIENT__GET,  line 1367 of ./fcl-web/src/base/fphttpclient.pp
  $004158BC  TFPCUSTOMHTTPCLIENT__GET,  line 1398 of ./fcl-web/src/base/fphttpclient.pp
  $0040180A  main,  line 16 of project1.lpr
  $004158BC  TFPCUSTOMHTTPCLIENT__GET,  line 1398 of ./fcl-web/src/base/fphttpclient.pp
« Last Edit: January 24, 2017, 06:41:23 pm by rvk »

molly

  • Hero Member
  • *****
  • Posts: 2330
Re: memleak in fphttpclient?
« Reply #6 on: January 24, 2017, 06:42:52 pm »
in case it matter, i tried simple www.google.com and that throws a 302 with similar outcome (mode objfpc).

rvk

  • Hero Member
  • *****
  • Posts: 6171
Re: memleak in fphttpclient?
« Reply #7 on: January 24, 2017, 07:28:57 pm »
The problem isn't in fphttpclient at all. It is in sysutils.

When you don't handle an exception in your console program and sysutils is used... you get a leak when the program ends. This is only when the finalization handles the exception.

Example:
Code: Pascal  [Select][+][-]
  1. program project1;
  2. uses sysutils;
  3. var
  4.   i: integer;
  5. begin
  6.   try
  7.     i := 0;
  8.     i := 7 div i;
  9.   finally
  10.     writeln('finally');
  11.   end;
  12.   writeln('normal end');
  13. end.

Solution... always handle any exception in a console program when you're using sysutils (which is used by fphttpclient). It's also not a recurring leak (only when the program end, so it might not matter a lot).
« Last Edit: January 24, 2017, 07:31:01 pm by rvk »

billyb123

  • New Member
  • *
  • Posts: 26
Re: memleak in fphttpclient?
« Reply #8 on: January 24, 2017, 08:19:18 pm »
your example still leaks here.
if i put a normal address in url like 'https://webflow.com/discover/popular' which gets http response 200, and the 'except' section, it still leaks 80kb.


I'm getting an 404 exception with your program (with that page).

Try the following:
Code: Pascal  [Select][+][-]
  1. {$MODE DELPHI}
  2. program project1;
  3. uses
  4.   fphttpclient;
  5.  
  6. const
  7.   url = 'https://api.darksky.net/';
  8.  
  9. var
  10.   page: ansistring;
  11.   http: tfphttpclient;
  12.  
  13. begin
  14.   http := tfphttpclient.create (nil);
  15.   try
  16.     try
  17.       page := http.get (url);
  18.     except
  19.       writeln('woops, exception');
  20.     end;
  21.   finally
  22.     http.free;
  23.   end;
  24.   writeln (page);
  25. end.

So without proper exception handling it seems not everything is freed. With above example I don't get a leak.

rvk

  • Hero Member
  • *****
  • Posts: 6171
Re: memleak in fphttpclient?
« Reply #9 on: January 24, 2017, 08:32:12 pm »
your example still leaks here.
if i put a normal address in url like 'https://webflow.com/discover/popular' which gets http response 200, and the 'except' section, it still leaks 80kb.

Not for me. Source below gives me:
Code: [Select]
no leak. page-length: 402866
Heap dump by heaptrc unit
379 memory blocks allocated : 20288435/20289736
379 memory blocks freed     : 20288435/20289736
0 unfreed memory blocks : 0
True heap size : 425984 (160 used in System startup)
True free heap : 425824
On:
Lazarus 1.2.0 / FPC 2.6.2 32 bit
Lazarus 1.6.2 / FPC 3.0.0 64 bit
Lazarus 1.7 trunk / FPC 3.1.1 32 bit

Code: Pascal  [Select][+][-]
  1. {$MODE DELPHI}
  2. program project1;
  3. uses
  4.   fphttpclient;
  5.  
  6. const
  7.   url = 'https://webflow.com/discover/popular';
  8.  
  9. var
  10.   page: ansistring;
  11.   http: tfphttpclient;
  12.  
  13. begin
  14.   http := tfphttpclient.create (nil);
  15.   try
  16.     try
  17.       page := http.get (url);
  18.     except
  19.       writeln('woops, exception');
  20.     end;
  21.   finally
  22.     http.free;
  23.   end;
  24.   // writeln (page);
  25.   writeln ('no leak. page-length: ', length(page));
  26. end.

Thaddy

  • Hero Member
  • *****
  • Posts: 14393
  • Sensorship about opinions does not belong here.
Re: memleak in fphttpclient?
« Reply #10 on: January 24, 2017, 09:07:38 pm »
@rvk
Same here. No leaks after program termination.
Code: [Select]
no leak. page-length: 402866
Heap dump by heaptrc unit
468 memory blocks allocated : 20291888/20293664
468 memory blocks freed     : 20291888/20293664
0 unfreed memory blocks : 0
True heap size : 425984
True free heap : 425984
« Last Edit: January 24, 2017, 09:11:11 pm by Thaddy »
Object Pascal programmers should get rid of their "component fetish" especially with the non-visuals.

 

TinyPortal © 2005-2018