[Patch, fortran] Runtime memory leak checking.

Janus Weil janus@gcc.gnu.org
Thu Apr 23 09:20:00 GMT 2009


Hi all,

I just updated the memleak patch to current trunk, since I
incidentally found some use for it lately and wanted to try it.

Up to now I basically just re-diffed it (repairing some failed hunks)
and fixed some indentation problems reported by Mikael, but maybe I'll
be working some more on this soon. Seems like the patch may be almost
ready to go into trunk, I guess?

Some comments by previous reviewers that still need to be addressed:

*******************************

* this one by Daniel Franke:

> > +      st_printf (" !! Memory leak in the code generated by the GNU Fortran
> > " +            "compiler.\n !! Please report this issue to "
> > +              "http://gcc.gnu.org/bugzilla/\n";);
>
> There's a toplevel configuration option, '--with-bugurl'.
> Maybe the configured url should  be used instead of a hardcoded one?

*******************************

* this one by Tobias Burnus:

> What is "memusage" supposed to do?
>
> (I think you plan to add a patch for "memusage" soon; if not I'd prefer
> that remove the option.)

I would think that "memusage" should just output the memory usage
statistics that "memleaks" also prints:

Peak user-allocated memory: ...
Peak memory created by the compiler for temporaries: ...

but without the memleak analysis. Or maybe a more detailed memory
usage analysis like valgrind (massif) does? I think in any way this
may be useful as a separate feature and we should keep the option in.

*******************************

* another comment by Tobias:

> @@ -5453,8 +5469,9 @@
>                                    TYPE_SIZE_UNIT (gfc_get_element_type (type))));
>
>   /* Allocate memory to the destination.  */
> -  tmp = gfc_call_malloc (&block, TREE_TYPE (gfc_conv_descriptor_data_get (src)),
> -                        size);
> +  tmp = gfc_allocate_with_status (&block, size, NULL_TREE,
> +                                 &gfc_current_locus);
> +  tmp = fold_convert (TREE_TYPE (gfc_conv_descriptor_data_get (src)), tmp);
>   gfc_conv_descriptor_data_set (&block, dest, tmp);
>
>
> Is there a reason that you don't use
>  if (gfc_option.rtcheck & GFC_RTCHECK_MEMLEAKS)
> here, but that you have such an if in lines
> @@ -4179,7 +4186,12 @@

*******************************

* and this one:

> You need to update invoke.texi. Additionally, you need to add the new
> functions to  gfortran.map. After doing so, one can actually get rid of
> the -static.
>
> Is it really necessary to link libiberty even if no memleak checks are
> enabled?

Actually, where in gfortan.map do they have to be added? Should there
be a GFORTRAN_1.2 for 4.5?

*******************************

* Note also that the patch fails on the following test case (which is
perfectly legal):

implicit none
character(100), save :: path_To_Input='../test.dat'
logical :: ex
Inquire(file=trim(path_to_Input),exist=ex)
print *,ex
end

with the following message:

Error in memory deallocation at line 4 of source file 'test.f90':
freeing memory that has not been allocated by us.

*******************************

Cheers,
Janus





