为最小 Space 用法重新排列对齐对象的顺序
Rearranging Order of Aligned Objects For Minimal Space Usage
我有一个数据结构需要 4-KiB 对齐。我可以使用 __attribute__ ((aligned (4096)))
.
强制执行此操作
问题在于这种对齐要求会导致内存浪费。这是链接器放置符号的方式(pg_dir
是对齐的数据结构):
00011000 <cursor_loc>:
00012000 <pg_dir>:
00013000 <idt>:
cursor_loc
的大小只有四个字节。这样会更好:
00011000 <pg_dir>:
00012000 <cursor_loc>:
00012008 <idt>:
(idt
这里必须8字节对齐。)
您可以像这样使用多个文件重现它:
test1.c
:
char aligned[4096] __attribute__ ((aligned (4096)));
int i;
test2.c
:
int j;
int main(void) { }
然后用
构建它
gcc test1.c test2.c
和 objdump -D a.out
打印如下:
0000000000602004 <j>:
...
0000000000603000 <aligned>:
...
0000000000604000 <i>:
我如何移动 GNU ld 以重新排列符号以将 space 浪费降至最低?我真的很奇怪为什么它没有自动完成。
有一些习语要求对象按照对象在命令行中指定的顺序排列(这就是为什么您的结果有点奇怪,可能是由于常用符号),以及对象内定义没有重新排序。要解决这个问题,您需要这样的东西:
gcc -fno-common -fdata-sections -Wl,--sort-section=alignment test1.c test2.c
-fno-common
禁用公共符号,-fdata-sections
允许链接器对同一文件中的符号重新排序,-Wl,--sort-section=alignment
最后启用对齐排序。
我有一个数据结构需要 4-KiB 对齐。我可以使用 __attribute__ ((aligned (4096)))
.
问题在于这种对齐要求会导致内存浪费。这是链接器放置符号的方式(pg_dir
是对齐的数据结构):
00011000 <cursor_loc>:
00012000 <pg_dir>:
00013000 <idt>:
cursor_loc
的大小只有四个字节。这样会更好:
00011000 <pg_dir>:
00012000 <cursor_loc>:
00012008 <idt>:
(idt
这里必须8字节对齐。)
您可以像这样使用多个文件重现它:
test1.c
:
char aligned[4096] __attribute__ ((aligned (4096)));
int i;
test2.c
:
int j;
int main(void) { }
然后用
构建它gcc test1.c test2.c
和 objdump -D a.out
打印如下:
0000000000602004 <j>:
...
0000000000603000 <aligned>:
...
0000000000604000 <i>:
我如何移动 GNU ld 以重新排列符号以将 space 浪费降至最低?我真的很奇怪为什么它没有自动完成。
有一些习语要求对象按照对象在命令行中指定的顺序排列(这就是为什么您的结果有点奇怪,可能是由于常用符号),以及对象内定义没有重新排序。要解决这个问题,您需要这样的东西:
gcc -fno-common -fdata-sections -Wl,--sort-section=alignment test1.c test2.c
-fno-common
禁用公共符号,-fdata-sections
允许链接器对同一文件中的符号重新排序,-Wl,--sort-section=alignment
最后启用对齐排序。