Windows 上 cmakejs 配置 asan
1. 下载 Detours 并安装
git clone https://github.com/microsoft/Detours
cd Detours
nmake
2. 如果是 x64 项目,则打开 x64 Native Tools Command Prompt
命令行窗口,并找到 bin.X64 文件夹,运行使用 withdll
命令将 clang_rt.asan_dbg_dynamic-x86_64.dll
挂载到 node.exe 中,node.exe 路径默认为系统环境变量中设置的 node.exe 路径
D:\Detours\bin.X64>withdll /d:"C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.29.30133\bin\Hostx64\x64\clang_rt.asan_dbg_dynamic-x86_64.dll" node.exe
在 /d: 后面指定 clang_rt.asan_dbg_dynamic-x86_64.dll
的绝对路径
3. 在项目的 CMakeLists.txt
中添加 asan
命令,并编译出 .node 文件,如果项目还依赖其他的 .node 文件,那相关项目的 cmake
都需要添加 asan
命令
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /fsanitize=address /Zi")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /fsanitize=address /Zi")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /DEBUG")
set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded$<$<CONFIG:Debug>:Debug>DLL")
add_definitions(-D_DEBUG)
endif()
4. 使用 node
命令运行 js 文件,即可查看相关的内存泄漏信息
比如我在项目文件中添加下面有内存问题的代码
char *x = (char *)malloc(2000);
strcpy(x, "hello");
free(x);
printf("%s",x);
运行后,会显示在 msr_ohos.c
的 935 行分配了内存,并在 937 行释放了内存,又在 938 行调用了 printf
命令,从而出错了
0x142809a20080 is located 0 bytes inside of 2000-byte region [0x142809a20080,0x142809a20850)
freed by thread T0 here:
#0 0x7fffa1a10062 (C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.29.30133\bin\HostX64\x64\clang_rt.asan_dbg_dynamic-x86_64.dll+0x180050062)
#1 0x7fffb4a73030 in msr_napi_register D:\msr\src\platform\ohos\msr_ohos.c:937
#2 0x7fffb4a772cc in create_addon D:\msr\src\platform\ohos\msr_ohos.c:976
#3 0x7fffb4a7735c in napi_register_module_v1 D:\msr\src\platform\ohos\msr_ohos.c:993
#4 0x7ff61724d045 (C:\Program Files\nodejs\node.exe+0x14028d045)
#5 0x7ff617248d29 (C:\Program Files\nodejs\node.exe+0x140288d29)
previously allocated by thread T0 here:
#0 0x7fffa1a101d2 (C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.29.30133\bin\HostX64\x64\clang_rt.asan_dbg_dynamic-x86_64.dll+0x1800501d2)
#1 0x7fffb4a73006 in msr_napi_register D:\msr\src\platform\ohos\msr_ohos.c:935
#2 0x7fffb4a772cc in create_addon D:\msr\src\platform\ohos\msr_ohos.c:976
#3 0x7fffb4a7735c in napi_register_module_v1 D:\msr\src\platform\ohos\msr_ohos.c:993
#4 0x7ff61724d045 (C:\Program Files\nodejs\node.exe+0x14028d045)
#5 0x7ff617248d29 (C:\Program Files\nodejs\node.exe+0x140288d29)
5. 因为 node 运行 js 文件时,会默认延迟加载 node.exe,所以我们可以先将原始的 node.exe 备份,并将已注入 clang_rt.asan_dbg_dynamic-x86_64.dll 的 node.exe 命名为 node.exe,即替换为原始的 node.exe
$ cmake-js compile -D
info TOOL Using Visual Studio 16 generator, as specified from commandline.
info CMD CONFIGURE
info RUN [
info RUN 'cmake',
info RUN 'D:\\msr\\projects\\ohos\\cmakejs',
info RUN '--no-warn-unused-cli',
info RUN '-G',
info RUN 'Visual Studio 16',
info RUN '-DCMAKE_JS_VERSION=7.3.0',
info RUN '-DCMAKE_BUILD_TYPE=Debug',
info RUN '-DCMAKE_RUNTIME_OUTPUT_DIRECTORY=D:\\msr\\projects\\ohos\\cmakejs\\build',
info RUN '-DCMAKE_MSVC_RUNTIME_LIBRARY=MultiThreaded$<$<CONFIG:Debug>:Debug>',
info RUN '-DCMAKE_JS_INC=C:\\Users\\sunjinlei\\.cmake-js\\node-x64\\v18.17.1\\include\\node',
info RUN '-DCMAKE_JS_SRC=C:/Users/sunjinlei/AppData/Roaming/npm/node_modules/cmake-js/lib/cpp/win_delay_load_hook.cc',
info RUN '-DNODE_RUNTIME=node',
info RUN '-DNODE_RUNTIMEVERSION=18.17.1',
info RUN '-DNODE_ARCH=x64',
info RUN '-DCMAKE_JS_LIB=C:\\Users\\sunjinlei\\.cmake-js\\node-x64\\v18.17.1\\win-x64\\node.lib',
info RUN '-DCMAKE_SHARED_LINKER_FLAGS=/DELAYLOAD:NODE.EXE',
info RUN '-Djs_G=Visual Studio 16',
info RUN '-Djs_arch=x64'
info RUN ]
参考文章:Debugging random memory corruption with ASAN in a Node.js addon on Windows with MSVC