diff options
Diffstat (limited to 'bridges/source/cpp_uno/gcc3_linux_intel/cpp2uno.cxx')
-rw-r--r-- | bridges/source/cpp_uno/gcc3_linux_intel/cpp2uno.cxx | 68 |
1 files changed, 54 insertions, 14 deletions
diff --git a/bridges/source/cpp_uno/gcc3_linux_intel/cpp2uno.cxx b/bridges/source/cpp_uno/gcc3_linux_intel/cpp2uno.cxx index 8e3c391ca..0850d5c53 100644 --- a/bridges/source/cpp_uno/gcc3_linux_intel/cpp2uno.cxx +++ b/bridges/source/cpp_uno/gcc3_linux_intel/cpp2uno.cxx @@ -1,3 +1,4 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ /************************************************************************* * * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. @@ -67,7 +68,7 @@ void cpp2uno_call( if (pReturnTypeDescr) { - if (bridges::cpp_uno::shared::isSimpleType( pReturnTypeDescr )) + if (x86::isSimpleReturnType( pReturnTypeDescr )) { pUnoReturn = pReturnValue; // direct way for simple types } @@ -163,7 +164,7 @@ void cpp2uno_call( (*pThis->getUnoI()->pDispatcher)( pThis->getUnoI(), pMemberTypeDescr, pUnoReturn, pUnoArgs, &pUnoExc ); - // in case an exception occured... + // in case an exception occurred... if (pUnoExc) { // destruct temporary in/inout params @@ -182,7 +183,7 @@ void cpp2uno_call( &aUnoExc, pThis->getBridge()->getUno2Cpp() ); // has to destruct the any } - else // else no exception occured... + else // else no exception occurred... { // temporary params for ( ; nTempIndizes--; ) @@ -252,7 +253,7 @@ extern "C" void cpp_vtable_call( if (nFunctionIndex >= pTypeDescr->nMapFunctionIndexToMemberIndex) { throw RuntimeException( - rtl::OUString::createFromAscii("illegal vtable index!"), + rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "illegal vtable index!" )), (XInterface *)pThis ); } @@ -341,7 +342,7 @@ extern "C" void cpp_vtable_call( default: { throw RuntimeException( - rtl::OUString::createFromAscii("no member description found!"), + rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "no member description found!" )), (XInterface *)pThis ); } } @@ -358,15 +359,40 @@ extern "C" typedef void (*PrivateSnippetExecutor)(); int const codeSnippetSize = 16; +#if defined (FREEBSD) || defined(NETBSD) || defined(OPENBSD) || defined(MACOSX) || \ + defined(DRAGONFLY) +namespace +{ + PrivateSnippetExecutor returnsInRegister(typelib_TypeDescriptionReference * pReturnTypeRef) + { + //These archs apparently are returning small structs in registers, while Linux + //doesn't + PrivateSnippetExecutor exec=NULL; + + typelib_TypeDescription * pReturnTypeDescr = 0; + TYPELIB_DANGER_GET( &pReturnTypeDescr, pReturnTypeRef ); + const bool bSimpleReturnStruct = x86::isSimpleReturnType(pReturnTypeDescr); + const sal_Int32 nRetSize = pReturnTypeDescr->nSize; + TYPELIB_DANGER_RELEASE( pReturnTypeDescr ); + if (bSimpleReturnStruct) + { + exec = privateSnippetExecutorGeneral; // fills eax + if (nRetSize > 4) + exec = privateSnippetExecutorHyper; // fills eax/edx + } + return exec; + } +} +#endif + unsigned char * codeSnippet( unsigned char * code, sal_PtrDiff writetoexecdiff, sal_Int32 functionIndex, sal_Int32 vtableOffset, - typelib_TypeClass returnTypeClass) + typelib_TypeDescriptionReference * pReturnTypeRef) { - if (!bridges::cpp_uno::shared::isSimpleType(returnTypeClass)) { - functionIndex |= 0x80000000; - } PrivateSnippetExecutor exec; - switch (returnTypeClass) { + typelib_TypeClass eReturnClass = pReturnTypeRef ? pReturnTypeRef->eTypeClass : typelib_TypeClass_VOID; + switch (eReturnClass) + { case typelib_TypeClass_VOID: exec = privateSnippetExecutorVoid; break; @@ -380,13 +406,25 @@ unsigned char * codeSnippet( case typelib_TypeClass_DOUBLE: exec = privateSnippetExecutorDouble; break; + case typelib_TypeClass_STRUCT: + case typelib_TypeClass_EXCEPTION: +#if defined(FREEBSD) || defined(NETBSD) || defined(OPENBSD) || defined(MACOSX) || \ + defined(DRAGONFLY) + exec = returnsInRegister(pReturnTypeRef); + if (!exec) + { + exec = privateSnippetExecutorClass; + functionIndex |= 0x80000000; + } + break; +#endif case typelib_TypeClass_STRING: case typelib_TypeClass_TYPE: case typelib_TypeClass_ANY: case typelib_TypeClass_SEQUENCE: - case typelib_TypeClass_STRUCT: case typelib_TypeClass_INTERFACE: exec = privateSnippetExecutorClass; + functionIndex |= 0x80000000; break; default: exec = privateSnippetExecutorGeneral; @@ -454,7 +492,7 @@ unsigned char * bridges::cpp_uno::shared::VtableFactory::addLocalFunctions( code = codeSnippet( code, writetoexecdiff, functionOffset++, vtableOffset, reinterpret_cast< typelib_InterfaceAttributeTypeDescription * >( - member)->pAttributeTypeRef->eTypeClass); + member)->pAttributeTypeRef); // Setter: if (!reinterpret_cast< typelib_InterfaceAttributeTypeDescription * >( @@ -463,7 +501,7 @@ unsigned char * bridges::cpp_uno::shared::VtableFactory::addLocalFunctions( (s++)->fn = code + writetoexecdiff; code = codeSnippet( code, writetoexecdiff, functionOffset++, vtableOffset, - typelib_TypeClass_VOID); + NULL); } break; @@ -472,7 +510,7 @@ unsigned char * bridges::cpp_uno::shared::VtableFactory::addLocalFunctions( code = codeSnippet( code, writetoexecdiff, functionOffset++, vtableOffset, reinterpret_cast< typelib_InterfaceMethodTypeDescription * >( - member)->pReturnTypeRef->eTypeClass); + member)->pReturnTypeRef); break; default: @@ -487,3 +525,5 @@ unsigned char * bridges::cpp_uno::shared::VtableFactory::addLocalFunctions( void bridges::cpp_uno::shared::VtableFactory::flushCode( unsigned char const *, unsigned char const *) {} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |