From fd045c7021cabe4462dd99611ab9d003adc203a5 Mon Sep 17 00:00:00 2001 From: Gustavo Frederico Temple Pedrosa Date: Thu, 11 Dec 2014 17:48:41 +0000 Subject: [PATCH] PowerPC64 support for operators with overflow check This adds fast architecture-specific implementations of the following functions for the ppc64: * fast_increment_function * fast_decrement_function --- Zend/zend_operators.h | 54 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 54 insertions(+) diff --git a/Zend/zend_operators.h b/Zend/zend_operators.h index d7967c458a..c6d40b8f85 100644 --- a/Zend/zend_operators.h +++ b/Zend/zend_operators.h @@ -443,6 +443,33 @@ static zend_always_inline int fast_increment_function(zval *op1) "n"(IS_DOUBLE), "n"(ZVAL_OFFSETOF_TYPE) : "cc"); +#elif defined(__GNUC__) && defined(__powerpc64__) + __asm__( + "ld 14, 0(%0)\n\t" + "li 15, 1\n\t" + "li 16, 0\n\t" + "mtxer 16\n\t" + "addo. 14, 14, 15\n\t" + "std 14, 0(%0)\n\t" + "bns+ 0f\n\t" + "xor 14, 14, 14\n\t" + "lis 15, 0x43e00000@h\n\t" + "ori 15, 15, 0x43e00000@l\n\t" +#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__ + "stw 14, 0(%0)\n\t" + "stw 15, 0x4(%0)\n\t" +#else + "stw 14, 0x4(%0)\n\t" + "stw 15, 0(%0)\n\t" +#endif + "li 14, %1\n\t" + "stw 14, %c2(%0)\n" + "0:" + : + : "r"(&op1->value), + "n"(IS_DOUBLE), + "n"(ZVAL_OFFSETOF_TYPE) + : "r14", "r15", "r16", "cc"); #else if (UNEXPECTED(Z_LVAL_P(op1) == ZEND_LONG_MAX)) { /* switch to double */ @@ -485,6 +512,33 @@ static zend_always_inline int fast_decrement_function(zval *op1) "n"(IS_DOUBLE), "n"(ZVAL_OFFSETOF_TYPE) : "cc"); +#elif defined(__GNUC__) && defined(__powerpc64__) + __asm__( + "ld 14, 0(%0)\n\t" + "li 15, 1\n\t" + "li 16, 0\n\t" + "mtxer 16\n\t" + "subo. 14, 14, 15\n\t" + "std 14, 0(%0)\n\t" + "bns+ 0f\n\t" + "xor 14, 14, 14\n\t" + "lis 15, 0xc3e00000@h\n\t" + "ori 15, 15, 0xc3e00000@l\n\t" +#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__ + "stw 14, 0(%0)\n\t" + "stw 15, 0x4(%0)\n\t" +#else + "stw 14, 0x4(%0)\n\t" + "stw 15, 0(%0)\n\t" +#endif + "li 14, %1\n\t" + "stw 14, %c2(%0)\n" + "0:" + : + : "r"(&op1->value), + "n"(IS_DOUBLE), + "n"(ZVAL_OFFSETOF_TYPE) + : "r14", "r15", "r16", "cc"); #else if (UNEXPECTED(Z_LVAL_P(op1) == ZEND_LONG_MIN)) { /* switch to double */ -- 2.40.0