Index: configure.ac ================================================================== --- configure.ac +++ configure.ac @@ -356,12 +356,10 @@ AC_SUBST(OBJFW_SHARED_LIB, "${LIB_PREFIX}objfw${LIB_SUFFIX}") AC_SUBST(EXCEPTIONS_LIB_A, "exceptions.lib.a") AC_SUBST(EXCEPTIONS_EXCEPTIONS_LIB_A, "exceptions/exceptions.lib.a") AC_SUBST(FORWARDING_LIB_A, "forwarding.lib.a") AC_SUBST(FORWARDING_FORWARDING_LIB_A, "forwarding/forwarding.lib.a") - AC_SUBST(INVOCATION_LIB_A, "invocation.lib.a") - AC_SUBST(INVOCATION_INVOCATION_LIB_A, "invocation/invocation.lib.a") AC_SUBST(LOOKUP_ASM_LIB_A, "lookup-asm.lib.a") AC_SUBST(LOOKUP_ASM_LOOKUP_ASM_LIB_A, "lookup-asm/lookup-asm.lib.a") BUILDSYS_FRAMEWORK([ AC_SUBST(OBJFW_FRAMEWORK, "ObjFW.framework") @@ -395,12 +393,10 @@ AC_SUBST(OBJFW_STATIC_LIB, "libobjfw.a") AC_SUBST(EXCEPTIONS_A, "exceptions.a") AC_SUBST(EXCEPTIONS_EXCEPTIONS_A, "exceptions/exceptions.a") AC_SUBST(FORWARDING_A, "forwarding.a") AC_SUBST(FORWARDING_FORWARDING_A, "forwarding/forwarding.a") - AC_SUBST(INVOCATION_A, "invocation.a") - AC_SUBST(INVOCATION_INVOCATION_A, "invocation/invocation.a") AC_SUBST(LOOKUP_ASM_A, "lookup-asm.a") AC_SUBST(LOOKUP_ASM_LOOKUP_ASM_A, "lookup-asm/lookup-asm.a") ]) AC_DEFINE_UNQUOTED(PLUGIN_SUFFIX, "$PLUGIN_SUFFIX", [Suffix for plugins]) Index: src/Makefile ================================================================== --- src/Makefile +++ src/Makefile @@ -1,8 +1,8 @@ include ../extra.mk -SUBDIRS = ${RUNTIME} exceptions ${ENCODINGS} forwarding invocation +SUBDIRS = ${RUNTIME} exceptions ${ENCODINGS} forwarding SUBDIRS_AFTER = ${BRIDGE} DISTCLEAN = objfw-defs.h SHARED_LIB = ${OBJFW_SHARED_LIB} STATIC_LIB = ${OBJFW_STATIC_LIB} @@ -209,17 +209,15 @@ ${OFSELECTKERNELEVENTOBSERVER_M} OBJS_EXTRA = ${RUNTIME_RUNTIME_A} \ ${EXCEPTIONS_EXCEPTIONS_A} \ ${ENCODINGS_ENCODINGS_A} \ - ${FORWARDING_FORWARDING_A} \ - ${INVOCATION_INVOCATION_A} + ${FORWARDING_FORWARDING_A} LIB_OBJS_EXTRA = ${RUNTIME_RUNTIME_LIB_A} \ ${EXCEPTIONS_EXCEPTIONS_LIB_A} \ ${ENCODINGS_ENCODINGS_LIB_A} \ - ${FORWARDING_FORWARDING_LIB_A} \ - ${INVOCATION_INVOCATION_LIB_A} + ${FORWARDING_FORWARDING_LIB_A} include ../buildsys.mk CPPFLAGS += -I. -I.. -Iexceptions -Iruntime LD = ${OBJC} Index: src/OFInvocation.h ================================================================== --- src/OFInvocation.h +++ src/OFInvocation.h @@ -17,22 +17,10 @@ #import "OFObject.h" OF_ASSUME_NONNULL_BEGIN -#ifdef OF_APPLE_RUNTIME -# ifdef OF_X86_64 -# define OF_INVOCATION_CAN_INVOKE -# endif -#else -# ifdef OF_ELF -# ifdef OF_X86_64 -# define OF_INVOCATION_CAN_INVOKE -# endif -# endif -#endif - @class OFMethodSignature; @class OFMutableArray OF_GENERIC(ObjectType); @class OFMutableData; /*! @@ -98,15 +86,8 @@ * @brief Gets the return value. * * @param buffer The buffer in which the return value is stored */ - (void)getReturnValue: (void *)buffer; - -#ifdef OF_INVOCATION_CAN_INVOKE -/*! - * @brief Invokes the method. - */ -- (void)invoke; -#endif @end OF_ASSUME_NONNULL_END Index: src/OFInvocation.m ================================================================== --- src/OFInvocation.m +++ src/OFInvocation.m @@ -22,14 +22,10 @@ #import "OFInvocation.h" #import "OFArray.h" #import "OFData.h" #import "OFMethodSignature.h" -#ifdef OF_INVOCATION_CAN_INVOKE -extern void of_invocation_invoke(OFInvocation *); -#endif - @implementation OFInvocation @synthesize methodSignature = _methodSignature; + (instancetype)invocationWithMethodSignature: (OFMethodSignature *)signature { @@ -113,13 +109,6 @@ - (void)getReturnValue: (void *)buffer { memcpy(buffer, _returnValue.items, _returnValue.itemSize); } - -#ifdef OF_INVOCATION_CAN_INVOKE -- (void)invoke -{ - of_invocation_invoke(self); -} -#endif @end DELETED src/invocation/Makefile Index: src/invocation/Makefile ================================================================== --- src/invocation/Makefile +++ src/invocation/Makefile @@ -1,12 +0,0 @@ -include ../../extra.mk - -STATIC_PIC_LIB_NOINST = ${INVOCATION_LIB_A} -STATIC_LIB_NOINST = ${INVOCATION_A} - -SRCS = call.S \ - invoke.m - -include ../../buildsys.mk - -ASFLAGS += -I../.. -I.. -OBJCFLAGS += -I../.. -I.. -I../exceptions -I../runtime DELETED src/invocation/apple-call-x86_64.S Index: src/invocation/apple-call-x86_64.S ================================================================== --- src/invocation/apple-call-x86_64.S +++ src/invocation/apple-call-x86_64.S @@ -1,118 +0,0 @@ -/* - * Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, - * 2018, 2019 - * Jonathan Schleifer - * - * All rights reserved. - * - * This file is part of ObjFW. It may be distributed under the terms of the - * Q Public License 1.0, which can be found in the file LICENSE.QPL included in - * the packaging of this file. - * - * Alternatively, it may be distributed under the terms of the GNU General - * Public License, either version 2 or 3, which can be found in the file - * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this - * file. - */ - -#include "config.h" - -#include "invoke-x86_64.h" - -.globl _of_invocation_call - -.section __TEXT, __text, regular, pure_instructions -_of_invocation_call: - pushq %rbp - movq %rsp, %rbp - - subq $16, %rsp - andq $-16, %rsp - movq %rdi, -8(%rbp) - - leaq OFFSET_STACK(%rdi), %rdx - movq OFFSET_STACK_SIZE(%rdi), %rcx - - testq $1, %rcx - jnz Lfix_align - -Lfill_stack: - testq %rcx, %rcx - jz Lstack_filled - - decq %rcx - movq (%rdx,%rcx,8), %r11 - pushq %r11 - - jmp Lfill_stack - -Lstack_filled: - movb OFFSET_NUM_SSE_USED(%rdi), %al - - movaps OFFSET_SSE_INOUT+112(%rdi), %xmm7 - movaps OFFSET_SSE_INOUT+96(%rdi), %xmm6 - movaps OFFSET_SSE_INOUT+80(%rdi), %xmm5 - movaps OFFSET_SSE_INOUT+64(%rdi), %xmm4 - movaps OFFSET_SSE_INOUT+48(%rdi), %xmm3 - movaps OFFSET_SSE_INOUT+32(%rdi), %xmm2 - movaps OFFSET_SSE_INOUT+16(%rdi), %xmm1 - movaps OFFSET_SSE_INOUT(%rdi), %xmm0 - - movq OFFSET_GPR_IN+40(%rdi), %r9 - movq OFFSET_GPR_IN+32(%rdi), %r8 - movq OFFSET_GPR_IN+24(%rdi), %rcx - movq OFFSET_GPR_IN+16(%rdi), %rdx - movq OFFSET_GPR_IN+8(%rdi), %rsi - - movb OFFSET_RETURN_TYPE(%rdi), %r11b - movq OFFSET_GPR_IN(%rdi), %rdi - - cmpb $RETURN_TYPE_STRET, %r11b - je Lcall_send_stret - - cmpb $RETURN_TYPE_JMP, %r11b - je _objc_msgSend - - cmpb $RETURN_TYPE_JMP_STRET, %r11b - je _objc_msgSend_stret - - call _objc_msgSend - -Lafter_send: - movq -8(%rbp), %rdi - movq %rax, OFFSET_GPR_OUT(%rdi) - movq %rdx, OFFSET_GPR_OUT+8(%rdi) - movaps %xmm0, OFFSET_SSE_INOUT(%rdi) - movaps %xmm1, OFFSET_SSE_INOUT+16(%rdi) - - movb OFFSET_RETURN_TYPE(%rdi), %r11b - - cmpb $RETURN_TYPE_X87, %r11b - je Lpop_long_double - - cmpb $RETURN_TYPE_COMPLEX_X87, %r11b - je Lpop_complex_long_double - -Lreturn: - movq %rbp, %rsp - popq %rbp - - ret - -Lfix_align: - xorq %r11, %r11 - pushq %r11 - jmp Lfill_stack - -Lcall_send_stret: - call _objc_msgSend_stret - jmp Lafter_send - -Lpop_long_double: - fstpt OFFSET_X87_OUT(%rdi) - jmp Lreturn - -Lpop_complex_long_double: - fstpt OFFSET_X87_OUT(%rdi) - fstpt OFFSET_X87_OUT+16(%rdi) - jmp Lreturn DELETED src/invocation/call-x86_64-elf.S Index: src/invocation/call-x86_64-elf.S ================================================================== --- src/invocation/call-x86_64-elf.S +++ src/invocation/call-x86_64-elf.S @@ -1,140 +0,0 @@ -/* - * Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, - * 2018, 2019 - * Jonathan Schleifer - * - * All rights reserved. - * - * This file is part of ObjFW. It may be distributed under the terms of the - * Q Public License 1.0, which can be found in the file LICENSE.QPL included in - * the packaging of this file. - * - * Alternatively, it may be distributed under the terms of the GNU General - * Public License, either version 2 or 3, which can be found in the file - * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this - * file. - */ - -#include "config.h" - -#include "invoke-x86_64.h" - -.globl of_invocation_call - -.section .text -of_invocation_call: - pushq %rbp - movq %rsp, %rbp - - subq $16, %rsp - andq $-16, %rsp - movq %rdi, -8(%rbp) - - movb OFFSET_RETURN_TYPE(%rdi), %r11b - cmpb $RETURN_TYPE_STRET, %r11b - je .lookup_stret - cmpb $RETURN_TYPE_JMP_STRET, %r11b - je .lookup_stret - - movq OFFSET_GPR_IN+8(%rdi), %rsi - movq OFFSET_GPR_IN+0(%rdi), %rdi - call objc_msg_lookup@PLT - -.after_lookup: - movq %rax, -16(%rbp) - movq -8(%rbp), %rdi - - leaq OFFSET_STACK(%rdi), %rdx - movq OFFSET_STACK_SIZE(%rdi), %rcx - - testq $1, %rcx - jnz .fix_align - -.fill_stack: - testq %rcx, %rcx - jz .stack_filled - - decq %rcx - movq (%rdx,%rcx,8), %r11 - pushq %r11 - - jmp .fill_stack - -.stack_filled: - movb OFFSET_NUM_SSE_USED(%rdi), %al - - movaps OFFSET_SSE_INOUT+112(%rdi), %xmm7 - movaps OFFSET_SSE_INOUT+96(%rdi), %xmm6 - movaps OFFSET_SSE_INOUT+80(%rdi), %xmm5 - movaps OFFSET_SSE_INOUT+64(%rdi), %xmm4 - movaps OFFSET_SSE_INOUT+48(%rdi), %xmm3 - movaps OFFSET_SSE_INOUT+32(%rdi), %xmm2 - movaps OFFSET_SSE_INOUT+16(%rdi), %xmm1 - movaps OFFSET_SSE_INOUT(%rdi), %xmm0 - - movq OFFSET_GPR_IN+40(%rdi), %r9 - movq OFFSET_GPR_IN+32(%rdi), %r8 - movq OFFSET_GPR_IN+24(%rdi), %rcx - movq OFFSET_GPR_IN+16(%rdi), %rdx - movq OFFSET_GPR_IN+8(%rdi), %rsi - - movb OFFSET_RETURN_TYPE(%rdi), %r11b - movq OFFSET_GPR_IN(%rdi), %rdi - - cmpb $RETURN_TYPE_JMP, %r11b - je .jmp_into_method - cmpb $RETURN_TYPE_JMP_STRET, %r11b - je .jmp_into_method - - movq -16(%rbp), %r11 - call *%r11 - -.after_send: - movq -8(%rbp), %rdi - movq %rax, OFFSET_GPR_OUT(%rdi) - movq %rdx, OFFSET_GPR_OUT+8(%rdi) - movaps %xmm0, OFFSET_SSE_INOUT(%rdi) - movaps %xmm1, OFFSET_SSE_INOUT+16(%rdi) - - movb OFFSET_RETURN_TYPE(%rdi), %r11b - - cmpb $RETURN_TYPE_X87, %r11b - je .pop_long_double - - cmpb $RETURN_TYPE_COMPLEX_X87, %r11b - je .pop_complex_long_double - -.return: - movq %rbp, %rsp - popq %rbp - - ret - -.fix_align: - xorq %r11, %r11 - pushq %r11 - jmp .fill_stack - -.lookup_stret: - movq OFFSET_GPR_IN+16(%rdi), %rsi - movq OFFSET_GPR_IN+8(%rdi), %rdi - call objc_msg_lookup_stret@PLT - - jmp .after_lookup - -.jmp_into_method: - movq -16(%rbp), %r11 - jmp *%r11 - -.pop_long_double: - fstpt OFFSET_X87_OUT(%rdi) - jmp .return - -.pop_complex_long_double: - fstpt OFFSET_X87_OUT(%rdi) - fstpt OFFSET_X87_OUT+16(%rdi) - jmp .return - -#ifdef OF_LINUX -.section .note.GNU-stack, "", %progbits -#endif DELETED src/invocation/call.S Index: src/invocation/call.S ================================================================== --- src/invocation/call.S +++ src/invocation/call.S @@ -1,32 +0,0 @@ -/* - * Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, - * 2018, 2019 - * Jonathan Schleifer - * - * All rights reserved. - * - * This file is part of ObjFW. It may be distributed under the terms of the - * Q Public License 1.0, which can be found in the file LICENSE.QPL included in - * the packaging of this file. - * - * Alternatively, it may be distributed under the terms of the GNU General - * Public License, either version 2 or 3, which can be found in the file - * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this - * file. - */ - -#include "config.h" - -#include "platform.h" - -#ifdef OF_APPLE_RUNTIME -# ifdef OF_X86_64 -# include "apple-call-x86_64.S" -# endif -#else -# ifdef OF_ELF -# ifdef OF_X86_64 -# include "call-x86_64-elf.S" -# endif -# endif -#endif DELETED src/invocation/invoke-x86_64.h Index: src/invocation/invoke-x86_64.h ================================================================== --- src/invocation/invoke-x86_64.h +++ src/invocation/invoke-x86_64.h @@ -1,37 +0,0 @@ -/* - * Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, - * 2018, 2019 - * Jonathan Schleifer - * - * All rights reserved. - * - * This file is part of ObjFW. It may be distributed under the terms of the - * Q Public License 1.0, which can be found in the file LICENSE.QPL included in - * the packaging of this file. - * - * Alternatively, it may be distributed under the terms of the GNU General - * Public License, either version 2 or 3, which can be found in the file - * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this - * file. - */ - -#define RETURN_TYPE_NORMAL 0 -#define RETURN_TYPE_STRET 1 -#define RETURN_TYPE_X87 2 -#define RETURN_TYPE_COMPLEX_X87 3 -#define RETURN_TYPE_JMP 4 -#define RETURN_TYPE_JMP_STRET 5 - -#define NUM_GPR_IN 6 -#define NUM_GPR_OUT 2 -#define NUM_SSE_INOUT 8 -#define NUM_X87_OUT 2 - -#define OFFSET_GPR_IN 0 -#define OFFSET_GPR_OUT (OFFSET_GPR_IN + NUM_GPR_IN * 8) -#define OFFSET_SSE_INOUT (OFFSET_GPR_OUT + NUM_GPR_OUT * 8) -#define OFFSET_X87_OUT (OFFSET_SSE_INOUT + NUM_SSE_INOUT * 16) -#define OFFSET_NUM_SSE_USED (OFFSET_X87_OUT + NUM_X87_OUT * 16) -#define OFFSET_RETURN_TYPE (OFFSET_NUM_SSE_USED + 1) -#define OFFSET_STACK_SIZE (OFFSET_RETURN_TYPE + 7) -#define OFFSET_STACK (OFFSET_STACK_SIZE + 8) DELETED src/invocation/invoke-x86_64.m Index: src/invocation/invoke-x86_64.m ================================================================== --- src/invocation/invoke-x86_64.m +++ src/invocation/invoke-x86_64.m @@ -1,452 +0,0 @@ -/* - * Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, - * 2018, 2019 - * Jonathan Schleifer - * - * All rights reserved. - * - * This file is part of ObjFW. It may be distributed under the terms of the - * Q Public License 1.0, which can be found in the file LICENSE.QPL included in - * the packaging of this file. - * - * Alternatively, it may be distributed under the terms of the GNU General - * Public License, either version 2 or 3, which can be found in the file - * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this - * file. - */ - -#include "config.h" - -#include -#include -#include - -#import "OFInvocation.h" -#import "OFMethodSignature.h" - -#import "OFInvalidFormatException.h" -#import "OFOutOfMemoryException.h" - -#import "invoke-x86_64.h" - -#import "macros.h" - -struct call_context { - uint64_t GPR[NUM_GPR_IN + NUM_GPR_OUT]; - __m128 SSE[NUM_SSE_INOUT]; - long double X87[NUM_X87_OUT]; - uint8_t numSSEUsed; - uint8_t returnType; - uint64_t stackSize; - uint64_t stack[]; -}; - -extern void of_invocation_call(struct call_context *); - -static void -pushGPR(struct call_context **context, uint_fast8_t *currentGPR, uint64_t value) -{ - struct call_context *newContext; - - if (*currentGPR < NUM_GPR_IN) { - (*context)->GPR[(*currentGPR)++] = value; - return; - } - - if ((newContext = realloc(*context, - sizeof(**context) + ((*context)->stackSize + 1) * 8)) == NULL) { - free(*context); - @throw [OFOutOfMemoryException exceptionWithRequestedSize: - sizeof(**context) + ((*context)->stackSize + 1) * 8]; - } - - newContext->stack[newContext->stackSize] = value; - newContext->stackSize++; - *context = newContext; -} - -static void -pushDouble(struct call_context **context, uint_fast8_t *currentSSE, - double value) -{ - struct call_context *newContext; - - if (*currentSSE < NUM_SSE_INOUT) { - (*context)->SSE[(*currentSSE)++] = (__m128)_mm_set_sd(value); - (*context)->numSSEUsed++; - return; - } - - if ((newContext = realloc(*context, - sizeof(**context) + ((*context)->stackSize + 1) * 8)) == NULL) { - free(*context); - @throw [OFOutOfMemoryException exceptionWithRequestedSize: - sizeof(**context) + ((*context)->stackSize + 1) * 8]; - } - - memcpy(&newContext->stack[newContext->stackSize], &value, 8); - newContext->stackSize++; - *context = newContext; -} - -static void -pushQuad(struct call_context **context, uint_fast8_t *currentSSE, - double low, double high) -{ - size_t stackSize; - struct call_context *newContext; - - if (*currentSSE + 1 < NUM_SSE_INOUT) { - (*context)->SSE[(*currentSSE)++] = (__m128)_mm_set_sd(low); - (*context)->SSE[(*currentSSE)++] = (__m128)_mm_set_sd(high); - (*context)->numSSEUsed += 2; - return; - } - - stackSize = (*context)->stackSize + 2; - - if ((newContext = realloc(*context, - sizeof(**context) + stackSize * 8)) == NULL) { - free(*context); - @throw [OFOutOfMemoryException exceptionWithRequestedSize: - sizeof(**context) + stackSize * 8]; - } - - memset(&newContext->stack[newContext->stackSize], '\0', - (stackSize - newContext->stackSize) * 8); - memcpy(&newContext->stack[stackSize - 2], &low, 8); - memcpy(&newContext->stack[stackSize - 1], &high, 8); - newContext->stackSize = stackSize; - *context = newContext; -} - -static void -pushLongDouble(struct call_context **context, long double value) -{ - struct call_context *newContext; - - if ((newContext = realloc(*context, - sizeof(**context) + ((*context)->stackSize + 2) * 8)) == NULL) { - free(*context); - @throw [OFOutOfMemoryException exceptionWithRequestedSize: - sizeof(**context) + ((*context)->stackSize + 2) * 8]; - } - - memcpy(&newContext->stack[newContext->stackSize], &value, 16); - newContext->stackSize += 2; - *context = newContext; -} - -static void -pushLongDoublePair(struct call_context **context, long double value[2]) -{ - size_t stackSize; - struct call_context *newContext; - - stackSize = OF_ROUND_UP_POW2(2UL, (*context)->stackSize) + 4; - - if ((newContext = realloc(*context, - sizeof(**context) + stackSize * 8)) == NULL) { - free(*context); - @throw [OFOutOfMemoryException exceptionWithRequestedSize: - sizeof(**context) + stackSize * 8]; - } - - memset(&newContext->stack[newContext->stackSize], '\0', - (stackSize - newContext->stackSize) * 8); - memcpy(&newContext->stack[stackSize - 4], value, 32); - newContext->stackSize = stackSize; - *context = newContext; -} - -#if defined(__SIZEOF_INT128__) && !defined(__clang__) -static void -pushInt128(struct call_context **context, uint_fast8_t *currentGPR, - uint64_t value[2]) -{ - size_t stackSize; - struct call_context *newContext; - - if (*currentGPR + 1 < NUM_GPR_IN) { - (*context)->GPR[(*currentGPR)++] = value[0]; - (*context)->GPR[(*currentGPR)++] = value[1]; - return; - } - - stackSize = OF_ROUND_UP_POW2(2, (*context)->stackSize) + 2; - - if ((newContext = realloc(*context, - sizeof(**context) + stackSize * 8)) == NULL) { - free(*context); - @throw [OFOutOfMemoryException exceptionWithRequestedSize: - sizeof(**context) + stackSize * 8]; - } - - memset(&newContext->stack[newContext->stackSize], '\0', - (stackSize - newContext->stackSize) * 8); - memcpy(&newContext->stack[stackSize - 2], value, 16); - newContext->stackSize = stackSize; - *context = newContext; -} -#endif - -void -of_invocation_invoke(OFInvocation *invocation) -{ - OFMethodSignature *methodSignature = invocation.methodSignature; - size_t numberOfArguments = methodSignature.numberOfArguments; - struct call_context *context; - const char *typeEncoding; - uint_fast8_t currentGPR = 0, currentSSE = 0; - - if ((context = calloc(sizeof(*context), 1)) == NULL) - @throw [OFOutOfMemoryException exception]; - - for (size_t i = 0; i < numberOfArguments; i++) { - typeEncoding = [methodSignature argumentTypeAtIndex: i]; - - if (*typeEncoding == 'r') - typeEncoding++; - - switch (*typeEncoding) { -#define CASE_GPR(encoding, type) \ - case encoding: \ - { \ - type tmp; \ - [invocation getArgument: &tmp \ - atIndex: i]; \ - pushGPR(&context, ¤tGPR, (uint64_t)tmp); \ - } \ - break; - CASE_GPR('c', char) - CASE_GPR('C', unsigned char) - CASE_GPR('i', int) - CASE_GPR('I', unsigned int) - CASE_GPR('s', short) - CASE_GPR('S', unsigned short) - CASE_GPR('l', long) - CASE_GPR('L', unsigned long) - CASE_GPR('q', long long) - CASE_GPR('Q', unsigned long long) - CASE_GPR('B', _Bool) - CASE_GPR('*', char *) - CASE_GPR('@', id) - CASE_GPR('#', Class) - /* - * Using SEL triggers a warning that casting a SEL to an - * integer is deprecated. - */ - CASE_GPR(':', void *) - CASE_GPR('^', void *) -#undef CASE_GPR -#ifdef __SIZEOF_INT128__ - case 't': - case 'T':; - uint64_t int128Tmp[2]; - [invocation getArgument: &int128Tmp - atIndex: i]; -# ifndef __clang__ - pushInt128(&context, ¤tGPR, int128Tmp); -# else - /* See https://bugs.llvm.org/show_bug.cgi?id=34646 */ - pushGPR(&context, ¤tGPR, int128Tmp[0]); - pushGPR(&context, ¤tGPR, int128Tmp[1]); -# endif - break; -#endif - case 'f':; - double floatTmp = 0; - [invocation getArgument: &floatTmp - atIndex: i]; - pushDouble(&context, ¤tSSE, floatTmp); - break; - case 'd':; - double doubleTmp; - [invocation getArgument: &doubleTmp - atIndex: i]; - pushDouble(&context, ¤tSSE, doubleTmp); - break; - case 'D':; - long double longDoubleTmp; - [invocation getArgument: &longDoubleTmp - atIndex: i]; - pushLongDouble(&context, longDoubleTmp); - break; - case 'j': - switch (typeEncoding[1]) { - case 'f':; - double complexFloatTmp; - [invocation getArgument: &complexFloatTmp - atIndex: i]; - pushDouble(&context, ¤tSSE, - complexFloatTmp); - break; - case 'd':; - double complexDoubleTmp[2]; - [invocation getArgument: &complexDoubleTmp - atIndex: i]; - pushQuad(&context, ¤tSSE, - complexDoubleTmp[0], complexDoubleTmp[1]); - break; - case 'D':; - long double complexLongDoubleTmp[2]; - [invocation getArgument: &complexLongDoubleTmp - atIndex: i]; - pushLongDoublePair(&context, - complexLongDoubleTmp); - break; - default: - free(context); - @throw [OFInvalidFormatException exception]; - } - - break; - /* TODO: '[' */ - /* TODO: '{' */ - /* TODO: '(' */ - default: - free(context); - @throw [OFInvalidFormatException exception]; - } - } - - typeEncoding = methodSignature.methodReturnType; - - if (*typeEncoding == 'r') - typeEncoding++; - - switch (*typeEncoding) { - case 'v': - case 'c': - case 'C': - case 'i': - case 'I': - case 's': - case 'S': - case 'l': - case 'L': - case 'q': - case 'Q': - case 'B': - case '*': - case '@': - case '#': - case ':': - case '^': -#ifdef __SIZEOF_INT128__ - case 't': - case 'T': -#endif - case 'f': - case 'd': - context->returnType = RETURN_TYPE_NORMAL; - break; - case 'D': - context->returnType = RETURN_TYPE_X87; - break; - case 'j': - switch (typeEncoding[1]) { - case 'f': - case 'd': - context->returnType = RETURN_TYPE_NORMAL; - break; - case 'D': - context->returnType = RETURN_TYPE_COMPLEX_X87; - break; - default: - free(context); - @throw [OFInvalidFormatException exception]; - } - - break; - /* TODO: '[' */ - /* TODO: '{' */ - /* TODO: '(' */ - default: - free(context); - @throw [OFInvalidFormatException exception]; - } - - of_invocation_call(context); - - switch (*typeEncoding) { - case 'v': - break; -#define CASE_GPR(encoding, type) \ - case encoding: \ - { \ - type tmp = (type)context->GPR[NUM_GPR_IN]; \ - [invocation setReturnValue: &tmp]; \ - } \ - break; - CASE_GPR('c', char) - CASE_GPR('C', unsigned char) - CASE_GPR('i', int) - CASE_GPR('I', unsigned int) - CASE_GPR('s', short) - CASE_GPR('S', unsigned short) - CASE_GPR('l', long) - CASE_GPR('L', unsigned long) - CASE_GPR('q', long long) - CASE_GPR('Q', unsigned long long) - CASE_GPR('B', _Bool) - CASE_GPR('*', char *) - CASE_GPR('@', id) - CASE_GPR('#', Class) - CASE_GPR(':', SEL) - CASE_GPR('^', void *) -#undef CASE_GPR -#ifdef __SIZEOF_INT128__ - case 't': - case 'T':; - [invocation setReturnValue: &context->GPR[NUM_GPR_IN]]; - break; -#endif - case 'f':; - float floatTmp; - _mm_store_ss(&floatTmp, context->SSE[0]); - [invocation setReturnValue: &floatTmp]; - break; - case 'd':; - double doubleTmp; - _mm_store_sd(&doubleTmp, (__m128d)context->SSE[0]); - [invocation setReturnValue: &doubleTmp]; - break; - case 'D': - [invocation setReturnValue: &context->X87[0]]; - break; - case 'j': - switch (typeEncoding[1]) { - case 'f':; - double complexFloatTmp; - _mm_store_sd(&complexFloatTmp, - (__m128d)context->SSE[0]); - [invocation setReturnValue: &complexFloatTmp]; - break; - case 'd':; - double complexDoubleTmp[2]; - _mm_store_sd(&complexDoubleTmp[0], - (__m128d)context->SSE[0]); - _mm_store_sd(&complexDoubleTmp[1], - (__m128d)context->SSE[1]); - [invocation setReturnValue: &complexDoubleTmp]; - break; - case 'D': - [invocation setReturnValue: context->X87]; - break; - default: - free(context); - @throw [OFInvalidFormatException exception]; - } - - break; - /* TODO: '[' */ - /* TODO: '{' */ - /* TODO: '(' */ - default: - free(context); - @throw [OFInvalidFormatException exception]; - } - - free(context); -} DELETED src/invocation/invoke.m Index: src/invocation/invoke.m ================================================================== --- src/invocation/invoke.m +++ src/invocation/invoke.m @@ -1,27 +0,0 @@ -/* - * Copyright (c) 2008, 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, - * 2018, 2019 - * Jonathan Schleifer - * - * All rights reserved. - * - * This file is part of ObjFW. It may be distributed under the terms of the - * Q Public License 1.0, which can be found in the file LICENSE.QPL included in - * the packaging of this file. - * - * Alternatively, it may be distributed under the terms of the GNU General - * Public License, either version 2 or 3, which can be found in the file - * LICENSE.GPLv2 or LICENSE.GPLv3 respectively included in the packaging of this - * file. - */ - -#include "config.h" - -#include "platform.h" - -#if defined(OF_X86_64) && (defined(OF_APPLE_RUNTIME) || defined(OF_ELF)) -# include "invoke-x86_64.m" -#else -/* To not have an empty translation unit otherwise */ -int of_invocation_cannot_invoke; -#endif Index: tests/OFInvocationTests.m ================================================================== --- tests/OFInvocationTests.m +++ tests/OFInvocationTests.m @@ -309,213 +309,8 @@ TEST(@"-[getArgument:atIndex:] #4", R([invocation getArgument: &st2 atIndex: 5]) && memcmp(&st, &st2, sizeof(st)) == 0) -#ifdef OF_INVOCATION_CAN_INVOKE - /* -[invoke] #1 */ - selector = @selector(invocationTestMethod2:); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - [invocation setArgument: &self - atIndex: 2]; - - TEST(@"-[invoke] #1", R([invocation invoke])) - - /* -[invoke] #2 */ - selector = @selector(invocationTestMethod3::::::::::::::::); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - - for (int j = 1; j <= 16; j++) - [invocation setArgument: &j - atIndex: j + 1]; - - int intResult; - TEST(@"-[invoke] #2", R([invocation invoke]) && - R([invocation getReturnValue: &intResult]) && intResult == 8) - - /* -[invoke] #3 */ - selector = @selector(invocationTestMethod4::::::::::::::::); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - - for (int j = 1; j <= 16; j++) { - double d = j; - [invocation setArgument: &d - atIndex: j + 1]; - } - - double doubleResult; - TEST(@"-[invoke] #3", R([invocation invoke]) && - R([invocation getReturnValue: &doubleResult]) && - doubleResult == 8.5) - - /* -[invoke] #4 */ - selector = @selector(invocationTestMethod5::::::::::::::::); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - - for (int j = 1; j <= 16; j++) { - float f = j; - double d = j; - - if (j == 1 || j == 10) - [invocation setArgument: &d - atIndex: j + 1]; - else - [invocation setArgument: &f - atIndex: j + 1]; - } - - float floatResult; - TEST(@"-[invoke] #4", R([invocation invoke]) && - R([invocation getReturnValue: &floatResult]) && floatResult == 8.5) - - /* Only when encoding long doubles is supported */ - if (strcmp(@encode(double), @encode(long double)) != 0) { - /* -[invoke] #5 */ - selector = @selector(invocationTestMethod6::::::::::::::::); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - - for (int j = 1; j <= 16; j++) { - long double d = j; - [invocation setArgument: &d - atIndex: j + 1]; - } - - long double longDoubleResult; - TEST(@"-[invoke] #5", R([invocation invoke]) && - R([invocation getReturnValue: &longDoubleResult]) && - longDoubleResult == 8.5) - } - -# if defined(HAVE_COMPLEX_H) && !defined(__STDC_NO_COMPLEX__) - /* -[invoke] #6 */ - selector = @selector(invocationTestMethod7::::::::::::::::); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - - for (int j = 1; j <= 16; j++) { - complex float cf = j + 0.5 * j * I; - complex double cd = j + 0.5 * j * I; - - if (j & 1) - [invocation setArgument: &cf - atIndex: j + 1]; - else - [invocation setArgument: &cd - atIndex: j + 1]; - } - - complex double complexDoubleResult; - TEST(@"-[invoke] #6", R([invocation invoke]) && - R([invocation getReturnValue: &complexDoubleResult]) && - complexDoubleResult == 8.5 + 4.25 * I) - - /* Only when encoding complex long doubles is supported */ - if (strcmp(@encode(complex double), - @encode(complex long double)) != 0) { - /* -[invoke] #7 */ - selector = @selector(invocationTestMethod8::::::::::::::::); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - - for (int j = 1; j <= 16; j++) { - complex double cd = j + 0.5 * j * I; - complex float cf = j + 0.5 * j * I; - complex long double cld = j + 0.5 * j * I; - - switch (j % 3) { - case 0: - [invocation setArgument: &cld - atIndex: j + 1]; - break; - case 1: - [invocation setArgument: &cd - atIndex: j + 1]; - break; - case 2: - [invocation setArgument: &cf - atIndex: j + 1]; - break; - } - } - - complex long double complexLongDoubleResult; - TEST(@"-[invoke] #7", R([invocation invoke]) && - R([invocation getReturnValue: &complexLongDoubleResult]) && - complexLongDoubleResult == 8.5 + 4.25 * I) - } -# endif - -# ifdef __SIZEOF_INT128__ - /* -[invoke] #8 */ - selector = @selector(invocationTestMethod9::::::::::::::::); - invocation = [OFInvocation invocationWithMethodSignature: - [self methodSignatureForSelector: selector]]; - - [invocation setArgument: &self - atIndex: 0]; - [invocation setArgument: &selector - atIndex: 1]; - - for (int j = 1; j <= 16; j++) { - __extension__ __int128 i128 = 0xFFFFFFFFFFFFFFFF; - i128 <<= 64; - i128 |= j; - - if (j == 1 || j == 5) - [invocation setArgument: &j - atIndex: j + 1]; - else - [invocation setArgument: &i128 - atIndex: j + 1]; - } - - __extension__ __int128 int128Result; - TEST(@"-[invoke] #8", R([invocation invoke]) && - R([invocation getReturnValue: &int128Result]) && - int128Result == __extension__ ((__int128)0xFFFFFFFFFFFFFFFF << 64) + - 8) -# endif -#endif - [pool drain]; } @end