From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 12530 invoked by alias); 24 Jun 2013 00:26:29 -0000 Mailing-List: contact libffi-discuss-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: libffi-discuss-owner@sourceware.org Received: (qmail 12500 invoked by uid 89); 24 Jun 2013 00:26:26 -0000 X-Spam-SWARE-Status: No, score=-2.2 required=5.0 tests=AWL,BAYES_00,FREEMAIL_FROM,RCVD_IN_DNSWL_LOW,RCVD_IN_HOSTKARMA_YE,SPF_PASS,TW_BF,TW_CP,TW_LB,TW_LW,TW_SR autolearn=ham version=3.3.1 Received: from mail-pb0-f48.google.com (HELO mail-pb0-f48.google.com) (209.85.160.48) by sourceware.org (qpsmtpd/0.84/v0.84-167-ge50287c) with ESMTP; Mon, 24 Jun 2013 00:26:24 +0000 Received: by mail-pb0-f48.google.com with SMTP id ma3so10100281pbc.7 for ; Sun, 23 Jun 2013 17:26:22 -0700 (PDT) X-Received: by 10.66.234.232 with SMTP id uh8mr18781774pac.155.1372033582451; Sun, 23 Jun 2013 17:26:22 -0700 (PDT) Received: from bubble.grove.modra.org ([101.166.26.37]) by mx.google.com with ESMTPSA id at1sm15340895pbc.10.2013.06.23.17.26.19 for (version=TLSv1.1 cipher=ECDHE-RSA-RC4-SHA bits=128/128); Sun, 23 Jun 2013 17:26:21 -0700 (PDT) Received: by bubble.grove.modra.org (Postfix, from userid 1000) id E8CBFEA008F; Mon, 24 Jun 2013 09:56:16 +0930 (CST) Date: Mon, 24 Jun 2013 00:26:00 -0000 From: Alan Modra To: David Edelsohn Cc: GCC Patches , libffi-discuss@sourceware.org Subject: Re: [RS6000] libffi little-endian Message-ID: <20130624002616.GG21523@bubble.grove.modra.org> Mail-Followup-To: David Edelsohn , GCC Patches , libffi-discuss@sourceware.org References: <20130607013408.GI6878@bubble.grove.modra.org> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-SW-Source: 2013/txt/msg00145.txt.bz2 On Fri, Jun 07, 2013 at 12:12:17AM -0400, David Edelsohn wrote: > On Thu, Jun 6, 2013 at 9:34 PM, Alan Modra wrote: > > Bootstrapped and regression tested powerpc64-linux. OK to apply? > > > > * src/powerpc/linux64_closure.S (ffi_closure_LINUX64): Support > > little-endian. > > * src/powerpc/ppc_closure.S (ffi_closure_SYSV): Likewise. > > This patch needs to be applied upstream in the libffi repository. > > All of the handling of structs in ffi.c and ffi_darwin.c doesn't need > any changes? Cool. I thought there might be a padding issue. You were right, of course. When we finally got around to running an all languages bootstrap on powerpc64le, we discovered some missing pieces in libffi. The following adds some ffi.c changes to the previous patch (closure.S patches are unchanged). I haven't tackled ffi_darwin.c. Bootstrapped and regression tested powerpc64-linux. This one passes the libffi testsuite on powerpc64le-linux. OK mainline and 4.8? * src/powerpc/ffi.c (ffi_prep_args_SYSV): Move var declaration before statements. (ffi_prep_args64): Support little-endian. (ffi_closure_helper_SYSV, ffi_closure_helper_LINUX64): Likewise. * src/powerpc/linux64_closure.S (ffi_closure_LINUX64): Likewise. * src/powerpc/ppc_closure.S (ffi_closure_SYSV): Likewise. Index: libffi/src/powerpc/ffi.c =================================================================== --- libffi/src/powerpc/ffi.c (revision 200159) +++ libffi/src/powerpc/ffi.c (working copy) @@ -127,6 +127,9 @@ ffi_prep_args_SYSV (extended_cif *ecif, unsigned * int i; ffi_type **ptr; +#ifndef __NO_FPRS__ + double double_tmp; +#endif union { void **v; char **c; @@ -146,7 +149,6 @@ ffi_prep_args_SYSV (extended_cif *ecif, unsigned * gpr_base.u = stacktop.u - ASM_NEEDS_REGISTERS - NUM_GPR_ARG_REGISTERS; intarg_count = 0; #ifndef __NO_FPRS__ - double double_tmp; fpr_base.d = gpr_base.d - NUM_FPR_ARG_REGISTERS; fparg_count = 0; copy_space.c = ((flags & FLAG_FP_ARGUMENTS) ? fpr_base.c : gpr_base.c); @@ -542,11 +544,12 @@ ffi_prep_args64 (extended_cif *ecif, unsigned long { char *where = next_arg.c; +#ifndef __LITTLE_ENDIAN__ /* Structures with size less than eight bytes are passed left-padded. */ if ((*ptr)->size < 8) where += 8 - (*ptr)->size; - +#endif memcpy (where, *p_argv.c, (*ptr)->size); next_arg.ul += words; if (next_arg.ul == gpr_end.ul) @@ -1208,6 +1211,7 @@ ffi_closure_helper_SYSV (ffi_closure *closure, voi case FFI_TYPE_SINT8: case FFI_TYPE_UINT8: +#ifndef __LITTLE_ENDIAN__ /* there are 8 gpr registers used to pass values */ if (ng < 8) { @@ -1221,9 +1225,10 @@ ffi_closure_helper_SYSV (ffi_closure *closure, voi pst++; } break; - +#endif case FFI_TYPE_SINT16: case FFI_TYPE_UINT16: +#ifndef __LITTLE_ENDIAN__ /* there are 8 gpr registers used to pass values */ if (ng < 8) { @@ -1237,7 +1242,7 @@ ffi_closure_helper_SYSV (ffi_closure *closure, voi pst++; } break; - +#endif case FFI_TYPE_SINT32: case FFI_TYPE_UINT32: case FFI_TYPE_POINTER: @@ -1367,22 +1372,25 @@ ffi_closure_helper_LINUX64 (ffi_closure *closure, { case FFI_TYPE_SINT8: case FFI_TYPE_UINT8: +#ifndef __LITTLE_ENDIAN__ avalue[i] = (char *) pst + 7; pst++; break; - +#endif case FFI_TYPE_SINT16: case FFI_TYPE_UINT16: +#ifndef __LITTLE_ENDIAN__ avalue[i] = (char *) pst + 6; pst++; break; - +#endif case FFI_TYPE_SINT32: case FFI_TYPE_UINT32: +#ifndef __LITTLE_ENDIAN__ avalue[i] = (char *) pst + 4; pst++; break; - +#endif case FFI_TYPE_SINT64: case FFI_TYPE_UINT64: case FFI_TYPE_POINTER: @@ -1391,11 +1399,13 @@ ffi_closure_helper_LINUX64 (ffi_closure *closure, break; case FFI_TYPE_STRUCT: +#ifndef __LITTLE_ENDIAN__ /* Structures with size less than eight bytes are passed left-padded. */ if (arg_types[i]->size < 8) avalue[i] = (char *) pst + 8 - arg_types[i]->size; else +#endif avalue[i] = pst; pst += (arg_types[i]->size + 7) / 8; break; Index: libffi/src/powerpc/linux64_closure.S =================================================================== --- libffi/src/powerpc/linux64_closure.S (revision 200159) +++ libffi/src/powerpc/linux64_closure.S (working copy) @@ -132,7 +132,11 @@ ffi_closure_LINUX64: blr nop # case FFI_TYPE_INT +#ifdef __LITTLE_ENDIAN__ + lwa %r3, 112+0(%r1) +#else lwa %r3, 112+4(%r1) +#endif mtlr %r0 addi %r1, %r1, 240 blr @@ -152,33 +156,57 @@ ffi_closure_LINUX64: lfd %f2, 112+8(%r1) b .Lfinish # case FFI_TYPE_UINT8 +#ifdef __LITTLE_ENDIAN__ + lbz %r3, 112+0(%r1) +#else lbz %r3, 112+7(%r1) +#endif mtlr %r0 addi %r1, %r1, 240 blr # case FFI_TYPE_SINT8 +#ifdef __LITTLE_ENDIAN__ + lbz %r3, 112+0(%r1) +#else lbz %r3, 112+7(%r1) +#endif extsb %r3,%r3 mtlr %r0 b .Lfinish # case FFI_TYPE_UINT16 +#ifdef __LITTLE_ENDIAN__ + lhz %r3, 112+0(%r1) +#else lhz %r3, 112+6(%r1) +#endif mtlr %r0 .Lfinish: addi %r1, %r1, 240 blr # case FFI_TYPE_SINT16 +#ifdef __LITTLE_ENDIAN__ + lha %r3, 112+0(%r1) +#else lha %r3, 112+6(%r1) +#endif mtlr %r0 addi %r1, %r1, 240 blr # case FFI_TYPE_UINT32 +#ifdef __LITTLE_ENDIAN__ + lwz %r3, 112+0(%r1) +#else lwz %r3, 112+4(%r1) +#endif mtlr %r0 addi %r1, %r1, 240 blr # case FFI_TYPE_SINT32 +#ifdef __LITTLE_ENDIAN__ + lwa %r3, 112+0(%r1) +#else lwa %r3, 112+4(%r1) +#endif mtlr %r0 addi %r1, %r1, 240 blr Index: libffi/src/powerpc/ppc_closure.S =================================================================== --- libffi/src/powerpc/ppc_closure.S (revision 200159) +++ libffi/src/powerpc/ppc_closure.S (working copy) @@ -159,25 +159,41 @@ ENTRY(ffi_closure_SYSV) #endif # case FFI_TYPE_UINT8 +#ifdef __LITTLE_ENDIAN__ + lbz %r3,112+0(%r1) +#else lbz %r3,112+3(%r1) +#endif mtlr %r0 addi %r1,%r1,144 blr # case FFI_TYPE_SINT8 +#ifdef __LITTLE_ENDIAN__ + lbz %r3,112+0(%r1) +#else lbz %r3,112+3(%r1) +#endif extsb %r3,%r3 mtlr %r0 b .Lfinish # case FFI_TYPE_UINT16 +#ifdef __LITTLE_ENDIAN__ + lhz %r3,112+0(%r1) +#else lhz %r3,112+2(%r1) +#endif mtlr %r0 addi %r1,%r1,144 blr # case FFI_TYPE_SINT16 +#ifdef __LITTLE_ENDIAN__ + lha %r3,112+0(%r1) +#else lha %r3,112+2(%r1) +#endif mtlr %r0 addi %r1,%r1,144 blr @@ -239,9 +255,15 @@ ENTRY(ffi_closure_SYSV) # case FFI_SYSV_TYPE_SMALL_STRUCT + 3. Three byte struct. lwz %r3,112+0(%r1) +#ifdef __LITTLE_ENDIAN__ + mtlr %r0 + addi %r1,%r1,144 + blr +#else srwi %r3,%r3,8 mtlr %r0 b .Lfinish +#endif # case FFI_SYSV_TYPE_SMALL_STRUCT + 4. Four byte struct. lwz %r3,112+0(%r1) @@ -252,20 +274,35 @@ ENTRY(ffi_closure_SYSV) # case FFI_SYSV_TYPE_SMALL_STRUCT + 5. Five byte struct. lwz %r3,112+0(%r1) lwz %r4,112+4(%r1) +#ifdef __LITTLE_ENDIAN__ + mtlr %r0 + b .Lfinish +#else li %r5,24 b .Lstruct567 +#endif # case FFI_SYSV_TYPE_SMALL_STRUCT + 6. Six byte struct. lwz %r3,112+0(%r1) lwz %r4,112+4(%r1) +#ifdef __LITTLE_ENDIAN__ + mtlr %r0 + b .Lfinish +#else li %r5,16 b .Lstruct567 +#endif # case FFI_SYSV_TYPE_SMALL_STRUCT + 7. Seven byte struct. lwz %r3,112+0(%r1) lwz %r4,112+4(%r1) +#ifdef __LITTLE_ENDIAN__ + mtlr %r0 + b .Lfinish +#else li %r5,8 b .Lstruct567 +#endif # case FFI_SYSV_TYPE_SMALL_STRUCT + 8. Eight byte struct. lwz %r3,112+0(%r1) @@ -273,6 +310,7 @@ ENTRY(ffi_closure_SYSV) mtlr %r0 b .Lfinish +#ifndef __LITTLE_ENDIAN__ .Lstruct567: subfic %r6,%r5,32 srw %r4,%r4,%r5 @@ -282,6 +320,7 @@ ENTRY(ffi_closure_SYSV) mtlr %r0 addi %r1,%r1,144 blr +#endif .Luint128: lwz %r6,112+12(%r1) -- Alan Modra Australia Development Lab, IBM