The Museum of HP Calculators

HP Forum Archive 21

[ Return to Index | Top of Index ]

[wp34s] Converting to/from IEEE 754 Binary64 (Double Precision)
Message #1 Posted by David Maier on 15 June 2013, 7:14 p.m.

Here's a program to convert to/from IEEE 754 binary64 (double precision) format:

/* Program to convert to/from IEEE 754 binary64 (double precision) format
 * Remarks:
 *     - XEQ A converts DP real numbers to IEEE 754 binary64 (double precision) format
 *     - XEQ B converts IEEE 754 binary64 (double precision) format numbers to DP real
 *     - XEQ 'IED' converts to DP real if the calculator is in integer mode, converts to IEEE 754 binary64 otherwise
 *     - Denormalized numbers (|x|<2.2250738585072014e-308 ) are supported. "Denorm" is shown as a warning in the alpha display. 
 *       If |x|<5e-324, the number will be silently converted to 0.
 *     - +/- Infinity and NaN are supported. Since the WP-34S has "constants" for these values (see the Const catalog), large numbers
 *       are not considered to be infinite (see next note).
 *     - Numbers larger/smaller than +/- 1.7976931348623157e308 generate an Out of range error. 
 *     - Negative 0 is supported. Since the sign may not be visible, depending on the setting of the global D (Danger) flag, 
 *       "Neg 0" is shown in the alpha display
 *     - The calculator is set to integer sign-with-mantissa, word size 64 (sm64) mode and assumed to be in this mode when working with the
 *       IEEE 754 binary 64 format. Similarily, on the real side, the calculator is assumed to be in double precision mode.
 */
            ****LBL'IED' 
            WSIZE 64    // Operations are performed on sign-with-mantissa, word size 64 integers
            SIGNMT
            DBLON
            INTM?
            GTO B

**LBL A // Convert DP real to IEEE 754 binary64 format LocR 001 CL[alpha] x=0? JMP ZeroF SPEC? // Infinite or NaN JMP SpecF ENTER[^] ABS LOG[sub-2] // This is why we need to be in DP mode FLOOR # 10 2[^x] DEC X x<? Y // Punt if number is too large ERR 08 // Note: Numbers too large for the format are not quietly replaced by infinity +/- MAX STO .00 // Exponent in R.00: Denormalized: -1023; otherwise: -1022 to 1023 # 052 x[<->] Y - # 179 // Denormalized values are scaled by 2^1074 before rounding; otherwise, 2 ^ (52 - exponent) # 6 // 1022 + 52 = 1074 = 179 * 6 [times] MIN 2[^x] [times] ROUNDI RCL .00 BASE 16 // x: exponent; y: mantissa, including sign # 10 // Convert exponent 2[^x] DEC X + CF .00 // Flag .00 set for denormalized value x=0? SF .00 SL 52 x[<->] Y MASKR 52 // This removes the hidden bit, if any +/- // Include sign in the mask AND OR // Insert exponent into result FC? .00 // Warn if denormalized RTN "Denorm" VW[alpha]+ X RTN ZeroF:: CF .01 x=-0? // Flag .01 set for negative 0 SF .01 BASE 16 FS? .01 SB 63 RTN SpecF:: [infinity]? // Handle NaN here, infinity below JMP InfF BASE 16 MASKR 12 // Use 0x7FF8000000000000 for NaN SL 51 [alpha]'NaN' VW[alpha]+ X RTN InfF:: CF .01 // Flag .01 set for negative infinity x<0? SF .01 BASE 16 MASKR 11 SL 52 FS? .01 SB 63 RTN

**LBL B // Convert IEEE 754 binary64 format to DP real LocR 001 CL[alpha] x=0? JMP ZeroI ENTER[^] // Extract the exponent CB 63 SR 52 # 11 // Are we special? 2[^x] DEC X x=? Y JMP SpecI DROP CF .00 // Flag .00: denormalized x=0? SF .00 # 001 // Fix the minimum exponent MAX # 10 2[^x] DEC X - x[<->] Y MASKR 11 SL 52 NOT AND FC? .00 // Restore hidden bit if not denormalized SB 52 DECM x[<->] Y // Apply exponent # 052 x[<->] Y - 2[^x] / FC? .00 // Warn if denormalized RTN "Denorm" VW[alpha]+ X RTN ZeroI:: CF .01 // +/- 0; flag .01 is negative zero x=-0? SF .01 DECM FC? .01 RTN "Neg 0" // Warn if negative (not visible if D flag not set) 0 +/- VW[alpha]+ X RTN SpecI:: DROP // NaN or +/- infinity; don't need exponent DROP ENTER[^] MASKR 52 AND x=0? // Handle NaN here; infinity below JMP InfI DECM # NaN RTN InfI:: DROP // +/- infinity; don't need mantissa CF .01 // Flag .01 is negative infinity x<0? SF .01 DECM # [infinity] FS? .01 +/- RTN END

Edited: 15 June 2013, 8:18 p.m.

      
Re: [wp34s] Converting to/from IEEE 754 Binary64 (Double Precision)
Message #2 Posted by Paul Dale on 15 June 2013, 9:21 p.m.,
in response to message #1 by David Maier

Nice program. The first time I've seen sign and mantissa mode used in a real program.

A word of caution for people. The 34S's reals are not strictly in either IEEE decimal64 or decimal128 format. They perform the same and have the same number of digits, same exponent range, same extras and even the same general layout in memory, however there is a mapping stage for the triad of decimal digits that we left out for spaces reasons.

Pauli


[ Return to Index | Top of Index ]

Go back to the main exhibit hall