This is an automated email from the ASF dual-hosted git repository. truckman pushed a commit to branch AOO42X in repository https://gitbox.apache.org/repos/asf/openoffice.git
commit ef5264004c932fc38b2a5794649728e62c1b1769 Author: Curtis Hamilton <[email protected]> AuthorDate: Thu Oct 3 09:16:32 2024 -0400 Add files via upload (cherry picked from commit a0c169eada6c214aa8a607fe32f38941ee624052) --- .../source/cpp_uno/gcc3_freebsd_powerpc64/call.s | 478 +++++++++++++++++++++ .../cpp_uno/gcc3_freebsd_powerpc64/cpp2uno.cxx | 141 +++--- .../cpp_uno/gcc3_freebsd_powerpc64/makefile.mk | 7 +- .../cpp_uno/gcc3_freebsd_powerpc64/share.hxx | 62 ++- .../cpp_uno/gcc3_freebsd_powerpc64/uno2cpp.cxx | 247 ++++++++--- 5 files changed, 810 insertions(+), 125 deletions(-) diff --git a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/call.s b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/call.s new file mode 100644 index 0000000000..f20c598e6c --- /dev/null +++ b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/call.s @@ -0,0 +1,478 @@ + .file "uno_ppc64_asm.cc" + .machine power4 + .abiversion 2 + .section ".text" + .align 2 + .globl callVirtualMethod + .type callVirtualMethod, @function +callVirtualMethod: +.LFB0: + .cfi_startproc +.LCF0: +0: addis 2,12,.TOC.-.LCF0@ha + addi 2,2,.TOC.-.LCF0@l + .localentry callVirtualMethod,.-callVirtualMethod + mflr 0 + std 0,16(1) + std 31,-8(1) + stdu 1,-208(1) + .cfi_def_cfa_offset 208 + .cfi_offset 65, 16 + .cfi_offset 31, -8 + mr 31,1 + .cfi_def_cfa_register 31 + std 3,136(31) + std 5,128(31) + std 6,120(31) + std 7,112(31) + std 9,104(31) + mr 9,4 + stw 9,248(31) + mr 9,8 + stw 9,280(31) + mr 9,10 + stw 9,296(31) + ld 9,304(31) + std 9,96(31) + ld 9,-28688(13) + std 9,184(31) + li 9,0 + lwz 9,280(31) + cmpwi 0,9,0 + beq 0,.L2 + lwz 9,280(31) + addi 9,9,1 + rldicl 9,9,0,32 + rlwinm 9,9,0,0,30 + stw 9,280(31) +.L2: +#ifdef __LITTLE_ENDIAN__ + lwz 9,312(31) +#else + lwz 9,316(31) +#endif + cmplwi 0,9,13 + ble 0,.L3 + li 9,13 +#ifdef __LITTLE_ENDIAN__ + stw 9,312(31) +#else + stw 9,316(31) +#endif +.L3: + lwz 9,296(31) + cmplwi 0,9,8 + ble 0,.L4 + li 9,8 + stw 9,296(31) +.L4: + lwz 9,280(31) + slwi 9,9,3 + rldicl 9,9,0,32 + addi 9,9,15 + srdi 9,9,4 + sldi 9,9,4 + ld 10,0(1) + neg 9,9 + stdux 10,1,9 + addi 9,1,96 + addi 9,9,15 + srdi 9,9,4 + sldi 9,9,4 + std 9,160(31) + lwz 9,280(31) + slwi 9,9,3 + rldicl 9,9,0,32 + mr 8,9 + ld 10,160(31) + ld 9,112(31) + mr 5,8 + mr 4,9 + mr 3,10 + bl memcpy + nop + ld 9,136(31) + ld 9,0(9) + std 9,168(31) + lwz 9,248(31) + slwi 9,9,3 + rldicl 9,9,0,32 + mr 10,9 + ld 9,168(31) + add 9,9,10 + std 9,168(31) + ld 9,168(31) + ld 9,0(9) + std 9,168(31) + ld 9,168(31) + std 9,176(31) + ld 9,96(31) +#APP + # 123 "uno_ppc64_asm.cc" 1 + lfd 1, 0(9) + lfd 2, 8(9) + lfd 3, 16(9) + lfd 4, 24(9) + lfd 5, 32(9) + lfd 6, 40(9) + lfd 7, 48(9) + lfd 8, 56(9) + lfd 9, 64(9) + lfd 10, 72(9) + lfd 11, 80(9) + lfd 12, 88(9) + lfd 13, 96(9) + + # 0 "" 2 +#NO_APP + ld 9,104(31) + ld 3,0(9) + ld 9,104(31) + addi 9,9,8 + ld 4,0(9) + ld 9,104(31) + addi 9,9,16 + ld 5,0(9) + ld 9,104(31) + addi 9,9,24 + ld 6,0(9) + ld 9,104(31) + addi 9,9,32 + ld 7,0(9) + ld 9,104(31) + addi 9,9,40 + ld 8,0(9) + ld 9,104(31) + addi 9,9,48 + ld 0,0(9) + ld 9,104(31) + addi 9,9,56 + ld 9,0(9) + ld 11,176(31) + mr 10,9 + mr 9,0 + std 2,24(1) + mr 12,11 + mtctr 12 + bctrl + ld 2,24(1) +#APP + # 149 "uno_ppc64_asm.cc" 1 + mr 3, 3 + mr 4, 4 + fmr 0, 1 + + # 0 "" 2 +#NO_APP + stfd 0,152(31) + mr 9,3 + mr 10,4 + lfd 0,152(31) + ld 7,128(31) + ld 6,120(31) + fmr 1,0 + mr 4,10 + mr 3,9 + bl MapReturn + nop + nop + ld 9,184(31) + ld 10,-28688(13) + xor. 9,9,10 + li 10,0 + beq 0,.L5 + bl __stack_chk_fail + nop +.L5: + addi 1,31,208 + .cfi_def_cfa 1, 0 + ld 0,16(1) + mtlr 0 + ld 31,-8(1) + blr + .long 0 + .byte 0,9,0,1,128,1,0,1 + .cfi_endproc +.LFE0: + .size callVirtualMethod,.-callVirtualMethod + .section ".toc","aw" + .align 3 +.LC0: + .quad .L9 + .section ".text" + .align 2 + .globl privateSnippetExecutor + .type privateSnippetExecutor, @function +privateSnippetExecutor: +.LFB1: + .cfi_startproc +.LCF1: +0: addis 2,12,.TOC.-.LCF1@ha + addi 2,2,.TOC.-.LCF1@l + .localentry privateSnippetExecutor,.-privateSnippetExecutor + mflr 0 + std 0,16(1) + std 31,-8(1) + stdu 1,-272(1) + .cfi_def_cfa_offset 272 + .cfi_offset 65, 16 + .cfi_offset 31, -8 + mr 31,1 + .cfi_def_cfa_register 31 + ld 0,-28688(13) + std 0,248(31) + li 0,0 + std 3,80(31) + std 4,88(31) + std 5,96(31) + std 6,104(31) + std 7,112(31) + std 8,120(31) + std 9,128(31) + mr 9,10 + std 9,136(31) + addi 9,31,144 +#APP + # 173 "uno_ppc64_asm.cc" 1 + stfd 1, 0(9) +stfd 2, 8(9) +stfd 3, 16(9) +stfd 4, 24(9) +stfd 5, 32(9) +stfd 6, 40(9) +stfd 7, 48(9) +stfd 8, 56(9) +stfd 9, 64(9) +stfd 10, 72(9) +stfd 11, 80(9) +stfd 12, 88(9) +stfd 13, 96(9) + + # 0 "" 2 +#NO_APP + std 11,48(31) + std 1,56(31) + ld 9,48(31) + addi 7,31,64 + addi 8,31,144 + addi 10,31,80 + ld 6,56(31) + mr 5,8 + mr 4,10 + mr 3,9 + bl cpp_mediate + nop + mr 9,3 + stw 9,44(31) + lwa 9,44(31) + cmplwi 0,9,15 + bgt 0,.L7 + sldi 10,9,2 + addis 8,2,.LC0@toc@ha + ld 9,.LC0@toc@l(8) + add 9,10,9 + lwz 10,0(9) + ld 9,.LC0@toc@l(8) + extsw 10,10 + add 9,10,9 + mtctr 9 + bctr + .p2align 2 + .align 2 +.L9: + .long .L19-.L9 + .long .L13-.L9 + .long .L15-.L9 + .long .L15-.L9 + .long .L14-.L9 + .long .L13-.L9 + .long .L12-.L9 + .long .L8-.L9 + .long .L7-.L9 + .long .L7-.L9 + .long .L11-.L9 + .long .L10-.L9 + .long .L7-.L9 + .long .L7-.L9 + .long .L7-.L9 + .long .L8-.L9 +.L15: +#APP + # 209 "uno_ppc64_asm.cc" 1 + lbz 3,64(31) + + # 0 "" 2 +#NO_APP + b .L17 +.L13: +#APP + # 214 "uno_ppc64_asm.cc" 1 + lhz 3,64(31) + + # 0 "" 2 +#NO_APP + b .L17 +.L14: +#APP + # 218 "uno_ppc64_asm.cc" 1 + lha 3,64(31) + + # 0 "" 2 +#NO_APP + b .L17 +.L8: +#APP + # 223 "uno_ppc64_asm.cc" 1 + lwz 3,64(31) + + # 0 "" 2 +#NO_APP + b .L17 +.L12: +#APP + # 227 "uno_ppc64_asm.cc" 1 + lwa 3,64(31) + + # 0 "" 2 +#NO_APP + b .L17 +.L11: + addi 9,31,64 +#APP + # 231 "uno_ppc64_asm.cc" 1 + lfs 1,0(9) + + # 0 "" 2 +#NO_APP + b .L17 +.L10: + addi 9,31,64 +#APP + # 235 "uno_ppc64_asm.cc" 1 + lfd 1,0(9) + + # 0 "" 2 +#NO_APP + b .L17 +.L7: +#APP + # 239 "uno_ppc64_asm.cc" 1 + ld 3,64(31) + + # 0 "" 2 + # 241 "uno_ppc64_asm.cc" 1 + ld 4,72(31) + + # 0 "" 2 +#NO_APP + b .L17 +.L19: + nop +.L17: + nop + ld 9,248(31) + ld 10,-28688(13) + xor. 9,9,10 + li 10,0 + beq 0,.L18 + bl __stack_chk_fail + nop +.L18: + addi 1,31,272 + .cfi_def_cfa 1, 0 + ld 0,16(1) + mtlr 0 + ld 31,-8(1) + blr + .long 0 + .byte 0,9,0,1,128,1,0,1 + .cfi_endproc +.LFE1: + .size privateSnippetExecutor,.-privateSnippetExecutor + .section .rodata + .align 2 + .type _ZL15codeSnippetSize, @object + .size _ZL15codeSnippetSize, 4 +_ZL15codeSnippetSize: + .long 32 + .section ".text" + .align 2 + .globl codeSnippet + .type codeSnippet, @function +codeSnippet: +.LFB2: + .cfi_startproc +.LCF2: +0: addis 2,12,.TOC.-.LCF2@ha + addi 2,2,.TOC.-.LCF2@l + .localentry codeSnippet,.-codeSnippet + std 31,-8(1) + stdu 1,-96(1) + .cfi_def_cfa_offset 96 + .cfi_offset 31, -8 + mr 31,1 + .cfi_def_cfa_register 31 + std 3,56(31) + mr 9,4 + mr 8,5 + mr 10,6 + stw 9,52(31) + mr 9,8 + stw 9,48(31) + mr 9,10 + stb 9,47(31) + lwa 9,48(31) + sldi 10,9,32 + lwa 9,52(31) + or 9,10,9 + std 9,64(31) + lbz 9,47(31) + cmpwi 0,9,0 + beq 0,.L21 + ld 9,64(31) + oris 9,9,0x8000 + std 9,64(31) +.L21: + ld 9,56(31) + std 9,72(31) + ld 9,72(31) + lis 10,0xe96c + ori 10,10,0x18 + stw 10,0(9) + ld 9,72(31) + addi 9,9,4 + lis 10,0xe98c + ori 10,10,0x10 + stw 10,0(9) + ld 9,72(31) + addi 9,9,8 + lis 10,0x7d89 + ori 10,10,0x3a6 + stw 10,0(9) + ld 9,72(31) + addi 9,9,12 + lis 10,0x4e80 + ori 10,10,0x420 + stw 10,0(9) + ld 9,72(31) + addi 9,9,16 + addis 10,2,privateSnippetExecutor@toc@ha + addi 10,10,privateSnippetExecutor@toc@l + std 10,0(9) + ld 9,72(31) + addi 9,9,24 + ld 10,64(31) + std 10,0(9) + ld 9,56(31) + addi 9,9,32 + mr 3,9 + addi 1,31,96 + .cfi_def_cfa 1, 0 + ld 31,-8(1) + blr + .long 0 + .byte 0,9,0,0,128,1,0,1 + .cfi_endproc +.LFE2: + .size codeSnippet,.-codeSnippet + .section .note.GNU-stack,"",@progbits diff --git a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/cpp2uno.cxx b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/cpp2uno.cxx index ca96db0c12..5d6712a826 100644 --- a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/cpp2uno.cxx +++ b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/cpp2uno.cxx @@ -28,6 +28,7 @@ #include <uno/data.h> #include <typelib/typedescription.hxx> +#include <osl/endian.h> #include "bridges/cpp_uno/shared/bridge.hxx" #include "bridges/cpp_uno/shared/cppinterfaceproxy.hxx" #include "bridges/cpp_uno/shared/types.hxx" @@ -37,6 +38,11 @@ #include <stdio.h> #include <string.h> +#ifdef OSL_BIGENDIAN +#define IS_BIG_ENDIAN 1 +#else +#define IS_BIG_ENDIAN 0 +#endif using namespace ::com::sun::star::uno; @@ -144,14 +150,14 @@ static typelib_TypeClass cpp2uno_call( case typelib_TypeClass_BYTE: case typelib_TypeClass_BOOLEAN: if (ng < ppc64::MAX_GPR_REGS) - { - pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)gpreg) + (sizeof(void*)-1)); + { + pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)gpreg) + 7*IS_BIG_ENDIAN); ng++; gpreg++; } else - { - pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)ovrflw) + (sizeof(void*)-1)); + { + pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)ovrflw) + 7*IS_BIG_ENDIAN); bOverFlowUsed = true; } if (bOverFlowUsed) ovrflw++; @@ -160,14 +166,14 @@ static typelib_TypeClass cpp2uno_call( case typelib_TypeClass_SHORT: case typelib_TypeClass_UNSIGNED_SHORT: if (ng < ppc64::MAX_GPR_REGS) - { - pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)gpreg) + (sizeof(void*)-2)); + { + pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)gpreg) + 6*IS_BIG_ENDIAN); ng++; gpreg++; } else - { - pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)ovrflw) + (sizeof(void*)-2)); + { + pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)ovrflw) + 6*IS_BIG_ENDIAN); bOverFlowUsed = true; } if (bOverFlowUsed) ovrflw++; @@ -176,14 +182,14 @@ static typelib_TypeClass cpp2uno_call( case typelib_TypeClass_LONG: case typelib_TypeClass_UNSIGNED_LONG: if (ng < ppc64::MAX_GPR_REGS) - { - pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)gpreg) + (sizeof(void*)-4)); + { + pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)gpreg) + 4*IS_BIG_ENDIAN); ng++; gpreg++; } else - { - pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)ovrflw) + (sizeof(void*)-4)); + { + pCppArgs[nPos] = pUnoArgs[nPos] = (((char *)ovrflw) + 4*IS_BIG_ENDIAN); bOverFlowUsed = true; } if (bOverFlowUsed) ovrflw++; @@ -327,21 +333,25 @@ static typelib_TypeClass cpp2uno_call( } } +#if defined(_CALL_ELF) && _CALL_ELF == 2 +# define PARAMSAVE 32 +#else +# define PARAMSAVE 48 +#endif -//================================================================================================== -static typelib_TypeClass cpp_mediate( - sal_uInt64 nOffsetAndIndex, +extern "C" typelib_TypeClass cpp_mediate( + sal_uInt64 nOffsetAndIndex, void ** gpreg, void ** fpreg, long sp, - sal_Int64 * pRegisterReturn /* space for register return */ ) + sal_Int64 * pRegisterReturn /* space for register return */ ) { - OSL_ENSURE( sizeof(sal_Int64)==sizeof(void *), "### unexpected!" ); + static_assert(sizeof(sal_Int64)==sizeof(void *), "### unexpected!"); sal_Int32 nVtableOffset = (nOffsetAndIndex >> 32); sal_Int32 nFunctionIndex = (nOffsetAndIndex & 0xFFFFFFFF); long sf = *(long*)sp; - void ** ovrflw = (void**)(sf + 112); - + void ** ovrflw = (void**)(sf + PARAMSAVE + 64); + // gpreg: [ret *], this, [other gpr params] // fpreg: [fpr params] // ovrflw: [gpr or fpr params (properly aligned)] @@ -501,54 +511,52 @@ static typelib_TypeClass cpp_mediate( return eRet; } -extern "C" void privateSnippetExecutor( ... ) +extern "C" void privateSnippetExecutor( ... ); +#if 0 { - volatile long nOffsetAndIndex; + sal_uInt64 gpreg[ppc64::MAX_GPR_REGS]; - //mr %r3, %r11 # move into arg1 the 64bit value passed from OOo - __asm__ __volatile__ ( - "mr %0, 11\n\t" - : "=r" (nOffsetAndIndex) : ); + register long r3 asm("r3"); gpreg[0] = r3; + register long r4 asm("r4"); gpreg[1] = r4; + register long r5 asm("r5"); gpreg[2] = r5; + register long r6 asm("r6"); gpreg[3] = r6; + register long r7 asm("r7"); gpreg[4] = r7; + register long r8 asm("r8"); gpreg[5] = r8; + register long r9 asm("r9"); gpreg[6] = r9; + register long r10 asm("r10"); gpreg[7] = r10; - sal_uInt64 gpreg[ppc64::MAX_GPR_REGS]; double fpreg[ppc64::MAX_SSE_REGS]; __asm__ __volatile__ ( - "std 3, 0(%0)\t\n" - "std 4, 8(%0)\t\n" - "std 5, 16(%0)\t\n" - "std 6, 24(%0)\t\n" - "std 7, 32(%0)\t\n" - "std 8, 40(%0)\t\n" - "std 9, 48(%0)\t\n" - "std 10, 56(%0)\t\n" - "stfd 1, 0(%1)\t\n" - "stfd 2, 8(%1)\t\n" - "stfd 3, 16(%1)\t\n" - "stfd 4, 24(%1)\t\n" - "stfd 5, 32(%1)\t\n" - "stfd 6, 40(%1)\t\n" - "stfd 7, 48(%1)\t\n" - "stfd 8, 56(%1)\t\n" - "stfd 9, 64(%1)\t\n" - "stfd 10, 72(%1)\t\n" - "stfd 11, 80(%1)\t\n" - "stfd 12, 88(%1)\t\n" - "stfd 13, 96(%1)\t\n" - : : "r" (gpreg), "r" (fpreg) - : "r0", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", - "fr1", "fr2", "fr3", "fr4", "fr5", "fr6", "fr7", "fr8", "fr9", + "stfd 1, 0(%0)\t\n" + "stfd 2, 8(%0)\t\n" + "stfd 3, 16(%0)\t\n" + "stfd 4, 24(%0)\t\n" + "stfd 5, 32(%0)\t\n" + "stfd 6, 40(%0)\t\n" + "stfd 7, 48(%0)\t\n" + "stfd 8, 56(%0)\t\n" + "stfd 9, 64(%0)\t\n" + "stfd 10, 72(%0)\t\n" + "stfd 11, 80(%0)\t\n" + "stfd 12, 88(%0)\t\n" + "stfd 13, 96(%0)\t\n" + : : "r" (fpreg) + : "fr1", "fr2", "fr3", "fr4", "fr5", "fr6", "fr7", "fr8", "fr9", "fr10", "fr11", "fr12", "fr13" ); - volatile long sp; + register long r11 asm("r11"); + const long nOffsetAndIndex = r11; - //stack pointer - __asm__ __volatile__ ( - "mr %0, 1\n\t" - : "=r" (sp) : ); + register long r1 asm("r1"); + const long sp = r1; +#if defined(_CALL_ELF) && _CALL_ELF == 2 + volatile long nRegReturn[2]; +#else volatile long nRegReturn[1]; +#endif typelib_TypeClass aType = cpp_mediate( nOffsetAndIndex, (void**)gpreg, (void**)fpreg, sp, (sal_Int64*)nRegReturn); @@ -591,11 +599,20 @@ extern "C" void privateSnippetExecutor( ... ) default: __asm__( "ld 3,%0\n\t" : : "m" (nRegReturn[0]) ); +#if defined(_CALL_ELF) && _CALL_ELF == 2 + __asm__( "ld 4,%0\n\t" + : : "m" (nRegReturn[1]) ); +#endif break; } } +#endif +#if defined(_CALL_ELF) && _CALL_ELF == 2 +const int codeSnippetSize = 32; +#else const int codeSnippetSize = 24; +#endif unsigned char * codeSnippet( unsigned char * code, sal_Int32 nFunctionIndex, sal_Int32 nVtableOffset, bool simpleRetType) @@ -609,10 +626,22 @@ unsigned char * codeSnippet( unsigned char * code, sal_Int32 nFunctionIndex, sa if ( !simpleRetType ) nOffsetAndIndex |= 0x80000000; - +#if defined(_CALL_ELF) && _CALL_ELF == 2 + unsigned int *raw = (unsigned int *)&code[0]; + + raw[0] = 0xe96c0018; /* 0: ld 11,2f-0b(12) */ + raw[1] = 0xe98c0010; /* ld 12,1f-0b(12) */ + raw[2] = 0x7d8903a6; /* mtctr 12 */ + raw[3] = 0x4e800420; /* bctr */ + /* 1: .quad function_addr */ + /* 2: .quad context */ + *(void **)&raw[4] = (void *)privateSnippetExecutor; + *(void **)&raw[6] = (void*)nOffsetAndIndex; +#else void ** raw = (void **)&code[0]; memcpy(raw, (char*) privateSnippetExecutor, 16); raw[2] = (void*) nOffsetAndIndex; +#endif #ifdef CMC_DEBUG fprintf(stderr, "in: offset/index is %x %x %d, %lx\n", nFunctionIndex, nVtableOffset, !simpleRetType, raw[2]); diff --git a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/makefile.mk b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/makefile.mk index 931edd8f80..0aa77c48e9 100644 --- a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/makefile.mk +++ b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/makefile.mk @@ -53,7 +53,8 @@ CFLAGSNOOPT=-O0 SLOFILES= \ $(SLO)$/except.obj \ $(SLO)$/cpp2uno.obj \ - $(SLO)$/uno2cpp.obj + $(SLO)$/uno2cpp.obj \ + $(SLO)$/call.obj SHL1TARGET= $(TARGET) @@ -73,3 +74,7 @@ SHL1STDLIBS= \ # --- Targets ------------------------------------------------------ .INCLUDE : target.mk + +$(SLO)$/%.obj: %.s + $(CC) -c -o $(SLO)$/$(@:b).o $< + touch $@ diff --git a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/share.hxx b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/share.hxx index 649be7dd22..21e9763486 100644 --- a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/share.hxx +++ b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/share.hxx @@ -25,16 +25,64 @@ #include <typeinfo> #include <exception> + +#include <cxxabi.h> +#ifndef _GLIBCXX_CDTOR_CALLABI // new in GCC 4.7 cxxabi.h +#define _GLIBCXX_CDTOR_CALLABI +#endif #include <cstddef> +#ifndef CONFIG_CXXABI_H +#define CONFIG_CXXABI_H + +#define HAVE_CXXABI_H_BASE_CLASS_TYPE_INFO 0 +#define HAVE_CXXABI_H_CLASS_TYPE_INFO 0 +#define HAVE_CXXABI_H_CXA_ALLOCATE_EXCEPTION 0 +#define HAVE_CXXABI_H_CXA_EH_GLOBALS 1 +#define HAVE_CXXABI_H_CXA_EXCEPTION 1 +#define HAVE_CXXABI_H_CXA_GET_GLOBALS 1 +#define HAVE_CXXABI_H_CXA_CURRENT_EXCEPTION_TYPE 1 +#define HAVE_CXXABI_H_CXA_THROW 0 +#define HAVE_CXXABI_H_SI_CLASS_TYPE_INFO 0 +#define HAVE_CXXABI_H_VMI_CLASS_TYPE_INFO 0 + +#endif + +#if !HAVE_CXXABI_H_CLASS_TYPE_INFO +// <https://mentorembedded.github.io/cxx-abi/abi.html>, +// libstdc++-v3/libsupc++/cxxabi.h: +namespace __cxxabiv1 { +class __class_type_info: public std::type_info { +public: + explicit __class_type_info(char const * n): type_info(n) {} + ~__class_type_info(); +}; +} +#endif + +#if !HAVE_CXXABI_H_SI_CLASS_TYPE_INFO +// <https://mentorembedded.github.io/cxx-abi/abi.html>, +// libstdc++-v3/libsupc++/cxxabi.h: +namespace __cxxabiv1 { +class __si_class_type_info: public __class_type_info { +public: + __class_type_info const * __base_type; + explicit __si_class_type_info( + char const * n, __class_type_info const *base): + __class_type_info(n), __base_type(base) {} + ~__si_class_type_info(); +}; +} +#endif + namespace CPPU_CURRENT_NAMESPACE { - void dummy_can_throw_anything( char const * ); - +void dummy_can_throw_anything( char const * ); // ----- following decl from libstdc++-v3/libsupc++/unwind-cxx.h and unwind.h +#ifdef __GLIBCXX__ struct _Unwind_Exception { unsigned exception_class __attribute__((__mode__(__DI__))); @@ -63,18 +111,21 @@ struct __cxa_exception _Unwind_Exception unwindHeader; }; +#endif /* __GLIBCXX__ */ extern "C" void *__cxa_allocate_exception( std::size_t thrown_size ) throw(); extern "C" void __cxa_throw ( void *thrown_exception, std::type_info *tinfo, void (*dest) (void *) ) __attribute__((noreturn)); +#ifdef __GLIBCXX__ struct __cxa_eh_globals { __cxa_exception *caughtExceptions; unsigned int uncaughtExceptions; }; extern "C" __cxa_eh_globals *__cxa_get_globals () throw(); +#endif /* __GLIBCXX__ */ // ----- @@ -82,11 +133,16 @@ extern "C" __cxa_eh_globals *__cxa_get_globals () throw(); void raiseException( uno_Any * pUnoExc, uno_Mapping * pUno2Cpp ); //================================================================================================== +#ifndef __GLIBCXX__ +using __cxxabiv1:: __cxa_exception; +#endif /* __GLIBCXX__ */ + void fillUnoException( __cxa_exception * header, uno_Any *, uno_Mapping * pCpp2Uno ); } namespace ppc64 { - enum ppclimits { MAX_GPR_REGS = 8, MAX_SSE_REGS = 13 }; + enum ppclimits { MAX_GPR_REGS = 8, MAX_SSE_REGS = 13 }; + bool return_in_hidden_param( typelib_TypeDescriptionReference *pTypeRef ); } diff --git a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/uno2cpp.cxx b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/uno2cpp.cxx index 59f9e3acf1..7f1193e45d 100644 --- a/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/uno2cpp.cxx +++ b/main/bridges/source/cpp_uno/gcc3_freebsd_powerpc64/uno2cpp.cxx @@ -26,6 +26,12 @@ #include <stdlib.h> +#include <exception> +#include <malloc.h> +#include <typeinfo> + +#include <com/sun/star/uno/Exception.hpp> +#include <com/sun/star/uno/RuntimeException.hpp> #include <com/sun/star/uno/genfunc.hxx> #include <uno/data.h> @@ -42,10 +48,68 @@ using namespace ::rtl; using namespace ::com::sun::star::uno; +#ifdef __GLIBCXX__ +using CPPU_CURRENT_NAMESPACE::__cxa_exception; +using CPPU_CURRENT_NAMESPACE::__cxa_get_globals; +#else +using __cxxabiv1::__cxa_exception; +using __cxxabiv1::__cxa_current_primary_exception; +using __cxxabiv1::__cxa_decrement_exception_refcount; +#endif + +namespace ppc64 +{ +#if defined(_CALL_ELF) && _CALL_ELF == 2 + bool is_complex_struct(const typelib_TypeDescription * type) + { + const typelib_CompoundTypeDescription * p + = reinterpret_cast< const typelib_CompoundTypeDescription * >(type); + for (sal_Int32 i = 0; i < p->nMembers; ++i) + { + if (p->ppTypeRefs[i]->eTypeClass == typelib_TypeClass_STRUCT || + p->ppTypeRefs[i]->eTypeClass == typelib_TypeClass_EXCEPTION) + { + typelib_TypeDescription * t = 0; + TYPELIB_DANGER_GET(&t, p->ppTypeRefs[i]); + bool b = is_complex_struct(t); + TYPELIB_DANGER_RELEASE(t); + if (b) { + return true; + } + } + else if (!bridges::cpp_uno::shared::isSimpleType(p->ppTypeRefs[i]->eTypeClass)) + return true; + } + if (p->pBaseTypeDescription != 0) + return is_complex_struct(&p->pBaseTypeDescription->aBase); + return false; + } +#endif + + bool return_in_hidden_param( typelib_TypeDescriptionReference *pTypeRef ) + { + if (bridges::cpp_uno::shared::isSimpleType(pTypeRef)) + return false; +#if defined(_CALL_ELF) && _CALL_ELF == 2 + else if (pTypeRef->eTypeClass == typelib_TypeClass_STRUCT || pTypeRef->eTypeClass == typelib_TypeClass_EXCEPTION) + { + typelib_TypeDescription * pTypeDescr = 0; + TYPELIB_DANGER_GET( &pTypeDescr, pTypeRef ); + + //A Composite Type not larger than 16 bytes is returned in up to two GPRs + bool bRet = pTypeDescr->nSize > 16 || is_complex_struct(pTypeDescr); + + TYPELIB_DANGER_RELEASE( pTypeDescr ); + return bRet; + } +#endif + return true; + } +} -void MapReturn(long r3, double dret, typelib_TypeClass eTypeClass, void *pRegisterReturn) +extern "C" void MapReturn(long r3, long r4, double dret, typelib_TypeDescriptionReference* pReturnType, void *pRegisterReturn) { - switch (eTypeClass) + switch (pReturnType->eTypeClass) { case typelib_TypeClass_HYPER: case typelib_TypeClass_UNSIGNED_HYPER: @@ -67,10 +131,23 @@ void MapReturn(long r3, double dret, typelib_TypeClass eTypeClass, void *pRegist break; case typelib_TypeClass_FLOAT: *reinterpret_cast<float *>( pRegisterReturn ) = dret; - break; + break; case typelib_TypeClass_DOUBLE: *reinterpret_cast<double *>( pRegisterReturn ) = dret; break; +#if defined(_CALL_ELF) && _CALL_ELF == 2 + case typelib_TypeClass_STRUCT: + case typelib_TypeClass_EXCEPTION: + if (!ppc64::return_in_hidden_param(pReturnType)) + { + sal_uInt64 *pRegisters = reinterpret_cast<sal_uInt64*>(pRegisterReturn); + pRegisters[0] = r3; + if (pReturnType->pType->nSize > 8) + pRegisters[1] = r4; + } +#else + (void)r4; +#endif default: break; } @@ -79,11 +156,13 @@ void MapReturn(long r3, double dret, typelib_TypeClass eTypeClass, void *pRegist namespace { //================================================================================================== -static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, - void * pRegisterReturn, typelib_TypeDescription * pReturnTypeDescr, +extern "C" void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, + void * pRegisterReturn, typelib_TypeDescription * pReturnTypeDescr, sal_uInt64 *pStack, sal_uInt32 nStack, sal_uInt64 *pGPR, sal_uInt32 nGPR, - double *pFPR, sal_uInt32 nFPR) + double *pFPR, sal_uInt32 nFPR); + +#if 0 { // Stack, if used, must be 16-bytes aligned if ( nStack ) @@ -99,13 +178,13 @@ static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, // Let's figure out what is really going on here { fprintf( stderr, "= callVirtualMethod() =\nGPR's (%d): ", nGPR ); - for ( int i = 0; i < nGPR; ++i ) + for ( sal_uInt32 i = 0; i < nGPR; ++i ) fprintf( stderr, "0x%lx, ", pGPR[i] ); fprintf( stderr, "\nFPR's (%d): ", nFPR ); - for ( int i = 0; i < nFPR; ++i ) - fprintf( stderr, "0x%lx (%f), ", pFPR[i], pFPR[i] ); + for ( sal_uInt32 i = 0; i < nFPR; ++i ) + fprintf( stderr, "0x%lx (%lf), ", (sal_Int64)pFPR[i], pFPR[i] ); fprintf( stderr, "\nStack (%d): ", nStack ); - for ( int i = 0; i < nStack; ++i ) + for ( sal_uInt32 i = 0; i < nStack; ++i ) fprintf( stderr, "0x%lx, ", pStack[i] ); fprintf( stderr, "\n" ); } @@ -120,52 +199,40 @@ static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, pMethod += 8 * nVtableIndex; pMethod = *((sal_uInt64 *)pMethod); +#if defined(_CALL_ELF) && _CALL_ELF == 2 + typedef void (* FunctionCall )(...); +#else typedef void (* FunctionCall )( sal_uInt64, sal_uInt64, sal_uInt64, sal_uInt64, sal_uInt64, sal_uInt64, sal_uInt64, sal_uInt64 ); +#endif FunctionCall pFunc = (FunctionCall)pMethod; volatile double dret; // fill registers __asm__ __volatile__ ( - "ld 3, 0(%0)\n\t" - "ld 4, 8(%0)\n\t" - "ld 5, 16(%0)\n\t" - "ld 6, 24(%0)\n\t" - "ld 7, 32(%0)\n\t" - "ld 8, 40(%0)\n\t" - "ld 9, 48(%0)\n\t" - "ld 10, 56(%0)\n\t" - "lfd 1, 0(%1)\n\t" - "lfd 2, 8(%1)\n\t" - "lfd 3, 16(%1)\n\t" - "lfd 4, 24(%1)\n\t" - "lfd 5, 32(%1)\n\t" - "lfd 6, 40(%1)\n\t" - "lfd 7, 48(%1)\n\t" - "lfd 8, 56(%1)\n\t" - "lfd 9, 64(%1)\n\t" - "lfd 10, 72(%1)\n\t" - "lfd 11, 80(%1)\n\t" - "lfd 12, 88(%1)\n\t" - "lfd 13, 96(%1)\n\t" - : : "r" (pGPR), "r" (pFPR) - : "r0", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", - "fr1", "fr2", "fr3", "fr4", "fr5", "fr6", "fr7", "fr8", "fr9", - "fr10", "fr11", "fr12", "fr13" + "lfd 1, 0(%0)\n\t" + "lfd 2, 8(%0)\n\t" + "lfd 3, 16(%0)\n\t" + "lfd 4, 24(%0)\n\t" + "lfd 5, 32(%0)\n\t" + "lfd 6, 40(%0)\n\t" + "lfd 7, 48(%0)\n\t" + "lfd 8, 56(%0)\n\t" + "lfd 9, 64(%0)\n\t" + "lfd 10, 72(%0)\n\t" + "lfd 11, 80(%0)\n\t" + "lfd 12, 88(%0)\n\t" + "lfd 13, 96(%0)\n\t" + : : "r" (pFPR) + : "fr1", "fr2", "fr3", "fr4", "fr5", "fr6", "fr7", "fr8", "fr9", + "fr10", "fr11", "fr12", "fr13" ); // tell gcc that r3 to r11 are not available to it for doing the TOC and exception munge on the func call register sal_uInt64 r3 asm("r3"); register sal_uInt64 r4 asm("r4"); - register sal_uInt64 r5 asm("r5"); - register sal_uInt64 r6 asm("r6"); - register sal_uInt64 r7 asm("r7"); - register sal_uInt64 r8 asm("r8"); - register sal_uInt64 r9 asm("r9"); - register sal_uInt64 r10 asm("r10"); - register sal_uInt64 r11 asm("r11"); - (*pFunc)(r3, r4, r5, r6, r7, r8, r9, r10); + (*pFunc)(pGPR[0], pGPR[1], pGPR[2], pGPR[3], pGPR[4], pGPR[5], pGPR[6], pGPR[7]); // get return value __asm__ __volatile__ ( @@ -174,8 +241,9 @@ static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, "fmr %0, 1\n\t" : "=f" (dret), "=r" (r3), "=r" (r4) : ); - MapReturn(r3, dret, pReturnTypeDescr->eTypeClass, pRegisterReturn); + MapReturn(r3, r4, dret, reinterpret_cast<typelib_TypeDescriptionReference *>(pReturnTypeDescr), pRegisterReturn); } +#endif // Macros for easier insertion of values to registers or stack // pSV - pointer to the source @@ -185,23 +253,35 @@ static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, // The value in %xmm register is already prepared to be retrieved as a float, // thus we treat float and double the same -#define INSERT_FLOAT( pSV, nr, pFPR, pDS, bOverflow ) \ - if ( nr < ppc64::MAX_SSE_REGS ) \ +#define INSERT_FLOAT( pSV, nr, pFPR, nGPR, pDS, bOverFlow ) \ + if ( nGPR < ppc64::MAX_GPR_REGS ) \ + ++nGPR; \ + if ( nr < ppc64::MAX_SSE_REGS ) \ pFPR[nr++] = *reinterpret_cast<float *>( pSV ); \ else \ - bOverFlow = true; \ + bOverFlow = true; \ if (bOverFlow) \ *pDS++ = *reinterpret_cast<sal_uInt64 *>( pSV ); // verbatim! -#define INSERT_DOUBLE( pSV, nr, pFPR, pDS, bOverflow ) \ - if ( nr < ppc64::MAX_SSE_REGS ) \ +#define INSERT_DOUBLE( pSV, nr, pFPR, nGPR, pDS, bOverFlow ) \ + if ( nGPR < ppc64::MAX_GPR_REGS ) \ + ++nGPR; \ + if ( nr < ppc64::MAX_SSE_REGS ) \ pFPR[nr++] = *reinterpret_cast<double *>( pSV ); \ else \ - bOverFlow = true; \ + bOverFlow = true; \ if (bOverFlow) \ *pDS++ = *reinterpret_cast<sal_uInt64 *>( pSV ); // verbatim! -#define INSERT_INT64( pSV, nr, pGPR, pDS, bOverflow ) \ +#define INSERT_INT64( pSV, nr, pGPR, pDS, bOverFlow ) \ + if ( nr < ppc64::MAX_GPR_REGS ) \ + pGPR[nr++] = *reinterpret_cast<sal_Int64 *>( pSV ); \ + else \ + bOverFlow = true; \ + if (bOverFlow) \ + *pDS++ = *reinterpret_cast<sal_Int64 *>( pSV ); + +#define INSERT_UINT64( pSV, nr, pGPR, pDS, bOverFlow ) \ if ( nr < ppc64::MAX_GPR_REGS ) \ pGPR[nr++] = *reinterpret_cast<sal_uInt64 *>( pSV ); \ else \ @@ -209,7 +289,15 @@ static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, if (bOverFlow) \ *pDS++ = *reinterpret_cast<sal_uInt64 *>( pSV ); -#define INSERT_INT32( pSV, nr, pGPR, pDS, bOverflow ) \ +#define INSERT_INT32( pSV, nr, pGPR, pDS, bOverFlow ) \ + if ( nr < ppc64::MAX_GPR_REGS ) \ + pGPR[nr++] = *reinterpret_cast<sal_Int32 *>( pSV ); \ + else \ + bOverFlow = true; \ + if (bOverFlow) \ + *pDS++ = *reinterpret_cast<sal_Int32 *>( pSV ); + +#define INSERT_UINT32( pSV, nr, pGPR, pDS, bOverFlow ) \ if ( nr < ppc64::MAX_GPR_REGS ) \ pGPR[nr++] = *reinterpret_cast<sal_uInt32 *>( pSV ); \ else \ @@ -217,7 +305,15 @@ static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, if (bOverFlow) \ *pDS++ = *reinterpret_cast<sal_uInt32 *>( pSV ); -#define INSERT_INT16( pSV, nr, pGPR, pDS, bOverflow ) \ +#define INSERT_INT16( pSV, nr, pGPR, pDS, bOverFlow ) \ + if ( nr < ppc64::MAX_GPR_REGS ) \ + pGPR[nr++] = *reinterpret_cast<sal_Int16 *>( pSV ); \ + else \ + bOverFlow = true; \ + if (bOverFlow) \ + *pDS++ = *reinterpret_cast<sal_Int16 *>( pSV ); + +#define INSERT_UINT16( pSV, nr, pGPR, pDS, bOverFlow ) \ if ( nr < ppc64::MAX_GPR_REGS ) \ pGPR[nr++] = *reinterpret_cast<sal_uInt16 *>( pSV ); \ else \ @@ -225,7 +321,15 @@ static void callVirtualMethod(void * pThis, sal_uInt32 nVtableIndex, if (bOverFlow) \ *pDS++ = *reinterpret_cast<sal_uInt16 *>( pSV ); -#define INSERT_INT8( pSV, nr, pGPR, pDS, bOverflow ) \ +#define INSERT_INT8( pSV, nr, pGPR, pDS, bOverFlow ) \ + if ( nr < ppc64::MAX_GPR_REGS ) \ + pGPR[nr++] = *reinterpret_cast<sal_Int8 *>( pSV ); \ + else \ + bOverFlow = true; \ + if (bOverFlow) \ + *pDS++ = *reinterpret_cast<sal_Int8 *>( pSV ); + +#define INSERT_UINT8( pSV, nr, pGPR, pDS, bOverFlow ) \ if ( nr < ppc64::MAX_GPR_REGS ) \ pGPR[nr++] = *reinterpret_cast<sal_uInt8 *>( pSV ); \ else \ @@ -337,19 +441,23 @@ static void cpp_call( INSERT_INT32( pCppArgs[nPos], nGPR, pGPR, pStack, bOverFlow ); break; case typelib_TypeClass_SHORT: + INSERT_INT16( pCppArgs[nPos], nGPR, pGPR, pStack, bOverFlow ); + break; case typelib_TypeClass_CHAR: case typelib_TypeClass_UNSIGNED_SHORT: INSERT_INT16( pCppArgs[nPos], nGPR, pGPR, pStack, bOverFlow ); break; case typelib_TypeClass_BOOLEAN: + INSERT_UINT8( pCppArgs[nPos], nGPR, pGPR, pStack, bOverFlow ); + break; case typelib_TypeClass_BYTE: INSERT_INT8( pCppArgs[nPos], nGPR, pGPR, pStack, bOverFlow ); break; case typelib_TypeClass_FLOAT: - INSERT_FLOAT( pCppArgs[nPos], nFPR, pFPR, pStack, bOverFlow ); - break; + INSERT_FLOAT( pCppArgs[nPos], nFPR, pFPR, nGPR, pStack, bOverFlow ); + break; case typelib_TypeClass_DOUBLE: - INSERT_DOUBLE( pCppArgs[nPos], nFPR, pFPR, pStack, bOverFlow ); + INSERT_DOUBLE( pCppArgs[nPos], nFPR, pFPR, nGPR, pStack, bOverFlow ); break; } @@ -448,9 +556,18 @@ static void cpp_call( } catch (...) { + __cxa_exception *header; +#ifdef __GLIBCXX__ + header = __cxa_get_globals()->caughtExceptions; +#else + header = reinterpret_cast<__cxa_exception *>( __cxa_current_primary_exception() ); + if (header) { + __cxa_decrement_exception_refcount( header ); + header--; + } +#endif // fill uno exception - fillUnoException( CPPU_CURRENT_NAMESPACE::__cxa_get_globals()->caughtExceptions, - *ppUnoExc, pThis->getBridge()->getCpp2Uno() ); + CPPU_CURRENT_NAMESPACE::fillUnoException( header, *ppUnoExc, pThis->getBridge()->getCpp2Uno() ); // temporary params for ( ; nTempIndizes--; ) @@ -475,8 +592,8 @@ void unoInterfaceProxyDispatch( void * pReturn, void * pArgs[], uno_Any ** ppException ) { // is my surrogate - bridges::cpp_uno::shared::UnoInterfaceProxy * pThis - = static_cast< bridges::cpp_uno::shared::UnoInterfaceProxy *> (pUnoI); + ::bridges::cpp_uno::shared::UnoInterfaceProxy * pThis + = static_cast< ::bridges::cpp_uno::shared::UnoInterfaceProxy *> (pUnoI); typelib_InterfaceTypeDescription * pTypeDescr = pThis->pTypeDescr; switch (pMemberDescr->eTypeClass) @@ -484,8 +601,8 @@ void unoInterfaceProxyDispatch( case typelib_TypeClass_INTERFACE_ATTRIBUTE: { - VtableSlot aVtableSlot( - getVtableSlot( + ::bridges::cpp_uno::shared::VtableSlot aVtableSlot( + ::bridges::cpp_uno::shared::getVtableSlot( reinterpret_cast< typelib_InterfaceAttributeTypeDescription const * >( pMemberDescr))); @@ -529,8 +646,8 @@ void unoInterfaceProxyDispatch( case typelib_TypeClass_INTERFACE_METHOD: { - VtableSlot aVtableSlot( - getVtableSlot( + ::bridges::cpp_uno::shared::VtableSlot aVtableSlot( + ::bridges::cpp_uno::shared::getVtableSlot( reinterpret_cast< typelib_InterfaceMethodTypeDescription const * >( pMemberDescr)));
