我有一个有趣的问题,我不确定为什么。
inline void mergeWChar(wchar_t*& dest, const wchar_t* source) {
if (dest == nullptr) {
dest = const_cast<wchar_t*>(source);
return;
}
int size = wcslen(dest);
wcscat_s(dest, size, source);
}
inline void test() {
wchar_t* msg = nullptr;
wchar_t* t = L"BLA.BLA.BLA";
mergeWChar(msg, L"Ts is jut a phrase in order to test my function");
mergeWChar(msg, t);
}
我正在尝试制作一个将使用wcscat_s函数合并更难的2个wchar_t *的函数,但由于某种原因无法正常工作,并且我收到此错误消息。
在ConsoleApplication1.exe中的0x5D8C3A18(ucrtbased.dll)引发异常:0xC0000005:访问冲突写入位置0x0082DD60。
此外,我已经检查了这两个问题,对我没有帮助。
wcscat_s function - buffer error
我不能做什么
我正在处理一些旧代码,我可以不使用某些东西,例如:
答案 0 :(得分:1)
这里:
mergeWChar(msg, t);
msg
指向字符串文字L"Ts is jut a phrase in order to test my function"
。您不能修改字符串文字。
您想要这个:
inline void mergeWChar(wchar_t*& dest, const wchar_t* source) {
if (dest == nullptr) {
dest = const_cast<wchar_t*>(source);
return;
}
wchar_t *newdest = (wchar_t*)malloc((wcslen(dest) + wcslen(source) + 1) * sizeof *newdest);
wcscpy(newdest, dest); // the *_s functions are useless here
wcscat(newdest, source); // as you know that newdest point to
// a long enough buffer
dest = newdest;
}
免责声明:为简洁起见,此处不进行错误检查。
问题的根源是mergeWChar
函数的不良设计和const_cast<wchar_t*>
的可疑使用,这基本上使您可以将指向常量字符串的指针分配给普通指针,然后再将其分配给普通指针您需要修改该常量内存,而该内存最终会失败。
但是这种设计存在一个问题:您不能释放分配的内存,因为dest
指针不一定是通过malloc
继承的指针。因此,以下设计是更好的IMO:
inline void mergeWChar(wchar_t*& dest, const wchar_t* source) {
int size = (dest ? wcslen(dest) : 0) + wcslen(source) + 1;
wchar_t *newdest = (wchar_t*)malloc(size * sizeof *newdest);
if (dest)
wcscpy(newdest, dest);
else
newdest[0] = 0;
wcscat(newdest, source);
dest = newdest;
}
那样,就不会出现难看的强制转换,也不会出现指向常量内存的非const指针的风险,并且您可以确保无论如何都可以释放由mergeWChar
修改的指针。代价是您需要更多的内存。
用法示例:
...
wchar_t* msg = nullptr;
wchar_t* t = L"BLA.BLA.BLA";
mergeWChar(msg, L"Ts is jut a phrase in order to test my function");
mergeWChar(msg, t);
...
free(msg);
...