From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 17084 invoked by alias); 17 Mar 2003 16:59:56 -0000 Mailing-List: contact gdb-patches-help@sources.redhat.com; run by ezmlm Precedence: bulk List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sources.redhat.com Received: (qmail 17030 invoked from network); 17 Mar 2003 16:59:55 -0000 Received: from unknown (HELO localhost.redhat.com) (66.30.197.194) by sources.redhat.com with SMTP; 17 Mar 2003 16:59:55 -0000 Received: from redhat.com (localhost [127.0.0.1]) by localhost.redhat.com (Postfix) with ESMTP id 8BDC62B11; Mon, 17 Mar 2003 11:59:52 -0500 (EST) Message-ID: <3E75FF08.5020906@redhat.com> Date: Mon, 17 Mar 2003 16:59:00 -0000 From: Andrew Cagney User-Agent: Mozilla/5.0 (X11; U; NetBSD macppc; en-US; rv:1.0.2) Gecko/20030223 X-Accept-Language: en-us, en MIME-Version: 1.0 To: Kevin Buettner Cc: gdb-patches@sources.redhat.com Subject: Re: [rfa] Add e500 function call support to PPC References: <3E6A4068.9000506@redhat.com> <1030309005725.ZM21224@localhost.localdomain> <3E6CAB16.10607@redhat.com> <1030310175404.ZM3626@localhost.localdomain> <3E6CEE02.10005@redhat.com> <1030310214650.ZM4443@localhost.localdomain> Content-Type: multipart/mixed; boundary="------------030807060306070609080902" X-SW-Source: 2003-03/txt/msg00367.txt.bz2 This is a multi-part message in MIME format. --------------030807060306070609080902 Content-Type: text/plain; charset=us-ascii; format=flowed Content-Transfer-Encoding: 7bit Content-length: 1463 > For the time being, how about introducing a predicate (function) to > ppc-sysv-tdep.c (or perhaps rs6000-tdep.c) named > have_floating_point_registers_p() (or something along those lines). > > In the short term this could be defined as: > > int > have_floating_point_registers_p (struct gdbarch *gdbarch) > { > const struct bfd_arch_info *arch_info = gdbarch_bfd_arch_info (gdbarch); > > /* Note: It has been proposed that a ``ppc_fp0_regnum'' member be added > to the ppc tdep struct. If/when this occurs, it may be preferable to > implement this as: > > struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); > > return tdep->ppc_fp0_regnum >= 0; > */ > > return arch_info->mach != bfd_mach_ppc_e500; > } I called it ppc_floating_point_unit_p(). > It occurs to me that such a predicate would be useful for checking > the state of a global variable in the event that a command similar to > ``set nomipsfpu'' were added for the powerpc. (Well, maybe. Then > again, maybe it'd be better to just set ppc_fp0_regnum to -1 when > such a setting were made.) It is definitly better than a ppc_fp0_regnum test. As with the MIPS, it's one thing to have FP registers, it is another to use them. > In any event, a name like have_floating_point_registers_p() is > reasonably self docuementing whereas ``tdep->ppc_fp0_regnum >= 0'' > requires a little bit more thought to discern the meaning. How about the attached? Andrew --------------030807060306070609080902 Content-Type: text/plain; name="diffs" Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="diffs" Content-length: 9306 2003-03-17 Andrew Cagney * rs6000-tdep.c (ppc_floating_point_unit_p): New function. * ppc-tdep.h (ppc_floating_point_unit_p): Declare. From Elena Zannoni * ppc-sysv-tdep.c (ppc_sysv_abi_push_arguments): Handle e500 vector and floating-point parameters. (ppc_sysv_abi_use_struct_convention): Handle e500 struct return convention. (ppc_sysv_abi_broken_use_struct_convention): Ditto. Index: ppc-sysv-tdep.c =================================================================== RCS file: /cvs/src/src/gdb/ppc-sysv-tdep.c,v retrieving revision 1.3 diff -u -r1.3 ppc-sysv-tdep.c --- ppc-sysv-tdep.c 14 Nov 2002 20:37:28 -0000 1.3 +++ ppc-sysv-tdep.c 17 Mar 2003 16:43:36 -0000 @@ -61,11 +61,12 @@ int structstkspace; int argoffset; int structoffset; - struct value *arg; struct type *type; int len; char old_sp_buf[4]; CORE_ADDR saved_sp; + struct gdbarch_tdep *tdep = gdbarch_tdep (current_gdbarch); + const struct bfd_arch_info *arch_info = gdbarch_bfd_arch_info (current_gdbarch); greg = struct_return ? 4 : 3; freg = 1; @@ -79,11 +80,12 @@ are put in registers. */ for (argno = 0; argno < nargs; argno++) { - arg = args[argno]; + struct value *arg = args[argno]; type = check_typedef (VALUE_TYPE (arg)); len = TYPE_LENGTH (type); - if (TYPE_CODE (type) == TYPE_CODE_FLT) + if (TYPE_CODE (type) == TYPE_CODE_FLT + && ppc_floating_point_unit_p (current_gdbarch)) { if (freg <= 8) freg++; @@ -96,7 +98,10 @@ argstkspace += 8; } } - else if (TYPE_CODE (type) == TYPE_CODE_INT && len == 8) /* long long */ + else if (len == 8 + && (TYPE_CODE (type) == TYPE_CODE_INT /* long long */ + || (!ppc_floating_point_unit_p (current_gdbarch) + && TYPE_CODE (type) == TYPE_CODE_FLT))) /* double */ { if (greg > 9) { @@ -144,6 +149,20 @@ argstkspace += 16; } } + else if (len == 8 + && TYPE_CODE (type) == TYPE_CODE_ARRAY + && TYPE_VECTOR (type)) + { + if (greg <= 10) + greg++; + else + { + /* Vector arguments must be aligned to 8 bytes on + the stack. */ + argstkspace += round2 (argstkspace, 8); + argstkspace += 8; + } + } } } @@ -170,30 +189,33 @@ freg = 1; greg = 3; vreg = 2; + /* Fill in r3 with the return structure, if any */ if (struct_return) { - char val_buf[4]; - store_address (val_buf, 4, struct_addr); - memcpy (&deprecated_registers[REGISTER_BYTE (greg)], val_buf, 4); + write_register (tdep->ppc_gp0_regnum + greg, struct_addr); greg++; } + /* Now fill in the registers and stack... */ for (argno = 0; argno < nargs; argno++) { - arg = args[argno]; + struct value *arg = args[argno]; + char *val = VALUE_CONTENTS (arg); type = check_typedef (VALUE_TYPE (arg)); len = TYPE_LENGTH (type); - if (TYPE_CODE (type) == TYPE_CODE_FLT) + if (TYPE_CODE (type) == TYPE_CODE_FLT + && ppc_floating_point_unit_p (current_gdbarch)) { if (freg <= 8) { + ULONGEST regval; if (len > 8) printf_unfiltered ( "Fatal Error: a floating point parameter #%d with a size > 8 is found!\n", argno); - memcpy (&deprecated_registers[REGISTER_BYTE (FP0_REGNUM + freg)], - VALUE_CONTENTS (arg), len); + regval = extract_unsigned_integer (val, len); + write_register (FP0_REGNUM + freg, regval); freg++; } else @@ -203,29 +225,32 @@ /* FIXME: Convert floats to doubles */ if (argoffset & 0x4) argoffset += 4; - write_memory (sp + argoffset, (char *) VALUE_CONTENTS (arg), len); + write_memory (sp + argoffset, val, len); argoffset += 8; } } - else if (TYPE_CODE (type) == TYPE_CODE_INT && len == 8) /* long long */ + else if (len == 8 + && (TYPE_CODE (type) == TYPE_CODE_INT /* long long */ + || (!ppc_floating_point_unit_p (current_gdbarch) + && TYPE_CODE (type) == TYPE_CODE_FLT))) /* double */ { if (greg > 9) { greg = 11; if (argoffset & 0x4) argoffset += 4; - write_memory (sp + argoffset, (char *) VALUE_CONTENTS (arg), len); + write_memory (sp + argoffset, val, len); argoffset += 8; } else { + ULONGEST regval; if ((greg & 1) == 0) greg++; - - memcpy (&deprecated_registers[REGISTER_BYTE (greg)], - VALUE_CONTENTS (arg), 4); - memcpy (&deprecated_registers[REGISTER_BYTE (greg + 1)], - VALUE_CONTENTS (arg) + 4, 4); + regval = extract_unsigned_integer (val, 4); + write_register (tdep->ppc_gp0_regnum + greg, regval); + regval = extract_unsigned_integer (val + 4, 4); + write_register (tdep->ppc_gp0_regnum + greg + 1, regval); greg += 2; } } @@ -236,18 +261,19 @@ || TYPE_CODE (type) == TYPE_CODE_STRUCT || TYPE_CODE (type) == TYPE_CODE_UNION) { - write_memory (sp + structoffset, VALUE_CONTENTS (arg), len); + write_memory (sp + structoffset, val, len); store_address (val_buf, 4, sp + structoffset); structoffset += round2 (len, 8); } else { memset (val_buf, 0, 4); - memcpy (val_buf, VALUE_CONTENTS (arg), len); + memcpy (val_buf, val, len); } if (greg <= 10) { - memcpy (&deprecated_registers[REGISTER_BYTE (greg)], val_buf, 4); + ULONGEST regval = extract_unsigned_integer (val_buf, 4); + write_register (tdep->ppc_gp0_regnum + greg, regval); greg++; } else @@ -262,15 +288,14 @@ && TYPE_CODE (type) == TYPE_CODE_ARRAY && TYPE_VECTOR (type)) { - struct gdbarch_tdep *tdep = gdbarch_tdep (current_gdbarch); char *v_val_buf = alloca (16); memset (v_val_buf, 0, 16); - memcpy (v_val_buf, VALUE_CONTENTS (arg), len); + memcpy (v_val_buf, val, len); if (vreg <= 13) { - memcpy (&deprecated_registers[REGISTER_BYTE (tdep->ppc_vr0_regnum - + vreg)], - v_val_buf, 16); + regcache_cooked_write (current_regcache, + tdep->ppc_vr0_regnum + vreg, + v_val_buf); vreg++; } else @@ -279,6 +304,26 @@ argoffset += 16; } } + else if (len == 8 + && TYPE_CODE (type) == TYPE_CODE_ARRAY + && TYPE_VECTOR (type)) + { + char *v_val_buf = alloca (8); + memset (v_val_buf, 0, 8); + memcpy (v_val_buf, val, len); + if (greg <= 10) + { + regcache_cooked_write (current_regcache, + tdep->ppc_ev0_regnum + greg, + v_val_buf); + greg++; + } + else + { + write_memory (sp + argoffset, v_val_buf, 8); + argoffset += 8; + } + } } } @@ -293,7 +338,7 @@ int ppc_sysv_abi_broken_use_struct_convention (int gcc_p, struct type *value_type) { - if (TYPE_LENGTH (value_type) == 16 + if ((TYPE_LENGTH (value_type) == 16 || TYPE_LENGTH (value_type) == 8) && TYPE_VECTOR (value_type)) return 0; @@ -305,7 +350,7 @@ int ppc_sysv_abi_use_struct_convention (int gcc_p, struct type *value_type) { - if (TYPE_LENGTH (value_type) == 16 + if ((TYPE_LENGTH (value_type) == 16 || TYPE_LENGTH (value_type) == 8) && TYPE_VECTOR (value_type)) return 0; Index: ppc-tdep.h =================================================================== RCS file: /cvs/src/src/gdb/ppc-tdep.h,v retrieving revision 1.14 diff -u -r1.14 ppc-tdep.h --- ppc-tdep.h 4 Jan 2003 23:38:45 -0000 1.14 +++ ppc-tdep.h 17 Mar 2003 16:43:36 -0000 @@ -49,6 +49,11 @@ CORE_ADDR rs6000_frame_chain (struct frame_info *); int altivec_register_p (int regno); + +/* Return non-zero when the architecture has an FPU (or at least when + the ABI is using the FPU). */ +int ppc_floating_point_unit_p (struct gdbarch *gdbarch); + /* Private data that this module attaches to struct gdbarch. */ struct gdbarch_tdep Index: rs6000-tdep.c =================================================================== RCS file: /cvs/src/src/gdb/rs6000-tdep.c,v retrieving revision 1.111 diff -u -r1.111 rs6000-tdep.c --- rs6000-tdep.c 13 Mar 2003 21:45:41 -0000 1.111 +++ rs6000-tdep.c 17 Mar 2003 16:43:38 -0000 @@ -137,6 +137,18 @@ return (regno >= tdep->ppc_vr0_regnum && regno <= tdep->ppc_vrsave_regnum); } +/* Use the architectures FP registers? */ +int +ppc_floating_point_unit_p (struct gdbarch *gdbarch) +{ + const struct bfd_arch_info *info = gdbarch_bfd_arch_info (gdbarch); + if (info->arch == bfd_arch_powerpc) + return (info->mach != bfd_mach_ppc_e500); + if (info->arch == bfd_arch_rs6000) + return 1; + return 0; +} + /* Read a LEN-byte address from debugged memory address MEMADDR. */ static CORE_ADDR --------------030807060306070609080902--