Performance tweaks
authorMichael Meissner <gnu@the-meissners.org>
Thu, 12 Oct 1995 21:49:37 +0000 (21:49 +0000)
committerMichael Meissner <gnu@the-meissners.org>
Thu, 12 Oct 1995 21:49:37 +0000 (21:49 +0000)
sim/ppc/ChangeLog
sim/ppc/ppc-endian.c
sim/ppc/ppc-endian.h

index 5e657ed6ad69d9603961748b98e6c313c4043aff..c4d314e16918102da1576e37255887df1db26267 100644 (file)
@@ -1,5 +1,20 @@
 Thu Oct 12 11:35:53 1995  Michael Meissner  <meissner@tiktok.cygnus.com>
 
+       * ppc-endian.c (SWAP_n): New macros to speed up byte swapping for
+       2, 4, and 8 bytes.
+       (ENDIAN_N): If both target and host byte orders are known, don't
+       bother testing CURRENT_{TARGET,HOST}_BYTE_ORDER.
+
+       * ppc-endian.h (target specific H2T_n/T2H_n macros): Remove #if 0
+       to allow target specific H2T_n/T2H_n macros to be used.
+       (htonl, ntohl): If compiled on a 486 by GCC and WITH_BSWAP is
+       non-zero, redefine the htonl/ntohl macros to use the BSWAP instead
+       of the 3 instruction sequence that runs on 386s.
+
+       * std-config.h (WITH_{HOST,TARGET}_BYTE_ORDER): Don't override if
+       specified on the compile line.
+       (WITH_BSWAP): If not defined, define as 0.
+
        * Makefile.in (INLINE_CFLAGS): Add -DDEFAULT_INLINE=2 to add
        default inline support.  Pass INLINE_CFLAGS when compiling.
 
index 734ea213e52e3894f7a2e8174c496ee6b66a3342..daa749c1395e5d4218ddf8b66eb15bc71c7a91ca 100644 (file)
@@ -41,6 +41,61 @@ typedef union {
   unsigned_8 val_8[1];
 } endian_map;
 
+#define SWAP_N(RAW,BYTE_SIZE) \
+    endian_map in; \
+    endian_map out; \
+    int byte_nr; \
+    in.val_##BYTE_SIZE[0] = RAW; \
+    for (byte_nr = 0; byte_nr < BYTE_SIZE; byte_nr++) { \
+      out.val_1[BYTE_SIZE-1-byte_nr] = in.val_1[byte_nr]; \
+    } \
+    return out.val_##BYTE_SIZE[0]; \
+
+#if (WITH_HOST_BYTE_ORDER == LITTLE_ENDIAN) && WITH_NTOH
+#define SWAP_2(RAW) return htons (RAW)
+#endif
+
+#ifndef        SWAP_2
+#define SWAP_2(RAW) return (((RAW) >> 8) | ((RAW) << 8))
+#endif
+
+#if !defined(SWAP_4) && (WITH_HOST_BYTE_ORDER == LITTLE_ENDIAN) && WITH_NTOH
+#define SWAP_4(RAW) return htonl (RAW)
+#endif
+
+#ifndef SWAP_4
+#define        SWAP_4(RAW) return (((RAW) << 24) | (((RAW) & 0xff00) << 8) | (((RAW) & 0xff0000) >> 8) | ((RAW) >> 24))
+#endif
+
+#ifndef SWAP_8
+#define        SWAP_8(RAW) SWAP_N(RAW,4)
+#endif
+
+/* no need to swap */
+#if (WITH_HOST_BYTE_ORDER \
+     && WITH_TARGET_BYTE_ORDER \
+     && WITH_HOST_BYTE_ORDER == WITH_TARGET_BYTE_ORDER )
+#define ENDIAN_N(NAME,BYTE_SIZE) \
+unsigned_##BYTE_SIZE \
+endian_##NAME##_##BYTE_SIZE(unsigned_##BYTE_SIZE raw_in) \
+{ \
+  return raw_in; \
+}
+#endif
+
+/* always need to swap */
+#if (WITH_HOST_BYTE_ORDER \
+     && WITH_TARGET_BYTE_ORDER \
+     && WITH_HOST_BYTE_ORDER != WITH_TARGET_BYTE_ORDER )
+#define ENDIAN_N(NAME,BYTE_SIZE) \
+unsigned_##BYTE_SIZE \
+endian_##NAME##_##BYTE_SIZE(unsigned_##BYTE_SIZE raw_in) \
+{ \
+  SWAP_##BYTE_SIZE(raw_in); \
+}
+#endif
+
+#ifndef ENDIAN_N
 #define ENDIAN_N(NAME,BYTE_SIZE) \
 unsigned_##BYTE_SIZE \
 endian_##NAME##_##BYTE_SIZE(unsigned_##BYTE_SIZE raw_in) \
@@ -49,17 +104,10 @@ endian_##NAME##_##BYTE_SIZE(unsigned_##BYTE_SIZE raw_in) \
     return raw_in; \
   } \
   else { \
-    endian_map in; \
-    endian_map out; \
-    int byte_nr; \
-    in.val_##BYTE_SIZE[0] = raw_in; \
-    for (byte_nr = 0; byte_nr < BYTE_SIZE; byte_nr++) { \
-      out.val_1[BYTE_SIZE-1-byte_nr] = in.val_1[byte_nr]; \
-    } \
-    return out.val_##BYTE_SIZE[0]; \
+    SWAP_##BYTE_SIZE(raw_in); \
   } \
 }
-
+#endif
 
 ENDIAN_N(h2t, 2)
 ENDIAN_N(h2t, 4)
index 496d36a5f89b9828784eb3c5e15c92aaf89387da..748d2efd8b6063730d3ebf74a9f2b9f2941be66f 100644 (file)
@@ -199,7 +199,6 @@ do { \
    Returns the value swapped according to the host/target byte order */
 
 /* no need to swap */
-#if 0
 #if (WITH_HOST_BYTE_ORDER \
      && WITH_TARGET_BYTE_ORDER \
      && WITH_HOST_BYTE_ORDER == WITH_TARGET_BYTE_ORDER )
@@ -227,6 +226,13 @@ do { \
 #define T2H_1(X) (X)
 #endif
 
+#if (defined (__i486__) || defined (__i586__)) && defined(__GNUC__) && WITH_BSWAP && WITH_NTOH
+#undef  htonl
+#undef  ntohl
+#define htonl(IN) __extension__ ({ int _out; __asm__ ("bswap %0" : "=r" (_out) : "0" (IN)); _out; })
+#define ntohl(IN) __extension__ ({ int _out; __asm__ ("bswap %0" : "=r" (_out) : "0" (IN)); _out; })
+#endif
+
 /* have ntoh, little host and unknown target */
 #if (WITH_HOST_BYTE_ORDER == LITTLE_ENDIAN \
      && WITH_TARGET_BYTE_ORDER == 0 \
@@ -240,7 +246,6 @@ do { \
 #define T2H_2(X) (CURRENT_TARGET_BYTE_ORDER == CURRENT_HOST_BYTE_ORDER ? (X) : htons(X))
 #define T2H_1(X) (CURRENT_TARGET_BYTE_ORDER == CURRENT_HOST_BYTE_ORDER ? (X) : (X))
 #endif
-#endif
 
 /* if all else fails use software */
 #ifndef H2T_1