In perl.git, the branch blead has been updated

<http://perl5.git.perl.org/perl.git/commitdiff/5124ce1ebfdf638521d2a0e17ddc9f6c56faa4ff?hp=ee30e416ad055ff6c8dae1391480d560139666ca>

- Log -----------------------------------------------------------------
commit 5124ce1ebfdf638521d2a0e17ddc9f6c56faa4ff
Author: Jarkko Hietaniemi <[email protected]>
Date:   Mon Nov 3 21:32:19 2014 -0500

    S_hextract for mixed endian doubles.

M       sv.c

commit f8d924aed543b0e974ba0edec10a6d60b7ee7d81
Author: Jarkko Hietaniemi <[email protected]>
Date:   Mon Nov 3 21:17:40 2014 -0500

    Add scan for ARM mixed-endian doubles.
    
    (Working in theory... no hardware.)

M       Configure
M       Porting/Glossary
M       config_h.SH

commit 17059a03f667b30230374a63a775d805949955fe
Author: Jarkko Hietaniemi <[email protected]>
Date:   Mon Nov 3 21:08:48 2014 -0500

    8e581bbf covered up this bug.

M       Configure
-----------------------------------------------------------------------

Summary of changes:
 Configure        | 22 ++++++++++++++++++----
 Porting/Glossary |  2 ++
 config_h.SH      |  4 ++++
 sv.c             | 26 ++++++++++++++++++++++++--
 4 files changed, 48 insertions(+), 6 deletions(-)

diff --git a/Configure b/Configure
index 9494ab1..9bd6f18 100755
--- a/Configure
+++ b/Configure
@@ -6813,24 +6813,38 @@ int main() {
   }
 #endif
 #if DOUBLESIZE == 8
