当前不会命中断点:Dll 调试
This breakpoint will not be currently be hit: Dll debugging
我有一个用 /mt 编译的 dll。该 dll 导出一个函数 'main',我使用 rundll32 从 cmd 调用它。此函数将从我包含的 header 中调用另一个函数,该函数应该采用存储在环境下的注册表中的一些设置。想象一下我在做什么,这里有一些代码:
Dll:main
#include "..\Header.h"
extern "C" void APIEXP WINAPI main(HWND hwnd, HINSTANCE hinst, LPSTR lpszCmdLine, int nCmdShow){
char *parentPath = nullptr;
size_t sz;
DWORD buffSize;
block; //this is a messagebox
buffSize = sizeof(client.pc_name);
if (!GetComputerNameA(client.pc_name, &buffSize)) strcpy(client.pc_name, "");
if (!GetUserNameA(client.user_name, &buffSize)) strcpy(client.user_name, "");
client.os_time = time(0);
client.version = Version;
client.os_version = Exe_version;
TextSetting("pc_description", client.pc_description);
TextSetting("custom_name", client.custom_name);
}
Header
LPSTR TextSetting(LPSTR setting,LPSTR buff) {
//Returns all data in buff
DWORD type, sz;
msg("dll: ","function called");
if (RegGetValueA(HKEY_CURRENT_USER,"Environment", setting, RRF_RT_REG_SZ | RRF_RT_REG_MULTI_SZ, &type, (LPBYTE)buff, &sz) != ERROR_SUCCESS) {
buff[0] = 0;
msg("sdsv: ", "err");
return buff;
}
return buff;
}
LPSTR con(LPSTR dest, LPSTR a, LPSTR b, LPSTR c) {
//c is optional and default: ""
strcpy(dest, a);
strcat(dest, b);
strcat(dest, c);
return dest;
}
VOID msg(LPSTR app,LPSTR a) {
char temp_buffer[2048];
con(temp_buffer , app,a, "\n");
OutputDebugStringA(temp_buffer);
}
上面显示的代码完美运行:这里的兴趣点是 main 中的 TextSetting。它按应有的方式检索数据。但是当我从 TextSetting 中删除 msg("dll: ","function called");
时,它只是给出了一个错误(return 代码不是 ERROR_SUCCESS)。此外,我什至无法调试 function.When 我将调试器附加到 rundll32 进程我在 TextSettings 中的 if 语句上设置的断点给出了标题中提到的警告。
这是工作:
这很奇怪:
我注意到一些额外的事情:
如果我调用 msg 或 con 函数它会起作用(看起来 con 中使用的 str* 函数使代码起作用)。更进一步:如果我只在 if 语句之前使用 strcpy 和 strcat,我也可以工作。我不知道问题是什么(也许是一些缓冲区溢出奇迹般地修复了 if 语句中使用的代码?)
RegGetValue API 函数要求最后一个参数是缓冲区的大小。
您在那里传递了一个未初始化的变量。
这可能是它在 release/debug 之间具有不同行为的原因。
RegGetValue
我有一个用 /mt 编译的 dll。该 dll 导出一个函数 'main',我使用 rundll32 从 cmd 调用它。此函数将从我包含的 header 中调用另一个函数,该函数应该采用存储在环境下的注册表中的一些设置。想象一下我在做什么,这里有一些代码:
Dll:main
#include "..\Header.h"
extern "C" void APIEXP WINAPI main(HWND hwnd, HINSTANCE hinst, LPSTR lpszCmdLine, int nCmdShow){
char *parentPath = nullptr;
size_t sz;
DWORD buffSize;
block; //this is a messagebox
buffSize = sizeof(client.pc_name);
if (!GetComputerNameA(client.pc_name, &buffSize)) strcpy(client.pc_name, "");
if (!GetUserNameA(client.user_name, &buffSize)) strcpy(client.user_name, "");
client.os_time = time(0);
client.version = Version;
client.os_version = Exe_version;
TextSetting("pc_description", client.pc_description);
TextSetting("custom_name", client.custom_name);
}
Header
LPSTR TextSetting(LPSTR setting,LPSTR buff) {
//Returns all data in buff
DWORD type, sz;
msg("dll: ","function called");
if (RegGetValueA(HKEY_CURRENT_USER,"Environment", setting, RRF_RT_REG_SZ | RRF_RT_REG_MULTI_SZ, &type, (LPBYTE)buff, &sz) != ERROR_SUCCESS) {
buff[0] = 0;
msg("sdsv: ", "err");
return buff;
}
return buff;
}
LPSTR con(LPSTR dest, LPSTR a, LPSTR b, LPSTR c) {
//c is optional and default: ""
strcpy(dest, a);
strcat(dest, b);
strcat(dest, c);
return dest;
}
VOID msg(LPSTR app,LPSTR a) {
char temp_buffer[2048];
con(temp_buffer , app,a, "\n");
OutputDebugStringA(temp_buffer);
}
上面显示的代码完美运行:这里的兴趣点是 main 中的 TextSetting。它按应有的方式检索数据。但是当我从 TextSetting 中删除 msg("dll: ","function called");
时,它只是给出了一个错误(return 代码不是 ERROR_SUCCESS)。此外,我什至无法调试 function.When 我将调试器附加到 rundll32 进程我在 TextSettings 中的 if 语句上设置的断点给出了标题中提到的警告。
这是工作:
这很奇怪:
我注意到一些额外的事情: 如果我调用 msg 或 con 函数它会起作用(看起来 con 中使用的 str* 函数使代码起作用)。更进一步:如果我只在 if 语句之前使用 strcpy 和 strcat,我也可以工作。我不知道问题是什么(也许是一些缓冲区溢出奇迹般地修复了 if 语句中使用的代码?)
RegGetValue API 函数要求最后一个参数是缓冲区的大小。 您在那里传递了一个未初始化的变量。 这可能是它在 release/debug 之间具有不同行为的原因。 RegGetValue