This is the mail archive of the
gcc-bugs@gcc.gnu.org
mailing list for the GCC project.
[Bug fortran/30285] gfortran excessive memory usage with COMMON blocks in modules
- From: "fxcoudert at gcc dot gnu dot org" <gcc-bugzilla at gcc dot gnu dot org>
- To: gcc-bugs at gcc dot gnu dot org
- Date: 9 Nov 2007 12:36:16 -0000
- Subject: [Bug fortran/30285] gfortran excessive memory usage with COMMON blocks in modules
- References: <bug-30285-6318@http.gcc.gnu.org/bugzilla/>
- Reply-to: gcc-bugzilla at gcc dot gnu dot org
------- Comment #14 from fxcoudert at gcc dot gnu dot org 2007-11-09 12:36 -------
I think the problem starts with:
module mod0
integer mpi_bottom
common /mpipriv/ mpi_bottom
end module mod0
module mod1
use mod0
end module mod1
module mod2
use mod0
use mod1
end module mod2
Because in that case, mod2.mod already has two copies of the common:
(('mpipriv' 2 0 0 'mpipriv') ('mpipriv' 2 0 0 'mpipriv'))
and I don't think that's desirable. I think that the module loading is actually
wrong here: the code in gfc_get_common (match.c) takes special care to
duplicate this common name by creating a unique name for it. While I believe
that mangling is necessary, the mangled name shouldn't be unique but simply
prefixed, so that of the same name are merged, while prevented to clash with
the namespace of the use'ing procedure.
I'm regtesting the following patch:
Index: match.c
===================================================================
--- match.c (revision 129869)
+++ match.c (working copy)
@@ -2608,23 +2608,19 @@ gfc_common_head *
gfc_get_common (const char *name, int from_module)
{
gfc_symtree *st;
- static int serial = 0;
- char mangled_name[GFC_MAX_SYMBOL_LEN + 1];
+ char mangled_name[GFC_MAX_SYMBOL_LEN + 12];
if (from_module)
- {
- /* A use associated common block is only needed to correctly layout
- the variables it contains. */
- snprintf (mangled_name, GFC_MAX_SYMBOL_LEN, "_%d_%s", serial++, name);
- st = gfc_new_symtree (&gfc_current_ns->common_root, mangled_name);
- }
- else
- {
- st = gfc_find_symtree (gfc_current_ns->common_root, name);
-
- if (st == NULL)
- st = gfc_new_symtree (&gfc_current_ns->common_root, name);
- }
+ /* A use associated common block is only needed to correctly layout
+ the variables it contains. */
+ snprintf (mangled_name, GFC_MAX_SYMBOL_LEN, "_frommodule_%s", name);
+
+ st = gfc_find_symtree (gfc_current_ns->common_root,
+ from_module ? mangled_name : name);
+
+ if (st == NULL)
+ st = gfc_new_symtree (&gfc_current_ns->common_root,
+ from_module ? mangled_name : name);
if (st->n.common == NULL)
{
--
fxcoudert at gcc dot gnu dot org changed:
What |Removed |Added
----------------------------------------------------------------------------
CC| |fxcoudert at gcc dot gnu dot
| |org
AssignedTo|unassigned at gcc dot gnu |fxcoudert at gcc dot gnu dot
|dot org |org
Status|NEW |ASSIGNED
GCC host triplet|i686-pc-linux-gnu |
Last reconfirmed|2006-12-24 10:47:43 |2007-11-09 12:36:15
date| |
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=30285