问题标签 [struct-member-alignment]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
3 回答
307 浏览

c - fread():从文件中读取(不对齐)会导致跳过字节

我有一个文件,并且使用 CI 想要使用 fread() (来自 stdio.h)读取它的内容并将其写入结构的成员中。(在我的情况下,开头有一个 2 字节的 int,后跟一个 4 字节的 int。)但是在将文件的内容正确写入结构的前两个字节变量后,它会跳过两个字节,然后继续执行后四个字节变量。

为了演示,我创建了一个 16 字节的文件来读取。在十六进制中它看起来像这样(小端): 22 11 66 55 44 33 11 11 00 00 00 00 00 00 00 00

使用以下代码,我希望第一个变量 ,twobytes0x1122,第二个变量 ,fourbytes0x33445566。但相反,它打印:

跳过字节 3 和 4 ( 0x66& 0x55)。代码:

使用具有两个相同大小整数的结构按预期工作。


所以:使用 fread() 写入不同大小的变量会导致跳过字节:

22 11 .. .. 44 33 11 11 ...

代替

22 11 66 55 44 33 ...


我知道关于字节对齐的一些东西在这里发挥了作用,但这对字节的读取有何影响?如果 C 想要为结构添加填充,这对从文件中读取有何影响?我不在乎 C 是否将结构成员存储为 or ,我很困惑为什么它无法正确读取我的文件。22 11 .. .. 66 55 44 33 ...22 11 66 55 44 33 ...

另外,我正在使用gcc version 6.3.0 (MinGW.org GCC-6.3.0-1)

0 投票
4 回答
353 浏览

c - 在小结构的末尾而不是在 2 个成员之间进行对齐填充会更好吗?

我们知道 C 中的某些结构中存在填充。请考虑以下 2:

假设sizeof(int) = alignof(int)= 4 bytes:
sizeof(node1) = sizeof(node2) = 12,由于填充。

两者在性能上有什么区别?(如果有的话,wrt 编译器或系统架构,尤其是 GCC)

0 投票
4 回答
113 浏览

c++ - 有没有办法访问结构的成员

我希望能够找到结构中各个成员的大小。例如

现在 sizeof(A) 为 8,但假设我正在编写一个函数,该函数将打印 A 的对齐方式,如下所示,其中“aa”表示填充。

数据 A:
0x00:00 00 00 00
0x04:00 aa aa aa
*-------------------------
大小:8 填充:3

为了让我计算填充,我需要知道结构中每个单独成员的大小。所以我的问题是如何访问给定结构的各个成员。

另外,让我知道是否有另一种方法可以找到填充的数量。

0 投票
2 回答
597 浏览

c - 为什么 Clang-Tidy 建议进行更大的对齐?

给定以下 c 语言结构定义:

Clang-Tidy 给出以下信息:

由于对齐不佳,访问 struct 'PackTest' 中的字段效率低下;当前对齐为 8 字节,但建议对齐为 16 字节

我知道为什么该结构与 8 个字节对齐,但我不知道该建议是否有效以及为什么。

0 投票
0 回答
163 浏览

c - 无法从 Turbo C 中读取文件

以下代码在 Dev C++ 中运行良好,但是当我在 turbo CI 中运行时没有得到任何输出。我已经将数据存储在 users.bin 文件中。

0 投票
1 回答
47 浏览

c - 嵌套结构/联合中的对齐

我有以下由 VC 2005 编译的结构:

在观察窗口中:

谢谢。

0 投票
0 回答
21 浏览

c - 查找地址大小的差异(填充)

我在 c 中有一个结构,这样,

现在 ch 和 num 的地址应该根据它们存储的地址相差多少字节?当我运行 sizeof 时,structB 的大小是 8,但 char 应该是 1 字节?那么,结构内的元素是否仍应相差 4 个字节?我对此有点困惑。

注意:这个问题似乎已经关闭,因为它与另一个问题相似,但我仍然对填充感到困惑。那么有人可以参考上面提供的 structB 来解释一下吗?

0 投票
1 回答
85 浏览

c - 如果数组大小发生变化以及定义的宏如何在此处计算偏移量,为什么 C 结构中的字符数组的偏移量会有所不同?

我已经定义了一个宏来计算结构到任何结构字段的偏移量。代码如下:

如果我编译并运行代码,字段“salary”的偏移量为 20,它应该是 20。但是如果我将结构字段更改char name[20];char name[30];“salary”的偏移量,则更改为 32,但它应该是 30。如果我进一步更改结构字段将char name[1];“工资”的偏移更改为 4,但它应该是 1。为什么会发生这些偏移值差异?

问题的第二部分是宏究竟是如何#define offset计算偏移量的?&(((struct_name *)0)->fld_name)实际在做什么?外部&表示地址,但剩下的到底是什么(((struct_name *)0)->fld_name)意思?

0 投票
1 回答
105 浏览

c++ - 升级 C++ 工具版本后 fread() 无法正确读取结构数据

我有一个较旧的项目,它使用 fread() 将二进制文件读入结构。它使用 Visual Studio 2017 (v141)

我将项目升级到 VS 2019 的最新 C++ 工具版本 (v142),并将解决方案从 AnyCPU 更改为 x86。

我还将结构成员对齐方式从:1 字节 (/Zp1) 更改为:默认

因为这个错误:

错误 C2338 Windows 标头需要默认打包选项。更改此设置可能会导致内存损坏。可以通过定义 WINDOWS_IGNORE_PACKING_MISMATCH 来禁用此诊断。

但是现在数据不再被正确读取。

这是我用来读取二进制文件的代码:

recipe是一个结构。见下文。

我注意到这sizeof(recipe)给出了与文件大小不同的结果。使用工具集 141,我得到 798276 字节。使用工具集 142,我得到 824304 字节。实际文件大小为 771088 字节。

这个问题真的是由结构成员对齐的变化引起的吗?

如何修复错误,以便再次正确读取文件?

编辑:我尝试将编译指示包指令添加到结构中,如下所示:

但它似乎对错误没有任何影响。

0 投票
0 回答
117 浏览

linux - windows和Linux gcc编译器之间奇怪的字节对齐

与 linux gcc 编译器相比,我看到读取 bin 文件并映射到 windows 中的结构的奇怪行为。

下面是我的c代码:

这是它读取的输入二进制文件。(此示例 bin 文件为0x01(20 次)... 0xFF(20 次) = 所以255 x 20 = 5100 字节)相同的代码在 windows mingW-gcc 和 linux gcc 中编译和运行。

以下是在 windows 运行中看到的奇怪观察: 在此处输入图像描述

  1. blk_hdr_tstruct 虽然 4 字节对齐,总共 16 字节:22 字节(更新:我发现这个解决方案与 -mno-ms-bitfields 选项一起使用)
  2. 尽管有 5100 字节可用,但 read() 函数只能读取 1000 字节。是什么让它进一步阅读?
  3. read() 还会将具有“0x00”字节值的“孔”放入其中。我不明白这种奇怪的行为。
  4. 启用 lseek 跳过前 1024 个字节应到达文件末尾。

linux 结果上的一切看起来都很完美(尽管第 3 点)在 linux 端也确实存在:虽然这对我来说微不足道,但我对这种行为很好奇)

所以最后,如何在 windows gcc 上使用与linux gcc 中的精确结果一样的代码?谁能启发我?(结构中的参数不能重新洗牌)