// File: rurban[P]dgnlib/dgnfloat.cpp
// Function: IEEE2DGNDouble(void*)
void    IEEE2DGNDouble(void * dbl)

{
    double64_t  dt;
    GInt32      exponent;
    GInt32      sign;
    GByte       *src,*dest;
        
#ifdef CPL_LSB
    src  = (GByte *) dbl;
    dest = (GByte *) &dt;

    dest[0] = src[4];
    dest[1] = src[5];
    dest[2] = src[6];
    dest[3] = src[7];
    dest[4] = src[0];
    dest[5] = src[1];
    dest[6] = src[2];
    dest[7] = src[3];
#else
    memcpy( &dt, dbl, 8 );
#endif

    sign         = dt.hi & 0x80000000;
    exponent = dt.hi >> 20;
    exponent = exponent & 0x000007ff;

/* -------------------------------------------------------------------- */
/*      An exponent of zero means a zero value.                         */
/* -------------------------------------------------------------------- */
    if (exponent)
        exponent = exponent -1023+129;

/* -------------------------------------------------------------------- */
/*      In the case of overflow, return the largest number we can       */
/* -------------------------------------------------------------------- */
    if (exponent > 255)
    {
        dest = (GByte *) dbl;

        if (sign) 
            dest[1] = 0xff;
        else
            dest[1] = 0x7f;

        dest[0] = 0xff;
        dest[2] = 0xff;
        dest[3] = 0xff;
        dest[4] = 0xff;
        dest[5] = 0xff;
        dest[6] = 0xff;
        dest[7] = 0xff;

        return;
    }   

/* -------------------------------------------------------------------- */
/*      In the case of of underflow return zero                         */
/* -------------------------------------------------------------------- */
    else if ((exponent < 0 ) ||
             (exponent == 0 && sign == 0))
    {
        dest = (GByte *) dbl;

        dest[0] = 0x00;
        dest[1] = 0x00;
        dest[2] = 0x00;
        dest[3] = 0x00;
        dest[4] = 0x00;
        dest[5] = 0x00;
        dest[6] = 0x00;
        dest[7] = 0x00;

        return;
    }
    else
    {
/* -------------------------------------------------------------------- */
/*          Shift the fraction 3 bits left and set the exponent and sign*/
/* -------------------------------------------------------------------- */
        dt.hi = dt.hi << 3;
        dt.hi = dt.hi | (dt.lo >> 29);
        dt.hi = dt.hi & 0x007fffff;
        dt.hi = dt.hi | (exponent << 23) | sign;
            
        dt.lo = dt.lo << 3;
    }

/* -------------------------------------------------------------------- */
/*      Convert the double back to VAX format                           */
/* -------------------------------------------------------------------- */
    src = (GByte *) &dt;
    dest = (GByte *) dbl;

#ifdef CPL_LSB
    dest[2] = src[0];
    dest[3] = src[1];
    dest[0] = src[2];
    dest[1] = src[3];
    dest[6] = src[4];
    dest[7] = src[5];
    dest[4] = src[6];
    dest[5] = src[7];
#else
    dest[1] = src[0];
    dest[0] = src[1];
    dest[3] = src[2];
    dest[2] = src[3];
    dest[5] = src[4];
    dest[4] = src[5];
    dest[7] = src[6];
    dest[6] = src[7];
#endif
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
movq %rdi, -0x8(%rbp)
movq -0x8(%rbp), %rax
movq %rax, -0x20(%rbp)
leaq -0x10(%rbp), %rax
movq %rax, -0x28(%rbp)
movq -0x20(%rbp), %rax
movb 0x4(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, (%rax)
movq -0x20(%rbp), %rax
movb 0x5(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x1(%rax)
movq -0x20(%rbp), %rax
movb 0x6(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x2(%rax)
movq -0x20(%rbp), %rax
movb 0x7(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x3(%rax)
movq -0x20(%rbp), %rax
movb (%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x4(%rax)
movq -0x20(%rbp), %rax
movb 0x1(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x5(%rax)
movq -0x20(%rbp), %rax
movb 0x2(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x6(%rax)
movq -0x20(%rbp), %rax
movb 0x3(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x7(%rax)
movl -0x10(%rbp), %eax
andl $0x80000000, %eax       # imm = 0x80000000
movl %eax, -0x18(%rbp)
movl -0x10(%rbp), %eax
shrl $0x14, %eax
movl %eax, -0x14(%rbp)
movl -0x14(%rbp), %eax
andl $0x7ff, %eax            # imm = 0x7FF
movl %eax, -0x14(%rbp)
cmpl $0x0, -0x14(%rbp)
je 0xa3db
movl -0x14(%rbp), %eax
subl $0x3ff, %eax            # imm = 0x3FF
addl $0x81, %eax
movl %eax, -0x14(%rbp)
cmpl $0xff, -0x14(%rbp)
jle 0xa440
movq -0x8(%rbp), %rax
movq %rax, -0x28(%rbp)
cmpl $0x0, -0x18(%rbp)
je 0xa3fc
movq -0x28(%rbp), %rax
movb $-0x1, 0x1(%rax)
jmp 0xa404
movq -0x28(%rbp), %rax
movb $0x7f, 0x1(%rax)
movq -0x28(%rbp), %rax
movb $-0x1, (%rax)
movq -0x28(%rbp), %rax
movb $-0x1, 0x2(%rax)
movq -0x28(%rbp), %rax
movb $-0x1, 0x3(%rax)
movq -0x28(%rbp), %rax
movb $-0x1, 0x4(%rax)
movq -0x28(%rbp), %rax
movb $-0x1, 0x5(%rax)
movq -0x28(%rbp), %rax
movb $-0x1, 0x6(%rax)
movq -0x28(%rbp), %rax
movb $-0x1, 0x7(%rax)
jmp 0xa55a
cmpl $0x0, -0x14(%rbp)
jl 0xa452
cmpl $0x0, -0x14(%rbp)
jne 0xa49e
cmpl $0x0, -0x18(%rbp)
jne 0xa49e
movq -0x8(%rbp), %rax
movq %rax, -0x28(%rbp)
movq -0x28(%rbp), %rax
movb $0x0, (%rax)
movq -0x28(%rbp), %rax
movb $0x0, 0x1(%rax)
movq -0x28(%rbp), %rax
movb $0x0, 0x2(%rax)
movq -0x28(%rbp), %rax
movb $0x0, 0x3(%rax)
movq -0x28(%rbp), %rax
movb $0x0, 0x4(%rax)
movq -0x28(%rbp), %rax
movb $0x0, 0x5(%rax)
movq -0x28(%rbp), %rax
movb $0x0, 0x6(%rax)
movq -0x28(%rbp), %rax
movb $0x0, 0x7(%rax)
jmp 0xa55a
movl -0x10(%rbp), %eax
shll $0x3, %eax
movl %eax, -0x10(%rbp)
movl -0x10(%rbp), %eax
movl -0xc(%rbp), %ecx
shrl $0x1d, %ecx
orl %ecx, %eax
movl %eax, -0x10(%rbp)
movl -0x10(%rbp), %eax
andl $0x7fffff, %eax         # imm = 0x7FFFFF
movl %eax, -0x10(%rbp)
movl -0x10(%rbp), %eax
movl -0x14(%rbp), %ecx
shll $0x17, %ecx
orl %ecx, %eax
orl -0x18(%rbp), %eax
movl %eax, -0x10(%rbp)
movl -0xc(%rbp), %eax
shll $0x3, %eax
movl %eax, -0xc(%rbp)
jmp 0xa4dc
leaq -0x10(%rbp), %rax
movq %rax, -0x20(%rbp)
movq -0x8(%rbp), %rax
movq %rax, -0x28(%rbp)
movq -0x20(%rbp), %rax
movb (%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x2(%rax)
movq -0x20(%rbp), %rax
movb 0x1(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x3(%rax)
movq -0x20(%rbp), %rax
movb 0x2(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, (%rax)
movq -0x20(%rbp), %rax
movb 0x3(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x1(%rax)
movq -0x20(%rbp), %rax
movb 0x4(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x6(%rax)
movq -0x20(%rbp), %rax
movb 0x5(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x7(%rax)
movq -0x20(%rbp), %rax
movb 0x6(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x4(%rax)
movq -0x20(%rbp), %rax
movb 0x7(%rax), %cl
movq -0x28(%rbp), %rax
movb %cl, 0x5(%rax)
popq %rbp
retq
nopl (%rax)