This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
PATCH for static DWARF2 buffers
- To: egcs-patches at cygnus dot com
- Subject: PATCH for static DWARF2 buffers
- From: Mark Mitchell <mark at markmitchell dot com>
- Date: Sun, 19 Jul 1998 18:33:44 -0700
- Cc: Jason Merrill <jason at cygnus dot com>
- Reply-to: mark at markmitchell dot com
Here's a patch to eliminate some static buffers in the DWARF2 code.
These buffers were overflowing because of symbol names in excess of
1000 characters. (Sounds crazy until you remember the long names
generated by templates.)
Since the functions involved were already using xmalloc to allocate
memory, rather than obstacks, I chose not to use obstacks. Instead,
since there were rumors that gcc will eventually head away from
obstacks, I wrote (for the umpteenth time) a small dynamically
allocated string ADT, and used that.
May I check this in? Should it also go on the 1.1 branch?
--
Mark Mitchell mark@markmitchell.com
Mark Mitchell Consulting http://www.markmitchell.com
Sun Jul 19 18:09:00 1998 Mark Mitchell <mark@markmitchell.com>
* dyn-string.h: New file.
* dyn-string.c: Likewise.
* Makefile.in (OBJS): Add dyn-string.o.
(dwarf2out.o): Add dyn-string.h dependency.
(dyn-string.o): List dependencies.
* dwarf2out.c: Include dyn-string.h.
(ASM_NAME_TO_STRING): Use dyn_string_append, rather than strcpy.
(addr_const_to_string): Take a dyn_string_t, not a char* as a
prototype. Use dyn_string_append rather than strcat, throughout.
(addr_to_string): Use dyn_string_t.
Index: Makefile.in
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/Makefile.in,v
retrieving revision 1.151
diff -c -p -r1.151 Makefile.in
*** Makefile.in 1998/07/09 22:55:40 1.151
--- Makefile.in 1998/07/20 01:15:46
*************** OBJS = toplev.o version.o tree.o print-t
*** 641,647 ****
regclass.o local-alloc.o global.o reload.o reload1.o caller-save.o gcse.o \
insn-peep.o reorg.o $(SCHED_PREFIX)sched.o final.o recog.o reg-stack.o \
insn-opinit.o insn-recog.o insn-extract.o insn-output.o insn-emit.o \
! profile.o insn-attrtab.o $(out_object_file) getpwd.o $(EXTRA_OBJS) convert.o
# GEN files are listed separately, so they can be built before doing parallel
# makes for cc1 or cc1plus. Otherwise sequent parallel make attempts to load
--- 641,648 ----
regclass.o local-alloc.o global.o reload.o reload1.o caller-save.o gcse.o \
insn-peep.o reorg.o $(SCHED_PREFIX)sched.o final.o recog.o reg-stack.o \
insn-opinit.o insn-recog.o insn-extract.o insn-output.o insn-emit.o \
! profile.o insn-attrtab.o $(out_object_file) getpwd.o $(EXTRA_OBJS) convert.o \
! dyn-string.o
# GEN files are listed separately, so they can be built before doing parallel
# makes for cc1 or cc1plus. Otherwise sequent parallel make attempts to load
*************** dwarfout.o : dwarfout.c $(CONFIG_H) syst
*** 1413,1419 ****
flags.h insn-config.h reload.h output.h defaults.h toplev.h dwarfout.h
dwarf2out.o : dwarf2out.c $(CONFIG_H) system.h $(TREE_H) $(RTL_H) dwarf2.h \
flags.h insn-config.h reload.h output.h defaults.h \
! hard-reg-set.h $(REGS_H) $(EXPR_H) toplev.h dwarf2out.h
xcoffout.o : xcoffout.c $(CONFIG_H) system.h $(TREE_H) $(RTL_H) xcoffout.h \
flags.h toplev.h output.h dbxout.h
emit-rtl.o : emit-rtl.c $(CONFIG_H) system.h $(RTL_H) $(TREE_H) flags.h \
--- 1414,1420 ----
flags.h insn-config.h reload.h output.h defaults.h toplev.h dwarfout.h
dwarf2out.o : dwarf2out.c $(CONFIG_H) system.h $(TREE_H) $(RTL_H) dwarf2.h \
flags.h insn-config.h reload.h output.h defaults.h \
! hard-reg-set.h $(REGS_H) $(EXPR_H) toplev.h dwarf2out.h dyn-string.h
xcoffout.o : xcoffout.c $(CONFIG_H) system.h $(TREE_H) $(RTL_H) xcoffout.h \
flags.h toplev.h output.h dbxout.h
emit-rtl.o : emit-rtl.c $(CONFIG_H) system.h $(RTL_H) $(TREE_H) flags.h \
*************** recog.o : recog.c $(CONFIG_H) system.h $
*** 1489,1494 ****
--- 1490,1496 ----
insn-flags.h insn-codes.h real.h
reg-stack.o : reg-stack.c $(CONFIG_H) system.h $(RTL_H) $(TREE_H) \
$(REGS_H) hard-reg-set.h flags.h insn-config.h insn-flags.h toplev.h
+ dyn-string.o: dyn-string.c dyn-string.h $(CONFIG_H) system.h gansidecl.h
$(out_object_file): $(out_file) $(CONFIG_H) $(TREE_H) \
$(RTL_H) $(REGS_H) hard-reg-set.h real.h insn-config.h conditions.h \
Index: dyn-string.h
===================================================================
RCS file: dyn-string.h
diff -N dyn-string.h
*** /dev/null Mon Dec 31 20:00:00 1979
--- dyn-string.h Sun Jul 19 18:15:46 1998
***************
*** 0 ****
--- 1,31 ----
+ /* An abstract string datatype.
+ Copyright (C) 1998 Free Software Foundation, Inc.
+ Contributed by Mark Mitchell (mark@markmitchell.com).
+
+ This file is part of GNU CC.
+
+ GNU CC is free software; you can redistribute it and/or modify it
+ under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU CC is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU CC; see the file COPYING. If not, write to the Free
+ Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+ typedef struct dyn_string
+ {
+ int allocated; /* The amount of space allocated for the string. */
+ int length; /* The actual length of the string. */
+ char *s; /* The string itself, NUL-terminated. */
+ }* dyn_string_t;
+
+ extern dyn_string_t dyn_string_new PROTO((int));
+ extern void dyn_string_delete PROTO((dyn_string_t));
+ extern dyn_string_t dyn_string_append PROTO((dyn_string_t, char*));
+ extern dyn_string_t dyn_string_resize PROTO((dyn_string_t, int));
Index: dyn-string.c
===================================================================
RCS file: dyn-string.c
diff -N dyn-string.c
*** /dev/null Mon Dec 31 20:00:00 1979
--- dyn-string.c Sun Jul 19 18:27:36 1998
***************
*** 0 ****
--- 1,86 ----
+ /* An abstract string datatype.
+ Copyright (C) 1998 Free Software Foundation, Inc.
+ Contributed by Mark Mitchell (mark@markmitchell.com).
+
+ This file is part of GNU CC.
+
+ GNU CC is free software; you can redistribute it and/or modify it
+ under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU CC is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU CC; see the file COPYING. If not, write to the Free
+ Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
+
+ #include "config.h"
+ #include "system.h"
+ #include "gansidecl.h"
+ #include "dyn-string.h"
+
+ extern char* xmalloc ();
+ extern char* xrealloc ();
+
+ dyn_string_t dyn_string_new (space)
+ int space;
+ {
+ dyn_string_t result = (dyn_string_t) xmalloc (sizeof (struct dyn_string));
+
+ if (space == 0)
+ /* We need at least one byte in which to store the terminating
+ NUL. */
+ space = 1;
+
+ result->allocated = space;
+ result->s = (char*) xmalloc (space);
+ result->length = 0;
+ result->s[0] = '\0';
+
+ return result;
+ }
+
+
+ void dyn_string_delete (ds)
+ dyn_string_t ds;
+ {
+ free (ds->s);
+ free (ds);
+ }
+
+
+ dyn_string_t dyn_string_append (ds, s)
+ dyn_string_t ds;
+ char *s;
+ {
+ int len = strlen (s);
+ dyn_string_resize (ds, ds->length + len + 1 /* '\0' */);
+ strcpy (ds->s + ds->length, s);
+ ds->length += len;
+
+ return ds;
+ }
+
+
+ dyn_string_t dyn_string_resize (ds, space)
+ dyn_string_t ds;
+ int space;
+ {
+ int new_allocated = ds->allocated;
+
+ while (space > new_allocated)
+ new_allocated *= 2;
+
+ if (new_allocated != ds->allocated)
+ {
+ /* We actually need more space. */
+ ds->allocated = new_allocated;
+ ds->s = xrealloc (ds->s, ds->allocated);
+ }
+
+ return ds;
+ }
Index: dwarf2out.c
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/dwarf2out.c,v
retrieving revision 1.62
diff -c -p -r1.62 dwarf2out.c
*** dwarf2out.c 1998/06/29 21:39:39 1.62
--- dwarf2out.c 1998/07/20 01:16:34
*************** the Free Software Foundation, 675 Mass A
*** 42,47 ****
--- 42,48 ----
#include "dwarf2.h"
#include "dwarf2out.h"
#include "toplev.h"
+ #include "dyn-string.h"
/* We cannot use <assert.h> in GCC source, since that would include
GCC's assert.h, which may not be compatible with the host compiler. */
*************** static tree dwarf_last_decl;
*** 2374,2380 ****
/* Forward declarations for functions defined in this file. */
! static void addr_const_to_string PROTO((char *, rtx));
static char *addr_to_string PROTO((rtx));
static int is_pseudo_reg PROTO((rtx));
static tree type_main_variant PROTO((tree));
--- 2375,2381 ----
/* Forward declarations for functions defined in this file. */
! static void addr_const_to_string PROTO((dyn_string_t, rtx));
static char *addr_to_string PROTO((rtx));
static int is_pseudo_reg PROTO((rtx));
static tree type_main_variant PROTO((tree));
*************** static char text_end_label[MAX_ARTIFICIA
*** 2639,2647 ****
#define ASM_NAME_TO_STRING(STR, NAME) \
do { \
if ((NAME)[0] == '*') \
! strcpy (STR, NAME+1); \
else \
! strcpy (STR, NAME); \
} \
while (0)
#endif
--- 2640,2648 ----
#define ASM_NAME_TO_STRING(STR, NAME) \
do { \
if ((NAME)[0] == '*') \
! dyn_string_append (STR, NAME + 1); \
else \
! dyn_string_append (STR, NAME); \
} \
while (0)
#endif
*************** static char text_end_label[MAX_ARTIFICIA
*** 2654,2703 ****
static void
addr_const_to_string (str, x)
! char *str;
rtx x;
{
char buf1[256];
- char buf2[256];
restart:
- str[0] = '\0';
switch (GET_CODE (x))
{
case PC:
if (flag_pic)
! strcat (str, ",");
else
abort ();
break;
case SYMBOL_REF:
! ASM_NAME_TO_STRING (buf1, XSTR (x, 0));
! strcat (str, buf1);
break;
case LABEL_REF:
ASM_GENERATE_INTERNAL_LABEL (buf1, "L", CODE_LABEL_NUMBER (XEXP (x, 0)));
! ASM_NAME_TO_STRING (buf2, buf1);
! strcat (str, buf2);
break;
case CODE_LABEL:
ASM_GENERATE_INTERNAL_LABEL (buf1, "L", CODE_LABEL_NUMBER (x));
! ASM_NAME_TO_STRING (buf2, buf1);
! strcat (str, buf2);
break;
case CONST_INT:
sprintf (buf1, HOST_WIDE_INT_PRINT_DEC, INTVAL (x));
! strcat (str, buf1);
break;
case CONST:
/* This used to output parentheses around the expression, but that does
not work on the 386 (either ATT or BSD assembler). */
! addr_const_to_string (buf1, XEXP (x, 0));
! strcat (str, buf1);
break;
case CONST_DOUBLE:
--- 2655,2698 ----
static void
addr_const_to_string (str, x)
! dyn_string_t str;
rtx x;
{
char buf1[256];
restart:
switch (GET_CODE (x))
{
case PC:
if (flag_pic)
! dyn_string_append (str, ",");
else
abort ();
break;
case SYMBOL_REF:
! ASM_NAME_TO_STRING (str, XSTR (x, 0));
break;
case LABEL_REF:
ASM_GENERATE_INTERNAL_LABEL (buf1, "L", CODE_LABEL_NUMBER (XEXP (x, 0)));
! ASM_NAME_TO_STRING (str, buf1);
break;
case CODE_LABEL:
ASM_GENERATE_INTERNAL_LABEL (buf1, "L", CODE_LABEL_NUMBER (x));
! ASM_NAME_TO_STRING (str, buf1);
break;
case CONST_INT:
sprintf (buf1, HOST_WIDE_INT_PRINT_DEC, INTVAL (x));
! dyn_string_append (str, buf1);
break;
case CONST:
/* This used to output parentheses around the expression, but that does
not work on the 386 (either ATT or BSD assembler). */
! addr_const_to_string (str, XEXP (x, 0));
break;
case CONST_DOUBLE:
*************** restart:
*** 2712,2718 ****
else
sprintf (buf1, HOST_WIDE_INT_PRINT_DEC,
CONST_DOUBLE_LOW (x));
! strcat (str, buf1);
}
else
/* We can't handle floating point constants; PRINT_OPERAND must
--- 2707,2713 ----
else
sprintf (buf1, HOST_WIDE_INT_PRINT_DEC,
CONST_DOUBLE_LOW (x));
! dyn_string_append (str, buf1);
}
else
/* We can't handle floating point constants; PRINT_OPERAND must
*************** restart:
*** 2724,2746 ****
/* Some assemblers need integer constants to appear last (eg masm). */
if (GET_CODE (XEXP (x, 0)) == CONST_INT)
{
! addr_const_to_string (buf1, XEXP (x, 1));
! strcat (str, buf1);
if (INTVAL (XEXP (x, 0)) >= 0)
! strcat (str, "+");
! addr_const_to_string (buf1, XEXP (x, 0));
! strcat (str, buf1);
}
else
{
! addr_const_to_string (buf1, XEXP (x, 0));
! strcat (str, buf1);
if (INTVAL (XEXP (x, 1)) >= 0)
! strcat (str, "+");
! addr_const_to_string (buf1, XEXP (x, 1));
! strcat (str, buf1);
}
break;
--- 2719,2737 ----
/* Some assemblers need integer constants to appear last (eg masm). */
if (GET_CODE (XEXP (x, 0)) == CONST_INT)
{
! addr_const_to_string (str, XEXP (x, 1));
if (INTVAL (XEXP (x, 0)) >= 0)
! dyn_string_append (str, "+");
! addr_const_to_string (str, XEXP (x, 0));
}
else
{
! addr_const_to_string (str, XEXP (x, 0));
if (INTVAL (XEXP (x, 1)) >= 0)
! dyn_string_append (str, "+");
! addr_const_to_string (str, XEXP (x, 1));
}
break;
*************** restart:
*** 2751,2778 ****
if (GET_CODE (x) != MINUS)
goto restart;
! addr_const_to_string (buf1, XEXP (x, 0));
! strcat (str, buf1);
! strcat (str, "-");
if (GET_CODE (XEXP (x, 1)) == CONST_INT
&& INTVAL (XEXP (x, 1)) < 0)
{
! strcat (str, ASM_OPEN_PAREN);
! addr_const_to_string (buf1, XEXP (x, 1));
! strcat (str, buf1);
! strcat (str, ASM_CLOSE_PAREN);
}
else
! {
! addr_const_to_string (buf1, XEXP (x, 1));
! strcat (str, buf1);
! }
break;
case ZERO_EXTEND:
case SIGN_EXTEND:
! addr_const_to_string (buf1, XEXP (x, 0));
! strcat (str, buf1);
break;
default:
--- 2742,2763 ----
if (GET_CODE (x) != MINUS)
goto restart;
! addr_const_to_string (str, XEXP (x, 0));
! dyn_string_append (str, "-");
if (GET_CODE (XEXP (x, 1)) == CONST_INT
&& INTVAL (XEXP (x, 1)) < 0)
{
! dyn_string_append (str, ASM_OPEN_PAREN);
! addr_const_to_string (str, XEXP (x, 1));
! dyn_string_append (str, ASM_CLOSE_PAREN);
}
else
! addr_const_to_string (str, XEXP (x, 1));
break;
case ZERO_EXTEND:
case SIGN_EXTEND:
! addr_const_to_string (str, XEXP (x, 0));
break;
default:
*************** static char *
*** 2787,2795 ****
addr_to_string (x)
rtx x;
{
! char buf[1024];
! addr_const_to_string (buf, x);
! return xstrdup (buf);
}
/* Test if rtl node points to a pseudo register. */
--- 2772,2787 ----
addr_to_string (x)
rtx x;
{
! dyn_string_t ds = dyn_string_new (256);
! char* s;
!
! addr_const_to_string (ds, x);
!
! /* Return the dynamically allocated string, but free the
! dyn_string_t itself. */
! s = ds->s;
! free (ds);
! return s;
}
/* Test if rtl node points to a pseudo register. */