20070611 BitConverter LittleEndian BigEndian
http://www.yippeesoft.com
网络字节顺序与主机字节顺的转换
在写socket程序时要注意,如果要发送整型(short, int, long等)类型的数据,需要将这些值转换成网络字节顺序后才后再发送,同时接收方也要将网络字节顺序的值转为主机字节顺序的。System.Net.IPAddress类提供了HostToNetworkOrder 、HostToNetworkOrder 来完成相应的功能。
class Test
&leftsign;
public static byte[] Struct2Bytes(Object obj)
&leftsign;
int size = Marshal.SizeOf(obj);
byte[] bytes = new byte[size];
IntPtr arrPtr=Marshal.UnsafeAddrOfPinnedArrayElement(bytes, 0);
Marshal.StructureToPtr(obj,arrPtr,true);
return bytes;
&rightsign;
public static Object Bytes2Struct(byte[] bytes)
&leftsign;
IntPtr arrPtr=Marshal.UnsafeAddrOfPinnedArrayElement(bytes, 0);
return Marshal.PtrToStructure(arrPtr, typeof(Data));
&rightsign;
&rightsign;
反转整个一维 Array 中元素的顺序。
命名空间:System
程序集:mscorlib(在 mscorlib.dll 中)
// Example of the BitConverter::IsLittleEndian field.
using namespace System;
int main()
&leftsign;
Console::WriteLine( "This example of the BitConverter::IsLittleEndian field "
"generates \\nthe following output when run on "
"x86-class computers.\\n" );
Console::WriteLine( "IsLittleEndian: &leftsign;0&rightsign;", BitConverter::IsLittleEndian );
&rightsign;
/*
This example of the BitConverter::IsLittleEndian field generates
the following output when run on x86-class computers.
IsLittleEndian: True
*/
指示数据在此计算机结构中存储时的字节顺序(“Endian”性质)。
对于Unsigned Integer 和Interger字段,需要按照网络字节顺序和x86机器的字节编码顺序对照关系进行转换
转换网络字节主要是为廖网络交互,所谓网络字节顺序是一种网络传输的标准,如果你知道自己的程序要交互的对象认识你的host字节顺序,你也可以不转换。但还是建议转换,就像网络通讯需要tcp协议一样
最近使用C#进行网络开发,需要处理ISO8583报文,由于其中有些域是数值型的,于是在传输的时候涉及到了字节序的转换。字节顺序是指占内存多于一个字节类型的数据在内存中的存放顺序,通常有两种字节顺序,根据他们所处的位置我们分别称为主机节序和网络字节序。通常我们认为网络字节序为标准顺序,封包的时候,将主机字节序转换为网络字节序,拆包的时候要将网络字节序转换为主机字节序。原以为还要自己写函数,其实网络库已经提供了。 主机到网络:short/int/long IPAddress.HostToNetworkOrder(short/int/long) 网络到主机:short/int/long IPAddress.NetworkToHostOrder(short/int/long) 主机字节序指低字节数据存放在内存低地址处,高字节数据存放在内存高地址处,如: int x=1; //此时x为主机字节序:[1][0][0][0] 低位到高位 int y=65536 //此时y为主机字节序:[0][0][1][0] 低位到高位我们通过主机到网络字节序的转换函数分别对x和y进行转换得到他们对应的网络字节序值,网络节序是高字节数据存放在低地址处,低字节数据存放在高地址处,如: int m=IPAddress.HostToNetworkOrder(x); //此时m为主机[改为网络[/color:4d5c53bbac]]字节序:[0][0][0][1] 高位到低位 int n=IPAddress.HostToNetworkOrder(y); //此时n为主机[改为网络[/color:4d5c53bbac]]字节序:[0][1][0][0] 高位到低位 经过转换以后,我们就可以通过 byte[]btValue=BitConverter.GetBytes(m); 得到一个长度为4的byte数组,然后将这个数组设置到报文的相应位置发送出去即可。同样,收到报文后,可以将报文按域拆分,得到btValue,使用 int m=BitConverter.ToInt32(btValue,0);//从btValue的第0位开始转换得到该域的值,此时还不能直接使用,应该再用网络到主机字节序的转换函数进行转换: int x=IPAddress.NetworkToHostOrder(m); 这时得到的x才是报文中的实际值。
Han,
Intel CPUs are Little Endian. Unix variants tend to be Big Endian.
Your problem is sender:
byte[] fSize = new byte[4];
fSize = BitConverter.GetBytes(fInfo.Length);
sock.Send(fSize);
You are correctly sending your data size to the receiver so that your receiver knows how much data to expect.
However, \’fSize\’ is not network byte ordered. You are sending a 32 bit value as 4 seperate bytes without care for network byte ordering. Further, your receiver does not account for netwrork byte ordering of that value and will misinterpret it.
I think that\’s the problem but it\’s almost 3 in the morning where I live so I will reserve further judgement till tomorrow.
当一个逻辑上长于一个字节的整形数据放置在内存中时(比如16位,32位,和64位的整数),计算机设计者需要考虑这些字节的存储顺序。一些体系结构的设计者选择了将字节的逻辑顺序与物理顺序一致,即将逻辑上较低的字节放置在物理上较低的字节上;另外一些设计者则选择了将字节的逻辑顺序与物理顺序相反,即将逻辑上较低的字节放置在物理上较高的字节上。前者被称为“little endian”,比如Intel x86系列;后者则被称为“big endian”,比如Motorola的PowerPC以及Sun Sparc。还有一些平台同时支持两种方案,由开发者决定使用哪一种。
历史博文
- c# bmp save - 2009
- 20070210 qq 手机 CMWAP 代理 - 2008
- 0520 T5直播 天津 VS 八一 3:1 1 2006年步步高全国女排锦标赛 决赛 - 2006
- SONY TR2C WINXP SP1 安装 - 2005