-  if (b[0] == 0x9A && b[7] == 0xBD) {
+  if (b[0] == 0x9A && b[7] == 0xBF) {
     /* IEEE 754 64-bit little-endian */
     printf("3\n");
     exit(0);
   }
-  if (b[0] == 0x9A && b[7] == 0xCD) {
+  if (b[0] == 0xBF && b[7] == 0x9A) {
     /* IEEE 754 64-bit big-endian */
     printf("4\n");
     exit(0);
   }
+  if (b[0] == 0x99 && b[3] == 0xBF && b[4] == 0x9A && b[7] == 0x99) {
+   /* ARM mixed endian: two little-endian 32-bit floats, in big endian order:
+    * 4 5 6 7 0 1 2 3 (MSB = 7, LSB = 0)
+    * 99 99 b9 bf 9a 99 99 99 */
+    printf("7\n");
+    exit(0);
+  }
+  if (b[0] == 0x99 && b[3] == 0x9A && b[4] == 0xBF && b[7] == 0x99) {
+   /* The opposite of case 7, mixed endian: two big-endian 32-bit floats,
+    * in little endian order: 3 2 1 0 7 6 5 4 (MSB = 7, LSB = 0)
+    * 99 99 99 9a bf b9 99 99 */
+    printf("8\n");
+    exit(0);
+  }
 #endif
 #if DOUBLESIZE == 16
-  if (b[0] == 0x9A && b[15] == 0xBD) {
+  if (b[0] == 0x9A && b[15] == 0xBF) {
     /* IEEE 754 128-bit little-endian */
     printf("5\n");
     exit(0);
   }
-  if (b[0] == 0x9A && b[15] == 0xCD) {
+  if (b[0] == 0xBF && b[15] == 0x9A) {
     /* IEEE 754 128-bit big-endian */
     printf("6\n");
     exit(0);
diff --git a/Porting/Glossary b/Porting/Glossary
index 1a9d770..f0970a2 100644
--- a/Porting/Glossary
+++ b/Porting/Glossary
@@ -2647,6 +2647,8 @@ doublekind (doublekind.U):
        4 = IEEE 754 64-bit big big endian,
        5 = IEEE 754 128-bit big little endian,
        6 = IEEE 754 128-bit big big endian,
+       7 = IEEE 754 64-bit big mixed endian le-be,
+       8 = IEEE 754 64-bit big mixed endian be-le,
        -1 = unknown format.
 
 doublesize (doublesize.U):
diff --git a/config_h.SH b/config_h.SH
index 3e6e5d2..c3b5642 100755
--- a/config_h.SH
+++ b/config_h.SH
@@ -2712,6 +2712,8 @@ sed <<!GROK!THIS! >$CONFIG_H -e 
's!^#undef\(.*/\)\*!/\*#define\1 \*!' -e 's!^#un
  *     DOUBLE_IS_IEEE_754_64_BIT_BIG_ENDIAN
  *     DOUBLE_IS_IEEE_754_128_BIT_LITTLE_ENDIAN
  *     DOUBLE_IS_IEEE_754_128_BIT_BIG_ENDIAN
+ *     DOUBLE_IS_IEEE_754_64_BIT_MIXED_ENDIAN_LE_BE
+ *     DOUBLE_IS_IEEE_754_64_BIT_MIXED_ENDIAN_BE_LE
  *     DOUBLE_IS_UNKNOWN_FORMAT
  */
 #define DOUBLEKIND $doublekind         /**/
@@ -2721,6 +2723,8 @@ sed <<!GROK!THIS! >$CONFIG_H -e 
's!^#undef\(.*/\)\*!/\*#define\1 \*!' -e 's!^#un
 #define DOUBLE_IS_IEEE_754_64_BIT_BIG_ENDIAN   4
 #define DOUBLE_IS_IEEE_754_128_BIT_LITTLE_ENDIAN       5
 #define DOUBLE_IS_IEEE_754_128_BIT_BIG_ENDIAN  6
+#define DOUBLE_IS_IEEE_754_64_BIT_MIXED_ENDIAN_LE_BE   7
+#define DOUBLE_IS_IEEE_754_64_BIT_MIXED_ENDIAN_BE_LE   8
 #define DOUBLE_IS_UNKNOWN_FORMAT               -1
 
 /* EBCDIC:
diff --git a/sv.c b/sv.c
index f398a93..27fc0da 100644
--- a/sv.c
+++ b/sv.c
@@ -10781,8 +10781,10 @@ Perl_sv_vcatpvfn(pTHX_ SV *const sv, const char *const 
pat, const STRLEN patlen,
  * Also: the S_hextract() doesn't handle 32-bit or 128-bit doubles. */
 #if defined(DOUBLE_LITTLE_ENDIAN) || defined(LONGDOUBLE_LITTLE_ENDIAN)
 #  define HEXTRACT_LITTLE_ENDIAN
-#else
+#elif defined(DOUBLE_BIG_ENDIAN) || defined(LONGDOUBLE_BIG_ENDIAN)
 #  define HEXTRACT_BIG_ENDIAN
+#else
+#  define HEXTRACT_MIX_ENDIAN
 #endif
 
 /* S_hextract() is a helper for Perl_sv_vcatpvfn_flags, for extracting
@@ -11006,11 +11008,31 @@ S_hextract(pTHX_ const NV nv, int* exponent, U8* 
vhex, U8* vend)
     for (ix = 5; ix >= 0; ix--) {
         HEXTRACT_BYTE(ix);
     }
-#  else
+#  elif defined(HEXTRACT_BIG_ENDIAN)
     HEXTRACT_LO_NYBBLE(1);
     for (ix = 2; ix < NVSIZE; ix++) {
         HEXTRACT_BYTE(ix);
     }
+#  else
+#    if DOUBLEKIND == DOUBLE_IS_IEEE_754_64_BIT_MIXED_ENDIAN_LE_BE
+     /* 4 5 6 7 0 1 2 3 (MSB = 7, LSB = 0, 6+7 = exponent + sign)
+        HEXTRACT_BYTE(2);
+        HEXTRACT_BYTE(1);
+        HEXTRACT_BYTE(7);
+        HEXTRACT_BYTE(6);
+        HEXTRACT_BYTE(5);
+        HEXTRACT_BYTE(4);
+#    elif DOUBLEKIND == DOUBLE_IS_IEEE_754_64_BIT_MIXED_ENDIAN_BE_LE
+     /* 3 2 1 0 7 6 5 4 (MSB = 7, LSB = 0, 0+1 = sign+exponent) */
+        HEXTRACT_BYTE(4);
+        HEXTRACT_BYTE(5);
+        HEXTRACT_BYTE(6);
+        HEXTRACT_BYTE(7);
+        HEXTRACT_BYTE(0);
+        HEXTRACT_BYTE(1);
+#    else
+#      error "Unknown DOUBLEKIND"
+#    endif
 #  endif
 #endif
     /* Croak for various reasons: if the output pointer escaped the

--
Perl5 Master Repository

Reply via email to