On Feb 12, 12:43*pm, Malcolm McLean <(E-Mail Removed)>

wrote:

> Anyone got a routine to portably read/write 64 bit IEEE numbers in

> litle-endian format?

>

> (I mean so that it is compatible with fwrite(&x, sizeof(double), 1,

> fp) ona Windows PC, and won't break should the program be run on a

> machine with a diferent internal floating-point unit).
For integer quantities I use hton[s|l]()/ntoh[s|l](). Generally

speaking though, how about encoding into IEEE-754? Here's some code I

copied a long time ago from...some fellow which I don't recall.

long long pack754(long double f, unsigned bits, unsigned expbits)

{

long double fnorm;

int shift;

long long sign, exp, significand;

unsigned significandbits = bits - expbits - 1; // -1 for sign bit

if (f == 0.0) return 0; // get this special case out of the way

// check sign and begin normalization

if (f < 0) { sign = 1; fnorm = -f; }

else { sign = 0; fnorm = f; }

// get the normalized form of f and track the exponent

shift = 0;

while(fnorm >= 2.0) { fnorm /= 2.0; shift++; }

while(fnorm < 1.0) { fnorm *= 2.0; shift--; }

fnorm = fnorm - 1.0;

// calculate the binary form (non-float) of the significand data

significand = fnorm * ((1LL<<significandbits) + 0.5f);

// get the biased exponent

exp = shift + ((1<<(expbits-1)) - 1); // shift + bias

// return the final answer

return (sign<<(bits-1)) | (exp<<(bits-expbits-1)) | significand;

}

long double unpack754(long long i, unsigned bits, unsigned expbits)

{

long double result;

long long shift;

unsigned bias;

unsigned significandbits = bits - expbits - 1; // -1 for sign bit

if (i == 0) return 0.0;

// pull the significand

result = (i&((1LL<<significandbits)-1)); // mask

result /= (1LL<<significandbits); // convert back to float

result += 1.0f; // add the one back on

// deal with the exponent

bias = (1<<(expbits-1)) - 1;

shift = ((i>>significandbits)&((1LL<<expbits)-1)) - bias;

while(shift > 0) { result *= 2.0; shift--; }

while(shift < 0) { result /= 2.0; shift++; }

// sign it

result *= (i>>(bits-1))&1? -1.0: 1.0;

return result;

}

Those don't handle NaN or infinity, but you wouldn't need a terrible

amount of time to do so.

You could also sprintf() encode if your application isn't bandwidth-

intensive.