+ LONGEST count = 0;
+ int i;
+
+ for (i = 0; i < TYPE_NFIELDS (type); i++)
+ {
+ LONGEST sub_count;
+
+ if (field_is_static (&TYPE_FIELD (type, i)))
+ continue;
+
+ sub_count = ppc64_aggregate_candidate
+ (TYPE_FIELD_TYPE (type, i), field_type);
+ if (sub_count == -1)
+ return -1;
+
+ if (TYPE_CODE (type) == TYPE_CODE_STRUCT)
+ count += sub_count;
+ else
+ count = max (count, sub_count);
+ }
+
+ /* There must be no padding. */
+ if (count == 0)
+ return TYPE_LENGTH (type) == 0 ? 0 : -1;
+ else if (TYPE_LENGTH (type) != count * TYPE_LENGTH (*field_type))
+ return -1;
+
+ return count;
+ }
+ break;
+
+ default:
+ break;
+ }
+
+ return -1;
+}
+
+/* If an argument of type TYPE is a homogeneous float or vector aggregate
+ that shall be passed in FP/vector registers according to the ELFv2 ABI,
+ return the homogeneous element type in *ELT_TYPE and the number of
+ elements in *N_ELTS, and return non-zero. Otherwise, return zero. */
+
+static int
+ppc64_elfv2_abi_homogeneous_aggregate (struct type *type,
+ struct type **elt_type, int *n_elts)
+{
+ /* Complex types at the top level are treated separately. However,
+ complex types can be elements of homogeneous aggregates. */
+ if (TYPE_CODE (type) == TYPE_CODE_STRUCT
+ || TYPE_CODE (type) == TYPE_CODE_UNION
+ || (TYPE_CODE (type) == TYPE_CODE_ARRAY && !TYPE_VECTOR (type)))
+ {
+ struct type *field_type = NULL;
+ LONGEST field_count = ppc64_aggregate_candidate (type, &field_type);
+
+ if (field_count > 0)
+ {
+ int n_regs = ((TYPE_CODE (field_type) == TYPE_CODE_FLT
+ || TYPE_CODE (field_type) == TYPE_CODE_DECFLOAT)?
+ (TYPE_LENGTH (field_type) + 7) >> 3 : 1);
+
+ /* The ELFv2 ABI allows homogeneous aggregates to occupy
+ up to 8 registers. */
+ if (field_count * n_regs <= 8)
+ {
+ if (elt_type)
+ *elt_type = field_type;
+ if (n_elts)
+ *n_elts = (int) field_count;
+ /* Note that field_count is LONGEST since it may hold the size
+ of an array, while *n_elts is int since its value is bounded
+ by the number of registers used for argument passing. The
+ cast cannot overflow due to the bounds checking above. */
+ return 1;
+ }
+ }
+ }
+
+ return 0;
+}
+
+/* Structure holding the next argument position. */
+struct ppc64_sysv_argpos
+ {
+ /* Register cache holding argument registers. If this is NULL,
+ we only simulate argument processing without actually updating
+ any registers or memory. */
+ struct regcache *regcache;
+ /* Next available general-purpose argument register. */
+ int greg;
+ /* Next available floating-point argument register. */
+ int freg;
+ /* Next available vector argument register. */
+ int vreg;
+ /* The address, at which the next general purpose parameter
+ (integer, struct, float, vector, ...) should be saved. */
+ CORE_ADDR gparam;
+ /* The address, at which the next by-reference parameter
+ (non-Altivec vector, variably-sized type) should be saved. */
+ CORE_ADDR refparam;
+ };
+
+/* VAL is a value of length LEN. Store it into the argument area on the
+ stack and load it into the corresponding general-purpose registers
+ required by the ABI, and update ARGPOS.
+
+ If ALIGN is nonzero, it specifies the minimum alignment required
+ for the on-stack copy of the argument. */
+
+static void
+ppc64_sysv_abi_push_val (struct gdbarch *gdbarch,
+ const bfd_byte *val, int len, int align,
+ struct ppc64_sysv_argpos *argpos)
+{
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ int offset = 0;
+
+ /* Enforce alignment of stack location, if requested. */
+ if (align > tdep->wordsize)
+ {
+ CORE_ADDR aligned_gparam = align_up (argpos->gparam, align);
+
+ argpos->greg += (aligned_gparam - argpos->gparam) / tdep->wordsize;
+ argpos->gparam = aligned_gparam;
+ }
+
+ /* The ABI (version 1.9) specifies that values smaller than one
+ doubleword are right-aligned and those larger are left-aligned.
+ GCC versions before 3.4 implemented this incorrectly; see
+ <http://gcc.gnu.org/gcc-3.4/powerpc-abi.html>. */
+ if (len < tdep->wordsize
+ && gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
+ offset = tdep->wordsize - len;
+
+ if (argpos->regcache)
+ write_memory (argpos->gparam + offset, val, len);
+ argpos->gparam = align_up (argpos->gparam + len, tdep->wordsize);
+
+ while (len >= tdep->wordsize)
+ {
+ if (argpos->regcache && argpos->greg <= 10)
+ regcache_cooked_write (argpos->regcache,
+ tdep->ppc_gp0_regnum + argpos->greg, val);
+ argpos->greg++;
+ len -= tdep->wordsize;
+ val += tdep->wordsize;
+ }
+
+ if (len > 0)
+ {
+ if (argpos->regcache && argpos->greg <= 10)
+ regcache_cooked_write_part (argpos->regcache,
+ tdep->ppc_gp0_regnum + argpos->greg,
+ offset, len, val);
+ argpos->greg++;
+ }
+}
+
+/* The same as ppc64_sysv_abi_push_val, but using a single-word integer
+ value VAL as argument. */
+
+static void
+ppc64_sysv_abi_push_integer (struct gdbarch *gdbarch, ULONGEST val,
+ struct ppc64_sysv_argpos *argpos)
+{
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
+ gdb_byte buf[MAX_REGISTER_SIZE];
+
+ if (argpos->regcache)
+ store_unsigned_integer (buf, tdep->wordsize, byte_order, val);
+ ppc64_sysv_abi_push_val (gdbarch, buf, tdep->wordsize, 0, argpos);
+}
+
+/* VAL is a value of TYPE, a (binary or decimal) floating-point type.
+ Load it into a floating-point register if required by the ABI,
+ and update ARGPOS. */
+
+static void
+ppc64_sysv_abi_push_freg (struct gdbarch *gdbarch,
+ struct type *type, const bfd_byte *val,
+ struct ppc64_sysv_argpos *argpos)
+{
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ if (tdep->soft_float)
+ return;
+
+ if (TYPE_LENGTH (type) <= 8
+ && TYPE_CODE (type) == TYPE_CODE_FLT)
+ {
+ /* Floats and doubles go in f1 .. f13. 32-bit floats are converted
+ to double first. */
+ if (argpos->regcache && argpos->freg <= 13)
+ {
+ int regnum = tdep->ppc_fp0_regnum + argpos->freg;
+ struct type *regtype = register_type (gdbarch, regnum);
+ gdb_byte regval[MAX_REGISTER_SIZE];
+
+ convert_typed_floating (val, type, regval, regtype);
+ regcache_cooked_write (argpos->regcache, regnum, regval);
+ }
+
+ argpos->freg++;
+ }
+ else if (TYPE_LENGTH (type) <= 8
+ && TYPE_CODE (type) == TYPE_CODE_DECFLOAT)
+ {
+ /* Floats and doubles go in f1 .. f13. 32-bit decimal floats are
+ placed in the least significant word. */
+ if (argpos->regcache && argpos->freg <= 13)
+ {
+ int regnum = tdep->ppc_fp0_regnum + argpos->freg;
+ int offset = 0;
+
+ if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
+ offset = 8 - TYPE_LENGTH (type);
+
+ regcache_cooked_write_part (argpos->regcache, regnum,
+ offset, TYPE_LENGTH (type), val);
+ }
+
+ argpos->freg++;
+ }
+ else if (TYPE_LENGTH (type) == 16
+ && TYPE_CODE (type) == TYPE_CODE_FLT
+ && (gdbarch_long_double_format (gdbarch)
+ == floatformats_ibm_long_double))
+ {
+ /* IBM long double stored in two consecutive FPRs. */
+ if (argpos->regcache && argpos->freg <= 13)
+ {
+ int regnum = tdep->ppc_fp0_regnum + argpos->freg;
+
+ regcache_cooked_write (argpos->regcache, regnum, val);
+ if (argpos->freg <= 12)
+ regcache_cooked_write (argpos->regcache, regnum + 1, val + 8);
+ }
+
+ argpos->freg += 2;
+ }
+ else if (TYPE_LENGTH (type) == 16
+ && TYPE_CODE (type) == TYPE_CODE_DECFLOAT)
+ {
+ /* 128-bit decimal floating-point values are stored in and even/odd
+ pair of FPRs, with the even FPR holding the most significant half. */
+ argpos->freg += argpos->freg & 1;
+
+ if (argpos->regcache && argpos->freg <= 12)
+ {
+ int regnum = tdep->ppc_fp0_regnum + argpos->freg;
+ int lopart = gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG ? 8 : 0;
+ int hipart = gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG ? 0 : 8;
+
+ regcache_cooked_write (argpos->regcache, regnum, val + hipart);
+ regcache_cooked_write (argpos->regcache, regnum + 1, val + lopart);
+ }
+
+ argpos->freg += 2;
+ }
+}
+
+/* VAL is a value of AltiVec vector type. Load it into a vector register
+ if required by the ABI, and update ARGPOS. */
+
+static void
+ppc64_sysv_abi_push_vreg (struct gdbarch *gdbarch, const bfd_byte *val,
+ struct ppc64_sysv_argpos *argpos)
+{
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+
+ if (argpos->regcache && argpos->vreg <= 13)
+ regcache_cooked_write (argpos->regcache,
+ tdep->ppc_vr0_regnum + argpos->vreg, val);
+
+ argpos->vreg++;
+}
+
+/* VAL is a value of TYPE. Load it into memory and/or registers
+ as required by the ABI, and update ARGPOS. */
+
+static void
+ppc64_sysv_abi_push_param (struct gdbarch *gdbarch,
+ struct type *type, const bfd_byte *val,
+ struct ppc64_sysv_argpos *argpos)
+{
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+
+ if (TYPE_CODE (type) == TYPE_CODE_FLT
+ || TYPE_CODE (type) == TYPE_CODE_DECFLOAT)
+ {
+ /* Floating-point scalars are passed in floating-point registers. */
+ ppc64_sysv_abi_push_val (gdbarch, val, TYPE_LENGTH (type), 0, argpos);
+ ppc64_sysv_abi_push_freg (gdbarch, type, val, argpos);
+ }
+ else if (TYPE_CODE (type) == TYPE_CODE_ARRAY && TYPE_VECTOR (type)
+ && tdep->vector_abi == POWERPC_VEC_ALTIVEC
+ && TYPE_LENGTH (type) == 16)
+ {
+ /* AltiVec vectors are passed aligned, and in vector registers. */
+ ppc64_sysv_abi_push_val (gdbarch, val, TYPE_LENGTH (type), 16, argpos);
+ ppc64_sysv_abi_push_vreg (gdbarch, val, argpos);
+ }
+ else if (TYPE_CODE (type) == TYPE_CODE_ARRAY && TYPE_VECTOR (type)
+ && TYPE_LENGTH (type) >= 16)
+ {
+ /* Non-Altivec vectors are passed by reference. */
+
+ /* Copy value onto the stack ... */
+ CORE_ADDR addr = align_up (argpos->refparam, 16);
+ if (argpos->regcache)
+ write_memory (addr, val, TYPE_LENGTH (type));
+ argpos->refparam = align_up (addr + TYPE_LENGTH (type), tdep->wordsize);
+
+ /* ... and pass a pointer to the copy as parameter. */
+ ppc64_sysv_abi_push_integer (gdbarch, addr, argpos);
+ }
+ else if ((TYPE_CODE (type) == TYPE_CODE_INT
+ || TYPE_CODE (type) == TYPE_CODE_ENUM
+ || TYPE_CODE (type) == TYPE_CODE_BOOL
+ || TYPE_CODE (type) == TYPE_CODE_CHAR
+ || TYPE_CODE (type) == TYPE_CODE_PTR
+ || TYPE_CODE (type) == TYPE_CODE_REF)
+ && TYPE_LENGTH (type) <= tdep->wordsize)
+ {
+ ULONGEST word = 0;
+
+ if (argpos->regcache)
+ {
+ /* Sign extend the value, then store it unsigned. */
+ word = unpack_long (type, val);
+
+ /* Convert any function code addresses into descriptors. */
+ if (tdep->elf_abi == POWERPC_ELF_V1
+ && (TYPE_CODE (type) == TYPE_CODE_PTR
+ || TYPE_CODE (type) == TYPE_CODE_REF))
+ {
+ struct type *target_type
+ = check_typedef (TYPE_TARGET_TYPE (type));
+
+ if (TYPE_CODE (target_type) == TYPE_CODE_FUNC
+ || TYPE_CODE (target_type) == TYPE_CODE_METHOD)
+ {
+ CORE_ADDR desc = word;
+
+ convert_code_addr_to_desc_addr (word, &desc);
+ word = desc;
+ }
+ }
+ }
+
+ ppc64_sysv_abi_push_integer (gdbarch, word, argpos);
+ }
+ else
+ {
+ ppc64_sysv_abi_push_val (gdbarch, val, TYPE_LENGTH (type), 0, argpos);
+
+ /* The ABI (version 1.9) specifies that structs containing a
+ single floating-point value, at any level of nesting of
+ single-member structs, are passed in floating-point registers. */
+ if (TYPE_CODE (type) == TYPE_CODE_STRUCT
+ && TYPE_NFIELDS (type) == 1)
+ {
+ while (TYPE_CODE (type) == TYPE_CODE_STRUCT
+ && TYPE_NFIELDS (type) == 1)
+ type = check_typedef (TYPE_FIELD_TYPE (type, 0));
+
+ if (TYPE_CODE (type) == TYPE_CODE_FLT)
+ ppc64_sysv_abi_push_freg (gdbarch, type, val, argpos);
+ }
+
+ /* In the ELFv2 ABI, homogeneous floating-point or vector
+ aggregates are passed in a series of registers. */
+ if (tdep->elf_abi == POWERPC_ELF_V2)
+ {
+ struct type *eltype;
+ int i, nelt;
+
+ if (ppc64_elfv2_abi_homogeneous_aggregate (type, &eltype, &nelt))
+ for (i = 0; i < nelt; i++)
+ {
+ const gdb_byte *elval = val + i * TYPE_LENGTH (eltype);
+
+ if (TYPE_CODE (eltype) == TYPE_CODE_FLT
+ || TYPE_CODE (eltype) == TYPE_CODE_DECFLOAT)
+ ppc64_sysv_abi_push_freg (gdbarch, eltype, elval, argpos);
+ else if (TYPE_CODE (eltype) == TYPE_CODE_ARRAY
+ && TYPE_VECTOR (eltype)
+ && tdep->vector_abi == POWERPC_VEC_ALTIVEC
+ && TYPE_LENGTH (eltype) == 16)
+ ppc64_sysv_abi_push_vreg (gdbarch, elval, argpos);
+ }
+ }
+ }
+}
+
+/* Pass the arguments in either registers, or in the stack. Using the
+ ppc 64 bit SysV ABI.
+
+ This implements a dumbed down version of the ABI. It always writes
+ values to memory, GPR and FPR, even when not necessary. Doing this
+ greatly simplifies the logic. */
+
+CORE_ADDR
+ppc64_sysv_abi_push_dummy_call (struct gdbarch *gdbarch,
+ struct value *function,
+ struct regcache *regcache, CORE_ADDR bp_addr,
+ int nargs, struct value **args, CORE_ADDR sp,
+ int struct_return, CORE_ADDR struct_addr)
+{
+ CORE_ADDR func_addr = find_function_addr (function, NULL);
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
+ int opencl_abi = ppc_sysv_use_opencl_abi (value_type (function));
+ ULONGEST back_chain;
+ /* See for-loop comment below. */
+ int write_pass;
+ /* Size of the by-reference parameter copy region, the final value is
+ computed in the for-loop below. */
+ LONGEST refparam_size = 0;
+ /* Size of the general parameter region, the final value is computed
+ in the for-loop below. */
+ LONGEST gparam_size = 0;
+ /* Kevin writes ... I don't mind seeing tdep->wordsize used in the
+ calls to align_up(), align_down(), etc. because this makes it
+ easier to reuse this code (in a copy/paste sense) in the future,
+ but it is a 64-bit ABI and asserting that the wordsize is 8 bytes
+ at some point makes it easier to verify that this function is
+ correct without having to do a non-local analysis to figure out
+ the possible values of tdep->wordsize. */
+ gdb_assert (tdep->wordsize == 8);
+
+ /* This function exists to support a calling convention that
+ requires floating-point registers. It shouldn't be used on
+ processors that lack them. */
+ gdb_assert (ppc_floating_point_unit_p (gdbarch));
+
+ /* By this stage in the proceedings, SP has been decremented by "red
+ zone size" + "struct return size". Fetch the stack-pointer from
+ before this and use that as the BACK_CHAIN. */
+ regcache_cooked_read_unsigned (regcache, gdbarch_sp_regnum (gdbarch),
+ &back_chain);
+
+ /* Go through the argument list twice.
+
+ Pass 1: Compute the function call's stack space and register
+ requirements.
+
+ Pass 2: Replay the same computation but this time also write the
+ values out to the target. */
+
+ for (write_pass = 0; write_pass < 2; write_pass++)
+ {
+ int argno;
+
+ struct ppc64_sysv_argpos argpos;
+ argpos.greg = 3;
+ argpos.freg = 1;
+ argpos.vreg = 2;
+
+ if (!write_pass)
+ {
+ /* During the first pass, GPARAM and REFPARAM are more like
+ offsets (start address zero) than addresses. That way
+ they accumulate the total stack space each region