* Makefile.in (VERSION): Bump to 4.7.4.

* Makefile.in (SFILES_MAINDIR):  Add typeprint.c, c-typeprint.c,
	  m2-typeprint.c, c-valprint.c cp-valprint.c m2-valprint.c.
	* Makefile.in (HFILES):  Add valprint.h.
	* Makefile.in (OBS):  Add typeprint.o, c-typeprint.o,
	  m2-typeprint.o, c-valprint.o, cp-valprint.o m2-valprint.o.
	* typeprint.c, typeprint.h:  New files for language independent
	  type printing functions.
	* c-typeprint.c, m2-typeprint.c:  New files for language dependent
	  type printing functions and definitions.
	* valprint.h:  New include file for language independent value
	  printing definitions.
	* c-valprint.c, cp-valprint.c, m2-valprint.c:  New files for language
	  dependent value printing functions.
	* c-exp.y (production ptype):  Add range_type variable and use new
	  create_range_type function.
	* c-exp.y (tokentab2, tokentab3), c-lang.c (c_op_print_tab),
	  infcmd.c (path_var_name), language.c (unk_op_print_tab),
	  m2-lang.c (m2_op_print_tab):  Change from ANSI-obsolescent
	  "const static" to ANSI-conformant "static const".
	* c-exp.y (c_create_fundamental_type):  Remove unused nbytes.
	* c-exp.y (c_language_defn, cplus_language_defn):  Add c_print_type,
	  and c_val_print.
	* c-lang.h (c_print_type, c_val_print):  Add prototypes.
	* coffread.c (decode_type):  Add range_type variable and call to
	  new create_range_type function.
	* complaints.c (complain):  Remove unused val variable.
	* complaints.c (_initialize_complaints):  Make it void.
	* convex-tdep.c (value_of_trapped_internalvar):  Add range_type
	  variable and call new create_range_type function.
	* defs.h (enum val_prettyprint):  Move enum from value.h to here
	  so we can avoid having to include value.h just for prototypes that
	  need the enum (thanks ANSI).
	* dwarfread.c (struct_type):  Local anonymous_size variable is
	  only used if !BITS_BIG_ENDIAN.
	* dwarfread.c (decode_subscript_data_item):  Add rangetype
	  variable and call new create_range_type function.
	* elfread.c (elf_symfile_read):  Remove unused dbx and text_sect
	  variables.
	* eval.c (evaluate_subexp):  Remove unused local variable name
	  and the statement with no side effects that initializes it.
	* expprint.c (print_subexp):  Change local_printstr to
	  LA_PRINT_STRING.
	* gdbtypes.c (create_range_type):  New function that creates
	  a range type using code fragments from object file readers as
	  an example of what has to be initialized.
	* gdbtypes.c (create_array_type):  Removed index_type, low_bound,
	  and high_bound parameters, replaced with a single range_type
	  parameter.  Change function body to use passed in range_type
	  rather than handcrafting one.
	* gdbtypes.h (create_range_type):  Add prototype.
	* gdbtypes.h (create_array_type):  Change prototype parameters.
	* infrun.c (normal_stop):  Remove unused local variables tem and c.
	* infrun.c (hook_stop_stub):  Return 0 rather than random value.
	* language.c (unk_lang_print_type, unk_lang_val_print):  Add
	  stub functions that call error if called.
	* language.c (unknown_language_defn, auto_language_defn,
	  local_language_defn):  Add initializers unk_lang_print_type and
	  unk_lang_val_print.
	* language.h (struct language_defn):  Reformat for larger
	  comments, add la_print_type and la_val_print members.  Add
	  LA_PRINT_TYPE and LA_VAL_PRINT macros.  Change local_printchar
	  to LA_PRINT_CHAR and local_printstr to LA_PRINT_STRING.
	* m2-lang.c (m2_create_fundamental_type):  Remove unused local
	  variable nbytes.
	* m2-lang.c (m2_language_defn):  Add initializers m2_print_type
	  and m2_val_print.
	* m2-lang.h (m2_print_type, m2_val_print):  Add prototypes.
	* main.c (execute_command): Remove unused local variable cmdlines.
	* main.c (echo_command), stabsread.c (read_type), printcmd.c
	  (clear_displays), symmisc.c (block_depth), values.c
	  (clear_value_history):
	  Make testing of truth value of assignment result explicit.
	* mipsread.c (upgrade_type):  Update FIXME to include future use
	  of create_range_type.
	* printcmd.c (ptype_command, ptype_eval, whatis_command,
	  whatis_exp, maintenance_print_type):  Move prototypes and functions
	  to new typeprint.c.
	* printcmd.c (_initialize_printcmd):  Move add_com calls for
	  ptype_command and whatis_command to new typeprint.c.
	* ser-bsd.c (serial_open):  Remove unused variable sgttyb.
	* source.c (find_source_lines):  Local variable c only used
	  when LSEEK_NOT_LINEAR is defined.
	* stabsread.c (read_array_type):  Use new create_range_type
	  function.
	* stabsread.c (read_range_type):  Add new index_type variable and
	  call new create_range_type function rather than handcrafting
	  range types.
	* symmisc.c (type_print_1):  Change usages to LA_PRINT_TYPE.
	* symtab.c (typedef_print usages):  Use c_typedef_print, renamed.
	* symtab.c (type_print_base usages):  Use c_type_print_base.
	* symtab.c (type_print_varspec_prefix usages):  Use
	  c_type_print_varspec_prefix.
	* symtab.c (type_print_method_args usages):  Use
	  cp_type_print_method_args.
	* valprint.c:  Completely ripped apart and the fragments used
	  to create c-valprint.c, cp-valprint.c, m2-valprint.c, and
	  valprint.h.  Remaining stuff is language independent.
	* value.h (struct fn_field):  Forward declare for prototypes.
	* value.h (type_print_1):  Remove prototype.
	* value.h (enum val_prettyprint):  Moved to defs.h.
	* value.h (typedef_print):  Prototype renamed to c_typedef_print.
	* value.h (baseclass_offset):  Add prototype.
	**** start-sanitize-chill ****
	* Makefile.in (SFILES_MAINDIR):  Add ch-typeprint.c, ch-valprint.c.
	* Makefile.in (OBS):  Add ch-typeprint.o, ch-valprint.o.
	* ch-typeprint.c:  New file for language dependent type printing.
	* ch-valprint.c:  New file for language dependent value printing.
	* ch-exp.y (parse_number):  Remove prototype and stub function.
	* ch-exp.y (decode_integer_literal):  Removed unused digits and
	  temp variables.
	* ch-exp.y (convert_float):  Completely ifdef out for now.
	* ch-exp.y (tokentab2, tokentab3, tokentab4, tokentab5),
	  ch-lang.c (chill_op_print_tab):
	  Change from ANSI-obsolescent "const static" to ANSI-conformant
	  "static const".
	* ch-exp.y (yylex):  Add unhandled storage class enumeration
	  literals to switch statement for completeness.
	* ch-lang.c (chill_create_fundamental_types):  Remove unused
	  nbytes variable.  Change dummy type to 2 bytes to match int.
	  Handle FT_VOID types gratuituously added to chill DWARF by
	  compiler.  Change FT_CHAR case to generate an TYPE_CODE_CHAR
	  type rather than a one byte TYPE_CODE_INT type.
	* ch-lang.c (chill_language_defn):  Add chill_print_type and
	  chill_val_print.
	* ch-lang.h (chill_print_type, chill_val_print):  Add prototypes.
	**** end-sanitize-chill ****
This commit is contained in:
Fred Fish 1992-12-18 20:21:32 +00:00
parent 6c1cabd48f
commit a8a69e6332
45 changed files with 3385 additions and 2130 deletions

View file

@ -16,7 +16,7 @@
Do-first:
if ( echo $* | grep keep\-chill > /dev/null ) ; then
keep_these_too="ch-exp.y ch-lang.c ch-lang.h"
keep_these_too="ch-exp.y ch-lang.c ch-lang.h ch-typeprint.c ch-valprint.c"
fi
# All files listed between the "Things-to-keep:" line and the
@ -57,6 +57,8 @@ buildsym.h
c-exp.y
c-lang.c
c-lang.h
c-typeprint.c
c-valprint.c
call-cmds.h
coffread.c
command.c
@ -74,6 +76,7 @@ copying.c
core.c
coredep.c
corelow.c
cp-valprint.c
createtags
dbxread.c
defs.h
@ -135,6 +138,8 @@ language.h
m2-exp.y
m2-lang.c
m2-lang.h
m2-typeprint.c
m2-valprint.c
m68k-pinsn.c
m68k-stub.c
m68k-tdep.c
@ -298,6 +303,8 @@ tm-umax.h
tm-vax.h
tm-vx68.h
tm-vx960.h
typeprint.c
typeprint.h
ultra3-nat.c
ultra3-xdep.c
umax-xdep.c
@ -305,6 +312,7 @@ utils.c
valarith.c
valops.c
valprint.c
valprint.h
value.h
values.c
vax-pinsn.c
@ -400,6 +408,10 @@ else
-e 's/ch-lang.h//g' \
-e 's/ch-lang.c//g' \
-e 's/ch-lang.o//g' \
-e 's/ch-typeprint.c//g' \
-e 's/ch-typeprint.o//g' \
-e 's/ch-valprint.c//g' \
-e 's/ch-valprint.o//g' \
< Makefile.in > new
if [ -n "${safe}" -a ! -f .Recover/Makefile.in ] ; then
echo Caching Makefile.in in .Recover...

View file

@ -1,3 +1,133 @@
Fri Dec 18 10:32:25 1992 Fred Fish (fnf@cygnus.com)
* Makefile.in (VERSION): Bump to 4.7.4.
* Makefile.in (SFILES_MAINDIR): Add typeprint.c, c-typeprint.c,
m2-typeprint.c, c-valprint.c cp-valprint.c m2-valprint.c.
* Makefile.in (HFILES): Add valprint.h.
* Makefile.in (OBS): Add typeprint.o, c-typeprint.o,
m2-typeprint.o, c-valprint.o, cp-valprint.o m2-valprint.o.
* typeprint.c, typeprint.h: New files for language independent
type printing functions.
* c-typeprint.c, m2-typeprint.c: New files for language dependent
type printing functions and definitions.
* valprint.h: New include file for language independent value
printing definitions.
* c-valprint.c, cp-valprint.c, m2-valprint.c: New files for language
dependent value printing functions.
* c-exp.y (production ptype): Add range_type variable and use new
create_range_type function.
* c-exp.y (tokentab2, tokentab3), c-lang.c (c_op_print_tab),
infcmd.c (path_var_name), language.c (unk_op_print_tab),
m2-lang.c (m2_op_print_tab): Change from ANSI-obsolescent
"const static" to ANSI-conformant "static const".
* c-exp.y (c_create_fundamental_type): Remove unused nbytes.
* c-exp.y (c_language_defn, cplus_language_defn): Add c_print_type,
and c_val_print.
* c-lang.h (c_print_type, c_val_print): Add prototypes.
* coffread.c (decode_type): Add range_type variable and call to
new create_range_type function.
* complaints.c (complain): Remove unused val variable.
* complaints.c (_initialize_complaints): Make it void.
* convex-tdep.c (value_of_trapped_internalvar): Add range_type
variable and call new create_range_type function.
* defs.h (enum val_prettyprint): Move enum from value.h to here
so we can avoid having to include value.h just for prototypes that
need the enum (thanks ANSI).
* dwarfread.c (struct_type): Local anonymous_size variable is
only used if !BITS_BIG_ENDIAN.
* dwarfread.c (decode_subscript_data_item): Add rangetype
variable and call new create_range_type function.
* elfread.c (elf_symfile_read): Remove unused dbx and text_sect
variables.
* eval.c (evaluate_subexp): Remove unused local variable name
and the statement with no side effects that initializes it.
* expprint.c (print_subexp): Change local_printstr to
LA_PRINT_STRING.
* gdbtypes.c (create_range_type): New function that creates
a range type using code fragments from object file readers as
an example of what has to be initialized.
* gdbtypes.c (create_array_type): Removed index_type, low_bound,
and high_bound parameters, replaced with a single range_type
parameter. Change function body to use passed in range_type
rather than handcrafting one.
* gdbtypes.h (create_range_type): Add prototype.
* gdbtypes.h (create_array_type): Change prototype parameters.
* infrun.c (normal_stop): Remove unused local variables tem and c.
* infrun.c (hook_stop_stub): Return 0 rather than random value.
* language.c (unk_lang_print_type, unk_lang_val_print): Add
stub functions that call error if called.
* language.c (unknown_language_defn, auto_language_defn,
local_language_defn): Add initializers unk_lang_print_type and
unk_lang_val_print.
* language.h (struct language_defn): Reformat for larger
comments, add la_print_type and la_val_print members. Add
LA_PRINT_TYPE and LA_VAL_PRINT macros. Change local_printchar
to LA_PRINT_CHAR and local_printstr to LA_PRINT_STRING.
* m2-lang.c (m2_create_fundamental_type): Remove unused local
variable nbytes.
* m2-lang.c (m2_language_defn): Add initializers m2_print_type
and m2_val_print.
* m2-lang.h (m2_print_type, m2_val_print): Add prototypes.
* main.c (execute_command): Remove unused local variable cmdlines.
* main.c (echo_command), stabsread.c (read_type), printcmd.c
(clear_displays), symmisc.c (block_depth), values.c
(clear_value_history):
Make testing of truth value of assignment result explicit.
* mipsread.c (upgrade_type): Update FIXME to include future use
of create_range_type.
* printcmd.c (ptype_command, ptype_eval, whatis_command,
whatis_exp, maintenance_print_type): Move prototypes and functions
to new typeprint.c.
* printcmd.c (_initialize_printcmd): Move add_com calls for
ptype_command and whatis_command to new typeprint.c.
* ser-bsd.c (serial_open): Remove unused variable sgttyb.
* source.c (find_source_lines): Local variable c only used
when LSEEK_NOT_LINEAR is defined.
* stabsread.c (read_array_type): Use new create_range_type
function.
* stabsread.c (read_range_type): Add new index_type variable and
call new create_range_type function rather than handcrafting
range types.
* symmisc.c (type_print_1): Change usages to LA_PRINT_TYPE.
* symtab.c (typedef_print usages): Use c_typedef_print, renamed.
* symtab.c (type_print_base usages): Use c_type_print_base.
* symtab.c (type_print_varspec_prefix usages): Use
c_type_print_varspec_prefix.
* symtab.c (type_print_method_args usages): Use
cp_type_print_method_args.
* valprint.c: Completely ripped apart and the fragments used
to create c-valprint.c, cp-valprint.c, m2-valprint.c, and
valprint.h. Remaining stuff is language independent.
* value.h (struct fn_field): Forward declare for prototypes.
* value.h (type_print_1): Remove prototype.
* value.h (enum val_prettyprint): Moved to defs.h.
* value.h (typedef_print): Prototype renamed to c_typedef_print.
* value.h (baseclass_offset): Add prototype.
**** start-sanitize-chill ****
* Makefile.in (SFILES_MAINDIR): Add ch-typeprint.c, ch-valprint.c.
* Makefile.in (OBS): Add ch-typeprint.o, ch-valprint.o.
* ch-typeprint.c: New file for language dependent type printing.
* ch-valprint.c: New file for language dependent value printing.
* ch-exp.y (parse_number): Remove prototype and stub function.
* ch-exp.y (decode_integer_literal): Removed unused digits and
temp variables.
* ch-exp.y (convert_float): Completely ifdef out for now.
* ch-exp.y (tokentab2, tokentab3, tokentab4, tokentab5),
ch-lang.c (chill_op_print_tab):
Change from ANSI-obsolescent "const static" to ANSI-conformant
"static const".
* ch-exp.y (yylex): Add unhandled storage class enumeration
literals to switch statement for completeness.
* ch-lang.c (chill_create_fundamental_types): Remove unused
nbytes variable. Change dummy type to 2 bytes to match int.
Handle FT_VOID types gratuituously added to chill DWARF by
compiler. Change FT_CHAR case to generate an TYPE_CODE_CHAR
type rather than a one byte TYPE_CODE_INT type.
* ch-lang.c (chill_language_defn): Add chill_print_type and
chill_val_print.
* ch-lang.h (chill_print_type, chill_val_print): Add prototypes.
**** end-sanitize-chill ****
Thu Dec 17 00:44:57 1992 John Gilmore (gnu@cygnus.com)
Eliminate uses of NAMES_HAVE_UNDERSCORE, using

View file

