在执行movl 100,%eax后,EAX的价值是什么?
如果机器是小端的?(我朋友的回答)
0x00 0x00 0x00 0x11
我的想法:
0x44332211? Also, does those 0x matter or can I just do one like this?
Run Code Online (Sandbox Code Playgroud)
对于Big Endian :(朋友的回答)
0x11 0x00 0x00 0x00
在这里,我认为:
0x11223344
Run Code Online (Sandbox Code Playgroud) 让我们看看以下代码:
int i = 10;
char c = reinterpret_cast<char&>(i);
Run Code Online (Sandbox Code Playgroud)
如果可以使用reinterpret_cast将"指向T1的指针"类型的表达式显式转换为"指向T2的指针"类型,则可以将类型T1的glvalue表达式强制转换为"对T2的引用".结果引用与源glvalue相同的对象,但具有指定的类型.
所以reinterpret_cast<char&>(i)具有指定char类型的左值引用该int对象i.
要进行初始化c,我们需要值,因此应用左值到右值的转换[conv.lval] /3.4:
glvalue指示的对象中包含的值是prvalue结果.
L2R转换的结果是i对象中包含的值.只要值i在char([expr]/4表示否则这是UB)可表示的范围内,变量c应初始化为具有相同的值.
从实现POV开始,在little-endian平台上,通过读取i对象地址处的字节可以轻松实现.但是,在big-endian平台上,编译器必须添加一个偏移量来获取最低有效字节.或者,将整个int对象读入寄存器并屏蔽第一个字节,这对两个端点都是可接受的方法.
如果您认为编译器可以轻松处理上面的代码以生成符合C++ 17标准所要求的代码,那么可以考虑将指针int指向指向i的指针char.这样的转换不会改变指针值,即它仍然指向int对象i,这意味着将间接运算符应用于具有以下L2R转换的指针应该如上所述,即int如果是,则获取对象的值按char类型表示.
在以下代码中
int i = 10;
f(reinterpret_cast<char*>(&i)); // void f(char*)
Run Code Online (Sandbox Code Playgroud)
如果编译器i不知道函数f将对其参数做什么,那么编译器是否应该调整某个偏移的地址?并且编译器也不知道将传递给函数的内容f.上面的代码和函数f在不同的翻译单元中.
例如,如果f …
我用 c 编写了一个简单的程序,它调用一个名为 while_loop 的函数,参数为 4,3,2。该函数基本上只是一个 while 循环,我认为它与我的问题并不真正相关,因为它更像是一个通用问题。有人告诉我运行 objdump -d,所以我做了。
我有多个问题,所以这里是:
不知何故,我的程序将变量视为大端,即使我的系统是小端。
当我执行“lscpu | grep Endian”时,它返回
Byte Order: Little Endian
Run Code Online (Sandbox Code Playgroud)
但是当我使用以下代码运行调试 gcc (x86_64 linux) 可执行文件时:
int x = 1235213421;
printf("%x", x);
Run Code Online (Sandbox Code Playgroud)
它返回 0x499FDC6D,而对于小端,它应该返回 0x6DDC9F49
u_int32_t ip6_address[1][4] = { {0x00000001, 0x0, 0x0, 0x12345678} };
Run Code Online (Sandbox Code Playgroud)
如果使用函数htonl()将little endian转换为big endian,则它对整数类型值有效,但对unsigned char或BYTE值返回0.
q = (int)htonl((u_long)p); // integer values
Modulus = (BYTE)htonl((u_long)modulus); // BYTE values
Prime1 = (BYTE)htonl((u_long)prime1); // BYTE values
Run Code Online (Sandbox Code Playgroud)
是否有可能改变BYTE值的endianess.
因此,根据此处的C编译器标准:
http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1124.pdf
我们发现无法精确确定在C编译器中如何实现位字段的要求。显然,只要位域的行为与任何其他标量域一样,任何事情都会发生。文档部分6.7.2.1-10说:
“一个实现可以分配任何足够大的可寻址存储单元来容纳一个位域。如果有足够的空间,则紧跟在结构中另一个位域之后的位域应打包到同一单元的相邻位中。如果不足,保留空间,是否将不合适的位字段放入下一个单元或与相邻单元重叠是由实现定义的。一个单元内位字段的分配顺序(高位到低位或低位)到高级)是由实现定义的。可寻址存储单元的对齐方式未指定。”
对于许多声称“您不能信任位域”或“位域不可移植”的人来说,对编译器的迫在眉睫的自由似乎是一站式服务。该警报表明,整个编译器编写者和CPU制造商在星空中密谋,只是因为标准允许而笑着急于做一些奇特的位域调整和对齐。
这些疯狂的波西米亚风格的编译器/ CPU设计人员在哪里致力于保证位域永远不依赖和不便携,这些证据在哪里?我想看看火星上绿人的确凿证据。
我已经附上了简单易懂的C ++源代码,以告诉有关使用C ++编译器的任何系统的位域真相。我要问社区,不是征求意见,而是要向您的系统和编译器提供确切的输出证据,如果它们与发布的结果有所出入。如果与发布的结果相比,我有能力对整个C / C ++社区进行相同/不相同的投票,我想知道百分比是多少?
#include <stdio.h>
/*
A simple program to illustrate the bitfields actual internal compiled layout.
Results depend on machine architecture and compiler implementation and flags.
*/
typedef unsigned long long int ulli;
struct bitf
{
// field bits offset
ulli f0 : 1; // 0
ulli f1 : 2; // 1
ulli f3 : 3; // 3
ulli f7 : 4; // 6
ulli f15 : 5; // …Run Code Online (Sandbox Code Playgroud) 我正在使用Perl Win32::SerialPort模块.在这个特殊模块中,我使用输入命令发送数据.我发送到嵌入式系统的数据是使用该transmit_char函数的标量数据(数字)(如果它是C它将是整数,但由于它是一种脚本语言,我不知道perl中的内部格式是什么.我的猜测是perl总是将所有数字存储为32位浮点,这些浮点在发送时由模块调整).
然后在发送数据后,我使用输入命令接收数据.我收到的数据可能是二进制形式,但perl不知道如何解释它.我使用这样的unpack功能
my $binData = $PortObj->input;
my $hexData = unpack("H*",$binData);
Run Code Online (Sandbox Code Playgroud)
假设我0x4294通过串行电缆传输,这是我正在与之通信的嵌入式系统上的一个命令,我希望得到一个响应 0x5245.现在问题在于endianess:当我解压缩时,我得到了0x4552,这是错误的.有没有办法通过调整二进制数据来纠正它.我也试过h*,这给了我0x5425,这也是不对的.
注意:我收到的数据一次通过字节发送,LSB首先发送
我正在使用人机接口设备协议从外部设备获取数据。我使用的库返回一个字节数组 ( [u8; 64]),我想从一个字节中提取一个字节i7(将i8在 Rust 中)。
我想要操作的字节中有两条不同的信息:
你知道我可以做什么来实现这个目标吗?