C++ 调用ReadFile后,程序在debug_heap.cpp中命中断点
这个函数应该从文件中读取字符串并返回它,但在调用ReadFile程序后,立即在第985行的debug_heap.cpp文件中点击断点C++ 调用ReadFile后,程序在debug_heap.cpp中命中断点,c++,winapi,C++,Winapi,这个函数应该从文件中读取字符串并返回它,但在调用ReadFile程序后,立即在第985行的debug_heap.cpp文件中点击断点 char* readFile() { char curDirectory[MAX_PATH]; GetCurrentDirectory(MAX_PATH, curDirectory); char filePath[MAX_PATH]; char *name = "\\data.txt"; sprintf_s(filePath, "%s%s", curDire
char* readFile()
{
char curDirectory[MAX_PATH];
GetCurrentDirectory(MAX_PATH, curDirectory);
char filePath[MAX_PATH];
char *name = "\\data.txt";
sprintf_s(filePath, "%s%s", curDirectory, name);
HANDLE hFile = CreateFile(filePath, GENERIC_ALL, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
if (hFile == INVALID_HANDLE_VALUE)
{
DisplayError("Can't Create File");
return NULL;
}
DWORD fileSize = GetFileSize(hFile, NULL);
char *buffer = new char[fileSize / 2 + 1];
DWORD bytesReaded;
if (ReadFile(hFile, buffer, fileSize, &bytesReaded, NULL) == 0)
{
DisplayError("Can't read File");
return NULL;
}
buffer[bytesReaded] = '\0';
CloseHandle(hFile);
return buffer;
}
这是因为您的代码写入的内容超出了缓冲区的末尾。您可以这样分配
缓冲区
:
char *buffer = new char[fileSize / 2 + 1];
但随后您尝试从文件中读取文件大小字节。您的分配应改为:
char *buffer = new char[fileSize + 1];
其他一些评论:
- 调用
sprintf\u s
可能会导致缓冲区溢出李>
由于C++中的代码,请使用<代码> STD::String < /C> >并使该类管理缓冲区。对于文件路径
和缓冲区
,都应该这样做。这将允许您避免当前代码的泄漏。例如,故障在ReadFile
泄漏内存后返回。而且它避免了调用代码释放内存的负担
- 如果代码在
ReadFile
之后接受失败返回,则也会泄漏文件句柄
bytesRead
应命名为bytesRead
,以使用正确的英语单词
- 没有真正的理由相信可执行文件位于当前工作目录中李>
这是因为您的代码写入的内容超出了缓冲区的末尾。您可以这样分配
缓冲区
:
char *buffer = new char[fileSize / 2 + 1];
但随后您尝试从文件中读取文件大小字节。您的分配应改为:
char *buffer = new char[fileSize + 1];
其他一些评论:
- 调用
sprintf\u s
可能会导致缓冲区溢出李>
由于C++中的代码,请使用<代码> STD::String < /C> >并使该类管理缓冲区。对于文件路径
和缓冲区
,都应该这样做。这将允许您避免当前代码的泄漏。例如,故障在ReadFile
泄漏内存后返回。而且它避免了调用代码释放内存的负担
- 如果代码在
ReadFile
之后接受失败返回,则也会泄漏文件句柄
bytesRead
应命名为bytesRead
,以使用正确的英语单词
- 没有真正的理由相信可执行文件位于当前工作目录中李>
你试着读文件大小
但你只分配新字符[fileSize/2+1]
你试着读文件大小
但你只分配新字符[fileSize/2+1]
关于最后一个要点,我在你的最后一个问题上告诉过你,但可能没有理解。当前目录并不总是可执行文件所在的目录。通常它是一个不同的目录。他也在泄漏句柄,最好用一个类或自定义删除器的唯一指针包装这些句柄。我是如何泄漏句柄的?文件句柄在函数末尾关闭。请参阅,这就是发明析构函数的原因。因为人们在C中泄漏,他们不知道为什么。如果ReadFile
失败会发生什么?如果在ReadFile
之后执行失败返回,则会泄漏内存和文件句柄。关于最后一个要点,我在你的最后一个问题中告诉过你,但可能没有理解。当前目录并不总是可执行文件所在的目录。通常它是一个不同的目录。他也在泄漏句柄,最好用一个类或自定义删除器的唯一指针包装这些句柄。我是如何泄漏句柄的?文件句柄在函数末尾关闭。请参阅,这就是发明析构函数的原因。因为人们在C中泄漏,他们不知道为什么。如果ReadFile
失败会发生什么情况?如果在ReadFile
之后执行失败返回,则会泄漏内存和文件句柄。