CacheManager: std::ofstream constructor error due to missing .c_str() call on std::wstring
https://github.com/openvinotoolkit/openvino/blob/bdc01107d989310c6efa7dd61c7fa5743c971f1d/src/inference/src/cache_manager.hpp#L128
I encountered a compilation error while building the OpenVINO project, specifically in the cache_manager.hpp file. The error occurs when attempting to construct a std::ofstream object with a std::wstring argument without first calling .c_str().
Error Message:
src/inference/src/cache_manager.hpp:129:91: error: no matching function for call to ‘std::basic_ofstream<wchar_t>::basic_ofstream(std::wstring, std::_Ios_Openmode)’
129 | std::wofstream stream(getBlobFile(id), std::ios_base::binary | std::wofstream::out);
Proposed Fix:
To resolve the error, I suggest modifying the line to convert the std::wstring returned by getBlobFile(id) to a const char* using the .c_str() method before passing it to the std::ofstream constructor.
std::ofstream stream(getBlobFile(id).c_str(), std::ios_base::binary | std::ofstream::out);
...
auto blobFileName = getBlobFile(id).c_str();
Justification:
std::ofstream does not have an overload that accepts std::wstring directly. The .c_str() method is necessary to provide the correct type (const char*) expected by the constructor.
Hi @max-my Could you please send this patch as PR to OpenVINO repo?
The error you're encountering is due to the fact that std::ofstream does not support std::wstring directly. Instead, it expects a const char* or std::string. To fix this, you need to convert the std::wstring to a std::string or const char* before passing it to the std::ofstream constructor.Here’s how you can modify the code to resolve the compilation error:Convert std::wstring to std::string:
This approach involves converting the std::wstring to std::string and then using the std::string with std::ofstream.
Use std::wofstream for wide characters:
If you need to handle wide characters, you should use std::wofstream instead of std::ofstream.
Solution 1: Convert std::wstring to std::string
#include
// Assuming getBlobFile(id) returns a std::wstring std::wstring getBlobFile(int id);
void someFunction(int id) { // Convert std::wstring to std::string std::wstring wstr = getBlobFile(id); std::string str(wstr.begin(), wstr.end());
// Use the converted std::string with std::ofstream
std::ofstream stream(str.c_str(), std::ios_base::binary | std::ofstream::out);
// ... rest of your code
}
Solution 2: Use std::wofstream for wide charactersIf you need to handle wide characters, you should use std::wofstream:
#include
// Assuming getBlobFile(id) returns a std::wstring std::wstring getBlobFile(int id);
void someFunction(int id) { // Use std::wofstream for wide characters std::wofstream stream(getBlobFile(id), std::ios_base::binary | std::wofstream::out); // ... rest of your code }
Explanation:Choose the solution that best fits your needs. If you don't need to handle wide characters specifically, the first solution is generally more straightforward. If you do need to handle wide characters, the second solution is more appropriate.
maxmy kindly check it
kindlly check the above text which i made first it contains the solution if it helps u
The error you're encountering is due to the fact that std::ofstream does not support std::wstring directly. Instead, it expects a const char* or std::string. To fix this, you need to convert the std::wstring to a std::string or const char* before passing it to the std::ofstream constructor.Here’s how you can modify the code to resolve the compilation error:Convert std::wstring to std::string: This approach involves converting the std::wstring to std::string and then using the std::string with std::ofstream. Use std::wofstream for wide characters: If you need to handle wide characters, you should use std::wofstream instead of std::ofstream. Solution 1: Convert std::wstring to std::string #include #include
// Assuming getBlobFile(id) returns a std::wstring std::wstring getBlobFile(int id);
void someFunction(int id) { // Convert std::wstring to std::string std::wstring wstr = getBlobFile(id); std::string str(wstr.begin(), wstr.end());
// Use the converted std::string with std::ofstream std::ofstream stream(str.c_str(), std::ios_base::binary | std::ofstream::out); // ... rest of your code}
Solution 2: Use std::wofstream for wide charactersIf you need to handle wide characters, you should use std::wofstream: #include #include
// Assuming getBlobFile(id) returns a std::wstring std::wstring getBlobFile(int id);
void someFunction(int id) { // Use std::wofstream for wide characters std::wofstream stream(getBlobFile(id), std::ios_base::binary | std::wofstream::out); // ... rest of your code }
Explanation:Choose the solution that best fits your needs. If you don't need to handle wide characters specifically, the first solution is generally more straightforward. If you do need to handle wide characters, the second solution is more appropriate.
Thank you for providing the two solutions. After careful review and testing, I've found that the first solution is well-suited for addressing the specific error we're encountering. While experimenting with the second solution, I encountered the need for additional code modifications due to the incompatibility of writer(stream); and reader(stream); with std::wofstream. The first solution, however, presents a more straightforward and efficient approach to achieving our desired outcome.
Hi @max-my Could you please send this patch as PR to OpenVINO repo?
Yes, I'd be happy to contribute the patch to the OpenVINO repository. I'll prepare the PR with the necessary details and descriptions shortly. Thank you for the opportunity to contribute.
I'm glad you liked the solution and that I could contribute to the project on GitHub; it was my first open source contribution.
DID IT FIX UR PROBLEM
I get a similar error in a different part of the code
openvino/src/core/src/pass/serialize.cpp:1266:77: error: no matching function for call to 'std::basic_ofstream<char>::basic_ofstream(const std::__cxx11::basic_string<wchar_t>&, std::_Ios_Openmode)'
1266 | std::ofstream bin_file(binPath_ref, std::ios::out | std::ios::binary);
| ^
This is using the very popular msys2/MINGW64. I have not updated it in a while; so. currently on gcc 14.1.0.
Hello @max-my, have you created a PR? If not, let's reopen the task and allow someone else to do it. I'm reopening the task.
.take
Thanks for being interested in this issue. It looks like this ticket is already assigned to a contributor. Please communicate with the assigned contributor to confirm the status of the issue.
@praasz I unassigned you because it forbids contributors from .taking the issue.
.take
Thank you for looking into this issue! Please let us know if you have any questions or require any help.
The proposed solution/fix for of using the method ".c_str()" for converting the output of "getBlobFile()" form std::wstring to cons char* (but actually for std::wstring the "c_str()" returns const wchar_t*) will work fine for windows as it handles the const wchar_t* by itself, but on other systems like linux (which use UTF-8, they have only const char* filenames) this may cause some issues.
So the solution I am proposing is that create a variable of std::filesystem::path and store the return value of getBlobFile() into that and later use that variable to pass the path into the std::ofstream constructor as argument.
i have launched a pull request for the issue which tries to use what i mentioned in the solution earlier but as I am new to github I am having issues with the PR check, i request for help regarding those.