@ -166,7 +166,7 @@ CDEPS = ${XM_CDEPS} ${TM_CDEPS} ${NAT_CDEPS} \
ADD_FILES = ${REGEX} ${ALLOCA} ${XM_ADD_FILES} ${TM_ADD_FILES} ${NAT_ADD_FILES}
ADD_DEPS = ${REGEX1} ${ALLOCA1} ${XM_ADD_FILES} ${TM_ADD_FILES} ${NAT_ADD_FILES}
VERSION = 4.7.3
VERSION = 4.7.4
DIST=gdb
LINT=/usr/5bin/lint
@ -202,7 +202,8 @@ SFILES_MAINDIR = \
dbxread.c coffread.c elfread.c dwarfread.c xcoffread.c stabsread.c \
ieee-float.c language.c parse.c buildsym.c objfiles.c \
minsyms.c mipsread.c maint.c ch-exp.y c-lang.c ch-lang.c m2-lang.c \
complaints.c
complaints.c typeprint.c c-typeprint.c ch-typeprint.c m2-typeprint.c \
c-valprint.c cp-valprint.c ch-valprint.c m2-valprint.c
# Source files in subdirectories (which will be handled separately by
# 'make gdb.tar.Z').
@ -263,7 +264,8 @@ HFILES= breakpoint.h buildsym.h call-cmds.h command.h defs.h \
nm-sun2.h nm-sun3.h nm-sun386.h nm-sun4os4.h nm-trash.h \
nm-ultra3.h nm-hppab.h nm-hppah.h nm-umax.h nm-sysv4.h \
nm-apollo68b.h nm-apollo68v.h nm-vax.h nm-hp300bsd.h \
nm-hp300hpux.h c-lang.h ch-lang.h m2-lang.h complaints.h
nm-hp300hpux.h c-lang.h ch-lang.h m2-lang.h complaints.h \
valprint.h
REMOTE_EXAMPLES = m68k-stub.c i386-stub.c sparc-stub.c rem-multi.shar
@ -303,7 +305,9 @@ OBS = version.o main.o blockframe.o breakpoint.o findvar.o stack.o source.o \
ieee-float.o putenv.o parse.o language.o $(YYOBJ) \
buildsym.o objfiles.o minsyms.o maint.o demangle.o \
dbxread.o coffread.o elfread.o dwarfread.o xcoffread.o mipsread.o \
stabsread.o core.o c-lang.o ch-lang.o m2-lang.o complaints.o
stabsread.o core.o c-lang.o ch-lang.o m2-lang.o complaints.o \
typeprint.o c-typeprint.o ch-typeprint.o m2-typeprint.o \
c-valprint.o cp-valprint.o ch-valprint.o m2-valprint.o
RAPP_OBS = rgdb.o rudp.o rserial.o serial.o udp.o $(XDEPFILES)

View file

@ -705,6 +705,7 @@ ptype : typebase
int done = 0;
int array_size;
struct type *follow_type = $1;
struct type *range_type;
while (!done)
switch (pop_type ())
@ -721,10 +722,15 @@ ptype : typebase
case tp_array:
array_size = pop_type_int ();
if (array_size != -1)
follow_type =
create_array_type ((struct type *) NULL,
follow_type, builtin_type_int,
0, array_size - 1);
{
range_type =
create_range_type ((struct type *) NULL,
builtin_type_int, 0,
array_size - 1);
follow_type =
create_array_type ((struct type *) NULL,
follow_type, range_type);
}
else
follow_type = lookup_pointer_type (follow_type);
break;
@ -1039,13 +1045,13 @@ struct token
enum exp_opcode opcode;
};
const static struct token tokentab3[] =
static const struct token tokentab3[] =
{
{">>=", ASSIGN_MODIFY, BINOP_RSH},
{"<<=", ASSIGN_MODIFY, BINOP_LSH}
};
const static struct token tokentab2[] =
static const struct token tokentab2[] =
{
{"+=", ASSIGN_MODIFY, BINOP_ADD},
{"-=", ASSIGN_MODIFY, BINOP_SUB},

View file

@ -211,7 +211,6 @@ c_create_fundamental_type (objfile, typeid)
int typeid;
{
register struct type *type = NULL;
register int nbytes;
switch (typeid)
{
@ -328,7 +327,7 @@ c_create_fundamental_type (objfile, typeid)
/* Table mapping opcodes into strings for printing operators
and precedences of the operators. */
const static struct op_print c_op_print_tab[] =
static const struct op_print c_op_print_tab[] =
{
{",", BINOP_COMMA, PREC_COMMA, 0},
{"=", BINOP_ASSIGN, PREC_ASSIGN, 1},
@ -418,6 +417,8 @@ const struct language_defn c_language_defn = {
c_printchar, /* Print a character constant */
c_printstr, /* Function to print string constant */
c_create_fundamental_type, /* Create fundamental type in this language */
c_print_type, /* Print a type using appropriate syntax */
c_val_print, /* Print a value using appropriate syntax */
&BUILTIN_TYPE_LONGEST, /* longest signed integral type */
&BUILTIN_TYPE_UNSIGNED_LONGEST,/* longest unsigned integral type */
&builtin_type_double, /* longest floating point type */ /*FIXME*/
@ -440,6 +441,8 @@ const struct language_defn cplus_language_defn = {
c_printchar, /* Print a character constant */
c_printstr, /* Function to print string constant */
c_create_fundamental_type, /* Create fundamental type in this language */
c_print_type, /* Print a type using appropriate syntax */
c_val_print, /* Print a value using appropriate syntax */
&BUILTIN_TYPE_LONGEST, /* longest signed integral type */
&BUILTIN_TYPE_UNSIGNED_LONGEST,/* longest unsigned integral type */
&builtin_type_double, /* longest floating point type */ /*FIXME*/

View file

@ -22,3 +22,10 @@ c_parse PARAMS ((void)); /* Defined in c-exp.y */
extern void
c_error PARAMS ((char *)); /* Defined in c-exp.y */
extern void /* Defined in c-typeprint.c */
c_print_type PARAMS ((struct type *, char *, FILE *, int, int));
extern int
c_val_print PARAMS ((struct type *, char *, CORE_ADDR, FILE *, int, int,
int, enum val_prettyprint));

774
gdb/c-typeprint.c Normal file
View file

@ -0,0 +1,774 @@
/* Support for printing C and C++ types for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "obstack.h"
#include "bfd.h" /* Binary File Description */
#include "symtab.h"
#include "gdbtypes.h"
#include "expression.h"
#include "value.h"
#include "gdbcore.h"
#include "target.h"
#include "command.h"
#include "gdbcmd.h"
#include "language.h"
#include "demangle.h"
#include "c-lang.h"
#include "typeprint.h"
#include <string.h>
#include <errno.h>
extern int demangle; /* whether to print C++ syms raw or source-form */
static void
c_type_print_args PARAMS ((struct type *, FILE *));
static void
c_type_print_varspec_suffix PARAMS ((struct type *, FILE *, int, int, int));
static void
cp_type_print_derivation_info PARAMS ((FILE *, struct type *));
void
c_type_print_varspec_prefix PARAMS ((struct type *, FILE *, int, int));
void
c_type_print_base PARAMS ((struct type *, FILE *, int, int));
/* Print a description of a type in the format of a
typedef for the current language.
NEW is the new name for a type TYPE. */
void
c_typedef_print (type, new, stream)
struct type *type;
struct symbol *new;
FILE *stream;
{
switch (current_language->la_language)
{
#ifdef _LANG_c
case language_c:
case language_cplus:
fprintf_filtered(stream, "typedef ");
type_print(type,"",stream,0);
if(TYPE_NAME ((SYMBOL_TYPE (new))) == 0
|| 0 != strcmp (TYPE_NAME ((SYMBOL_TYPE (new))),
SYMBOL_NAME (new)))
fprintf_filtered(stream, " %s", SYMBOL_NAME(new));
break;
#endif
#ifdef _LANG_m2
case language_m2:
fprintf_filtered(stream, "TYPE ");
if(!TYPE_NAME(SYMBOL_TYPE(new)) ||
strcmp (TYPE_NAME(SYMBOL_TYPE(new)),
SYMBOL_NAME(new)))
fprintf_filtered(stream, "%s = ", SYMBOL_NAME(new));
else
fprintf_filtered(stream, "<builtin> = ");
type_print(type,"",stream,0);
break;
#endif
/* start-sanitize-chill */
#ifdef _LANG_chill
case language_chill:
error ("Missing Chill support in function c_typedef_print."); /*FIXME*/
#endif
/* end-sanitize-chill */
default:
error("Language not supported.");
}
fprintf_filtered(stream, ";\n");
}
/* LEVEL is the depth to indent lines by. */
void
c_print_type (type, varstring, stream, show, level)
struct type *type;
char *varstring;
FILE *stream;
int show;
int level;
{
register enum type_code code;
char *demangled = NULL;
int demangled_args;
c_type_print_base (type, stream, show, level);
code = TYPE_CODE (type);
if ((varstring != NULL && *varstring != '\0')
||
/* Need a space if going to print stars or brackets;
but not if we will print just a type name. */
((show > 0 || TYPE_NAME (type) == 0)
&&
(code == TYPE_CODE_PTR || code == TYPE_CODE_FUNC
|| code == TYPE_CODE_METHOD
|| code == TYPE_CODE_ARRAY
|| code == TYPE_CODE_MEMBER
|| code == TYPE_CODE_REF)))
fputs_filtered (" ", stream);
c_type_print_varspec_prefix (type, stream, show, 0);
/* See if the name has a C++ demangled equivalent, and if so, print that
instead. */
if (demangle)
{
demangled = cplus_demangle (varstring, DMGL_ANSI | DMGL_PARAMS);
}
fputs_filtered ((demangled != NULL) ? demangled : varstring, stream);
/* For demangled function names, we have the arglist as part of the name,
so don't print an additional pair of ()'s */
demangled_args = (demangled != NULL) && (code == TYPE_CODE_FUNC);
c_type_print_varspec_suffix (type, stream, show, 0, demangled_args);
if (demangled != NULL)
{
free (demangled);
}
}
/* Print the C++ method arguments ARGS to the file STREAM. */
void
cp_type_print_method_args (args, prefix, varstring, staticp, stream)
struct type **args;
char *prefix;
char *varstring;
int staticp;
FILE *stream;
{
int i;
fputs_demangled (prefix, stream, DMGL_ANSI | DMGL_PARAMS);
fputs_demangled (varstring, stream, DMGL_ANSI | DMGL_PARAMS);
fputs_filtered (" (", stream);
if (args && args[!staticp] && args[!staticp]->code != TYPE_CODE_VOID)
{
i = !staticp; /* skip the class variable */
while (1)
{
type_print (args[i++], "", stream, 0);
if (!args[i])
{
fprintf_filtered (stream, " ...");
break;
}
else if (args[i]->code != TYPE_CODE_VOID)
{
fprintf_filtered (stream, ", ");
}
else break;
}
}
fprintf_filtered (stream, ")");
}
/* If TYPE is a derived type, then print out derivation information.
Print only the actual base classes of this type, not the base classes
of the base classes. I.E. for the derivation hierarchy:
class A { int a; };
class B : public A {int b; };
class C : public B {int c; };
Print the type of class C as:
class C : public B {
int c;
}
Not as the following (like gdb used to), which is not legal C++ syntax for
derived types and may be confused with the multiple inheritance form:
class C : public B : public A {
int c;
}
In general, gdb should try to print the types as closely as possible to
the form that they appear in the source code. */
static void
cp_type_print_derivation_info (stream, type)
FILE *stream;
struct type *type;
{
char *name;
int i;
for (i = 0; i < TYPE_N_BASECLASSES (type); i++)
{
fputs_filtered (i == 0 ? ": " : ", ", stream);
fprintf_filtered (stream, "%s%s ",
BASETYPE_VIA_PUBLIC (type, i) ? "public" : "private",
BASETYPE_VIA_VIRTUAL(type, i) ? " virtual" : "");
name = type_name_no_tag (TYPE_BASECLASS (type, i));
fprintf_filtered (stream, "%s", name ? name : "(null)");
}
if (i > 0)
{
fputs_filtered (" ", stream);
}
}
/* Print any asterisks or open-parentheses needed before the
variable name (to describe its type).
On outermost call, pass 0 for PASSED_A_PTR.
On outermost call, SHOW > 0 means should ignore
any typename for TYPE and show its details.
SHOW is always zero on recursive calls. */
void
c_type_print_varspec_prefix (type, stream, show, passed_a_ptr)
struct type *type;
FILE *stream;
int show;
int passed_a_ptr;
{
char *name;
if (type == 0)
return;
if (TYPE_NAME (type) && show <= 0)
return;
QUIT;
switch (TYPE_CODE (type))
{
case TYPE_CODE_PTR:
c_type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 1);
fprintf_filtered (stream, "*");
break;
case TYPE_CODE_MEMBER:
if (passed_a_ptr)
fprintf_filtered (stream, "(");
c_type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 0);
fprintf_filtered (stream, " ");
name = type_name_no_tag (TYPE_DOMAIN_TYPE (type));
if (name)
fputs_filtered (name, stream);
else
c_type_print_base (TYPE_DOMAIN_TYPE (type), stream, 0, passed_a_ptr);
fprintf_filtered (stream, "::");
break;
case TYPE_CODE_METHOD:
if (passed_a_ptr)
fprintf (stream, "(");
c_type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 0);
if (passed_a_ptr)
{
fprintf_filtered (stream, " ");
c_type_print_base (TYPE_DOMAIN_TYPE (type), stream, 0, passed_a_ptr);
fprintf_filtered (stream, "::");
}
break;
case TYPE_CODE_REF:
c_type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 1);
fprintf_filtered (stream, "&");
break;
case TYPE_CODE_FUNC:
c_type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 0);
if (passed_a_ptr)
fprintf_filtered (stream, "(");
break;
case TYPE_CODE_ARRAY:
c_type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 0);
if (passed_a_ptr)
fprintf_filtered (stream, "(");
break;
case TYPE_CODE_UNDEF:
case TYPE_CODE_STRUCT:
case TYPE_CODE_UNION:
case TYPE_CODE_ENUM:
case TYPE_CODE_INT:
case TYPE_CODE_FLT:
case TYPE_CODE_VOID:
case TYPE_CODE_ERROR:
case TYPE_CODE_CHAR:
case TYPE_CODE_BOOL:
case TYPE_CODE_SET:
case TYPE_CODE_RANGE:
case TYPE_CODE_PASCAL_ARRAY:
/* These types need no prefix. They are listed here so that
gcc -Wall will reveal any types that haven't been handled. */
break;
}
}
static void
c_type_print_args (type, stream)
struct type *type;
FILE *stream;
{
int i;
struct type **args;
fprintf_filtered (stream, "(");
args = TYPE_ARG_TYPES (type);
if (args != NULL)
{
if (args[1] == NULL)
{
fprintf_filtered (stream, "...");
}
else
{
for (i = 1;
args[i] != NULL && args[i]->code != TYPE_CODE_VOID;
i++)
{
c_print_type (args[i], "", stream, -1, 0);
if (args[i+1] == NULL)
{
fprintf_filtered (stream, "...");
}
else if (args[i+1]->code != TYPE_CODE_VOID)
{
fprintf_filtered (stream, ",");
wrap_here (" ");
}
}
}
}
fprintf_filtered (stream, ")");
}
/* Print any array sizes, function arguments or close parentheses
needed after the variable name (to describe its type).
Args work like c_type_print_varspec_prefix. */
static void
c_type_print_varspec_suffix (type, stream, show, passed_a_ptr, demangled_args)
struct type *type;
FILE *stream;
int show;
int passed_a_ptr;
int demangled_args;
{
if (type == 0)
return;
if (TYPE_NAME (type) && show <= 0)
return;
QUIT;
switch (TYPE_CODE (type))
{
case TYPE_CODE_ARRAY:
if (passed_a_ptr)
fprintf_filtered (stream, ")");
fprintf_filtered (stream, "[");
if (TYPE_LENGTH (type) > 0 && TYPE_LENGTH (TYPE_TARGET_TYPE (type)) > 0)
fprintf_filtered (stream, "%d",
(TYPE_LENGTH (type)
/ TYPE_LENGTH (TYPE_TARGET_TYPE (type))));
fprintf_filtered (stream, "]");
c_type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0, 0, 0);
break;
case TYPE_CODE_MEMBER:
if (passed_a_ptr)
fprintf_filtered (stream, ")");
c_type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0, 0, 0);
break;
case TYPE_CODE_METHOD:
if (passed_a_ptr)
fprintf_filtered (stream, ")");
c_type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0, 0, 0);
if (passed_a_ptr)
{
c_type_print_args (type, stream);
}
break;
case TYPE_CODE_PTR:
case TYPE_CODE_REF:
c_type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0, 1, 0);
break;
case TYPE_CODE_FUNC:
c_type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0,
passed_a_ptr, 0);
if (passed_a_ptr)
fprintf_filtered (stream, ")");
if (!demangled_args)
fprintf_filtered (stream, "()");
break;
case TYPE_CODE_UNDEF:
case TYPE_CODE_STRUCT:
case TYPE_CODE_UNION:
case TYPE_CODE_ENUM:
case TYPE_CODE_INT:
case TYPE_CODE_FLT:
case TYPE_CODE_VOID:
case TYPE_CODE_ERROR:
case TYPE_CODE_CHAR:
case TYPE_CODE_BOOL:
case TYPE_CODE_SET:
case TYPE_CODE_RANGE:
case TYPE_CODE_PASCAL_ARRAY:
/* These types do not need a suffix. They are listed so that
gcc -Wall will report types that may not have been considered. */
break;
}
}
/* Print the name of the type (or the ultimate pointer target,
function value or array element), or the description of a
structure or union.
SHOW nonzero means don't print this type as just its name;
show its real definition even if it has a name.
SHOW zero means print just typename or struct tag if there is one
SHOW negative means abbreviate structure elements.
SHOW is decremented for printing of structure elements.
LEVEL is the depth to indent by.
We increase it for some recursive calls. */
void
c_type_print_base (type, stream, show, level)
struct type *type;
FILE *stream;
int show;
int level;
{
char *name;
register int i;
register int len;
register int lastval;
char *mangled_name;
char *demangled_name;
enum {s_none, s_public, s_private, s_protected} section_type;
QUIT;
wrap_here (" ");
if (type == NULL)
{
fputs_filtered ("<type unknown>", stream);
return;
}
/* When SHOW is zero or less, and there is a valid type name, then always
just print the type name directly from the type. */
if ((show <= 0) && (TYPE_NAME (type) != NULL))
{
fputs_filtered (TYPE_NAME (type), stream);
return;
}
switch (TYPE_CODE (type))
{
case TYPE_CODE_ARRAY:
case TYPE_CODE_PTR:
case TYPE_CODE_MEMBER:
case TYPE_CODE_REF:
case TYPE_CODE_FUNC:
case TYPE_CODE_METHOD:
c_type_print_base (TYPE_TARGET_TYPE (type), stream, show, level);
break;
case TYPE_CODE_STRUCT:
fprintf_filtered (stream,
HAVE_CPLUS_STRUCT (type) ? "class " : "struct ");
goto struct_union;
case TYPE_CODE_UNION:
fprintf_filtered (stream, "union ");
struct_union:
if ((name = type_name_no_tag (type)) != NULL)
{
fputs_filtered (name, stream);
fputs_filtered (" ", stream);
wrap_here (" ");
}
if (show < 0)
fprintf_filtered (stream, "{...}");
else
{
check_stub_type (type);
cp_type_print_derivation_info (stream, type);
fprintf_filtered (stream, "{\n");
if ((TYPE_NFIELDS (type) == 0) && (TYPE_NFN_FIELDS (type) == 0))
{
if (TYPE_FLAGS (type) & TYPE_FLAG_STUB)
fprintfi_filtered (level + 4, stream, "<incomplete type>\n");
else
fprintfi_filtered (level + 4, stream, "<no data fields>\n");
}
/* Start off with no specific section type, so we can print
one for the first field we find, and use that section type
thereafter until we find another type. */
section_type = s_none;
/* If there is a base class for this type,
do not print the field that it occupies. */
len = TYPE_NFIELDS (type);
for (i = TYPE_N_BASECLASSES (type); i < len; i++)
{
QUIT;
/* Don't print out virtual function table. */
if ((TYPE_FIELD_NAME (type, i))[5] == CPLUS_MARKER &&
!strncmp (TYPE_FIELD_NAME (type, i), "_vptr", 5))
continue;
/* If this is a C++ class we can print the various C++ section
labels. */
if (HAVE_CPLUS_STRUCT (type))
{
if (TYPE_FIELD_PROTECTED (type, i))
{
if (section_type != s_protected)
{
section_type = s_protected;
fprintfi_filtered (level + 2, stream,
"protected:\n");
}
}
else if (TYPE_FIELD_PRIVATE (type, i))
{
if (section_type != s_private)
{
section_type = s_private;
fprintfi_filtered (level + 2, stream, "private:\n");
}
}
else
{
if (section_type != s_public)
{
section_type = s_public;
fprintfi_filtered (level + 2, stream, "public:\n");
}
}
}
print_spaces_filtered (level + 4, stream);
if (TYPE_FIELD_STATIC (type, i))
{
fprintf_filtered (stream, "static ");
}
c_print_type (TYPE_FIELD_TYPE (type, i),
TYPE_FIELD_NAME (type, i),
stream, show - 1, level + 4);
if (!TYPE_FIELD_STATIC (type, i)
&& TYPE_FIELD_PACKED (type, i))
{
/* It is a bitfield. This code does not attempt
to look at the bitpos and reconstruct filler,
unnamed fields. This would lead to misleading
results if the compiler does not put out fields
for such things (I don't know what it does). */
fprintf_filtered (stream, " : %d",
TYPE_FIELD_BITSIZE (type, i));
}
fprintf_filtered (stream, ";\n");
}
/* If there are both fields and methods, put a space between. */
len = TYPE_NFN_FIELDS (type);
if (len && section_type != s_none)
fprintf_filtered (stream, "\n");
/* C++: print out the methods */
for (i = 0; i < len; i++)
{
struct fn_field *f = TYPE_FN_FIELDLIST1 (type, i);
int j, len2 = TYPE_FN_FIELDLIST_LENGTH (type, i);
char *method_name = TYPE_FN_FIELDLIST_NAME (type, i);
int is_constructor = name && strcmp(method_name, name) == 0;
for (j = 0; j < len2; j++)
{
QUIT;
if (TYPE_FN_FIELD_PROTECTED (f, j))
{
if (section_type != s_protected)
{
section_type = s_protected;
fprintfi_filtered (level + 2, stream,
"protected:\n");
}
}
else if (TYPE_FN_FIELD_PRIVATE (f, j))
{
if (section_type != s_private)
{
section_type = s_private;
fprintfi_filtered (level + 2, stream, "private:\n");
}
}
else
{
if (section_type != s_public)
{
section_type = s_public;
fprintfi_filtered (level + 2, stream, "public:\n");
}
}
print_spaces_filtered (level + 4, stream);
if (TYPE_FN_FIELD_VIRTUAL_P (f, j))
fprintf_filtered (stream, "virtual ");
else if (TYPE_FN_FIELD_STATIC_P (f, j))
fprintf_filtered (stream, "static ");
if (TYPE_TARGET_TYPE (TYPE_FN_FIELD_TYPE (f, j)) == 0)
{
/* Keep GDB from crashing here. */
fprintf (stream, "<undefined type> %s;\n",
TYPE_FN_FIELD_PHYSNAME (f, j));
break;
}
else if (!is_constructor)
{
type_print (TYPE_TARGET_TYPE (TYPE_FN_FIELD_TYPE (f, j)),
"", stream, 0);
fputs_filtered (" ", stream);
}
if (TYPE_FN_FIELD_STUB (f, j))
{
/* Build something we can demangle. */
mangled_name = gdb_mangle_name (type, i, j);
demangled_name =
cplus_demangle (mangled_name,
DMGL_ANSI | DMGL_PARAMS);
if (demangled_name == NULL)
fprintf_filtered (stream, "<badly mangled name %s>",
mangled_name);
else
{
fprintf_filtered (stream, "%s",
strchr (demangled_name, ':') + 2);
free (demangled_name);
}
free (mangled_name);
}
else if (TYPE_FN_FIELD_PHYSNAME (f, j)[0] == '_'
&& TYPE_FN_FIELD_PHYSNAME (f, j)[1] == CPLUS_MARKER)
cp_type_print_method_args (TYPE_FN_FIELD_ARGS (f, j) + 1,
"~", method_name, 0, stream);
else
cp_type_print_method_args (TYPE_FN_FIELD_ARGS (f, j), "",
method_name,
TYPE_FN_FIELD_STATIC_P (f, j),
stream);
fprintf_filtered (stream, ";\n");
}
}
fprintfi_filtered (level, stream, "}");
}
break;
case TYPE_CODE_ENUM:
fprintf_filtered (stream, "enum ");
if ((name = type_name_no_tag (type)) != NULL)
{
fputs_filtered (name, stream);
fputs_filtered (" ", stream);
}
wrap_here (" ");
if (show < 0)
fprintf_filtered (stream, "{...}");
else
{
fprintf_filtered (stream, "{");
len = TYPE_NFIELDS (type);
lastval = 0;
for (i = 0; i < len; i++)
{
QUIT;
if (i) fprintf_filtered (stream, ", ");
wrap_here (" ");
fputs_filtered (TYPE_FIELD_NAME (type, i), stream);
if (lastval != TYPE_FIELD_BITPOS (type, i))
{
fprintf_filtered (stream, " = %d", TYPE_FIELD_BITPOS (type, i));
lastval = TYPE_FIELD_BITPOS (type, i);
}
lastval++;
}
fprintf_filtered (stream, "}");
}
break;
case TYPE_CODE_VOID:
fprintf_filtered (stream, "void");
break;
case TYPE_CODE_UNDEF:
fprintf_filtered (stream, "struct <unknown>");
break;
case TYPE_CODE_ERROR:
fprintf_filtered (stream, "<unknown type>");
break;
case TYPE_CODE_RANGE:
/* This should not occur */
fprintf_filtered (stream, "<range type>");
break;
default:
/* Handle types not explicitly handled by the other cases,
such as fundamental types. For these, just print whatever
the type name is, as recorded in the type itself. If there
is no type name, then complain. */
if (TYPE_NAME (type) != NULL)
{
fputs_filtered (TYPE_NAME (type), stream);
}
else
{
error ("Invalid type code (%d) in symbol table.", TYPE_CODE (type));
}
break;
}
}

