aboutsummaryrefslogtreecommitdiffstats
path: root/gcc-4.2.1-5666.3/more-hdrs/ppc_intrinsics.h
diff options
context:
space:
mode:
Diffstat (limited to 'gcc-4.2.1-5666.3/more-hdrs/ppc_intrinsics.h')
-rw-r--r--gcc-4.2.1-5666.3/more-hdrs/ppc_intrinsics.h1026
1 files changed, 0 insertions, 1026 deletions
diff --git a/gcc-4.2.1-5666.3/more-hdrs/ppc_intrinsics.h b/gcc-4.2.1-5666.3/more-hdrs/ppc_intrinsics.h
deleted file mode 100644
index 8cfe01f5d..000000000
--- a/gcc-4.2.1-5666.3/more-hdrs/ppc_intrinsics.h
+++ /dev/null
@@ -1,1026 +0,0 @@
-/* APPLE LOCAL file PPC_INTRINSICS */
-
-/* Definitions for PowerPC intrinsic instructions
- Copyright (C) 2002, 2003, 2004 Free Software Foundation, Inc.
-
-This file is part of GCC.
-
-GCC is free software; you can redistribute it and/or modify it under
-the terms of the GNU General Public License as published by the Free
-Software Foundation; either version 2, or (at your option) any later
-version.
-
-GCC is distributed in the hope that it will be useful, but WITHOUT ANY
-WARRANTY; without even the implied warranty of MERCHANTABILITY or
-FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
-for more details.
-
-You should have received a copy of the GNU General Public License
-along with GCC; see the file COPYING. If not, write to the Free
-Software Foundation, 59 Temple Place - Suite 330, Boston, MA
-02111-1307, USA. */
-
-/* As a special exception, if you include this header file into source
- files compiled by GCC, this header file does not by itself cause
- the resulting executable to be covered by the GNU General Public
- License. This exception does not however invalidate any other
- reasons why the executable file might be covered by the GNU General
- Public License. */
-
-/*
- * The following PowerPC intrinsics are provided by this header:
- *
- * Low-Level Processor Synchronization
- * __eieio - Enforce In-Order Execution of I/O
- * __isync - Instruction Synchronize
- * __sync - Synchronize
- * __lwsync - Lightweight Synchronize
- *
- * Manipulating the Contents of a Variable or Register
- * __cntlzw - Count Leading Zeros Word
- * __cntlzd - Count Leading Zeros Double Word
- * __rlwimi - Rotate Left Word Immediate then Mask Insert
- * __rlwinm - Rotate Left Word Immediate then AND with Mask
- * __rlwnm - Rotate Left Word then AND with Mask
- *
- * Byte-Reversing Functions
- * __lhbrx - Load Half Word Byte-Reverse Indexed
- * __lwbrx - Load Word Byte-Reverse Indexed
- * __sthbrx - Store Half Word Byte-Reverse Indexed
- * __stwbrx - Store Word Byte-Reverse Indexed
- *
- * Data Cache Manipulation
- * __dcba - Data Cache Block Allocate
- * __dcbf - Data Cache Block Flush
- * __dcbst - Data Cache Block Store
- * __dcbt - Data Cache Block Touch
- * __dcbtst - Data Cache Block Touch for Store
- * __dcbzl - Data Cache Block Set to Zero
- * __dcbz - Data Cache Block Set to Zero (32-bytes only)
- *
- * Setting the Floating-Point Environment
- * __setflm - Set Floating-point Mode
- *
- * Math Functions
- * __fabs - Floating-Point Absolute Value
- * __fnabs - Floating Negative Absolute Value
- * __fctiw - Floating Convert to Integer Word
- * __fctiwz - Floating Convert to Integer Word with Round toward Zero
- * __fctidz - Floating Convert to Integer Doubleword with Round toward Zero
- * __fctid - Floating Convert to Integer Doubleword
- * __fcfid - Floating Convert From Integer Doubleword
- * __fmadd - Floating Multiply-Add (Double-Precision)
- * __fmadds - Floating Multiply-Add Single
- * __fmsub - Floating Multiply-Subract (Double-Precision)
- * __fmsubs - Floating Multiply-Subract Single
- * __fmul - Floating Multiply (Double-Precision)
- * __fmuls - Floating Multiply Single
- * __fnmadd - Floating Negative Multiply-Add (Double-Precision)
- * __fnmadds - Floating Negative Multiply-Add Single
- * __fnmsub - Floating Negative Multiply-Subtract (Double-Precision)
- * __fnmsubs - Floating Negative Multiply-Subtract Single
- * __fres - Floating Reciprocal Estimate
- * __frsp - Floating Round to Single-Precision
- * __frsqrte - Floating Reciprocal Square Root Estimate
- * __frsqrtes - Floating Reciprocal Square Root Estimate Single
- * __fsel - Floating Select
- * __fsels - Floating Select (Single-Precision variant)
- * __fsqrt - Floating-Point Square Root (Double-Precision)
- * __fsqrts - Floating-Point Square Root Single-Precision
- * __mulhw - Multiply High Word
- * __mulhwu - Multiply High Word Unsigned
- * __stfiwx - Store Floating-Point as Integer Word Indexed
- *
- * Miscellaneous Functions
- * __nop - PPC preferred form of no operation
- * __astrcmp - assembly strcmp
- * __icbi - Instruction Cache Block Invalidate
- * __mffs - Move from FPSCR
- * __mfspr - Move from Special Purpose Register
- * __mtfsf - Move to SPSCR Fields
- * __mtspr - Move to Special Purpose Register
- * __OSReadSwapSInt16 - lhbrx for signed shorts
- * __OSReadSwapUInt16 - lhbrx for unsigned shorts
- *
- * TO DO:
- * - Desired:
- * mullw
- * - Available in CodeWarrior, not yet implemented here:
- * abs, labs, fabsf, fnabsf
- *
- * NOTES:
- * - Some of the intrinsics need to be macros because certain
- * parameters MUST be integer constants and not values in registers.
- * - The declarations use __asm__ instead of asm and __inline__ instead
- * of inline to prevent errors when -ansi is specified.
- * - Some of the intrinsic definitions use the "volatile" specifier on
- * the "asm" statements in order to work around what appears to be
- * a bug in the compiler/optimizer. In general we have avoided the
- * use of "volatile" because it suppresses optimization on the
- * generated instructions. The instructions to which "volatile"
- * has been added where it appears that it should not be needed are
- * lhbrx and lwbrx.
- *
- * Contributors: Fred Forsman (editor), Turly O'Connor, Ian Ollmann, Sanjay Patel
- * Last modified: October 6, 2004
- */
-
-#ifndef _PPC_INTRINSICS_H_
-#define _PPC_INTRINSICS_H_
-
-#if (defined(__ppc__) || defined(__ppc64__)) && ! defined(__MWERKS__)
-
-/*******************************************************************
- * Special Purpose Registers (SPRs) *
- *******************************************************************/
-
-#define __SPR_MQR 0 /* PPC 601 only */
-#define __SPR_XER 1
-#define __SPR_RTCU 4 /* Real time clock upper. PPC 601 only.*/
-#define __SPR_RTCL 5 /* Real time clock lower. PPC 601 only.*/
-#define __SPR_LR 8
-#define __SPR_CTR 9
-#define __SPR_VRSAVE 256 /* AltiVec */
-#define __SPR_TBL 268 /* Time-base Lower. Not on PPC 601 */
-#define __SPR_TBU 269 /* Time-base Upper. Not on PPC 601 */
-#define __SPR_UMMCR2 928 /* PPC 74xx */
-#define __SPR_UPMC5 929 /* PPC 745x */
-#define __SPR_UPMC6 930 /* PPC 745x */
-#define __SPR_UBAMR 935 /* PPC 7400 and 7410 */
-#define __SPR_UMMCR0 936 /* PPC 74xx and 750 */
-#define __SPR_UPMC1 937 /* PPC 74xx and 750 */
-#define __SPR_UPMC2 938 /* PPC 74xx and 750 */
-#define __SPR_USIAR 939 /* PPC 74xx and 750 */
-#define __SPR_UMMCR1 940 /* PPC 74xx and 750 */
-#define __SPR_UPMC3 941 /* PPC 74xx and 750 */
-#define __SPR_UPMC4 942 /* PPC 74xx and 750 */
-#define __SPR_PIR 1023 /* supervisor level only! */
-
-/*
- * Shorthand macros for some commonly used SPR's.
- */
-#define __mfxer() __mfspr(__SPR_XER)
-#define __mflr() __mfspr(__SPR_LR)
-#define __mfctr() __mfspr(__SPR_CTR)
-#define __mfvrsave() __mfspr(__SPR_VRSAVE)
-#define __mftb() __mfspr(__SPR_TBL)
-#define __mftbu() __mfspr(__SPR_TBU)
-
-#define __mtlr(value) __mtspr(__SPR_LR, value)
-#define __mtxer(value) __mtspr(__SPR_XER, value)
-#define __mtctr(value) __mtspr(__SPR_CTR, value)
-#define __mtvrsave(value) __mtspr(__SPR_VRSAVE, value)
-
-
-/*******************************************************************
- * Low-Level Processor Synchronization *
- *******************************************************************/
-
-/*
- * __eieio - Enforce In-Order Execution of I/O
- *
- * void __eieio (void);
- */
-#define __eieio() __asm__ ("eieio" : : : "memory")
-
-/*
- * __isync - Instruction Synchronize
- *
- * void __isync (void);
- */
-#define __isync() \
- __asm__ volatile ("isync")
-
-/*
- * __sync - Synchronize
- *
- * void __sync (void);
- */
-#define __sync() __asm__ volatile ("sync")
-
-/*
- * __lwsync - Lightweight Synchronize, see PPC2.01, Book 2
- *
- * void __lwsync (void);
- */
-#define __lwsync() __asm__ volatile ("sync 1")
-
-
-/*******************************************************************
- * Byte-Reversing Functions *
- *******************************************************************/
-
-/*
- * __lhbrx - Load Half Word Byte-Reverse Indexed
- *
- * int __lhbrx(void *, int);
- */
-#define __lhbrx(base, index) \
- ({ unsigned short __ppc_i_lhbrxResult; \
- __asm__ volatile ("lhbrx %0, %1, %2" : "=r" (__ppc_i_lhbrxResult) : "b%" (index), "r" (base) : "memory"); \
- /*return*/ __ppc_i_lhbrxResult; })
-
-/*
- * __lwbrx - Load Word Byte-Reverse Indexed
- *
- * int __lwbrx(void *, int);
- */
-#define __lwbrx(base, index) \
- ({ unsigned int __ppc_i_lwbrxResult; \
- __asm__ volatile ("lwbrx %0, %1, %2" : "=r" (__ppc_i_lwbrxResult) : "b%" (index), "r" (base) : "memory"); \
- /*return*/ __ppc_i_lwbrxResult; })
-
-/*
- * __sthbrx - Store Half Word Byte-Reverse Indexed
- *
- * int __sthbrx(unsigned short, void *, int);
- */
-#define __sthbrx(value, base, index) \
- __asm__ ("sthbrx %0, %1, %2" : : "r" (value), "b%" (index), "r" (base) : "memory")
-
-/*
- * __stwbrx - Store Word Byte-Reverse Indexed
- *
- * int __sthbrx(unsigned int, void *, int);
- */
-#define __stwbrx(value, base, index) \
- __asm__ ("stwbrx %0, %1, %2" : : "r" (value), "b%" (index), "r" (base) : "memory")
-
-
-/*******************************************************************
- * Manipulating the Contents of a Variable or Register *
- *******************************************************************/
-
-/*
- * __cntlzw - Count Leading Zeros Word
- * __cntlzd - Count Leading Zeros Double Word
- */
-
-#define __cntlzw(a) __builtin_clz(a)
-#define __cntlzd(a) __builtin_clzll(a)
-
-/*
- * __rlwimi - Rotate Left Word Immediate then Mask Insert
- *
- * int __rlwimi(int, long, int, int, int);
- *
- * We don't mention "%1" below: operand[1] needs to be skipped as
- * it's just a placeholder to let the compiler know that rA is read
- * from as well as written to.
- */
-#define __rlwimi(rA, rS, cnt, mb, me) \
- ({ __asm__ ("rlwimi %0,%2,%3,%4,%5" : "=r" (rA) \
- : "0" (rA), "r" (rS), "n" (cnt), "n" (mb), "n" (me)); \
- /*return*/ rA;})
-
-/*
- * __rlwinm - Rotate Left Word Immediate then AND with Mask
- *
- * int __rlwinm(long, int, int, int);
- */
-#define __rlwinm(rS, cnt, mb, me) \
- ({ unsigned int __ppc_i_val; \
- __asm__ ("rlwinm %0,%1,%2,%3,%4" : "=r" (__ppc_i_val) \
- : "r" (rS), "n" (cnt), "n" (mb), "n" (me)); \
- /*return*/ __ppc_i_val;})
-
-/*
- * __rlwnm - Rotate Left Word then AND with Mask
- *
- * int __rlwnm(long, int, int, int);
- */
-#define __rlwnm(value, leftRotateBits, maskStart, maskEnd) \
- ({ unsigned int __ppc_i_result; \
- __asm__ ("rlwnm %0, %1, %2, %3, %4" : "=r" (__ppc_i_result) : \
- "r" (value), "r" (leftRotateBits), "n" (maskStart), "n" (maskEnd)); \
- /*return */ __ppc_i_result; })
-
-
-/*******************************************************************
- * Data Cache Manipulation *
- *******************************************************************/
-
-/*
- * --- Data Cache Block instructions ---
- *
- * Please see Motorola's "The Programming Environments for 32-Bit
- * Microprocessors" for a description of what these do.
- *
- * Parameter descriptions:
- *
- * base starting address for figuring out where the
- * cacheline is
- *
- * index byte count to be added to the base address for
- * purposes of calculating the effective address
- * of the cacheline to be operated on.
- *
- * Effective Address of cacheline to be manipulated =
- * (char*) base + index
- *
- * WARNING: The size and alignment of cachelines are subject to
- * change on future processors! Cachelines are 32 bytes in
- * size and are aligned to 32 bytes on PowerPC 601, 603, 604,
- * 750, 7400, 7410, 7450, and 7455.
- *
- */
-
-/*
- * __dcba - Data Cache Block Allocate
- *
- * void __dcba(void *, int)
- *
- * WARNING: dcba is a valid instruction only on PowerPC 7400, 7410,
- * 7450 and 7455.
- */
-#define __dcba(base, index) \
- __asm__ ("dcba %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-/*
- * __dcbf - Data Cache Block Flush
- *
- * void __dcbf(void *, int);
- */
-#define __dcbf(base, index) \
- __asm__ ("dcbf %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-/*
- * __dcbst - Data Cache Block Store
- *
- * void __dcbst(void *, int);
- */
-#define __dcbst(base, index) \
- __asm__ ("dcbst %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-/*
- * __dcbt - Data Cache Block Touch
- *
- * void __dcbt(void *, int);
- */
-#define __dcbt(base, index) \
- __asm__ ("dcbt %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-/*
- * __dcbtst - Data Cache Block Touch for Store
- *
- * void __dcbtst(void *, int);
- */
-#define __dcbtst(base, index) \
- __asm__ ("dcbtst %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-/*
- * __dcbzl - Data Cache Block Set to Zero
- *
- * void __dcbzl(void *, int);
- */
-#define __dcbzl(base, index) \
- __asm__ ("dcbzl %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-/*
- * __dcbz - Data Cache Block Set to Zero (32-bytes only)
- *
- * WARNING: this is for legacy purposes only
- *
- * void __dcbz(void *, int);
- */
-#define __dcbz(base, index) \
- __asm__ ("dcbz %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-
-/*******************************************************************
- * Setting the Floating-Point Environment *
- *******************************************************************/
-
-/*
- * __setflm - Set Floating-point Mode
- *
- * Sets the FPSCR (floating-point status and control register),
- * returning the original value.
- *
- * ??? CW: float __setflm(float);
- */
-static inline double __setflm (double newflm) __attribute__((always_inline));
-static inline double
-__setflm(double newflm)
-{
- double original;
-
- __asm__ ("mffs %0"
- /* outputs: */ : "=f" (original));
- __asm__ ("mtfsf 255,%0"
- /* outputs: */ : /* none */
- /* inputs: */ : "f" (newflm));
- return original;
-}
-
-
-/*******************************************************************
- * Math Functions *
- *******************************************************************/
-
-/*
- * __fabs - Floating-Point Absolute Value
- */
-static inline double __fabs (double value) __attribute__((always_inline));
-static inline double
-__fabs (double value)
-{
- double result;
- __asm__ ("fabs %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (value));
- return result;
-}
-
-/*
- * __fnabs - Floating Negative Absolute Value
- */
-static inline double __fnabs (double b) __attribute__((always_inline));
-static inline double
-__fnabs (double b)
-{
- double result;
- __asm__ ("fnabs %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (b));
- return result;
-}
-
-/*
- * fctiw - Floating Convert to Integer Word
- *
- * Convert the input value to a signed long and place in the low 32
- * bits of the FP register. Clip to LONG_MIN or LONG_MAX if the FP
- * value exceeds the range representable by a long. Use the rounding
- * mode indicated in the FPSCR.
- */
-static inline double __fctiw (double b) __attribute__((always_inline));
-static inline double
-__fctiw (double b)
-{
- double result;
- __asm__ ("fctiw %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (b));
- return result;
-}
-
-/*
- * fctiwz - Floating Convert to Integer Word with Round toward Zero
- *
- * Convert the input value to a signed long and place in the low 32
- * bits of the FP register. Clip to LONG_MIN or LONG_MAX if the FP
- * value exceeds the range representable by a long.
- */
-static inline double __fctiwz (double b) __attribute__((always_inline));
-static inline double
-__fctiwz (double b)
-{
- double result;
- __asm__ ("fctiwz %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (b));
- return result;
-}
-
-/*
- * fctidz - Floating Convert to Integer Double Word with Round toward Zero
- *
- * Convert the input value to a signed 64-bit int and place in the FP
- * destination register. Clip to LLONG_MIN (-2**63) or LLONG_MAX (2**63-1)
- * if the FP value exceeds the range representable by a int64_t.
- *
- * WARNING: fctidz is a valid instruction only on 64-bit PowerPC
- */
-static inline double __fctidz (double b) __attribute__((always_inline));
-static inline double
-__fctidz (double b)
-{
- double result;
- __asm__ ("fctidz %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (b));
- return result;
-}
-
-/*
- * fctid - Floating Convert to Integer Double Word
- *
- * Convert the input value to a signed 64-bit int and place in the FP
- * destination register. Clip to LLONG_MIN (-2**63) or LLONG_MAX (2**63-1)
- * if the FP value exceeds the range representable by a int64_t. Use the
- * rounding mode indicated in the FPSCR.
- *
- * WARNING: fctid is a valid instruction only on 64-bit PowerPC
- */
-static inline double __fctid (double b) __attribute__((always_inline));
-static inline double
-__fctid (double b)
-{
- double result;
- __asm__ ("fctid %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (b));
- return result;
-}
-
-/*
- * fcfid - Floating Convert From Integer Double Word
- *
- * Convert the 64-bit signed integer input value to a 64-bit FP value.
- * Use the rounding mode indicated in the FPSCR if the integer is out of
- * double precision range.
- *
- * WARNING: fcfid is a valid instruction only on 64-bit PowerPC
- */
-static inline double __fcfid (double b) __attribute__((always_inline));
-static inline double
-__fcfid (double b)
-{
- double result;
- __asm__ ("fcfid %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (b));
- return result;
-}
-
-/*
- * fmadd - Floating Multiply-Add (Double-Precision)
- *
- * (a * c + b) double precision
- */
-static inline double __fmadd (double a, double c, double b) __attribute__((always_inline));
-static inline double
-__fmadd (double a, double c, double b)
-{
- double result;
- __asm__ ("fmadd %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * fmadds - Floating Multiply-Add Single
- *
- * (a * c + b) single precision
- *
- * Double precision arguments are used to prevent the compiler from
- * issuing frsp instructions upstream.
- */
-static inline float __fmadds (double a, double c, double b) __attribute__((always_inline));
-static inline float
-__fmadds (double a, double c, double b)
-{
- float result;
- __asm__ ("fmadds %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * fmsub - Floating Multiply-Subract (Double-Precision)
- *
- * (a * c - b) double precision
- */
-static inline double __fmsub (double a, double c, double b) __attribute__((always_inline));
-static inline double
-__fmsub (double a, double c, double b)
-{
- double result;
- __asm__ ("fmsub %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * fmsubs - Floating Multiply-Subract Single
- *
- * (a * c - b) single precision
- *
- * Double precision arguments are used to prevent the compiler from
- * issuing frsp instructions upstream.
- */
-static inline float __fmsubs (double a, double c, double b) __attribute__((always_inline));
-static inline float
-__fmsubs (double a, double c, double b)
-{
- float result;
- __asm__ ("fmsubs %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * fmul - Floating Multiply (Double-Precision)
- *
- * (a * c) double precision
- */
-static inline double __fmul (double a, double c) __attribute__((always_inline));
-static inline double
-__fmul (double a, double c)
-{
- double result;
- __asm__ ("fmul %0, %1, %2"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c));
- return result;
-}
-
-/*
- * fmuls - Floating Multiply Single
- *
- * (a * c) single precision
- *
- * Double precision arguments are used to prevent the compiler from
- * issuing frsp instructions upstream.
- */
-static inline float __fmuls (double a, double c) __attribute__((always_inline));
-static inline float
-__fmuls (double a, double c)
-{
- float result;
- __asm__ ("fmuls %0, %1, %2"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c));
- return result;
-}
-
-/*
- * __fnmadd - Floating Negative Multiply-Add (Double-Precision)
- *
- * -(a * c + b) double precision
- */
-static inline double __fnmadd (double a, double c, double b) __attribute__((always_inline));
-static inline double
-__fnmadd (double a, double c, double b)
-{
- double result;
- __asm__ ("fnmadd %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * __fnmadds - Floating Negative Multiply-Add Single
- *
- * -(a * c + b) single precision
- *
- * Double precision arguments are used to prevent the compiler from
- * issuing frsp instructions upstream.
- */
-static inline float __fnmadds (double a, double c, double b) __attribute__((always_inline));
-static inline float
-__fnmadds (double a, double c, double b)
-{
- float result;
- __asm__ ("fnmadds %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * __fnmsub - Floating Negative Multiply-Subtract (Double-Precision)
- *
- * -(a * c - B) double precision
- */
-static inline double __fnmsub (double a, double c, double b) __attribute__((always_inline));
-static inline double
-__fnmsub (double a, double c, double b)
-{
- double result;
- __asm__ ("fnmsub %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * __fnmsubs - Floating Negative Multiply-Subtract Single
- *
- * -(a * c - b) single precision
- *
- * Double precision arguments are used to prevent the compiler from
- * issuing frsp instructions upstream.
- */
-static inline float __fnmsubs (double a, double c, double b) __attribute__((always_inline));
-static inline float
-__fnmsubs (double a, double c, double b)
-{
- float result;
- __asm__ ("fnmsubs %0, %1, %2, %3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (a), "f" (c), "f" (b));
- return result;
-}
-
-/*
- * __fres - Floating Reciprocal Estimate
- *
- * Produces a double precision result with 5 bits of accuracy.
- * Note: not valid on the PowerPC 601.
- *
- * ??? CW: float __fres(float)
- */
-static inline float __fres (float val) __attribute__((always_inline));
-static inline float
-__fres (float val)
-{
- float estimate;
- __asm__ ("fres %0,%1"
- /* outputs: */ : "=f" (estimate)
- /* inputs: */ : "f" (val));
- return estimate;
-}
-
-/*
- * __frsp - Floating Round to Single-Precision
- */
-static inline float __frsp (double d) __attribute__((always_inline));
-static inline float
-__frsp (double d)
-{
- float result;
- __asm__ ("frsp %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (d));
- return result;
-}
-
-/*
- * __frsqrte - Floating Reciprocal Square Root Estimate
- *
- * Note: not valid on the PowerPC 601.
- */
-static inline double __frsqrte (double val) __attribute__((always_inline));
-static inline double
-__frsqrte (double val)
-{
- double estimate;
-
- __asm__ ("frsqrte %0,%1"
- /* outputs: */ : "=f" (estimate)
- /* inputs: */ : "f" (val));
- return estimate;
-}
-
-/*
- * __frsqrtes - Floating Reciprocal Square Root Estimate Single
- */
-static inline float __frsqrtes (double f) __attribute__((always_inline));
-static inline float
-__frsqrtes (double f)
-{
- float result;
- __asm__ ("frsqrte %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (f));
- return result;
-}
-
-/*
- * __fsel - Floating Select
- *
- * if (test >= 0) return a; else return b;
- *
- * Note: not valid on the PowerPC 601.
- */
-static inline double __fsel (double test, double a, double b) __attribute__((always_inline));
-static inline double
-__fsel (double test, double a, double b)
-{
- double result;
- __asm__ ("fsel %0,%1,%2,%3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (test), "f" (a), "f" (b));
- return result;
-}
-
-/*
- * __fsels - Floating Select (Single-Precision variant)
- *
- * An artificial single precision variant of fsel. This produces the
- * same results as fsel, but is useful because the result is cast as
- * a float, discouraging the compiler from issuing a frsp instruction
- * afterward.
- */
-static inline float __fsels (double test, double a, double b) __attribute__((always_inline));
-static inline float
-__fsels (double test, double a, double b)
-{
- float result;
- __asm__ ("fsel %0,%1,%2,%3"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (test), "f" (a), "f" (b));
- return result;
-}
-
-/*
- * __fsqrt - Floating-Point Square Root (Double-Precision)
- *
- * WARNING: Illegal instruction for PowerPC 603, 604, 750, 7400, 7410,
- * 7450, and 7455
- */
-static inline double __fsqrt (double b) __attribute__((always_inline));
-static inline double
-__fsqrt(double d)
-{
- double result;
- __asm__ ("fsqrt %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (d));
- return result;
-}
-
-/*
- * __fsqrts - Floating-Point Square Root Single-Precision
- *
- * WARNING: Illegal instruction for PowerPC 603, 604, 750, 7400, 7410,
- * 7450, and 7455
- */
-static inline float __fsqrts (float f) __attribute__((always_inline));
-static inline float
-__fsqrts (float f)
-{
- float result;
- __asm__ ("fsqrts %0, %1"
- /* outputs: */ : "=f" (result)
- /* inputs: */ : "f" (f));
- return result;
-}
-
-/*
- * __mulhw - Multiply High Word
- */
-static inline int __mulhw (int a, int b) __attribute__((always_inline));
-static inline int
-__mulhw (int a, int b)
-{
- int result;
- __asm__ ("mulhw %0, %1, %2"
- /* outputs: */ : "=r" (result)
- /* inputs: */ : "r" (a), "r"(b));
- return result;
-}
-
-/*
- * __mulhwu - Multiply High Word Unsigned
- */
-static inline unsigned int __mulhwu (unsigned int a, unsigned int b) __attribute__((always_inline));
-static inline unsigned int
-__mulhwu (unsigned int a, unsigned int b)
-{
- unsigned int result;
- __asm__ ("mulhwu %0, %1, %2"
- /* outputs: */ : "=r" (result)
- /* inputs: */ : "r" (a), "r"(b));
- return result;
-}
-
-/*
- * __stfiwx - Store Floating-Point as Integer Word Indexed
- *
- * void x(int, void *, int);
- */
-#define __stfiwx(value, base, index) \
- __asm__ ("stfiwx %0, %1, %2" : /*no result*/ \
- : "f" (value), "b%" (index), "r" (base) : "memory")
-
-
-/*******************************************************************
- * Miscellaneous Functions *
- *******************************************************************/
-
-/*
- * __nop - no operation (PowerPC preferred form)
- *
- * void __nop();
- */
-#define __nop() \
- __asm__ ("ori 0,0,0")
-
-/*
- * __icbi - Instruction Cache Block Invalidate
- *
- * void __icbi(void *, int);
- */
-#define __icbi(base, index) \
- __asm__ ("icbi %0, %1" : /*no result*/ : "b%" (index), "r" (base) : "memory")
-
-/*
- * __mffs - Move from FPSCR
- */
-static inline double __mffs (void) __attribute__((always_inline));
-static inline double
-__mffs (void)
-{
- double result;
- __asm__ volatile ("mffs %0"
- /* outputs: */ : "=f" (result));
- return result;
-}
-
-/*
- * __mfspr - Move from Special Purpose Register
- *
- * int __mfspr(int);
- */
-#define __mfspr(spr) \
- __extension__ ({ long __ppc_i_mfsprResult; \
- __asm__ volatile ("mfspr %0, %1" : "=r" (__ppc_i_mfsprResult) : "n" (spr)); \
- /*return*/ __ppc_i_mfsprResult; })
-
-/*
- * __mtfsf - Move to SPSCR Fields
- *
- * void __mtfsf(int, int);
- */
-#define __mtfsf(mask, newValue) \
- __asm__ volatile ("mtfsf %0, %1" : : "n" (mask), "f" (newValue))
-
-/*
- * __mtspr - Move to Special Purpose Register
- *
- * __mtspr x(int, int);
- */
-#define __mtspr(spr, value) \
- __asm__ volatile ("mtspr %0, %1" : : "n" (spr), "r" (value))
-
-/*
- * __OSReadSwapSInt16
- *
- * lhbrx for signed shorts. This will do the required sign
- * extension after load and byteswap.
- */
-static inline signed short __OSReadSwapSInt16 (signed short *base, int index) __attribute__((always_inline));
-static inline signed short
-__OSReadSwapSInt16 (signed short *base, int index)
-{
- signed long result;
- __asm__ volatile ("lhbrx %0, %1, %2"
- /* outputs: */ : "=r" (result)
- /* inputs: */ : "b%" (index), "r" (base)
- /* clobbers: */ : "memory");
- return result;
-}
-
-/*
- * __OSReadSwapUInt16
- */
-static inline unsigned short __OSReadSwapUInt16 (volatile void *base, int inex) __attribute__((always_inline));
-static inline unsigned short
-__OSReadSwapUInt16 (volatile void *base, int index)
-{
- unsigned long result;
- __asm__ volatile ("lhbrx %0, %1, %2"
- /* outputs: */ : "=r" (result)
- /* inputs: */ : "b" (index), "r" (base)
- /* clobbers: */ : "memory");
- return result;
-}
-
-/*
- * __astrcmp - assembly strcmp
- */
-static inline int astrcmp (const char *in_s1, const char *in_s2) __attribute__((always_inline));
-static inline int
-astrcmp (const char *in_s1, const char *in_s2)
-{
- int result, temp;
- register const char *s1 = in_s1 - 1;
- register const char *s2 = in_s2 - 1;
-
- __asm__ ("1:lbzu %0,1(%1)\n"
- "\tcmpwi cr1,%0,0\n"
- "\tlbzu %3,1(%2)\n"
- "\tsubf. %0,%3,%0\n"
- "\tbeq- cr1,2f\n"
- "\tbeq+ 1b\n2:"
- /* outputs: */ : "=&r" (result), "+b" (s1), "+b" (s2), "=r" (temp)
- /* inputs: */ :
- /* clobbers: */ : "cr0", "cr1", "memory");
-
- return result;
-
- /*
- * "=&r" (result) means: 'result' is written on (the '='), it's any GP
- * register (the 'r'), and it must not be the same as
- * any of the input registers (the '&').
- * "+b" (s1) means: 's1' is read from and written to (the '+'),
- * and it must be a base GP register (i.e., not R0.)
- * "=r" (temp) means: 'temp' is any GP reg and it's only written to.
- *
- * "memory" in the 'clobbers' section means that gcc will make
- * sure that anything that should be in memory IS there
- * before calling this routine.
- */
-}
-
-#endif /* (defined(__ppc__) || defined(__ppc64__)) && ! defined(__MWERKS__) */
-
-#endif /* _PPC_INTRINSICS_H_ */