[英]Valgrind reports uninitialized value when calling wcstombs
I have stumbled on a Valgrind report that I can't manage to fix by myself. 我偶然发现了Valgrind报告,我无法自己解决。 I have a function that reads a Microsoft "unicode" string (a series of two-byte aligned wchar_t prefixed by a size) from a file.
我有一个函数,可以从文件中读取Microsoft“ unicode”字符串(一系列由大小写为前缀的两字节对齐的wchar_t)。 A sample file might look like this:
示例文件可能如下所示:
0004 0041 0041 0041 0041 ..A.A.A.A.
The following code sample reads the "unicode" string from the file and uses wcstombs to make a std::string out of it. 下面的代码示例从文件中读取“ unicode”字符串,并使用wcstombs从其中生成std :: string。
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <string>
#include <iostream>
#include <boost/shared_array.hpp>
#include <boost/cstdint.hpp>
std::string read_unicode_string(FILE* f)
{
std::wstring s = std::wstring();
wchar_t c;
boost::uint16_t size;
if (2 !=fread(&size, 1, 2, f)) {
return "";
}
// Microsoft's "unicode" strings are word aligned.
for (unsigned int i = 0 ; i < size ; ++i)
{
if (2 != fread(&c, 1, 2, f)) {
break;
}
s += c;
}
s += L'\0';
// Convert the wstring into a string
boost::shared_array<char> conv = boost::shared_array<char>(new char[s.size() + 1]);
memset(conv.get(), 0, sizeof(char) * (s.size() + 1));
wcstombs(conv.get(), s.c_str(), s.size());
return std::string(conv.get());
}
int main(int argc, char** argv)
{
FILE* f = fopen("test", "rb");
if (f == NULL) {
return 1;
}
std::cout << read_unicode_string(f) << std::endl;
fclose(f);
return 0;
}
Although it does seem to work, valgrind reports that some jump in wcstombs depends on an initialized value: 尽管它确实起作用,但valgrind报告说wcstombs中的某些跳跃取决于初始化值:
==8440== Conditional jump or move depends on uninitialised value(s)
==8440== at 0x56606C2: wcsnlen (wcsnlen.c:40)
==8440== by 0x565FCF0: wcsrtombs (wcsrtombs.c:110)
==8440== by 0x56101A0: wcstombs (wcstombs.c:35)
==8440== by 0x401488: read_unicode_string(_IO_FILE*) (test.cpp:32)
==8440== by 0x40157C: main (test.cpp:42)
==8440==
==8440== Conditional jump or move depends on uninitialised value(s)
==8440== at 0x55F2D5B: __gconv_transform_internal_ascii (loop.c:332)
==8440== by 0x565FD41: wcsrtombs (wcsrtombs.c:116)
==8440== by 0x56101A0: wcstombs (wcstombs.c:35)
==8440== by 0x401488: read_unicode_string(_IO_FILE*) (test.cpp:32)
==8440== by 0x40157C: main (test.cpp:42)
I've been looking, but I feel that I have initialized every variable properly. 我一直在寻找,但是我觉得我已经正确地初始化了每个变量。 Does anyone see the problem in my code?
有人在我的代码中看到问题了吗?
Thanks in advance for your help! 在此先感谢您的帮助!
That is a nasty error! 那是一个讨厌的错误! If
sizeof(wchar_t)
is greater than 2 (lets say 4) the wide string 's' will get (2) uninitialized bytes which are reported as uninitialized value(s) in wcstombs
. 如果
sizeof(wchar_t)
大于2(假设为4),则宽字符串s将获得(2)个未初始化的字节,这些字节在wcstombs
中报告为未初始化的值。
The problem is not in your code. 问题不在您的代码中。 The call stacks show that the uninitialized variable is used somewhere inside the implementation of
wcstombs
- all you can do is try to tell valgrind not to inspect that library or filter those two messages from valgrind's output. 调用堆栈显示未初始化的变量在
wcstombs
实现的内部使用了-您所能做的就是尝试告诉valgrind不要检查该库或从valgrind的输出中过滤掉这两个消息。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.