542
gdb/c-valprint.c Normal file
View file

@ -0,0 +1,542 @@
/* Support for printing C values for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "symtab.h"
#include "gdbtypes.h"
#include "expression.h"
#include "value.h"
#include "demangle.h"
#include "valprint.h"
#include "language.h"
/* BEGIN-FIXME */
extern int vtblprint; /* Controls printing of vtbl's */
extern int demangle; /* whether to print C++ syms raw or src-form */
extern void
cp_print_class_member PARAMS ((char *, struct type *, FILE *, char *));
extern int
cp_is_vtbl_ptr_type PARAMS ((struct type *));
extern void
cp_print_value_fields PARAMS ((struct type *, char *, FILE *, int, int,
enum val_prettyprint, struct type **));
extern int
cp_is_vtbl_member PARAMS ((struct type *));
/* END-FIXME */
/* BEGIN-FIXME: Hooks into c-typeprint.c */
extern void
c_type_print_varspec_prefix PARAMS ((struct type *, FILE *, int, int));
extern void
cp_type_print_method_args PARAMS ((struct type **, char *, char *, int,
FILE *));
/* END-FIXME */
extern struct obstack dont_print_obstack;
/* Print data of type TYPE located at VALADDR (within GDB), which came from
the inferior at address ADDRESS, onto stdio stream STREAM according to
FORMAT (a letter or 0 for natural format). The data at VALADDR is in
target byte order.
If the data are a string pointer, returns the number of string characters
printed.
If DEREF_REF is nonzero, then dereference references, otherwise just print
them like pointers.
The PRETTY parameter controls prettyprinting. */
int
c_val_print (type, valaddr, address, stream, format, deref_ref, recurse,
pretty)
struct type *type;
char *valaddr;
CORE_ADDR address;
FILE *stream;
int format;
int deref_ref;
int recurse;
enum val_prettyprint pretty;
{
register unsigned int i;
unsigned len;
struct type *elttype;
unsigned eltlen;
LONGEST val;
unsigned char c;
switch (TYPE_CODE (type))
{
case TYPE_CODE_ARRAY:
if (TYPE_LENGTH (type) > 0 && TYPE_LENGTH (TYPE_TARGET_TYPE (type)) > 0)
{
elttype = TYPE_TARGET_TYPE (type);
eltlen = TYPE_LENGTH (elttype);
len = TYPE_LENGTH (type) / eltlen;
if (prettyprint_arrays)
{
print_spaces_filtered (2 + 2 * recurse, stream);
}
fprintf_filtered (stream, "{");
/* For an array of chars, print with string syntax. */
if (eltlen == 1 && TYPE_CODE (elttype) == TYPE_CODE_INT
&& (format == 0 || format == 's') )
{
LA_PRINT_STRING (stream, valaddr, len, 0);
}
else
{
/* If this is a virtual function table, print the 0th
entry specially, and the rest of the members normally. */
if (cp_is_vtbl_ptr_type (elttype))
{
i = 1;
fprintf_filtered (stream, "%d vtable entries", len - 1);
}
else
{
i = 0;
}
val_print_array_elements (type, valaddr, address, stream,
format, deref_ref, recurse, pretty, i);
}
fprintf_filtered (stream, "}");
break;
}
/* Array of unspecified length: treat like pointer to first elt. */
valaddr = (char *) &address;
case TYPE_CODE_PTR:
if (format && format != 's')
{
print_scalar_formatted (valaddr, type, format, 0, stream);
break;
}
if (TYPE_CODE (TYPE_TARGET_TYPE (type)) == TYPE_CODE_METHOD)
{
struct type *domain = TYPE_DOMAIN_TYPE (TYPE_TARGET_TYPE (type));
struct fn_field *f;
int j, len2;
char *kind = "";
CORE_ADDR addr;
addr = unpack_pointer (lookup_pointer_type (builtin_type_void),
valaddr);
if (METHOD_PTR_IS_VIRTUAL(addr))
{
int offset = METHOD_PTR_TO_VOFFSET(addr);
len = TYPE_NFN_FIELDS (domain);
for (i = 0; i < len; i++)
{
f = TYPE_FN_FIELDLIST1 (domain, i);
len2 = TYPE_FN_FIELDLIST_LENGTH (domain, i);
for (j = 0; j < len2; j++)
{
QUIT;
if (TYPE_FN_FIELD_VOFFSET (f, j) == offset)
{
kind = "virtual ";
goto common;
}
}
}
}
else
{
struct symbol *sym = find_pc_function (addr);
if (sym == 0)
{
error ("invalid pointer to member function");
}
len = TYPE_NFN_FIELDS (domain);
for (i = 0; i < len; i++)
{
f = TYPE_FN_FIELDLIST1 (domain, i);
len2 = TYPE_FN_FIELDLIST_LENGTH (domain, i);
for (j = 0; j < len2; j++)
{
QUIT;
if (!strcmp (SYMBOL_NAME (sym),
TYPE_FN_FIELD_PHYSNAME (f, j)))
{
goto common;
}
}
}
}
common:
if (i < len)
{
fprintf_filtered (stream, "&");
c_type_print_varspec_prefix (TYPE_FN_FIELD_TYPE (f, j), stream, 0, 0);
fprintf (stream, kind);
if (TYPE_FN_FIELD_PHYSNAME (f, j)[0] == '_'
&& TYPE_FN_FIELD_PHYSNAME (f, j)[1] == CPLUS_MARKER)
cp_type_print_method_args (TYPE_FN_FIELD_ARGS (f, j) + 1, "~",
TYPE_FN_FIELDLIST_NAME (domain, i),
0, stream);
else
cp_type_print_method_args (TYPE_FN_FIELD_ARGS (f, j), "",
TYPE_FN_FIELDLIST_NAME (domain, i),
0, stream);
break;
}
fprintf_filtered (stream, "(");
type_print (type, "", stream, -1);
fprintf_filtered (stream, ") %d", (int) addr >> 3);
}
else if (TYPE_CODE (TYPE_TARGET_TYPE (type)) == TYPE_CODE_MEMBER)
{
cp_print_class_member (valaddr,
TYPE_DOMAIN_TYPE (TYPE_TARGET_TYPE (type)),
stream, "&");
}
else
{
CORE_ADDR addr = unpack_pointer (type, valaddr);
elttype = TYPE_TARGET_TYPE (type);
if (TYPE_CODE (elttype) == TYPE_CODE_FUNC)
{
/* Try to print what function it points to. */
print_address_demangle (addr, stream, demangle);
/* Return value is irrelevant except for string pointers. */
return (0);
}
if (addressprint && format != 's')
{
fprintf_filtered (stream, "0x%x", addr);
}
/* For a pointer to char or unsigned char, also print the string
pointed to, unless pointer is null. */
i = 0; /* Number of characters printed. */
if (TYPE_LENGTH (elttype) == 1 &&
TYPE_CODE (elttype) == TYPE_CODE_INT &&
(format == 0 || format == 's') &&
addr != 0 &&
/* If print_max is UINT_MAX, the alloca below will fail.
In that case don't try to print the string. */
print_max < UINT_MAX)
{
int first_addr_err = 0;
int errcode = 0;
/* Get first character. */
errcode = target_read_memory (addr, (char *)&c, 1);
if (errcode != 0)
{
/* First address out of bounds. */
first_addr_err = 1;
}
else
{
/* A real string. */
char *string = (char *) alloca (print_max);
/* If the loop ends by us hitting print_max characters,
we need to have elipses at the end. */
int force_ellipses = 1;
/* This loop always fetches print_max characters, even
though LA_PRINT_STRING might want to print more or fewer
(with repeated characters). This is so that
we don't spend forever fetching if we print
a long string consisting of the same character
repeated. Also so we can do it all in one memory
operation, which is faster. However, this will be
slower if print_max is set high, e.g. if you set
print_max to 1000, not only will it take a long
time to fetch short strings, but if you are near
the end of the address space, it might not work. */
QUIT;
errcode = target_read_memory (addr, string, print_max);
if (errcode != 0)
{
/* Try reading just one character. If that succeeds,
assume we hit the end of the address space, but
the initial part of the string is probably safe. */
char x[1];
errcode = target_read_memory (addr, x, 1);
}
if (errcode != 0)
force_ellipses = 0;
else
for (i = 0; i < print_max; i++)
if (string[i] == '\0')
{
force_ellipses = 0;
break;
}
QUIT;
if (addressprint)
{
fputs_filtered (" ", stream);
}
LA_PRINT_STRING (stream, string, i, force_ellipses);
}
if (errcode != 0)
{
if (errcode == EIO)
{
fprintf_filtered (stream,
(" <Address 0x%x out of bounds>" +
first_addr_err),
addr + i);
}
else
{
error ("Error reading memory address 0x%x: %s.",
addr + i, safe_strerror (errcode));
}
}
fflush (stream);
}
else if (cp_is_vtbl_member(type))
{
/* print vtbl's nicely */
CORE_ADDR vt_address = unpack_pointer (type, valaddr);
struct minimal_symbol *msymbol =
lookup_minimal_symbol_by_pc (vt_address);
if ((msymbol != NULL) && (vt_address == msymbol -> address))
{
fputs_filtered (" <", stream);
fputs_demangled (msymbol -> name, stream,
DMGL_ANSI | DMGL_PARAMS);
fputs_filtered (">", stream);
}
if (vtblprint)
{
value vt_val;
vt_val = value_at (TYPE_TARGET_TYPE (type), vt_address);
val_print (VALUE_TYPE (vt_val), VALUE_CONTENTS (vt_val),
VALUE_ADDRESS (vt_val), stream, format,
deref_ref, recurse + 1, pretty);
if (pretty)
{
fprintf_filtered (stream, "\n");
print_spaces_filtered (2 + 2 * recurse, stream);
}
}
}
/* Return number of characters printed, plus one for the
terminating null if we have "reached the end". */
return (i + (print_max && i != print_max));
}
break;
case TYPE_CODE_MEMBER:
error ("not implemented: member type in c_val_print");
break;
case TYPE_CODE_REF:
if (TYPE_CODE (TYPE_TARGET_TYPE (type)) == TYPE_CODE_MEMBER)
{
cp_print_class_member (valaddr,
TYPE_DOMAIN_TYPE (TYPE_TARGET_TYPE (type)),
stream, "");
break;
}
if (addressprint)
{
fprintf_filtered (stream, "@0x%lx",
unpack_long (builtin_type_int, valaddr));
if (deref_ref)
fputs_filtered (": ", stream);
}
/* De-reference the reference. */
if (deref_ref)
{
if (TYPE_CODE (TYPE_TARGET_TYPE (type)) != TYPE_CODE_UNDEF)
{
value deref_val =
value_at
(TYPE_TARGET_TYPE (type),
unpack_pointer (lookup_pointer_type (builtin_type_void),
valaddr));
val_print (VALUE_TYPE (deref_val),
VALUE_CONTENTS (deref_val),
VALUE_ADDRESS (deref_val), stream, format,
deref_ref, recurse + 1, pretty);
}
else
fputs_filtered ("???", stream);
}
break;
case TYPE_CODE_UNION:
if (recurse && !unionprint)
{
fprintf_filtered (stream, "{...}");
break;
}
/* Fall through. */
case TYPE_CODE_STRUCT:
if (vtblprint && cp_is_vtbl_ptr_type(type))
{
/* Print the unmangled name if desired. */
print_address_demangle(*((int *) (valaddr + /* FIXME bytesex */
TYPE_FIELD_BITPOS (type, VTBL_FNADDR_OFFSET) / 8)),
stream, demangle);
break;
}
cp_print_value_fields (type, valaddr, stream, format, recurse, pretty,
0);
break;
case TYPE_CODE_ENUM:
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
break;
}
len = TYPE_NFIELDS (type);
val = unpack_long (builtin_type_int, valaddr);
for (i = 0; i < len; i++)
{
QUIT;
if (val == TYPE_FIELD_BITPOS (type, i))
{
break;
}
}
if (i < len)
{
fputs_filtered (TYPE_FIELD_NAME (type, i), stream);
}
else
{
#ifdef LONG_LONG
fprintf_filtered (stream, "%lld", val);
#else
fprintf_filtered (stream, "%ld", val);
#endif
}
break;
case TYPE_CODE_FUNC:
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
break;
}
/* FIXME, we should consider, at least for ANSI C language, eliminating
the distinction made between FUNCs and POINTERs to FUNCs. */
fprintf_filtered (stream, "{");
type_print (type, "", stream, -1);
fprintf_filtered (stream, "} ");
/* Try to print what function it points to, and its address. */
print_address_demangle (address, stream, demangle);
break;
case TYPE_CODE_INT:
format = format ? format : output_format;
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
}
else
{
val_print_type_code_int (type, valaddr, stream);
/* C and C++ has no single byte int type, char is used instead.
Since we don't know whether the value is really intended to
be used as an integer or a character, print the character
equivalent as well. */
if (TYPE_LENGTH (type) == 1)
{
fputs_filtered (" ", stream);
LA_PRINT_CHAR ((unsigned char) unpack_long (type, valaddr),
stream);
}
}
break;
case TYPE_CODE_CHAR:
format = format ? format : output_format;
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
}
else
{
fprintf_filtered (stream, TYPE_UNSIGNED (type) ? "%u" : "%d",
unpack_long (type, valaddr));
fputs_filtered (" ", stream);
LA_PRINT_CHAR ((unsigned char) unpack_long (type, valaddr), stream);
}
break;
case TYPE_CODE_FLT:
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
}
else
{
print_floating (valaddr, type, stream);
}
break;
case TYPE_CODE_VOID:
fprintf_filtered (stream, "void");
break;
case TYPE_CODE_ERROR:
fprintf_filtered (stream, "<error type>");
break;
case TYPE_CODE_RANGE:
/* FIXME, we should not ever have to print one of these yet. */
fprintf_filtered (stream, "<range type>");
break;
case TYPE_CODE_UNDEF:
/* This happens (without TYPE_FLAG_STUB set) on systems which don't use
dbx xrefs (NO_DBX_XREFS in gcc) if a file has a "struct foo *bar"
and no complete type for struct foo in that file. */
fprintf_filtered (stream, "<incomplete type>");
break;
default:
error ("Invalid C/C++ type code %d in symbol table.", TYPE_CODE (type));
}
fflush (stream);
return (0);
}

