From 98f96ba187da56d93a8b58e794bd6acb58c7034c Mon Sep 17 00:00:00 2001 From: Kevin Buettner Date: Sat, 2 Jun 2001 01:37:20 +0000 Subject: [PATCH] Make alignment of struct arguments in inferior function calls comply with the IA-64 Software Conventions and Runtime manual. --- gdb/ChangeLog | 9 +++++++++ gdb/ia64-tdep.c | 50 +++++++++++++++++++++++++++++++++++++++++++------ 2 files changed, 53 insertions(+), 6 deletions(-) diff --git a/gdb/ChangeLog b/gdb/ChangeLog index a737322f75f..507c5c0614f 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,3 +1,12 @@ +2001-06-01 Kevin Buettner + + * ia64-tdep.c (is_float_or_hfa_type_recurse): Call check_typedef() + on types that we wish to recurse on. + (slot_alignment_is_next_even): New function. + (ia64_push_arguments): Call slot_alignment_is_next_even() to + examine the type in order to decide if it's necessary to skip + an odd slot. + 2001-06-01 Michael Snyder * thread.c (delete_step_resume_breakpoint): New function. diff --git a/gdb/ia64-tdep.c b/gdb/ia64-tdep.c index afa0e1c76b9..cc2d0f23adc 100644 --- a/gdb/ia64-tdep.c +++ b/gdb/ia64-tdep.c @@ -1534,14 +1534,17 @@ is_float_or_hfa_type_recurse (struct type *t, struct type **etp) } break; case TYPE_CODE_ARRAY: - return is_float_or_hfa_type_recurse (TYPE_TARGET_TYPE (t), etp); + return + is_float_or_hfa_type_recurse (check_typedef (TYPE_TARGET_TYPE (t)), + etp); break; case TYPE_CODE_STRUCT: { int i; for (i = 0; i < TYPE_NFIELDS (t); i++) - if (!is_float_or_hfa_type_recurse (TYPE_FIELD_TYPE (t, i), etp)) + if (!is_float_or_hfa_type_recurse + (check_typedef (TYPE_FIELD_TYPE (t, i)), etp)) return 0; return 1; } @@ -1565,6 +1568,40 @@ is_float_or_hfa_type (struct type *t) } +/* Return 1 if the alignment of T is such that the next even slot + should be used. Return 0, if the next available slot should + be used. (See section 8.5.1 of the IA-64 Software Conventions + and Runtime manual.) */ + +static int +slot_alignment_is_next_even (struct type *t) +{ + switch (TYPE_CODE (t)) + { + case TYPE_CODE_INT: + case TYPE_CODE_FLT: + if (TYPE_LENGTH (t) > 8) + return 1; + else + return 0; + case TYPE_CODE_ARRAY: + return + slot_alignment_is_next_even (check_typedef (TYPE_TARGET_TYPE (t))); + case TYPE_CODE_STRUCT: + { + int i; + + for (i = 0; i < TYPE_NFIELDS (t); i++) + if (slot_alignment_is_next_even + (check_typedef (TYPE_FIELD_TYPE (t, i)))) + return 1; + return 0; + } + default: + return 0; + } +} + /* Attempt to find (and return) the global pointer for the given function. @@ -1732,9 +1769,7 @@ ia64_push_arguments (int nargs, value_ptr *args, CORE_ADDR sp, type = check_typedef (VALUE_TYPE (arg)); len = TYPE_LENGTH (type); - /* FIXME: This is crude and it is wrong (IMO), but it matches - what gcc does, I think. */ - if (len > 8 && (nslots & 1)) + if ((nslots & 1) && slot_alignment_is_next_even (type)) nslots++; if (TYPE_CODE (type) == TYPE_CODE_FUNC) @@ -1809,8 +1844,11 @@ ia64_push_arguments (int nargs, value_ptr *args, CORE_ADDR sp, } /* Normal slots */ - if (len > 8 && (slotnum & 1)) + + /* Skip odd slot if necessary... */ + if ((slotnum & 1) && slot_alignment_is_next_even (type)) slotnum++; + argoffset = 0; while (len > 0) { -- 2.30.2