有人能指出gcc -D_FORTIFY_SOURCE=1
和-D_FORTIFY_SOURCE=2
之间的区别吗?我猜=2
更安全?我还没有找到一个逐点列出差异的列表。
我也读到过-D_FORTIFY_SOURCE=2
应该与-O2
一起使用,否则不会有所有功能可用。同样,在这里我没有找到一个详细说明回归的列表。我特别想用-Os
编译,因为目标是一个闪存不太多的设备。
欢迎任何关于此文档的提示!
有人能指出gcc -D_FORTIFY_SOURCE=1
和-D_FORTIFY_SOURCE=2
之间的区别吗?我猜=2
更安全?我还没有找到一个逐点列出差异的列表。
我也读到过-D_FORTIFY_SOURCE=2
应该与-O2
一起使用,否则不会有所有功能可用。同样,在这里我没有找到一个详细说明回归的列表。我特别想用-Os
编译,因为目标是一个闪存不太多的设备。
欢迎任何关于此文档的提示!
从功能测试宏的手册页(man 7 feature_test_macros
)上可以得知:
此外,增强应用程序安全性的FORTIFY_SOURCE文章(2014年3月)表示:
_FORTIFY_SOURCE
(自glibc 2.3.4起)定义此宏会导致在使用各种字符串和内存操作函数(例如
memcpy
、memset
、stpcpy
、strcpy
、strncpy
、strcat
、strncat
、sprintf
、snprintf
、vsprintf
、vsnprintf
、gets
以及宽字符变体)时执行一些轻量级的检查,以检测一些缓冲区溢出错误。对于某些函数,还将检查参数的一致性;例如,当指定的标志包括O_CREAT
时,将检查是否已为open
提供了一个模式参数。并非所有问题都会被检测到,只有一些常见情况。如果将
_FORTIFY_SOURCE
设置为1,并且使用编译器优化级别1(gcc -O1
)及以上,则执行不应更改符合规范的程序行为的检查。将
_FORTIFY_SOURCE
设置为2后,会添加一些额外的检查,但某些符合规范的程序可能会失败。其中一些检查可以在编译时(通过头文件中实现的宏逻辑)进行,并导致编译器警告;其他检查发生在运行时,如果检查失败,则导致运行时错误。
使用此宏需要编译器支持,在
gcc
4.0版本及以上可用。
gcc -D_FORTIFY_SOURCE=1
仅在编译时添加检查(需要一些头文件,如#include <string.h>
)gcc -D_FORTIFY_SOURCE=2
还会在运行时添加检查(检测到缓冲区溢出将终止程序)_FORTIFY_SOURCE
级别2更安全,但是它是一种稍微有风险的编译策略。如果您使用它,请确保对编译代码进行非常强大的回归测试,以证明编译器没有引入任何意外的行为。-D_FORTIFY_SOURCE=1
至少添加了一项运行时检查:它启用了 __longjmp_chk
而不是 __longjmp
,前者会检查您是否在堆栈中向下跳转。 - Daniel Jourhttps://gcc.gnu.org/legacy-ml/gcc-patches/2004-09/msg02055.html比feature_test_macros(7)
更详细。
以下是相关摘录,经过轻微编辑/重新格式化以提高清晰度:
The difference between
-D_FORTIFY_SOURCE=1
and-D_FORTIFY_SOURCE=2
is e.g. for
struct S { struct T { char buf[5]; int x; } t; char buf[20]; } var;
With
-D_FORTIFY_SOURCE=1
,strcpy (&var.t.buf[1], "abcdefg");
is not considered an overflow (object is whole
var
), while with-D_FORTIFY_SOURCE=2
strcpy (&var.t.buf[1], "abcdefg");
will be considered a buffer overflow.
Another difference is that with
-D_FORTIFY_SOURCE=2
,%n
in format strings of the most common*printf
family functions is allowed only if it is stored in read-only memory (usually string literals,gettext
's_("%s string %n")
is fine too), but usually when an attacker attempts to exploit a format string vulnerability,%n
will be somewhere where the attacker could write it into.
=1
和=2
之间差异的一些详细信息)在这里;(2) 关于_FORTIFY_SOURCE
的“功能测试宏”手册页面在这里。 - ArjunShankar