View file

@ -135,10 +135,6 @@ yyparse PARAMS ((void));
int *ivec;
}
%{
static int parse_number PARAMS ((void));
%}
%token <voidval> FIXME
%token <typed_val> INTEGER_LITERAL
@ -874,8 +870,6 @@ decode_integer_literal (valptr, tokptrptr)
char *tokptr = *tokptrptr;
int base = 0;
int ival = 0;
int digits = 0;
int temp;
int explicit_base = 0;
/* Look for an explicit base specifier, which is optional. */
@ -1042,9 +1036,9 @@ match_integer_literal ()
}
}
#if 0
static void convert_float ()
{
#if 0
extern double strtod ();
double d;
char tmp[256];
@ -1075,8 +1069,8 @@ static void convert_float ()
;
}
yylval.dval = d;
#endif
}
#endif
/* Take care of parsing a number (anything that starts with a digit).
Set yylval and return the token type; update lexptr.
@ -1084,35 +1078,30 @@ static void convert_float ()
/*** Needs some error checking for the float case ***/
static int
parse_number ()
{
}
struct token
{
char *operator;
int token;
};
const static struct token tokentab5[] =
static const struct token tokentab5[] =
{
{ "ANDIF", ANDIF }
};
const static struct token tokentab4[] =
static const struct token tokentab4[] =
{
{ "ORIF", ORIF }
};
const static struct token tokentab3[] =
static const struct token tokentab3[] =
{
{ "NOT", NOT },
{ "XOR", LOGXOR },
{ "AND", LOGAND }
};
const static struct token tokentab2[] =
static const struct token tokentab2[] =
{
{ "//", SLASH_SLASH },
{ "/=", NOTEQUAL },
@ -1265,6 +1254,18 @@ yylex ()
case LOC_STATIC:
/* Found a global or local static variable. */
return (LOCATION_NAME);
case LOC_UNDEF:
case LOC_CONST:
case LOC_REGISTER:
case LOC_ARG:
case LOC_REF_ARG:
case LOC_REGPARM:
case LOC_LOCAL:
case LOC_TYPEDEF:
case LOC_LABEL:
case LOC_CONST_BYTES:
case LOC_LOCAL_ARG:
break;
}
}
else if (!have_full_symbols () && !have_partial_symbols ())

View file

