ABV.UNICODE.NNTS_MAP
映射函数中非 null 终止的字符串导致的缓冲区溢出
ABV.UNICODE.NNTS_MAP 可检查 MultiByteToWideChar 和 WideCharToMultiByte 映射函数中由非 null 终止的字符串导致的缓冲区溢出状况。通常,当任一函数未自动终止输出字符串时,该检查器便会检测到相应状况。
有关 MultiByteToWideChar 和 WideCharToMultiByte 映射函数运算的详细信息,请参阅 MSDN 网站。
漏洞与风险
如果未正确使用这些映射函数,将导致缓冲区溢出,从而威胁应用程序的安全。为避免在将来发生这种状况,请务必以 null 终止函数的输出字符串。
漏洞代码示例
复制
#include <windows.h>
#include <stdio.h>
#include <wchar.h>
#include <string.h>
int main()
{
wchar_t wstrTestNNTS[] = L"0123456789ABCDEF";
char strTestNNTS[16];
int res = WideCharToMultiByte(CP_UTF8, 0, wstrTestNNTS, -1, strTestNNTS, 16, NULL, NULL);
printf("res = %d\n", res);
printf("strTestNNTS = %s\n", strTestNNTS);
return 0;
}
Klocwork 为“WideCharToMultiByte”函数生成了一个 NNTS 报告,因为此函数不保证在字符串末尾写入以 null 终止的字符。如果使用目标缓冲区时未检查返回值,非 null 终止的字符串可能溢出。
修正代码示例
复制
#include <windows.h>
#include <stdio.h>
#include <wchar.h>
#include <string.h>
int main()
{
wchar_t wstrTestNNTS[] = L"0123456789ABCDEF";
char strTestNNTS[16];
int res = WideCharToMultiByte(CP_UTF8, 0, wstrTestNNTS, -1, strTestNNTS, 16, NULL, NULL);
if (res == sizeof(strTestNNTS)) {
strTestNNTS[res-1] = NULL;
} else {
strTestNNTS[res] = NULL;
}
printf("res = %d\n", res);
printf("strTestNNTS = %s\n", strTestNNTS);
return 0;
}
在该修正代码示例中,在第 11 到 14 行中检查了函数的返回值,如果需要,可添加以 null 终止的字符。
相关检查器
外部指导
扩展
此检查器可通过 Klocwork 知识库进行扩展。有关详情,请参阅调整 C/C++ 分析。