diff options
author | Steve Chamberlain <sac@cygnus> | 1995-10-05 20:57:30 +0000 |
---|---|---|
committer | Steve Chamberlain <sac@cygnus> | 1995-10-05 20:57:30 +0000 |
commit | 0694bce61924ece755442f0871d5900728b2e88b (patch) | |
tree | 435c9fb1687c8a8c8ec042ca9c4dbd4c0c5f456a /gdb/eval.c | |
parent | f4791d95f1ff9ffdf107b1fbf79aa6e3bf58c441 (diff) | |
download | gdb-0694bce61924ece755442f0871d5900728b2e88b.zip gdb-0694bce61924ece755442f0871d5900728b2e88b.tar.gz gdb-0694bce61924ece755442f0871d5900728b2e88b.tar.bz2 |
Thu Oct 5 13:27:30 1995 steve chamberlain <sac@slash.cygnus.com>
* win32.c: New file; support for debugging on windows NT.
* configure.in: (i[345]86-*-win32): New target.
* configure: Regnerated.
* eval.c (evaluate_subexp_standard): Remove unused name.
* serial.c (gdb_string.h): Include.
* source.c (value.h): Include.
* config/i386/i386win32.mh (XDEPFILES): Add win32.o
* config/i386/i386win32.mt: New.
* config/i386/tm-i386win32.h: New.
Diffstat (limited to 'gdb/eval.c')
-rw-r--r-- | gdb/eval.c | 209 |
1 files changed, 148 insertions, 61 deletions
@@ -16,7 +16,7 @@ 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. */ +Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #include "defs.h" #include "gdb_string.h" @@ -141,75 +141,165 @@ evaluate_type (exp) return evaluate_subexp (NULL_TYPE, exp, &pc, EVAL_AVOID_SIDE_EFFECTS); } -/* Helper function called by evaluate_subexp to initialize a field - a structure from a tuple in Chill. This is recursive, to handle - more than one field name labels. +/* If the next expression is an OP_LABELED, skips past it, + returning the label. Otherwise, does nothing and returns NULL. */ - STRUCT_VAL is the structure value we are constructing. - (*FIELDNOP) is the field to set, if there is no label. - It is set to the field following this one. - EXP, POS, and NOSIDE are as for evaluate_subexp. - - This function does not handle variant records. FIXME */ - -static value_ptr -evaluate_labeled_field_init (struct_val, fieldnop, exp, pos, noside) - value_ptr struct_val; - int *fieldnop; +static char* +get_label (exp, pos) register struct expression *exp; - register int *pos; - enum noside noside; + int *pos; { - int fieldno = *fieldnop; - value_ptr val; - int bitpos, bitsize; - char *addr; - struct type *struct_type = VALUE_TYPE (struct_val); if (exp->elts[*pos].opcode == OP_LABELED) { int pc = (*pos)++; char *name = &exp->elts[pc + 2].string; int tem = longest_to_int (exp->elts[pc + 1].longconst); (*pos) += 3 + BYTES_TO_EXP_ELEM (tem + 1); - for (fieldno = 0; ; fieldno++) - { - if (fieldno >= TYPE_NFIELDS (struct_type)) - error ("there is no field named %s", name); - if (STREQ (TYPE_FIELD_NAME (struct_type, fieldno), name)) - break; - } - *fieldnop = fieldno; - val = evaluate_labeled_field_init (struct_val, fieldnop, - exp, pos, noside); + return name; } else + return NULL; +} + +/* This function evaluates tupes (in Chill) or brace-initializers + (in C/C++) for structure types. */ + +static value_ptr +evaluate_struct_tuple (struct_val, exp, pos, noside, nargs) + value_ptr struct_val; + register struct expression *exp; + register int *pos; + enum noside noside; + int nargs; +{ + struct type *struct_type = VALUE_TYPE (struct_val); + struct type *substruct_type = struct_type; + struct type *field_type; + int fieldno = -1; + int variantno = -1; + int subfieldno = -1; + while (--nargs >= 0) { - fieldno = (*fieldnop)++; - if (fieldno >= TYPE_NFIELDS (struct_type)) - error ("too many initializers"); - val = evaluate_subexp (TYPE_FIELD_TYPE (struct_type, fieldno), - exp, pos, noside); - } + int pc = *pos; + value_ptr val = NULL; + int nlabels = 0; + int bitpos, bitsize; + char *addr; + + /* Skip past the labels, and count them. */ + while (get_label (exp, pos) != NULL) + nlabels++; - /* Assign val to field fieldno. */ - if (VALUE_TYPE (val) != TYPE_FIELD_TYPE (struct_type, fieldno)) - val = value_cast (TYPE_FIELD_TYPE (struct_type, fieldno), val); -#if 1 - bitsize = TYPE_FIELD_BITSIZE (struct_type, fieldno); - bitpos = TYPE_FIELD_BITPOS (struct_type, fieldno); - addr = VALUE_CONTENTS (struct_val); - addr += bitpos / 8; - if (bitsize) - modify_field (addr, value_as_long (val), - bitpos % 8, bitsize); - else - memcpy (addr, VALUE_CONTENTS (val), - TYPE_LENGTH (VALUE_TYPE (val))); -#else - value_assign (value_primitive_field (struct_val, 0, fieldno, struct_type), - val); -#endif - return val; + do + { + char *label = get_label (exp, &pc); + if (label) + { + for (fieldno = 0; fieldno < TYPE_NFIELDS (struct_type); + fieldno++) + { + char *field_name = TYPE_FIELD_NAME (struct_type, fieldno); + if (field_name != NULL && STREQ (field_name, label)) + { + variantno = -1; + subfieldno = fieldno; + substruct_type = struct_type; + goto found; + } + } + for (fieldno = 0; fieldno < TYPE_NFIELDS (struct_type); + fieldno++) + { + char *field_name = TYPE_FIELD_NAME (struct_type, fieldno); + field_type = TYPE_FIELD_TYPE (struct_type, fieldno); + if ((field_name == 0 || *field_name == '\0') + && TYPE_CODE (field_type) == TYPE_CODE_UNION) + { + variantno = 0; + for (; variantno < TYPE_NFIELDS (field_type); + variantno++) + { + substruct_type + = TYPE_FIELD_TYPE (field_type, variantno); + if (TYPE_CODE (substruct_type) == TYPE_CODE_STRUCT) + { + for (subfieldno = 0; + subfieldno < TYPE_NFIELDS (substruct_type); + subfieldno++) + { + if (STREQ (TYPE_FIELD_NAME (substruct_type, + subfieldno), + label)) + { + goto found; + } + } + } + } + } + } + error ("there is no field named %s", label); + found: + ; + } + else + { + /* Unlabelled tuple element - go to next field. */ + if (variantno >= 0) + { + subfieldno++; + if (subfieldno >= TYPE_NFIELDS (substruct_type)) + { + variantno = -1; + substruct_type = struct_type; + } + } + if (variantno < 0) + { + fieldno++; + subfieldno = fieldno; + if (fieldno >= TYPE_NFIELDS (struct_type)) + error ("too many initializers"); + field_type = TYPE_FIELD_TYPE (struct_type, fieldno); + if (TYPE_CODE (field_type) == TYPE_CODE_UNION + && TYPE_FIELD_NAME (struct_type, fieldno)[0] == '0') + error ("don't know which variant you want to set"); + } + } + + /* Here, struct_type is the type of the inner struct, + while substruct_type is the type of the inner struct. + These are the same for normal structures, but a variant struct + contains anonymous union fields that contain substruct fields. + The value fieldno is the index of the top-level (normal or + anonymous union) field in struct_field, while the value + subfieldno is the index of the actual real (named inner) field + in substruct_type. */ + + field_type = TYPE_FIELD_TYPE (substruct_type, subfieldno); + if (val == 0) + val = evaluate_subexp (substruct_type, exp, pos, noside); + + /* Now actually set the field in struct_val. */ + + /* Assign val to field fieldno. */ + if (VALUE_TYPE (val) != field_type) + val = value_cast (field_type, val); + + bitsize = TYPE_FIELD_BITSIZE (substruct_type, subfieldno); + bitpos = TYPE_FIELD_BITPOS (struct_type, fieldno); + if (variantno >= 0) + bitpos += TYPE_FIELD_BITPOS (substruct_type, subfieldno); + addr = VALUE_CONTENTS (struct_val) + bitpos / 8; + if (bitsize) + modify_field (addr, value_as_long (val), + bitpos % 8, bitsize); + else + memcpy (addr, VALUE_CONTENTS (val), + TYPE_LENGTH (VALUE_TYPE (val))); + } while (--nlabels > 0); + } + return struct_val; } value_ptr @@ -350,11 +440,8 @@ evaluate_subexp_standard (expect_type, exp, pos, noside) && TYPE_CODE (expect_type) == TYPE_CODE_STRUCT) { value_ptr rec = allocate_value (expect_type); - int fieldno = 0; memset (VALUE_CONTENTS_RAW (rec), '\0', TYPE_LENGTH (expect_type)); - for (tem = 0; tem < nargs; tem++) - evaluate_labeled_field_init (rec, &fieldno, exp, pos, noside); - return rec; + return evaluate_struct_tuple (rec, exp, pos, noside, nargs); } if (expect_type != NULL_TYPE && noside != EVAL_SKIP |