2008/11/29 Paul Richard Thomas <paul.richard.thomas@gmail.com>:
> This patch is almost entirely due to FX Coudert; I added the updating
> of gfc_current_locus in trans.c, the testcase and the ChangeLogs.  I
> also corrected one error.
>
> The patch implements checking for memory leaks, such that:
>
> [prt@localhost mem-check]# cat m*.f90
> ! { dg-do run }
> ! { dg-options = "-fruntime-check=memleaks" }
> !
> ! Test the runtime check for memory leaks.
> !
>  integer(4), pointer :: i(:)
>  allocate (i(10))
> end
> ! { dg-output "found 1 memory leaks" }
>
> [prt@localhost mem-check]# /irun/bin/gfortran -static
> -fruntime-check=memleaks m*.f90;./a.out
>
>
> Fortran runtime checking: found 1 memory leaks
>  - at line 7 of file 'mem_check_1.f90', allocation of 40.0 B (address
> 0x1749ee0)
>
> Peak user-allocated memory: 40.0 B
> Peak memory created by the compiler for temporaries: 0.00 B
>
> When applied to some of the allocatable component testcases, such as:
> [prt@localhost mem-check]# /irun/bin/gfortran -static
> -fruntime-check=memleaks
> /svn/trunk/gcc/testsuite/gfortran.dg/alloc_comp_basics_5.f90;./a.out
>
>
> Fortran runtime checking: found 1 memory leaks
>  - at line 25 of file
> '/svn/trunk/gcc/testsuite/gfortran.dg/alloc_comp_basics_5.f90',
> allocation of 40.0 B (address 0x24fdee0)
>
> Peak user-allocated memory: 40.0 B
> Peak memory created by the compiler for temporaries: 0.00 B
>
> It also adds hooks for memusage and recursion in runtime.
>
> All the action happens in libgfortran/runtime/mem-check.c.  This sets
> up and populates a hash table with allocations of temporaries.
> Deallocation removes the entries and anything that is left at the end
> of execution represents a memory leak.  The modifications to trans*.c
> implement the calls when memory is alloctaed or freed, if the
> runtime-check flag is set.
>
> Bootstrapped and regtested on FC9/x86_i64.
>
> OK to go on ice ready for 4.5?  (Is there any appetite to add it to 4.4?)
>
> Paul
>
> 2008-11-28  Francois-Xavier Coudert  <fxcoudert@gcc.gnu.org>
>                Paul Thomas  <pault@gcc.gnu.org>
>
>        * Makefile.in : Add runtime/memory_check.c and .lo.
>        * runtime/memory_check.c : New file containing:
>        (pretty_memsize, hashval, hasheq, do_nothing,
>        egister_allocation, malloc_check, register_deallocation,
>        free_check, realloc_check, report_callback,
>        memory_check_report): New functions.
>        * libgfortran.h : Add prototypes for malloc_check,
>        free_check, realloc_check and memory_check_report.
>        * Makefile.am : Add runtime/memory_check.c.
>
> 2008-11-28  Francois-Xavier Coudert  <fxcoudert@gcc.gnu.org>
>                Paul Thomas  <pault@gcc.gnu.org>
>
>        * trans-expr.c (gfc_conv_string_tmp): Update arguments for call
>        to gfc_call_free.
>        * trans-array.c (gfc_trans_allocate_array_storage): Add call
>        to gfc_allocate_with_status, if checking memory leaks and
>        extend argument to gfc_call_free.
>        (gfc_allocate_with_status): Extend arguments for calls to
>        gfc_allocate_with_status and gfc_allocate_array_with_status.
>        (gfc_array_deallocate): Add locus* to function declaration.
>        (gfc_array_deallocate): Add final argument to call to
>        gfc_deallocate_with_status.
>        (gfc_trans_auto_array_allocation): If -fmemleaks is set, call
>        gfc_allocate_with_status. Extend the arglist for gfc_call_free
>        (gfc_trans_dummy_array_bias): The same.
>        (gfc_conv_array_parameter): The same.
>        (gfc_trans_dealloc_allocated): Extend arguments for call to
>        gfc_deallocate_with_status.
>        (gfc_duplicate_allocatable): Extend arguments for call to
>        gfc_allocate_with_status.
>        * trans-array.h : Modify prototype for gfc_array_deallocate.
>        trans-openmp.c (gfc_omp_clause_default_ctor): Extend args for
>        call to gfc_allocate_array_with_status.
>        (gfc_omp_clause_copy_ctor): The same.
>        (gfc_trans_omp_array_reduction): The same.
>        * gfortran.h : Declare rtcheck.
>        * lang-opt : Correct --ffpe-trap and add -fruntime-check.
>        * trans-stmt.c (gfc_trans_assign_need_temp): Add arg to call
>        to gfc_call_free.
>        (gfc_trans_pointer_assign_need_temp): The same.
>        (gfc_trans_pointer_assign_need_temp): The same.
>        (gfc_trans_forall_1, gfc_trans_where_2): The same.
>        (gfc_trans_allocate): Add arg to call to
>        gfc_allocate_with_status.
>        (gfc_trans_deallocate): Add arg to calls to
>        gfc_array_deallocate and gfc_deallocate_with_status.
>        * libfortran.h : Add bitmasks for the various runtime checks
>        and an enum for the allocataion types.
>        * trans.c (gfc_allocate_with_status): Add arg to decl and code
>        for real-time checking.
>        (gfc_allocate_array_with_status, gfc_call_free): The same.
>        (gfc_deallocate_with_status, gfc_call_realloc): The same.
>        (gfc_trans_code): Update gfc_current_locus from gfc_code.
>        * trans.h: Modify prototypes for the above and add tree
>        decls for gfor_fndecl_malloc_check, gfor_fndecl_free_check,
>        gfor_fndecl_realloc_check and gfor_fndecl_memory_check_report.
>        * gfortranspec.c : Add -liberty and remove -lg2c.
>        * trans-decl.c (gfc_build_builtin_function_decls): Add the
>        memory checking functions and build them if memory checking
>        is enabled.
>        * trans-intrinsic.c (gfc_conv_intrinsic_conversion,
>        gfc_conv_intrinsic_ctime, gfc_conv_intrinsic_fdate,
>        gfc_conv_intrinsic_ttynam, gfc_conv_intrinsic_minmax_char,
>        gfc_conv_intrinsic_array_transfer, gfc_conv_intrinsic_trim):
>        Add extra args to calls to gfc_call_free.
>        * options.c (gfc_init_options): Add real time checking.
>        (gfc_handle_runtime_check_option): New function.
>        (gfc_handle_option): Add case of runtime_check.
>
> 2008-11-28  Paul Thomas  <pault@gcc.gnu.org>
>
>        * gfortran.dg/mem_check_1.f90: New test.
>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: memcheck146619.diff
Type: text/x-patch
Size: 42350 bytes
Desc: not available
URL: <http://gcc.gnu.org/pipermail/fortran/attachments/20090423/6feccfd4/attachment.bin>


More information about the Fortran mailing list