Networking 如何在主机和网络字节顺序之间转换double?

Networking 如何在主机和网络字节顺序之间转换double?,networking,linux-kernel,embedded,arm,endianness,Networking,Linux Kernel,Embedded,Arm,Endianness,谁能告诉我如何将双精度转换为网络字节排序。 我试过了 函数,它们工作得很好,但是没有一个能够进行双(浮点)转换,因为这些类型在每个体系结构上都是不同的。通过XDR,我找到了双浮点精度格式表示(),但没有字节排序 所以,如果有人能在这方面帮助我,我将不胜感激(C代码会很棒!)。 注意:操作系统是Linux内核(2.6.29),ARMv7 CPU体系结构。您可以查看浮点的交换格式 但关键应该是定义网络顺序,例如1。字节指数和符号,字节2到n作为尾数,按msb顺序排列 然后你可以声明你的函数 uint

谁能告诉我如何将双精度转换为网络字节排序。 我试过了

函数,它们工作得很好,但是没有一个能够进行双(浮点)转换,因为这些类型在每个体系结构上都是不同的。通过XDR,我找到了双浮点精度格式表示(),但没有字节排序

所以,如果有人能在这方面帮助我,我将不胜感激(C代码会很棒!)。 注意:操作系统是Linux内核(2.6.29),ARMv7 CPU体系结构。

您可以查看浮点的交换格式

但关键应该是定义网络顺序,例如1。字节指数和符号,字节2到n作为尾数,按msb顺序排列

然后你可以声明你的函数

uint64_t htond(double hostdouble);
double ntohd(uint64_t netdouble);
实现只取决于您的编译器/平台形式。
最好是使用一些自然的定义, 因此,您可以在ARM平台上使用简单的转换

编辑:

从评论中

static void htond (double &x)
{
  int *Double_Overlay; 
  int Holding_Buffer; 
  Double_Overlay = (int *) &x; 
  Holding_Buffer = Double_Overlay [0]; 
  Double_Overlay [0] = htonl (Double_Overlay [1]); 
  Double_Overlay [1] = htonl (Holding_Buffer); 
}
这可能会起作用,但显然只有在两个平台对double使用相同的编码模式,并且int的long大小相同的情况下才能起作用。
顺便说一句,返回值的方式有点奇怪

但您可以编写一个更稳定的版本,如以下(伪代码)

这可能是hacky(char*hack),但对我来说很有用:

double Buffer::get8AsDouble(){

    double little_endian = *(double*)this->cursor;

    double big_endian;

    int x = 0;
    char *little_pointer = (char*)&little_endian;
    char *big_pointer = (char*)&big_endian;

    while( x < 8 ){
        big_pointer[x] = little_pointer[7 - x];
        ++x;
    }

    return big_endian;

}
双缓冲区::get8AsDouble(){ double little_endian=*(double*)此->光标; 双大田; int x=0; 字符*小指针=(字符*)&小指针; 字符*大指针=(字符*)&大指针; 而(x<8){ 大指针[x]=小指针[7-x]; ++x; } 返回大田; }
为了简单起见,我没有包括射程守卫。但是,在这个级别上工作时,应该包括范围保护。

双字节没有网络字节顺序,因为没有为它们定义单一的网络表示。若你们真的想要,你们可以把它们分成尾数、符号和指数,或者把它们表示成分子和分母,但这很复杂。我发现了这个,但在服务器上收到了意想不到的值。静态void htond(double&x){int*double\u Overlay;int Holding\u Buffer;double\u Overlay=(int*)&x;Holding\u Buffer=double\u Overlay[0];double\u Overlay[0]=htonl(double\u Overlay[1]);double\u Overlay[1]=htonl(Holding\u Buffer);}
void htond (const double hostDouble, uint8_t result[8])
{
  result[0] = signOf(hostDouble);
  result[1] = exponentOf(hostDouble);
  result[2..7] = mantissaOf(hostDouble);
}
double Buffer::get8AsDouble(){

    double little_endian = *(double*)this->cursor;

    double big_endian;

    int x = 0;
    char *little_pointer = (char*)&little_endian;
    char *big_pointer = (char*)&big_endian;

    while( x < 8 ){
        big_pointer[x] = little_pointer[7 - x];
        ++x;
    }

    return big_endian;

}