@ -164,7 +164,6 @@ chill_create_fundamental_type (objfile, typeid)
int typeid;
{
register struct type *type = NULL;
register int nbytes;
switch (typeid)
{
@ -173,16 +172,20 @@ chill_create_fundamental_type (objfile, typeid)
language, create the equivalent of a C integer type with the
name "<?type?>". When all the dust settles from the type
reconstruction work, this should probably become an error. */
type = init_type (TYPE_CODE_INT,
TARGET_INT_BIT / TARGET_CHAR_BIT,
0, "<?type?>", objfile);
type = init_type (TYPE_CODE_INT, 2, 0, "<?type?>", objfile);
warning ("internal error: no chill fundamental type %d", typeid);
break;
case FT_VOID:
/* FIXME: Currently the GNU Chill compiler emits some DWARF entries for
typedefs, unrelated to anything directly in the code being compiled,
that have some FT_VOID types. Just fake it for now. */
type = init_type (TYPE_CODE_VOID, 0, 0, "<?VOID?>", objfile);
break;
case FT_BOOLEAN:
type = init_type (TYPE_CODE_BOOL, 1, TYPE_FLAG_UNSIGNED, "BOOL", objfile);
break;
case FT_CHAR:
type = init_type (TYPE_CODE_INT, 1, TYPE_FLAG_UNSIGNED, "CHAR", objfile);
type = init_type (TYPE_CODE_CHAR, 1, TYPE_FLAG_UNSIGNED, "CHAR", objfile);
break;
case FT_SIGNED_CHAR:
type = init_type (TYPE_CODE_INT, 1, TYPE_FLAG_SIGNED, "BYTE", objfile);
@ -215,7 +218,7 @@ chill_create_fundamental_type (objfile, typeid)
/* Table of operators and their precedences for printing expressions. */
const static struct op_print chill_op_print_tab[] = {
static const struct op_print chill_op_print_tab[] = {
{"AND", BINOP_LOGICAL_AND, PREC_LOGICAL_AND, 0},
{"OR", BINOP_LOGICAL_OR, PREC_LOGICAL_OR, 0},
{"NOT", UNOP_LOGICAL_NOT, PREC_PREFIX, 0},
@ -265,6 +268,8 @@ const struct language_defn chill_language_defn = {
chill_printchar, /* print a character constant */
chill_printstr, /* function to print a string constant */
chill_create_fundamental_type,/* Create fundamental type in this language */
chill_print_type, /* Print a type using appropriate syntax */
chill_val_print, /* Print a value using appropriate syntax */
&BUILTIN_TYPE_LONGEST, /* longest signed integral type */
&BUILTIN_TYPE_UNSIGNED_LONGEST,/* longest unsigned integral type */
&builtin_type_chill_real, /* longest floating point type */

View file

@ -22,3 +22,10 @@ chill_parse PARAMS ((void)); /* Defined in ch-exp.y */
extern void
chill_error PARAMS ((char *)); /* Defined in ch-exp.y */
extern void /* Defined in ch-typeprint.c */
chill_print_type PARAMS ((struct type *, char *, FILE *, int, int));
extern int
chill_val_print PARAMS ((struct type *, char *, CORE_ADDR, FILE *, int, int,
int, enum val_prettyprint));

155
gdb/ch-typeprint.c Normal file
View file

@ -0,0 +1,155 @@
/* Support for printing Chill types for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "obstack.h"
#include "bfd.h" /* Binary File Description */
#include "symtab.h"
#include "gdbtypes.h"
#include "expression.h"
#include "value.h"
#include "gdbcore.h"
#include "target.h"
#include "command.h"
#include "gdbcmd.h"
#include "language.h"
#include "demangle.h"
#include "ch-lang.h"
#include <string.h>
#include <errno.h>
void
chill_print_type_base PARAMS ((struct type *, FILE *, int, int));
void
chill_print_type (type, varstring, stream, show, level)
struct type *type;
char *varstring;
FILE *stream;
int show;
int level;
{
struct type *index_type;
struct type *range_type;
LONGEST low_bound;
LONGEST high_bound;
if (varstring != NULL && *varstring != '\0')
{
fputs_filtered (varstring, stream);
fputs_filtered (" ", stream);
}
switch (TYPE_CODE (type))
{
case TYPE_CODE_ARRAY:
range_type = TYPE_FIELD_TYPE (type, 0);
index_type = TYPE_TARGET_TYPE (range_type);
low_bound = TYPE_FIELD_BITPOS (range_type, 0);
high_bound = TYPE_FIELD_BITPOS (range_type, 1);
fputs_filtered ("array (", stream);
print_type_scalar (index_type, low_bound, stream);
fputs_filtered (":", stream);
print_type_scalar (index_type, high_bound, stream);
fputs_filtered (") ", stream);
chill_print_type (TYPE_TARGET_TYPE (type), "", stream, show, level);
break;
default:
chill_print_type_base (type, stream, show, level);
break;
}
}
/* Print the name of the type (or the ultimate pointer target,
function value or array element).
SHOW nonzero means don't print this type as just its name;
show its real definition even if it has a name.
SHOW zero means print just typename or tag if there is one
SHOW negative means abbreviate structure elements.
SHOW is decremented for printing of structure elements.
LEVEL is the depth to indent by.
We increase it for some recursive calls. */
void
chill_print_type_base (type, stream, show, level)
struct type *type;
FILE *stream;
int show;
int level;
{
QUIT;
wrap_here (" ");
if (type == NULL)
{
fputs_filtered ("<type unknown>", stream);
return;
}
/* When SHOW is zero or less, and there is a valid type name, then always
just print the type name directly from the type. */
if ((show <= 0) && (TYPE_NAME (type) != NULL))
{
fputs_filtered (TYPE_NAME (type), stream);
return;
}
switch (TYPE_CODE (type))
{
case TYPE_CODE_ARRAY:
case TYPE_CODE_PTR:
case TYPE_CODE_MEMBER:
case TYPE_CODE_REF:
case TYPE_CODE_FUNC:
chill_print_type_base (TYPE_TARGET_TYPE (type), stream, show, level);
break;
case TYPE_CODE_VOID:
case TYPE_CODE_UNDEF:
case TYPE_CODE_ERROR:
case TYPE_CODE_RANGE:
case TYPE_CODE_ENUM:
case TYPE_CODE_UNION:
case TYPE_CODE_STRUCT:
case TYPE_CODE_METHOD:
error ("missing language support in chill_print_type_base");
break;
default:
/* Handle types not explicitly handled by the other cases,
such as fundamental types. For these, just print whatever
the type name is, as recorded in the type itself. If there
is no type name, then complain. */
if (TYPE_NAME (type) != NULL)
{
fputs_filtered (TYPE_NAME (type), stream);
}
else
{
error ("Unrecognized type code (%d) in symbol table.",
TYPE_CODE (type));
}
break;
}
}

166
gdb/ch-valprint.c Normal file
View file

@ -0,0 +1,166 @@
/* Support for printing Chill values for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "obstack.h"
#include "symtab.h"
#include "gdbtypes.h"
#include "valprint.h"
#include "expression.h"
#include "language.h"
/* Print data of type TYPE located at VALADDR (within GDB), which came from
the inferior at address ADDRESS, onto stdio stream STREAM according to
FORMAT (a letter or 0 for natural format). The data at VALADDR is in
target byte order.
If the data are a string pointer, returns the number of string characters
printed.
If DEREF_REF is nonzero, then dereference references, otherwise just print
them like pointers.
The PRETTY parameter controls prettyprinting. */
int
chill_val_print (type, valaddr, address, stream, format, deref_ref, recurse,
pretty)
struct type *type;
char *valaddr;
CORE_ADDR address;
FILE *stream;
int format;
int deref_ref;
int recurse;
enum val_prettyprint pretty;
{
unsigned len;
struct type *elttype;
unsigned eltlen;
LONGEST val;
switch (TYPE_CODE (type))
{
case TYPE_CODE_ARRAY:
if (TYPE_LENGTH (type) > 0 && TYPE_LENGTH (TYPE_TARGET_TYPE (type)) > 0)
{
elttype = TYPE_TARGET_TYPE (type);
eltlen = TYPE_LENGTH (elttype);
len = TYPE_LENGTH (type) / eltlen;
if (prettyprint_arrays)
{
print_spaces_filtered (2 + 2 * recurse, stream);
}
fprintf_filtered (stream, "[");
/* For an array of chars, print with string syntax. */
if (eltlen == 1 && TYPE_CODE (elttype) == TYPE_CODE_INT
&& (format == 0 || format == 's') )
{
LA_PRINT_STRING (stream, valaddr, len, 0);
}
else
{
val_print_array_elements (type, valaddr, address, stream,
format, deref_ref, recurse, pretty, 0);
}
fprintf_filtered (stream, "]");
}
else
{
error ("unimplemented in chill_val_print; unspecified array length");
}
break;
case TYPE_CODE_INT:
format = format ? format : output_format;
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
}
else
{
val_print_type_code_int (type, valaddr, stream);
}
break;
case TYPE_CODE_CHAR:
format = format ? format : output_format;
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
}
else
{
LA_PRINT_CHAR ((unsigned char) unpack_long (type, valaddr),
stream);
}
break;
case TYPE_CODE_FLT:
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
}
else
{
print_floating (valaddr, type, stream);
}
break;
case TYPE_CODE_BOOL:
format = format ? format : output_format;
if (format)
{
print_scalar_formatted (valaddr, type, format, 0, stream);
}
else
{
val = unpack_long (builtin_type_chill_bool, valaddr);
fprintf_filtered (stream, val ? "TRUE" : "FALSE");
}
break;
case TYPE_CODE_UNDEF:
/* This happens (without TYPE_FLAG_STUB set) on systems which don't use
dbx xrefs (NO_DBX_XREFS in gcc) if a file has a "struct foo *bar"
and no complete type for struct foo in that file. */
fprintf_filtered (stream, "<incomplete type>");
break;
case TYPE_CODE_PTR:
case TYPE_CODE_MEMBER:
case TYPE_CODE_REF:
case TYPE_CODE_UNION:
case TYPE_CODE_STRUCT:
case TYPE_CODE_ENUM:
case TYPE_CODE_FUNC:
case TYPE_CODE_VOID:
case TYPE_CODE_ERROR:
case TYPE_CODE_RANGE:
error ("Unimplemented chill_val_print support for type %d",
TYPE_CODE (type));
break;
default:
error ("Invalid Chill type code %d in symbol table.", TYPE_CODE (type));
}
fflush (stream);
return (0);
}

View file

@ -1777,7 +1777,7 @@ decode_type (cs, c_type, aux)
{
int i, n;
register unsigned short *dim;
struct type *base_type, *index_type;
struct type *base_type, *index_type, *range_type;
/* Define an array type. */
/* auxent refers to array, not base type */
@ -1794,8 +1794,10 @@ decode_type (cs, c_type, aux)
base_type = decode_type (cs, new_c_type, aux);
index_type = lookup_fundamental_type (current_objfile, FT_INTEGER);
type = create_array_type ((struct type *) NULL, base_type,
index_type, 0, n - 1);
range_type =
create_range_type ((struct type *) NULL, index_type, 0, n - 1);
type =
create_array_type ((struct type *) NULL, base_type, range_type);
}
return type;
}

View file

@ -64,7 +64,6 @@ complain (va_alist)
{
va_list args;
struct complaint *complaint;
char *val;
va_start (args);
complaint = va_arg (args, struct complaint *);
@ -142,6 +141,7 @@ clear_complaints (sym_reading, noisy)
complaint_series = sym_reading ? 1 + noisy : 0;
}
void
_initialize_complaints ()
{
add_show_from_set

View file

@ -332,6 +332,7 @@ value_of_trapped_internalvar (var)
char *name = var->name;
value val;
struct type *type;
struct type *range_type;
long len = *read_vector_register (VL_REGNUM);
if (len <= 0 || len > 128) len = 128;
@ -350,8 +351,10 @@ value_of_trapped_internalvar (var)
long vm[4];
long i, *p;
bcopy (read_vector_register_1 (VM_REGNUM), vm, sizeof vm);
type = create_array_type ((struct type *) NULL, builtin_type_int,
builtin_type_int, 0, len - 1);
range_type =
create_range_type ((struct type *) NULL, builtin_type_int, 0, len - 1);
type =
create_array_type ((struct type *) NULL, builtin_type_int, range_type);
val = allocate_value (type);
p = (long *) VALUE_CONTENTS (val);
for (i = 0; i < len; i++)
@ -359,8 +362,11 @@ value_of_trapped_internalvar (var)
}
else if (name[0] == 'V')
{
type = create_array_type ((struct type *) NULL, builtin_type_long_long,
builtin_type_int, 0, len - 1);
range_type =
create_range_type ((struct type *) NULL, builtin_type_int 0, len - 1);
type =
create_array_type ((struct type *) NULL, builtin_type_long_long,
range_type);
val = allocate_value (type);
bcopy (read_vector_register_1 (name[1] - '0'),
VALUE_CONTENTS (val), TYPE_LENGTH (type));
@ -368,8 +374,11 @@ value_of_trapped_internalvar (var)
else if (name[0] == 'v')
{
long *p1, *p2;
type = create_array_type ((struct type *) NULL, builtin_type_long,
builtin_type_int, 0, len - 1);
range_type =
create_range_type ((struct type *) NULL, builtin_type_int 0, len - 1);
type =
create_array_type ((struct type *) NULL, builtin_type_long,
range_type);
val = allocate_value (type);
p1 = read_vector_register_1 (name[1] - '0');
p2 = (long *) VALUE_CONTENTS (val);

369
gdb/cp-valprint.c Normal file
View file

@ -0,0 +1,369 @@
/* Support for printing C++ values for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "obstack.h"
#include "symtab.h"
#include "gdbtypes.h"
#include "expression.h"
#include "value.h"
#include "command.h"
#include "gdbcmd.h"
int vtblprint; /* Controls printing of vtbl's */
int objectprint; /* Controls looking up an object's derived type
using what we find in its vtables. */
struct obstack dont_print_obstack;
static void
cplus_print_value PARAMS ((struct type *, char *, FILE *, int, int,
enum val_prettyprint, struct type **));
/* BEGIN-FIXME: Hooks into typeprint.c, find a better home for prototypes. */
extern void
c_type_print_base PARAMS ((struct type *, FILE *, int, int));
extern void
c_type_print_varspec_prefix PARAMS ((struct type *, FILE *, int, int));
extern void
cp_type_print_method_args PARAMS ((struct type **, char *, char *, int,
FILE *));
extern struct obstack dont_print_obstack;
/* END-FIXME */
/* BEGIN-FIXME: Hooks into c-valprint.c */
extern int
c_val_print PARAMS ((struct type *, char *, CORE_ADDR, FILE *, int, int, int,
enum val_prettyprint));
/* END-FIXME */
/* Return truth value for assertion that TYPE is of the type
"pointer to virtual function". */
int
cp_is_vtbl_ptr_type(type)
struct type *type;
{
char *typename = type_name_no_tag (type);
static const char vtbl_ptr_name[] =
{ CPLUS_MARKER,'v','t','b','l','_','p','t','r','_','t','y','p','e', 0 };
return (typename != NULL && !strcmp(typename, vtbl_ptr_name));
}
/* Return truth value for the assertion that TYPE is of the type
"pointer to virtual function table". */
int
cp_is_vtbl_member(type)
struct type *type;
{
if (TYPE_CODE (type) == TYPE_CODE_PTR)
type = TYPE_TARGET_TYPE (type);
else
return 0;
if (TYPE_CODE (type) == TYPE_CODE_ARRAY
&& TYPE_CODE (TYPE_TARGET_TYPE (type)) == TYPE_CODE_STRUCT)
/* Virtual functions tables are full of pointers to virtual functions. */
return cp_is_vtbl_ptr_type (TYPE_TARGET_TYPE (type));
return 0;
}
/* Mutually recursive subroutines of cplus_print_value and c_val_print to
print out a structure's fields: cp_print_value_fields and cplus_print_value.
TYPE, VALADDR, STREAM, RECURSE, and PRETTY have the
same meanings as in cplus_print_value and c_val_print.
DONT_PRINT is an array of baseclass types that we
should not print, or zero if called from top level. */
void
cp_print_value_fields (type, valaddr, stream, format, recurse, pretty,
dont_print)
struct type *type;
char *valaddr;
FILE *stream;
int format;
int recurse;
enum val_prettyprint pretty;
struct type **dont_print;
{
int i, len, n_baseclasses;
check_stub_type (type);
fprintf_filtered (stream, "{");
len = TYPE_NFIELDS (type);
n_baseclasses = TYPE_N_BASECLASSES (type);
/* Print out baseclasses such that we don't print
duplicates of virtual baseclasses. */
if (n_baseclasses > 0)
cplus_print_value (type, valaddr, stream, format, recurse+1, pretty,
dont_print);
if (!len && n_baseclasses == 1)
fprintf_filtered (stream, "<No data fields>");
else
{
extern int inspect_it;
int fields_seen = 0;
for (i = n_baseclasses; i < len; i++)
{
/* Check if static field */
if (TYPE_FIELD_STATIC (type, i))
continue;
if (fields_seen)
fprintf_filtered (stream, ", ");
else if (n_baseclasses > 0)
{
if (pretty)
{
fprintf_filtered (stream, "\n");
print_spaces_filtered (2 + 2 * recurse, stream);
fputs_filtered ("members of ", stream);
fputs_filtered (type_name_no_tag (type), stream);
fputs_filtered (": ", stream);
}
}
fields_seen = 1;
if (pretty)
{
fprintf_filtered (stream, "\n");
print_spaces_filtered (2 + 2 * recurse, stream);
}
else
{
wrap_here (n_spaces (2 + 2 * recurse));
}
if (inspect_it)
{
if (TYPE_CODE (TYPE_FIELD_TYPE (type, i)) == TYPE_CODE_PTR)
fputs_filtered ("\"( ptr \"", stream);
else
fputs_filtered ("\"( nodef \"", stream);
fprint_symbol (stream, TYPE_FIELD_NAME (type, i));
fputs_filtered ("\" \"", stream);
fprint_symbol (stream, TYPE_FIELD_NAME (type, i));
fputs_filtered ("\") \"", stream);
}
else
{
fprint_symbol (stream, TYPE_FIELD_NAME (type, i));
fputs_filtered (" = ", stream);
}
if (TYPE_FIELD_PACKED (type, i))
{
value v;
/* Bitfields require special handling, especially due to byte
order problems. */
v = value_from_longest (TYPE_FIELD_TYPE (type, i),
unpack_field_as_long (type, valaddr, i));
c_val_print (TYPE_FIELD_TYPE (type, i), VALUE_CONTENTS (v), 0,
stream, format, 0, recurse + 1, pretty);
}
else
{
c_val_print (TYPE_FIELD_TYPE (type, i),
valaddr + TYPE_FIELD_BITPOS (type, i) / 8,
0, stream, format, 0, recurse + 1, pretty);
}
}
if (pretty)
{
fprintf_filtered (stream, "\n");
print_spaces_filtered (2 * recurse, stream);
}
}
fprintf_filtered (stream, "}");
}
/* Special val_print routine to avoid printing multiple copies of virtual
baseclasses. */
static void
cplus_print_value (type, valaddr, stream, format, recurse, pretty, dont_print)
struct type *type;
char *valaddr;
FILE *stream;
int format;
int recurse;
enum val_prettyprint pretty;
struct type **dont_print;
{
struct obstack tmp_obstack;
struct type **last_dont_print
= (struct type **)obstack_next_free (&dont_print_obstack);
int i, n_baseclasses = TYPE_N_BASECLASSES (type);
if (dont_print == 0)
{
/* If we're at top level, carve out a completely fresh
chunk of the obstack and use that until this particular
invocation returns. */
tmp_obstack = dont_print_obstack;
/* Bump up the high-water mark. Now alpha is omega. */
obstack_finish (&dont_print_obstack);
}
for (i = 0; i < n_baseclasses; i++)
{
char *baddr;
int err;
if (BASETYPE_VIA_VIRTUAL (type, i))
{
struct type **first_dont_print
= (struct type **)obstack_base (&dont_print_obstack);
int j = (struct type **)obstack_next_free (&dont_print_obstack)
- first_dont_print;
while (--j >= 0)
if (TYPE_BASECLASS (type, i) == first_dont_print[j])
goto flush_it;
obstack_ptr_grow (&dont_print_obstack, TYPE_BASECLASS (type, i));
}
/* Fix to use baseclass_offset instead. FIXME */
baddr = baseclass_addr (type, i, valaddr, 0, &err);
if (err == 0 && baddr == 0)
error ("could not find virtual baseclass `%s'\n",
type_name_no_tag (TYPE_BASECLASS (type, i)));
if (pretty)
{
fprintf_filtered (stream, "\n");
print_spaces_filtered (2 * recurse, stream);
}
fputs_filtered ("<", stream);
fputs_filtered (type_name_no_tag (TYPE_BASECLASS (type, i)), stream);
fputs_filtered ("> = ", stream);
if (err != 0)
fprintf_filtered (stream, "<invalid address 0x%x>", baddr);
else
cp_print_value_fields (TYPE_BASECLASS (type, i), baddr, stream, format,
recurse, pretty,
(struct type **) obstack_base (&dont_print_obstack));
fputs_filtered (", ", stream);
flush_it:
;
}
if (dont_print == 0)
{
/* Free the space used to deal with the printing
of this type from top level. */
obstack_free (&dont_print_obstack, last_dont_print);
/* Reset watermark so that we can continue protecting
ourselves from whatever we were protecting ourselves. */
dont_print_obstack = tmp_obstack;
}
}
void
cp_print_class_member (valaddr, domain, stream, prefix)
char *valaddr;
struct type *domain;
FILE *stream;
char *prefix;
{
/* VAL is a byte offset into the structure type DOMAIN.
Find the name of the field for that offset and
print it. */
int extra = 0;
int bits = 0;
register unsigned int i;
unsigned len = TYPE_NFIELDS (domain);
/* @@ Make VAL into bit offset */
LONGEST val = unpack_long (builtin_type_int, valaddr) << 3;
for (i = TYPE_N_BASECLASSES (domain); i < len; i++)
{
int bitpos = TYPE_FIELD_BITPOS (domain, i);
QUIT;
if (val == bitpos)
break;
if (val < bitpos && i != 0)
{
/* Somehow pointing into a field. */
i -= 1;
extra = (val - TYPE_FIELD_BITPOS (domain, i));
if (extra & 0x7)
bits = 1;
else
extra >>= 3;
break;
}
}
if (i < len)
{
char *name;
fprintf_filtered (stream, prefix);
name = type_name_no_tag (domain);
if (name)
fputs_filtered (name, stream);
else
c_type_print_base (domain, stream, 0, 0);
fprintf_filtered (stream, "::");
fputs_filtered (TYPE_FIELD_NAME (domain, i), stream);
if (extra)
fprintf_filtered (stream, " + %d bytes", extra);
if (bits)
fprintf_filtered (stream, " (offset in bits)");
}
else
fprintf_filtered (stream, "%d", val >> 3);
}
void
_initialize_cp_valprint ()
{
add_show_from_set
(add_set_cmd ("vtbl", class_support, var_boolean, (char *)&vtblprint,
"Set printing of C++ virtual function tables.",
&setprintlist),
&showprintlist);
add_show_from_set
(add_set_cmd ("object", class_support, var_boolean, (char *)&objectprint,
"Set printing of object's derived type based on vtable info.",
&setprintlist),
&showprintlist);
/* Give people the defaults which they are used to. */
objectprint = 0;
vtblprint = 0;
obstack_begin (&dont_print_obstack, 32 * sizeof (struct type *));
}

View file

@ -358,6 +358,20 @@ enum language
language_m2 /* Modula-2 */
};
/* Possibilities for prettyprint parameters to routines which print
things. Like enum language, this should be in value.h, but needs
to be here for the same reason. FIXME: If we can eliminate this
as an arg to LA_VAL_PRINT, then we can probably move it back to
value.h. */
enum val_prettyprint
{
Val_no_prettyprint = 0,
Val_prettyprint,
/* Use the default setting which the user has specified. */
Val_pretty_default
};
/* Host machine definition. This will be a symlink to one of the
xm-*.h files, built by the `configure' script. */

View file

@ -1031,7 +1031,9 @@ struct_type (dip, thisdie, enddie, objfile)
char *tpart1;
struct dieinfo mbr;
char *nextdie;
#if !BITS_BIG_ENDIAN
int anonymous_size;
#endif
if ((type = lookup_utype (dip -> die_ref)) == NULL)
{
@ -1353,6 +1355,7 @@ decode_subscript_data_item (scan, end)
struct type *typep = NULL; /* Array type we are building */
struct type *nexttype; /* Type of each element (may be array) */
struct type *indextype; /* Type of this index */
struct type *rangetype;
unsigned int format;
unsigned short fundtype;
unsigned long lowbound;
@ -1384,8 +1387,9 @@ decode_subscript_data_item (scan, end)
complain (&subscript_data_items, DIE_ID, DIE_NAME);
nexttype = dwarf_fundamental_type (current_objfile, FT_INTEGER);
}
typep = create_array_type ((struct type *) NULL, nexttype, indextype,
lowbound, highbound);
rangetype = create_range_type ((struct type *) NULL, indextype,
lowbound, highbound);
typep = create_array_type ((struct type *) NULL, nexttype, rangetype);
break;
case FMT_FT_C_X:
case FMT_FT_X_C:
@ -1395,13 +1399,15 @@ decode_subscript_data_item (scan, end)
case FMT_UT_X_C:
case FMT_UT_X_X:
complain (&unhandled_array_subscript_format, DIE_ID, DIE_NAME, format);
typep = dwarf_fundamental_type (current_objfile, FT_INTEGER);
typep = create_array_type ((struct type *) NULL, typep, typep, 0, 1);
nexttype = dwarf_fundamental_type (current_objfile, FT_INTEGER);
rangetype = create_range_type ((struct type *) NULL, nexttype, 0, 0);
typep = create_array_type ((struct type *) NULL, nexttype, rangetype);
break;
default:
complain (&unknown_array_subscript_format, DIE_ID, DIE_NAME, format);
typep = dwarf_fundamental_type (current_objfile, FT_INTEGER);
typep = create_array_type ((struct type *) NULL, typep, typep, 0, 1);
nexttype = dwarf_fundamental_type (current_objfile, FT_INTEGER);
rangetype = create_range_type ((struct type *) NULL, nexttype, 0, 0);
typep = create_array_type ((struct type *) NULL, nexttype, rangetype);
break;
}
return (typep);

View file

@ -432,9 +432,7 @@ elf_symfile_read (objfile, section_offsets, mainline)
{
bfd *abfd = objfile->obfd;
struct elfinfo ei;
struct dbx_symfile_info *dbx;
struct cleanup *back_to;
asection *text_sect;
CORE_ADDR offset;
init_minimal_symbol_collection ();

View file

@ -174,22 +174,22 @@ evaluate_subexp (expect_type, exp, pos, noside)
switch (op)
{
case OP_SCOPE:
tem = strlen (&exp->elts[pc + 2].string);
(*pos) += 3 + ((tem + sizeof (union exp_element))
tem = longest_to_int (exp->elts[pc + 2].longconst);
(*pos) += 4 + ((tem + sizeof (union exp_element))
/ sizeof (union exp_element));
arg1 = value_struct_elt_for_reference (exp->elts[pc + 1].type,
0,
exp->elts[pc + 1].type,
&exp->elts[pc + 2].string,
&exp->elts[pc + 3].string,
expect_type);
if (arg1 == NULL)
error ("There is no field named %s", &exp->elts[pc + 2].string);
error ("There is no field named %s", &exp->elts[pc + 3].string);
return arg1;
case OP_LONG:
(*pos) += 3;
return value_from_longest (exp->elts[pc + 1].type,
exp->elts[pc + 2].longconst);
exp->elts[pc + 2].longconst);
case OP_DOUBLE:
(*pos) += 3;
@ -237,22 +237,24 @@ evaluate_subexp (expect_type, exp, pos, noside)
(*pos) += 2;
return value_of_register (longest_to_int (exp->elts[pc + 1].longconst));
/* start-sanitize-chill */
case OP_BOOL:
(*pos) += 2;
return value_from_longest (builtin_type_chill_bool,
exp->elts[pc + 1].longconst);
/* end-sanitize-chill */
case OP_INTERNALVAR:
(*pos) += 2;
return value_of_internalvar (exp->elts[pc + 1].internalvar);
case OP_STRING:
tem = strlen (&exp->elts[pc + 1].string);
(*pos) += 2 + ((tem + sizeof (union exp_element))
tem = longest_to_int (exp->elts[pc + 1].longconst);
(*pos) += 3 + ((tem + sizeof (union exp_element))
/ sizeof (union exp_element));
if (noside == EVAL_SKIP)
goto nosideret;
return value_string (&exp->elts[pc + 1].string, tem);
return value_string (&exp->elts[pc + 2].string, tem);
case TERNOP_COND:
/* Skip third and second args to evaluate the first one. */
@ -347,8 +349,8 @@ evaluate_subexp (expect_type, exp, pos, noside)
nargs = longest_to_int (exp->elts[pc + 1].longconst) + 1;
/* First, evaluate the structure into arg2 */
pc2 = (*pos)++;
tem2 = strlen (&exp->elts[pc2 + 1].string);
*pos += 2 + (tem2 + sizeof (union exp_element)) / sizeof (union exp_element);
tem2 = longest_to_int (exp->elts[pc2 + 1].longconst);
*pos += 3 + (tem2 + sizeof (union exp_element)) / sizeof (union exp_element);
if (noside == EVAL_SKIP)
goto nosideret;
@ -383,7 +385,7 @@ evaluate_subexp (expect_type, exp, pos, noside)
argvec[1] = arg2;
argvec[0] =
value_struct_elt (&temp, argvec+1, &exp->elts[pc2 + 1].string,
value_struct_elt (&temp, argvec+1, &exp->elts[pc2 + 2].string,
&static_memfuncp,
op == STRUCTOP_STRUCT
? "structure" : "structure pointer");
@ -428,40 +430,40 @@ evaluate_subexp (expect_type, exp, pos, noside)
return call_function_by_hand (argvec[0], nargs, argvec + 1);
case STRUCTOP_STRUCT:
tem = strlen (&exp->elts[pc + 1].string);
(*pos) += 2 + ((tem + sizeof (union exp_element))
tem = longest_to_int (exp->elts[pc + 1].longconst);
(*pos) += 3 + ((tem + sizeof (union exp_element))
/ sizeof (union exp_element));
arg1 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
if (noside == EVAL_SKIP)
goto nosideret;
if (noside == EVAL_AVOID_SIDE_EFFECTS)
return value_zero (lookup_struct_elt_type (VALUE_TYPE (arg1),
&exp->elts[pc + 1].string,
&exp->elts[pc + 2].string,
0),
lval_memory);
else
{
value temp = arg1;
return value_struct_elt (&temp, (value *)0, &exp->elts[pc + 1].string,
return value_struct_elt (&temp, (value *)0, &exp->elts[pc + 2].string,
(int *) 0, "structure");
}
case STRUCTOP_PTR:
tem = strlen (&exp->elts[pc + 1].string);
(*pos) += 2 + (tem + sizeof (union exp_element)) / sizeof (union exp_element);
tem = longest_to_int (exp->elts[pc + 1].longconst);
(*pos) += 3 + (tem + sizeof (union exp_element)) / sizeof (union exp_element);
arg1 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
if (noside == EVAL_SKIP)
goto nosideret;
if (noside == EVAL_AVOID_SIDE_EFFECTS)
return value_zero (lookup_struct_elt_type (TYPE_TARGET_TYPE
(VALUE_TYPE (arg1)),
&exp->elts[pc + 1].string,
&exp->elts[pc + 2].string,
0),
lval_memory);
else
{
value temp = arg1;
return value_struct_elt (&temp, (value *)0, &exp->elts[pc + 1].string,
return value_struct_elt (&temp, (value *)0, &exp->elts[pc + 2].string,
(int *) 0, "structure pointer");
}
@ -804,9 +806,8 @@ evaluate_subexp (expect_type, exp, pos, noside)
{
if (op == OP_SCOPE)
{
char *name = &exp->elts[pc+3].string;
int temm = strlen (name);
(*pos) += 2 + (temm + sizeof (union exp_element)) / sizeof (union exp_element);
int temm = longest_to_int (exp->elts[pc+3].longconst);
(*pos) += 3 + (temm + sizeof (union exp_element)) / sizeof (union exp_element);
}
else
evaluate_subexp (expect_type, exp, pos, EVAL_SKIP);

View file

@ -76,20 +76,20 @@ print_subexp (exp, pos, stream, prec)
case OP_SCOPE:
myprec = PREC_PREFIX;
assoc = 0;
(*pos) += 2;
(*pos) += 3;
print_subexp (exp, pos, stream,
(enum precedence) ((int) myprec + assoc));
fputs_filtered (" :: ", stream);
nargs = strlen (&exp->elts[pc + 2].string);
(*pos) += 1 + (nargs + sizeof (union exp_element)) / sizeof (union exp_element);
nargs = longest_to_int (exp->elts[pc + 2].longconst);
(*pos) += 2 + (nargs + sizeof (union exp_element)) / sizeof (union exp_element);
fputs_filtered (&exp->elts[pc + 2].string, stream);
fputs_filtered (&exp->elts[pc + 3].string, stream);
return;
case OP_LONG:
(*pos) += 3;
value_print (value_from_longest (exp->elts[pc + 1].type,
exp->elts[pc + 2].longconst),
exp->elts[pc + 2].longconst),
stream, 0, Val_no_prettyprint);
return;
@ -145,12 +145,13 @@ print_subexp (exp, pos, stream, prec)
return;
case OP_STRING:
nargs = strlen (&exp->elts[pc + 1].string);
(*pos) += 2 + (nargs + sizeof (union exp_element)) / sizeof (union exp_element);
/* local_printstr will print using the current repeat count threshold.
nargs = longest_to_int (exp -> elts[pc + 1].longconst);
(*pos) += 3 + (nargs + sizeof (union exp_element))
/ sizeof (union exp_element);
/* LA_PRINT_STRING will print using the current repeat count threshold.
If necessary, we can temporarily set it to zero, or pass it as an
additional parameter to local_printstr. -fnf */
local_printstr (stream, &exp->elts[pc + 1].string, nargs, 0);
additional parameter to LA_PRINT_STRING. -fnf */
LA_PRINT_STRING (stream, &exp->elts[pc + 2].string, nargs, 0);
return;
case TERNOP_COND:
@ -170,20 +171,20 @@ print_subexp (exp, pos, stream, prec)
return;
case STRUCTOP_STRUCT:
tem = strlen (&exp->elts[pc + 1].string);
(*pos) += 2 + (tem + sizeof (union exp_element)) / sizeof (union exp_element);
tem = longest_to_int (exp->elts[pc + 1].longconst);
(*pos) += 3 + (tem + sizeof (union exp_element)) / sizeof (union exp_element);
print_subexp (exp, pos, stream, PREC_SUFFIX);
fputs_filtered (".", stream);
fputs_filtered (&exp->elts[pc + 1].string, stream);
fputs_filtered (&exp->elts[pc + 2].string, stream);
return;
/* Will not occur for Modula-2 */
case STRUCTOP_PTR:
tem = strlen (&exp->elts[pc + 1].string);
(*pos) += 2 + (tem + sizeof (union exp_element)) / sizeof (union exp_element);
tem = longest_to_int (exp->elts[pc + 1].longconst);
(*pos) += 3 + (tem + sizeof (union exp_element)) / sizeof (union exp_element);
print_subexp (exp, pos, stream, PREC_SUFFIX);
fputs_filtered ("->", stream);
fputs_filtered (&exp->elts[pc + 1].string, stream);
fputs_filtered (&exp->elts[pc + 2].string, stream);
return;
case BINOP_SUBSCRIPT:

View file

@ -291,53 +291,78 @@ allocate_stub_method (type)
return (mtype);
}
/* Create a range type using either a blank type supplied in RESULT_TYPE,
or creating a new type. Indices will be of type INDEX_TYPE, and will
range from LOW_BOUND to HIGH_BOUND, inclusive.
FIXME: Maybe we should check the TYPE_CODE of RESULT_TYPE to make
sure it is TYPE_CODE_UNDEF before we bash it into a range type? */
struct type *
create_range_type (result_type, index_type, low_bound, high_bound)
struct type *result_type;
struct type *index_type;
int low_bound;
int high_bound;
{
if (result_type == NULL)
{
result_type = alloc_type (TYPE_OBJFILE (index_type));
}
TYPE_CODE (result_type) = TYPE_CODE_RANGE;
TYPE_TARGET_TYPE (result_type) = index_type;
TYPE_LENGTH (result_type) = TYPE_LENGTH (index_type);
TYPE_NFIELDS (result_type) = 2;
TYPE_FIELDS (result_type) = (struct field *)
TYPE_ALLOC (result_type, 2 * sizeof (struct field));
memset (TYPE_FIELDS (result_type), 0, 2 * sizeof (struct field));
TYPE_FIELD_BITPOS (result_type, 0) = low_bound;
TYPE_FIELD_BITPOS (result_type, 1) = high_bound;
TYPE_FIELD_TYPE (result_type, 0) = builtin_type_int; /* FIXME */
TYPE_FIELD_TYPE (result_type, 1) = builtin_type_int; /* FIXME */
return (result_type);
}
/* Create an array type using either a blank type supplied in RESULT_TYPE,
or creating a new type. Elements will be of type ELEMENT_TYPE, the
indices will be of type INDEX_TYPE, and will range from LOW_BOUND
to HIGH_BOUND, inclusive.
indices will be of type RANGE_TYPE.
FIXME: Maybe we should check the TYPE_CODE of RESULT_TYPE to make
sure it is TYPE_CODE_UNDEF before we bash it into an array type? */
struct type *
create_array_type (result_type, element_type, index_type, low_bound,
high_bound)
create_array_type (result_type, element_type, range_type)
struct type *result_type;
struct type *element_type;
struct type *index_type;
int low_bound;
int high_bound;
struct type *range_type;
{
struct type *range_type;
int low_bound;
int high_bound;
/* Create a blank type if we are not given one to bash on. */
if (TYPE_CODE (range_type) != TYPE_CODE_RANGE)
{
/* FIXME: We only handle range types at the moment. Complain and
create a dummy range type to use. */
warning ("internal error: array index type must be a range type");
range_type = lookup_fundamental_type (TYPE_OBJFILE (range_type),
FT_INTEGER);
range_type = create_range_type ((struct type *) NULL, range_type, 0, 0);
}
if (result_type == NULL)
{
result_type = alloc_type (TYPE_OBJFILE (element_type));
}
/* Create a range type. */
range_type = alloc_type (TYPE_OBJFILE (element_type));
TYPE_CODE (range_type) = TYPE_CODE_RANGE;
TYPE_TARGET_TYPE (range_type) = index_type;
TYPE_LENGTH (range_type) = sizeof (int); /* This should never be needed. */
TYPE_NFIELDS (range_type) = 2;
TYPE_FIELDS (range_type) = (struct field *)
TYPE_ALLOC (range_type, 2 * sizeof (struct field));
memset (TYPE_FIELDS (range_type), 0, 2 * sizeof (struct field));
TYPE_FIELD_BITPOS (range_type, 0) = low_bound;
TYPE_FIELD_BITPOS (range_type, 1) = high_bound;
TYPE_FIELD_TYPE (range_type, 0) = builtin_type_int; /* FIXME */
TYPE_FIELD_TYPE (range_type, 1) = builtin_type_int; /* FIXME */
/* Create the array type. */
TYPE_CODE (result_type) = TYPE_CODE_ARRAY;
TYPE_TARGET_TYPE (result_type) = element_type;
low_bound = TYPE_FIELD_BITPOS (range_type, 0);
high_bound = TYPE_FIELD_BITPOS (range_type, 1);
TYPE_LENGTH (result_type) =
TYPE_LENGTH (element_type) * (high_bound - low_bound + 1);
TYPE_NFIELDS (result_type) = 1;
TYPE_FIELDS (result_type) = (struct field *)
TYPE_ALLOC (result_type, sizeof (struct field));
TYPE_FIELDS (result_type) =
(struct field *) TYPE_ALLOC (result_type, sizeof (struct field));
memset (TYPE_FIELDS (result_type), 0, sizeof (struct field));
TYPE_FIELD_TYPE (result_type, 0) = range_type;
TYPE_VPTR_FIELDNO (result_type) = -1;
@ -1072,8 +1097,6 @@ print_cplus_stuff (type, spaces)
struct type *type;
int spaces;
{
int bitno;
printfi_filtered (spaces, "n_baseclasses %d\n",
TYPE_N_BASECLASSES (type));
printfi_filtered (spaces, "nfn_fields %d\n",

View file

@ -195,6 +195,7 @@ struct type
containing structure. For a function type, this is the
position in the argument list of this argument.
For a range bound or enum value, this is the value itself.
(FIXME: What about ranges larger than host int size?)
For BITS_BIG_ENDIAN=1 targets, it is the bit offset to the MSB.
For BITS_BIG_ENDIAN=0 targets, it is the bit offset to the LSB. */
@ -583,8 +584,10 @@ extern struct type *
lookup_function_type PARAMS ((struct type *));
extern struct type *
create_array_type PARAMS ((struct type *, struct type *, struct type *, int,
int));
create_range_type PARAMS ((struct type *, struct type *, int, int));
extern struct type *
create_array_type PARAMS ((struct type *, struct type *, struct type *));
extern struct type *
lookup_unsigned_typename PARAMS ((char *));

View file

@ -847,7 +847,7 @@ unset_environment_command (var, from_tty)
/* Handle the execution path (PATH variable) */
const static char path_var_name[] = "PATH";
static const char path_var_name[] = "PATH";
/* ARGSUSED */
static void

View file

@ -510,6 +510,7 @@ wait_for_inferior ()
int remove_breakpoints_on_following_step = 0;
int current_line;
int handling_longjmp = 0; /* FIXME */
struct symtab *symtab;
sal = find_pc_line(prev_pc, 0);
current_line = sal.line;
@ -972,8 +973,9 @@ wait_for_inferior ()
if (tmp != 0)
stop_func_start = tmp;
if (find_pc_function (stop_func_start) != 0)
goto step_into_function;
symtab = find_pc_symtab (stop_pc);
if (symtab && LINETABLE (symtab))
goto step_into_function;
step_over_function:
/* A subroutine call has happened. */
@ -1198,9 +1200,6 @@ save_pc:
void
normal_stop ()
{
char *tem;
struct cmd_list_element *c;
/* Make sure that the current_frame's pc is correct. This
is a correction for setting up the frame info before doing
DECR_PC_AFTER_BREAK */
@ -1301,6 +1300,7 @@ hook_stop_stub (cmd)
char *cmd;
{
execute_user_command ((struct cmd_list_element *)cmd, 0);
return (0);
}
@ -1695,7 +1695,7 @@ Pass means let program see this signal; otherwise program doesn't know.\n\
Ignore is a synonym for nopass and noignore is a synonym for pass.\n\
Pass and Stop may be combined.");
stop_command = add_cmd ("stop", class_pseudo, NO_FUNCTION,
stop_command = add_cmd ("stop", class_obscure, not_just_help_class_command,
"There is no `stop' command, but you can set a hook on `stop'.\n\
This allows you to set a list of commands to be run each time execution\n\
of the inferior program stops.", &cmdlist);

View file

@ -1140,8 +1140,36 @@ unk_lang_create_fundamental_type (objfile, typeid)
error ("internal error - unimplemented function unk_lang_create_fundamental_type called.");
}
void
unk_lang_print_type (type, varstring, stream, show, level)
struct type *type;
char *varstring;
FILE *stream;
int show;
int level;
{
error ("internal error - unimplemented function unk_lang_print_type called.");
}
int
unk_lang_val_print (type, valaddr, address, stream, format, deref_ref,
recurse, pretty)
struct type *type;
char *valaddr;
CORE_ADDR address;
FILE *stream;
int format;
int deref_ref;
int recurse;
enum val_prettyprint pretty;
{
error ("internal error - unimplemented function unk_lang_val_print called.");
}
static struct type ** const (unknown_builtin_types[]) = { 0 };
static const struct op_print unk_op_print_tab[] = { 0 };
static const struct op_print unk_op_print_tab[] = {
{NULL, 0, 0, 0}
};
const struct language_defn unknown_language_defn = {
"unknown",
@ -1154,6 +1182,8 @@ const struct language_defn unknown_language_defn = {
unk_lang_printchar, /* Print character constant */
unk_lang_printstr,
unk_lang_create_fundamental_type,
unk_lang_print_type, /* Print a type using appropriate syntax */
unk_lang_val_print, /* Print a value using appropriate syntax */
&builtin_type_error, /* longest signed integral type */
&builtin_type_error, /* longest unsigned integral type */
&builtin_type_error, /* longest floating point type */
@ -1177,6 +1207,8 @@ const struct language_defn auto_language_defn = {
unk_lang_printchar, /* Print character constant */
unk_lang_printstr,
unk_lang_create_fundamental_type,
unk_lang_print_type, /* Print a type using appropriate syntax */
unk_lang_val_print, /* Print a value using appropriate syntax */
&builtin_type_error, /* longest signed integral type */
&builtin_type_error, /* longest unsigned integral type */
&builtin_type_error, /* longest floating point type */
@ -1199,6 +1231,8 @@ const struct language_defn local_language_defn = {
unk_lang_printchar, /* Print character constant */
unk_lang_printstr,
unk_lang_create_fundamental_type,
unk_lang_print_type, /* Print a type using appropriate syntax */
unk_lang_val_print, /* Print a value using appropriate syntax */
&builtin_type_error, /* longest signed integral type */
&builtin_type_error, /* longest unsigned integral type */
&builtin_type_error, /* longest floating point type */

View file

@ -98,33 +98,89 @@ struct language_format_info
/* Structure tying together assorted information about a language. */
struct language_defn {
char * la_name; /* Name of the language */
enum language la_language; /* its symtab language-enum (defs.h) */
struct type ** const
*la_builtin_type_vector; /* Its builtin types */
enum range_check la_range_check; /* Default range checking */
enum type_check la_type_check; /* Default type checking */
int (*la_parser) PARAMS((void)); /* Parser function */
void (*la_error) PARAMS ((char *)); /* Parser error function */
void (*la_printchar) PARAMS ((int, FILE *));
void (*la_printstr) PARAMS ((FILE *, char *, unsigned int, int));
struct type *(*la_fund_type) PARAMS ((struct objfile *, int));
struct type **la_longest_int; /* Longest signed integral type */
struct type **la_longest_unsigned_int; /* Longest uns integral type */
struct type **la_longest_float; /* Longest floating point type */
struct language_format_info
la_binary_format; /* Base 2 (binary) formats. */
struct language_format_info
la_octal_format; /* Base 8 (octal) formats. */
struct language_format_info
la_decimal_format; /* Base 10 (decimal) formats */
struct language_format_info
la_hex_format; /* Base 16 (hexadecimal) formats */
const struct op_print
*la_op_print_tab; /* Table for printing expressions */
/* Add fields above this point, so the magic number is always last. */
long la_magic; /* Magic number for compat checking */
struct language_defn
{
/* Name of the language */
char *la_name;
/* its symtab language-enum (defs.h) */
enum language la_language;
/* Its builtin types */
struct type ** const *la_builtin_type_vector;
/* Default range checking */
enum range_check la_range_check;
/* Default type checking */
enum type_check la_type_check;
/* Parser function. */
int (*la_parser) PARAMS((void));
/* Parser error function */
void (*la_error) PARAMS ((char *));
void (*la_printchar) PARAMS ((int, FILE *));
void (*la_printstr) PARAMS ((FILE *, char *, unsigned int, int));
struct type *(*la_fund_type) PARAMS ((struct objfile *, int));
/* Print a type using syntax appropriate for this language. */
void (*la_print_type) PARAMS ((struct type *, char *, FILE *, int, int));
/* Print a value using syntax appropriate for this language. */
int (*la_val_print) PARAMS ((struct type *, char *, CORE_ADDR, FILE *,
int, int, int, enum val_prettyprint));
/* Longest signed integral type */
struct type **la_longest_int;
/* Longest unsigned integral type */
struct type **la_longest_unsigned_int;
/* Longest floating point type */
struct type **la_longest_float;
/* Base 2 (binary) formats. */
struct language_format_info la_binary_format;
/* Base 8 (octal) formats. */
struct language_format_info la_octal_format;
/* Base 10 (decimal) formats */
struct language_format_info la_decimal_format;
/* Base 16 (hexadecimal) formats */
struct language_format_info la_hex_format;
/* Table for printing expressions */
const struct op_print *la_op_print_tab;
/* Add fields above this point, so the magic number is always last. */
/* Magic number for compat checking */
long la_magic;
};
#define LANG_MAGIC 910823L
@ -181,6 +237,13 @@ set_language PARAMS ((enum language));
#define create_fundamental_type(objfile,typeid) \
(current_language->la_fund_type(objfile, typeid))
#define LA_PRINT_TYPE(type,varstring,stream,show,level) \
(current_language->la_print_type(type,varstring,stream,show,level))
#define LA_VAL_PRINT(type,valaddr,addr,stream,fmt,deref,recurse,pretty) \
(current_language->la_val_print(type,valaddr,addr,stream,fmt,deref, \
recurse,pretty))
/* Return a format string for printf that will print a number in one of
the local (language-specific) formats. Result is static and is
overwritten by the next call. Takes printf options like "08" or "l"
@ -222,9 +285,9 @@ set_language PARAMS ((enum language));
#define local_hex_format_suffix() \
(current_language->la_hex_format.la_format_suffix)
#define local_printchar(ch, stream) \
#define LA_PRINT_CHAR(ch, stream) \
(current_language->la_printchar(ch, stream))
#define local_printstr(stream, string, length, force_ellipses) \
#define LA_PRINT_STRING(stream, string, length, force_ellipses) \
(current_language->la_printstr(stream, string, length, force_ellipses))
/* Test a character to decide whether it can be printed in literal form

View file

@ -200,7 +200,6 @@ m2_create_fundamental_type (objfile, typeid)
int typeid;
{
register struct type *type = NULL;
register int nbytes;
switch (typeid)
{
@ -351,7 +350,7 @@ m2_create_fundamental_type (objfile, typeid)
/* Table of operators and their precedences for printing expressions. */
const static struct op_print m2_op_print_tab[] = {
static const struct op_print m2_op_print_tab[] = {
{"+", BINOP_ADD, PREC_ADD, 0},
{"+", UNOP_PLUS, PREC_PREFIX, 0},
{"-", BINOP_SUB, PREC_ADD, 0},
@ -404,6 +403,8 @@ const struct language_defn m2_language_defn = {
m2_printchar, /* Print character constant */
m2_printstr, /* function to print string constant */
m2_create_fundamental_type, /* Create fundamental type in this language */
m2_print_type, /* Print a type using appropriate syntax */
m2_val_print, /* Print a value using appropriate syntax */
&builtin_type_m2_int, /* longest signed integral type */
&builtin_type_m2_card, /* longest unsigned integral type */
&builtin_type_m2_real, /* longest floating point type */

View file

@ -22,3 +22,10 @@ m2_parse PARAMS ((void)); /* Defined in m2-exp.y */
extern void
m2_error PARAMS ((char *)); /* Defined in m2-exp.y */
extern void /* Defined in m2-typeprint.c */
m2_print_type PARAMS ((struct type *, char *, FILE *, int, int));
extern int
m2_val_print PARAMS ((struct type *, char *, CORE_ADDR, FILE *, int, int,
int, enum val_prettyprint));

49
gdb/m2-typeprint.c Normal file
View file

@ -0,0 +1,49 @@
/* Support for printing Modula 2 types for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "obstack.h"
#include "bfd.h" /* Binary File Description */
#include "symtab.h"
#include "gdbtypes.h"
#include "expression.h"
#include "value.h"
#include "gdbcore.h"
#include "target.h"
#include "command.h"
#include "gdbcmd.h"
#include "language.h"
#include "demangle.h"
#include "m2-lang.h"
#include <string.h>
#include <errno.h>
void
m2_print_type (type, varstring, stream, show, level)
struct type *type;
char *varstring;
FILE *stream;
int show;
int level;
{
extern void c_print_type PARAMS ((struct type *, char *, FILE *, int, int));
c_print_type (type, varstring, stream, show, level); /* FIXME */
}

45
gdb/m2-valprint.c Normal file
View file

@ -0,0 +1,45 @@
/* Support for printing Modula 2 values for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "obstack.h"
#include "symtab.h"
#include "gdbtypes.h"
#include "valprint.h"
/* FIXME: For now, just explicitly declare c_val_print and use it instead */
int
m2_val_print (type, valaddr, address, stream, format, deref_ref, recurse,
pretty)
struct type *type;
char *valaddr;
CORE_ADDR address;
FILE *stream;
int format;
int deref_ref;
int recurse;
enum val_prettyprint pretty;
{
extern int
c_val_print PARAMS ((struct type *, char *, CORE_ADDR, FILE *, int, int,
int, enum val_prettyprint));
return (c_val_print (type, valaddr, address, stream, format, deref_ref,
recurse, pretty));
}

View file

@ -898,7 +898,6 @@ execute_command (p, from_tty)
int from_tty;
{
register struct cmd_list_element *c;
register struct command_line *cmdlines;
register enum language flang;
static int warned = 0;
@ -2072,7 +2071,7 @@ echo_command (text, from_tty)
register int c;
if (text)
while (c = *p++)
while ((c = *p++) != '\0')
{
if (c == '\\')
{

View file

@ -1555,7 +1555,8 @@ upgrade_type(tpp, tq, ax, bigend)
return 0;
case tqArray:
/* We should probably try to use create_array_type here. FIXME! */
/* We should probably try to use create_range_type and
create_array_type here. FIXME! */
off = 0;
t = init_type(TYPE_CODE_ARRAY, 0, 0, (char *) NULL,
(struct objfile *) NULL);

View file

@ -136,18 +136,6 @@ free_display PARAMS ((struct display *));
static void
display_command PARAMS ((char *, int));
static void
ptype_command PARAMS ((char *, int));
static struct type *
ptype_eval PARAMS ((struct expression *));
static void
whatis_command PARAMS ((char *, int));
static void
whatis_exp PARAMS ((char *, int));
static void
x_command PARAMS ((char *, int));
@ -445,9 +433,9 @@ print_scalar_formatted (valaddr, type, format, size, stream)
case 'd':
#ifdef LONG_LONG
fprintf_filtered (stream, "%lld", val_long);
fprintf_filtered (stream, local_decimal_format_custom("ll"), val_long);
#else
fprintf_filtered (stream, "%d", val_long);
fprintf_filtered (stream, local_decimal_format(), val_long);
#endif
break;
@ -531,7 +519,9 @@ print_scalar_formatted (valaddr, type, format, size, stream)
if (*cp == '\0')
cp--;
}
fprintf_filtered (stream, local_binary_format_prefix());
fprintf_filtered (stream, cp);
fprintf_filtered (stream, local_binary_format_suffix());
}
break;
@ -1052,94 +1042,7 @@ x_command (exp, from_tty)
set_internalvar (lookup_internalvar ("__"), last_examine_value);
}
}
/* Commands for printing types of things. */
/* Print type of EXP, or last thing in value history if EXP == NULL.
show is passed to type_print. */
static void
whatis_exp (exp, show)
char *exp;
int show;
{
struct expression *expr;
register value val;
register struct cleanup *old_chain;
if (exp)
{
expr = parse_expression (exp);
old_chain = make_cleanup (free_current_contents, &expr);
val = evaluate_type (expr);
}
else
val = access_value_history (0);
printf_filtered ("type = ");
type_print (VALUE_TYPE (val), "", stdout, show);
printf_filtered ("\n");
if (exp)
do_cleanups (old_chain);
}
/* ARGSUSED */
static void
whatis_command (exp, from_tty)
char *exp;
int from_tty;
{
/* Most of the time users do not want to see all the fields
in a structure. If they do they can use the "ptype" command.
Hence the "-1" below. */
whatis_exp (exp, -1);
}
/* Simple subroutine for ptype_command. */
static
struct type *
ptype_eval(exp)
struct expression *exp;
{
if(exp->elts[0].opcode==OP_TYPE)
return exp->elts[1].type;
else
return 0;
}
/* TYPENAME is either the name of a type, or an expression. */
/* ARGSUSED */
static void
ptype_command (typename, from_tty)
char *typename;
int from_tty;
{
register struct type *type;
struct expression *expr;
register struct cleanup *old_chain;
if (typename)
{
expr = parse_expression (typename);
old_chain = make_cleanup (free_current_contents, &expr);
type = ptype_eval (expr);
if(type)
{
printf_filtered ("type = ");
type_print (type, "", stdout, 1);
printf_filtered ("\n");
do_cleanups (old_chain);
}
else
{
do_cleanups (old_chain);
whatis_exp (typename, 1);
}
}
else
whatis_exp (typename, 1);
}
/* Add an expression to the auto-display chain.
Specify the expression. */
@ -1211,7 +1114,7 @@ clear_displays ()
{
register struct display *d;
while (d = display_chain)
while ((d = display_chain) != NULL)
{
free ((PTR)d->exp);
display_chain = d->next;
@ -1583,18 +1486,17 @@ print_frame_args (func, fi, num, stream)
continue;
}
/* We have to re-look-up the symbol because arguments often have
/* If the symbol name is non-null,
we have to re-look-up the symbol because arguments often have
two entries (one a parameter, one a register or local), and the one
we want is the non-parm, which lookup_symbol will find for
us. After this, sym could be any SYMBOL_CLASS... */
#ifdef IBM6000_TARGET
/* AIX/RS6000 implements a concept of traceback tables, in which case
it creates nameless parameters. Looking for those parameter symbols
will result in an error. */
us. After this, sym could be any SYMBOL_CLASS...
if ( *SYMBOL_NAME (sym))
#endif
sym = lookup_symbol (SYMBOL_NAME (sym),
Null parameter names occur on the RS/6000, for traceback tables.
FIXME, should we even print them? */
if (*SYMBOL_NAME (sym))
sym = lookup_symbol (SYMBOL_NAME (sym),
b, VAR_NAMESPACE, (int *)NULL, (struct symtab **)NULL);
/* Print the current arg. */
@ -2006,15 +1908,6 @@ Default is the function surrounding the pc of the selected frame.\n\
With a single argument, the function surrounding that address is dumped.\n\
Two arguments are taken as a range of memory to dump.");
add_com ("ptype", class_vars, ptype_command,
"Print definition of type TYPE.\n\
Argument may be a type name defined by typedef, or \"struct STRUCTNAME\"\n\
or \"union UNIONNAME\" or \"enum ENUMNAME\".\n\
The selected stack frame's lexical context is used to look up the name.");
add_com ("whatis", class_vars, whatis_command,
"Print data type of expression EXP.");
#if 0
add_com ("whereis", class_vars, whereis_command,
"Print line number and file of definition of variable.");

View file

@ -69,8 +69,6 @@ int
serial_open(name)
const char *name;
{
struct sgttyb sgttyb;
desc = open (name, O_RDWR);
if (desc < 0)
error("Open of %s failed: %s", name, safe_strerror(errno));

View file

@ -427,9 +427,10 @@ source_info (ignore, from_tty)
if (s->fullname)
printf_filtered ("Located in %s\n", s->fullname);
if (s->nlines)
printf_filtered ("Contains %d lines\n", s->nlines);
printf_filtered ("Contains %d line%s.\n", s->nlines,
s->nlines == 1 ? "" : "s");
printf_filtered("Source language %s.\n", language_str (s->language));
printf_filtered("Source language is %s.\n", language_str (s->language));
}
@ -610,13 +611,15 @@ find_source_lines (s, desc)
int desc;
{
struct stat st;
char c;
register char *data, *p, *end;
int nlines = 0;
int lines_allocated = 1000;
int *line_charpos;
long exec_mtime;
int size;
#ifdef LSEEK_NOT_LINEAR
char c;
#endif
line_charpos = (int *) xmmalloc (s -> objfile -> md,
lines_allocated * sizeof (int));
@ -779,6 +782,8 @@ identify_source_line (s, line, mid_statement)
get_filename_and_charpos (s, (char **)NULL);
if (s->fullname == 0)
return 0;
if (line >= s->nlines)
return 0;
printf ("\032\032%s:%d:%d:%s:0x%x\n", s->fullname,
line, s->line_charpos[line - 1],
mid_statement ? "middle" : "beg",

View file

@ -1073,7 +1073,7 @@ read_type (pp, objfile)
/* Copy the prefix. */
from = prefix;
while (*to++ = *from++)
while ((*to++ = *from++) != '\0')
;
to--;
@ -2372,7 +2372,9 @@ read_array_type (pp, type, objfile)
upper = -1;
}
type = create_array_type (type, element_type, index_type, lower, upper);
range_type =
create_range_type ((struct type *) NULL, index_type, lower, upper);
type = create_array_type (type, element_type, range_type);
/* If we have an array whose element type is not yet known, but whose
bounds *are* known, record it to be adjusted at the end of the file. */
@ -2745,6 +2747,7 @@ read_range_type (pp, typenums, objfile)
int n2bits, n3bits;
int self_subrange;
struct type *result_type;
struct type *index_type;
/* First comes a type we are a subrange of.
In C it is usually 0, 1 or the type being defined. */
@ -2903,26 +2906,15 @@ read_range_type (pp, typenums, objfile)
if (self_subrange)
return error_type (pp);
result_type = alloc_type (objfile);
index_type = *dbx_lookup_type (rangenums);
if (index_type == NULL)
{
complain (&range_type_base_complaint, rangenums[1]);
index_type = lookup_fundamental_type (objfile, FT_INTEGER);
}
TYPE_CODE (result_type) = TYPE_CODE_RANGE;
TYPE_TARGET_TYPE (result_type) = *dbx_lookup_type(rangenums);
if (TYPE_TARGET_TYPE (result_type) == 0) {
complain (&range_type_base_complaint, rangenums[1]);
TYPE_TARGET_TYPE (result_type) = lookup_fundamental_type (objfile, FT_INTEGER);
}
TYPE_NFIELDS (result_type) = 2;
TYPE_FIELDS (result_type) = (struct field *)
TYPE_ALLOC (result_type, 2 * sizeof (struct field));
memset (TYPE_FIELDS (result_type), 0, 2 * sizeof (struct field));
TYPE_FIELD_BITPOS (result_type, 0) = n2;
TYPE_FIELD_BITPOS (result_type, 1) = n3;
TYPE_LENGTH (result_type) = TYPE_LENGTH (TYPE_TARGET_TYPE (result_type));
return result_type;
result_type = create_range_type ((struct type *) NULL, index_type, n2, n3);
return (result_type);
}
/* Read a number from the string pointed to by *PP.

View file

@ -55,29 +55,18 @@ dump_msymbols PARAMS ((struct objfile *, FILE *));
static void
dump_objfile PARAMS ((struct objfile *));
static void
printobjfiles_command PARAMS ((char *, int));
static int
block_depth PARAMS ((struct block *));
static void
print_partial_symbol PARAMS ((struct partial_symbol *, int, char *, FILE *));
static void
printpsyms_command PARAMS ((char *, int));
static void
print_symbol PARAMS ((struct symbol *, int, FILE *));
static void
printsyms_command PARAMS ((char *, int));
static void
free_symtab_block PARAMS ((struct objfile *, struct block *));
static void
printmsyms_command PARAMS ((char *, int));
/* Free a struct block <- B and all the symbols defined in that block. */
@ -152,6 +141,8 @@ free_symtab (s)
mfree (s -> objfile -> md, (PTR) s);
}
#if MAINTENANCE_CMDS
static void
dump_objfile (objfile)
struct objfile *objfile;
@ -267,11 +258,12 @@ dump_psymtab (objfile, psymtab, outfile)
/* FIXME, we need to be able to print the relocation stuff. */
/* This prints some garbage for anything but stabs right now. FIXME. */
fprintf_filtered (outfile, " Relocate symbols by 0x%x, 0x%x, 0x%x, 0x%x.\n",
ANOFFSET (psymtab->section_offsets, 0),
ANOFFSET (psymtab->section_offsets, 1),
ANOFFSET (psymtab->section_offsets, 2),
ANOFFSET (psymtab->section_offsets, 3));
if (psymtab->section_offsets)
fprintf_filtered (outfile, " Relocate symbols by 0x%x, 0x%x, 0x%x, 0x%x.\n",
ANOFFSET (psymtab->section_offsets, 0),
ANOFFSET (psymtab->section_offsets, 1),
ANOFFSET (psymtab->section_offsets, 2),
ANOFFSET (psymtab->section_offsets, 3));
fprintf_filtered (outfile, " Symbols cover text addresses 0x%x-0x%x\n",
psymtab -> textlow, psymtab -> texthigh);
@ -334,6 +326,8 @@ dump_symtab (objfile, symtab, outfile)
fprintf (outfile, " (under 0x%x)", (unsigned int) BLOCK_SUPERBLOCK (b));
if (BLOCK_FUNCTION (b))
fprintf (outfile, " %s", SYMBOL_NAME (BLOCK_FUNCTION (b)));
if (BLOCK_GCC_COMPILED(b))
fprintf (outfile, " gcc%d compiled", BLOCK_GCC_COMPILED(b));
fputc ('\n', outfile);
blen = BLOCK_NSYMS (b);
for (j = 0; j < blen; j++)
@ -344,8 +338,8 @@ dump_symtab (objfile, symtab, outfile)
fprintf (outfile, "\n");
}
static void
printsyms_command (args, from_tty)
void
maintenance_print_symbols (args, from_tty)
char *args;
int from_tty;
{
@ -361,7 +355,7 @@ printsyms_command (args, from_tty)
if (args == NULL)
{
error ("printsyms takes an output file name and optional symbol file name");
error ("print-symbols takes an output file name and optional symbol file name");
}
else if ((argv = buildargv (args)) == NULL)
{
@ -412,7 +406,7 @@ print_symbol (symbol, depth, outfile)
{
if (TYPE_NAME (SYMBOL_TYPE (symbol)))
{
type_print_1 (SYMBOL_TYPE (symbol), "", outfile, 1, depth);
LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth);
}
else
{
@ -422,7 +416,7 @@ print_symbol (symbol, depth, outfile)
: (TYPE_CODE (SYMBOL_TYPE (symbol)) == TYPE_CODE_STRUCT
? "struct" : "union")),
SYMBOL_NAME (symbol));
type_print_1 (SYMBOL_TYPE (symbol), "", outfile, 1, depth);
LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth);
}
fprintf (outfile, ";\n");
}
@ -433,9 +427,9 @@ print_symbol (symbol, depth, outfile)
if (SYMBOL_TYPE (symbol))
{
/* Print details of types, except for enums where it's clutter. */
type_print_1 (SYMBOL_TYPE (symbol), SYMBOL_NAME (symbol), outfile,
TYPE_CODE (SYMBOL_TYPE (symbol)) != TYPE_CODE_ENUM,
depth);
LA_PRINT_TYPE (SYMBOL_TYPE (symbol), SYMBOL_NAME (symbol), outfile,
TYPE_CODE (SYMBOL_TYPE (symbol)) != TYPE_CODE_ENUM,
depth);
fprintf (outfile, "; ");
}
else
@ -533,8 +527,8 @@ print_symbol (symbol, depth, outfile)
fprintf (outfile, "\n");
}
static void
printpsyms_command (args, from_tty)
void
maintenance_print_psymbols (args, from_tty)
char *args;
int from_tty;
{
@ -550,7 +544,7 @@ printpsyms_command (args, from_tty)
if (args == NULL)
{
error ("printpsyms takes an output file name and optional symbol file name");
error ("print-psymbols takes an output file name and optional symbol file name");
}
else if ((argv = buildargv (args)) == NULL)
{
@ -665,8 +659,8 @@ print_partial_symbol (p, count, what, outfile)
}
}
static void
printmsyms_command (args, from_tty)
void
maintenance_print_msymbols (args, from_tty)
char *args;
int from_tty;
{
@ -681,7 +675,7 @@ printmsyms_command (args, from_tty)
if (args == NULL)
{
error ("printmsyms takes an output file name and optional symbol file name");
error ("print-msymbols takes an output file name and optional symbol file name");
}
else if ((argv = buildargv (args)) == NULL)
{
@ -716,8 +710,8 @@ printmsyms_command (args, from_tty)
do_cleanups (cleanups);
}
static void
printobjfiles_command (ignore, from_tty)
void
maintenance_print_objfiles (ignore, from_tty)
char *ignore;
int from_tty;
{
@ -730,6 +724,7 @@ printobjfiles_command (ignore, from_tty)
dump_objfile (objfile);
immediate_quit--;
}
/* Return the nexting depth of a block within other blocks in its symtab. */
@ -738,10 +733,15 @@ block_depth (block)
struct block *block;
{
register int i = 0;
while (block = BLOCK_SUPERBLOCK (block)) i++;
while ((block = BLOCK_SUPERBLOCK (block)) != NULL)
{
i++;
}
return i;
}
#endif /* MAINTENANCE_CMDS */
/* Increase the space allocated for LISTP, which is probably
global_psymbol_list or static_psymbol_list. This space will eventually
@ -829,20 +829,3 @@ add_psymbol_addr_to_list (name, namelength, namespace, class, listp, psymval)
}
#endif /* DEBUG */
void
_initialize_symmisc ()
{
add_com ("printmsyms", class_obscure, printmsyms_command,
"Print dump of current minimal symbol definitions to file OUTFILE.\n\
If a SOURCE file is specified, dump only that file's symbols.");
add_com ("printpsyms", class_obscure, printpsyms_command,
"Print dump of current partial symbol definitions to file OUTFILE.\n\
If a SOURCE file is specified, dump only that file's partial symbols.");
add_com ("printsyms", class_obscure, printsyms_command,
"Print dump of current symbol definitions to file OUTFILE.\n\
If a SOURCE file is specified, dump only that file's symbols.");
add_com ("printobjfiles", class_obscure, printobjfiles_command,
"Print dump of current object file definitions.");
}

View file

@ -1145,7 +1145,7 @@ find_pc_line (pc, notcurrent)
val.pc = best->pc;
if (best_end && (!alt || best_end < alt->pc))
val.end = best_end;
else if (alt->pc)
else if (alt)
val.end = alt->pc;
else
val.end = BLOCK_END (BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK));
@ -2352,7 +2352,7 @@ list_symbols (regexp, class, bpt)
/* Typedef that is not a C++ class */
if (class == 2
&& SYMBOL_NAMESPACE (sym) != STRUCT_NAMESPACE)
typedef_print (SYMBOL_TYPE(sym), sym, stdout);
c_typedef_print (SYMBOL_TYPE(sym), sym, stdout);
/* variable, func, or typedef-that-is-c++-class */
else if (class < 2 ||
(class == 2 &&
@ -2367,13 +2367,15 @@ list_symbols (regexp, class, bpt)
}
else
{
# if 0
/* FIXME, why is this zapped out? */
# if 0 /* FIXME, why is this zapped out? */
char buf[1024];
type_print_base (TYPE_FN_FIELD_TYPE(t, i), stdout, 0, 0);
type_print_varspec_prefix (TYPE_FN_FIELD_TYPE(t, i), stdout, 0);
c_type_print_base (TYPE_FN_FIELD_TYPE(t, i),
stdout, 0, 0);
c_type_print_varspec_prefix (TYPE_FN_FIELD_TYPE(t, i),
stdout, 0);
sprintf (buf, " %s::", type_name_no_tag (t));
type_print_method_args (TYPE_FN_FIELD_ARGS (t, i), buf, name, stdout);
cp_type_print_method_args (TYPE_FN_FIELD_ARGS (t, i),
buf, name, stdout);
# endif
}
}

305
gdb/typeprint.c Normal file
View file

@ -0,0 +1,305 @@
/* Language independent support for printing types for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
#include "obstack.h"
#include "bfd.h" /* Binary File Description */
#include "symtab.h"
#include "gdbtypes.h"
#include "expression.h"
#include "value.h"
#include "gdbcore.h"
#include "command.h"
#include "gdbcmd.h"
#include "target.h"
#include "language.h"
#include "demangle.h"
#include <string.h>
#include <errno.h>
static void
ptype_command PARAMS ((char *, int));
static struct type *
ptype_eval PARAMS ((struct expression *));
static void
whatis_command PARAMS ((char *, int));
static void
whatis_exp PARAMS ((char *, int));
/* Print a description of a type TYPE in the form of a declaration of a
variable named VARSTRING. (VARSTRING is demangled if necessary.)
Output goes to STREAM (via stdio).
If SHOW is positive, we show the contents of the outermost level
of structure even if there is a type name that could be used instead.
If SHOW is negative, we never show the details of elements' types. */
void
type_print (type, varstring, stream, show)
struct type *type;
char *varstring;
FILE *stream;
int show;
{
LA_PRINT_TYPE (type, varstring, stream, show, 0);
}
/* Print type of EXP, or last thing in value history if EXP == NULL.
show is passed to type_print. */
static void
whatis_exp (exp, show)
char *exp;
int show;
{
struct expression *expr;
register value val;
register struct cleanup *old_chain;
if (exp)
{
expr = parse_expression (exp);
old_chain = make_cleanup (free_current_contents, &expr);
val = evaluate_type (expr);
}
else
val = access_value_history (0);
printf_filtered ("type = ");
type_print (VALUE_TYPE (val), "", stdout, show);
printf_filtered ("\n");
if (exp)
do_cleanups (old_chain);
}
/* ARGSUSED */
static void
whatis_command (exp, from_tty)
char *exp;
int from_tty;
{
/* Most of the time users do not want to see all the fields
in a structure. If they do they can use the "ptype" command.
Hence the "-1" below. */
whatis_exp (exp, -1);
}
/* Simple subroutine for ptype_command. */
static struct type *
ptype_eval (exp)
struct expression *exp;
{
if (exp->elts[0].opcode == OP_TYPE)
{
return (exp->elts[1].type);
}
else
{
return (NULL);
}
}
/* TYPENAME is either the name of a type, or an expression. */
/* ARGSUSED */
static void
ptype_command (typename, from_tty)
char *typename;
int from_tty;
{
register struct type *type;
struct expression *expr;
register struct cleanup *old_chain;
if (typename == NULL)
{
/* Print type of last thing in value history. */
whatis_exp (typename, 1);
}
else
{
expr = parse_expression (typename);
old_chain = make_cleanup (free_current_contents, &expr);
type = ptype_eval (expr);
if (type != NULL)
{
/* User did "ptype <typename>" */
printf_filtered ("type = ");
type_print (type, "", stdout, 1);
printf_filtered ("\n");
do_cleanups (old_chain);
}
else
{
/* User did "ptype <symbolname>" */
do_cleanups (old_chain);
whatis_exp (typename, 1);
}
}
}
/* Print integral scalar data VAL, of type TYPE, onto stdio stream STREAM.
Used to print data from type structures in a specified type. For example,
array bounds may be characters or booleans in some languages, and this
allows the ranges to be printed in their "natural" form rather than as
decimal integer values.
FIXME: This is here simply because only the type printing routines
currently use it, and it wasn't clear if it really belonged somewhere
else (like printcmd.c). There are a lot of other gdb routines that do
something similar, but they are generally concerned with printing values
that come from the inferior in target byte order and target size. */
void
print_type_scalar (type, val, stream)
struct type *type;
LONGEST val;
FILE *stream;
{
unsigned int i;
unsigned len;
switch (TYPE_CODE (type))
{
case TYPE_CODE_ENUM:
len = TYPE_NFIELDS (type);
for (i = 0; i < len; i++)
{
if (TYPE_FIELD_BITPOS (type, i) == val)
{
break;
}
}
if (i < len)
{
fputs_filtered (TYPE_FIELD_NAME (type, i), stream);
}
else
{
#ifdef LONG_LONG
fprintf_filtered (stream, "%lld", val);
#else
fprintf_filtered (stream, "%ld", val);
#endif
}
break;
case TYPE_CODE_INT:
#ifdef LONG_LONG
fprintf_filtered (stream, TYPE_UNSIGNED (type) ? "%llu" : "%lld", val);
#else
fprintf_filtered (stream, TYPE_UNSIGNED (type) ? "%u" : "%d", val);
#endif
break;
case TYPE_CODE_CHAR:
LA_PRINT_CHAR ((unsigned char) val, stream);
break;
case TYPE_CODE_BOOL:
fprintf_filtered (stream, val ? "TRUE" : "FALSE");
break;
case TYPE_CODE_UNDEF:
case TYPE_CODE_PTR:
case TYPE_CODE_ARRAY:
case TYPE_CODE_STRUCT:
case TYPE_CODE_UNION:
case TYPE_CODE_FUNC:
case TYPE_CODE_FLT:
case TYPE_CODE_VOID:
case TYPE_CODE_SET:
case TYPE_CODE_RANGE:
case TYPE_CODE_PASCAL_ARRAY:
case TYPE_CODE_ERROR:
case TYPE_CODE_MEMBER:
case TYPE_CODE_METHOD:
case TYPE_CODE_REF:
error ("internal error: unhandled type in print_type_scalar");
break;
default:
error ("Invalid type code in symbol table.");
}
fflush (stream);
}
#if MAINTENANCE_CMDS
/* Dump details of a type specified either directly or indirectly.
Uses the same sort of type lookup mechanism as ptype_command()
and whatis_command(). */
void
maintenance_print_type (typename, from_tty)
char *typename;
int from_tty;
{
register value val;
register struct type *type;
register struct cleanup *old_chain;
struct expression *expr;
if (typename != NULL)
{
expr = parse_expression (typename);
old_chain = make_cleanup (free_current_contents, &expr);
if (expr -> elts[0].opcode == OP_TYPE)
{
/* The user expression names a type directly, just use that type. */
type = expr -> elts[1].type;
}
else
{
/* The user expression may name a type indirectly by naming an
object of that type. Find that indirectly named type. */
val = evaluate_type (expr);
type = VALUE_TYPE (val);
}
if (type != NULL)
{
recursive_dump_type (type, 0);
}
do_cleanups (old_chain);
}
}
#endif /* MAINTENANCE_CMDS */
void
_initialize_typeprint ()
{
add_com ("ptype", class_vars, ptype_command,
"Print definition of type TYPE.\n\
Argument may be a type name defined by typedef, or \"struct STRUCTNAME\"\n\
or \"union UNIONNAME\" or \"enum ENUMNAME\".\n\
The selected stack frame's lexical context is used to look up the name.");
add_com ("whatis", class_vars, whatis_command,
"Print data type of expression EXP.");
}

23
gdb/typeprint.h Normal file
View file

@ -0,0 +1,23 @@
/* Language independent support for printing types for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
void
print_type_scalar PARAMS ((struct type *type, LONGEST, FILE *));

File diff suppressed because it is too large Load diff

40
gdb/valprint.h Normal file
View file

@ -0,0 +1,40 @@
/* Declarations for value printing routines for GDB, the GNU debugger.
Copyright 1986, 1988, 1989, 1991 Free Software Foundation, Inc.
This file is part of GDB.
This program 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 of the License, or
(at your option) any later version.
This program 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
extern int prettyprint_arrays; /* Controls pretty printing of arrays. */
extern int prettyprint_structs; /* Controls pretty printing of structures */
extern int prettyprint_arrays; /* Controls pretty printing of arrays. */
extern int vtblprint; /* Controls printing of vtbl's */
extern int unionprint; /* Controls printing of nested unions. */
extern int addressprint; /* Controls pretty printing of addresses. */
extern int objectprint; /* Controls looking up an object's derived type
using what we find in its vtables. */
extern unsigned int print_max; /* Max # of chars for strings/vectors */
extern int output_format;
extern void
val_print_array_elements PARAMS ((struct type *, char *, CORE_ADDR, FILE *,
int, int, int, enum val_prettyprint, int));
extern void
val_print_type_code_int PARAMS ((struct type *, char *, FILE *));

View file

@ -314,7 +314,7 @@ clear_value_history ()
while (value_history_chain)
{
for (i = 0; i < VALUE_HISTORY_CHUNK; i++)
if (val = value_history_chain->values[i])
if ((val = value_history_chain->values[i]) != NULL)
free ((PTR)val);
next = value_history_chain->next;
free ((PTR)value_history_chain);