Dev*_*lar 12 c language-lawyer
在C11中,K.3.7.4.1 memset_s函数,我发现了一些相当混乱的文本:
不同于
memset,memset_s必须严格按照(5.1.2.3)中所述的抽象机规则评估对函数的任何调用。也就是说,对该memset_s函数的任何调用均应假定指示,s并且n将来可能会访问该内存,因此必须包含指示的值c。
这意味着,memset是不(必须的)“进行评价严格按照抽象机的规则”。(所引用的章节是5.1.2.3 程序执行。)
我不明白标准memset在这里明确排除了的余地memset_s,以及这对任何一个函数的实现者意味着什么。
Jon*_*ler 12
假设您已经读过密码:
{
char password[128];
if (fgets(password, sizeof(password), stdin) != 0)
{
password[strcspn(password), "\n\r"]) = '\0';
validate_password(password);
memset(password, '\0', sizeof(password));
}
}
Run Code Online (Sandbox Code Playgroud)
您已经仔细修改了密码,以免意外被发现。
不幸的是,允许编译器省略该memset()调用,因为password不再使用它。的规则memset_s()意味着不能忽略该呼叫;该password变量必须被清零,不管优化。
memset_s(password, sizeof(password), '\0', sizeof(password));
Run Code Online (Sandbox Code Playgroud)
这是附件K中为数不多的真正有用的功能之一。(我们可以辩论必须重复使用大小的优点。但是,在更一般的情况下,第二个大小可以是变量,而不是常量,然后第一个大小将成为运行时保护,以防止变量失控。 )
请注意,此要求放在编译器而不是库上。该memset_s()功能将正确的行为,如果它被调用时,就如同memset()将正确的行为,如果它被调用。讨论中的规则说,编译器必须调用memset_s(),即使它可以省略该调用,memset()因为不再使用该变量。
| 归档时间: |
|
| 查看次数: |
126 次 |
| 最近记录: |