Files
pixiv_downloader/exif/patchs/basicio.cpp.patch
2023-05-17 10:38:42 +08:00

94 lines
3.0 KiB
Diff

diff --git a/src/basicio.cpp b/src/basicio.cpp
index 9ab953a3..68780d3a 100644
--- a/src/basicio.cpp
+++ b/src/basicio.cpp
@@ -64,6 +64,64 @@ void ReplaceStringInPlace(std::string& subject, std::string_view search, std::st
} // namespace
namespace Exiv2 {
+#if defined(__MINGW__) || (defined(WIN32) && !defined(__CYGWIN__))
+ /// Remove unsuportted options flags
+ unsigned long getMultiByteToWideCharOptions(const unsigned long ori_options, unsigned int cp) {
+ if (cp == CP_ACP) cp = GetACP();
+ if (cp == CP_OEMCP) cp = GetOEMCP();
+ switch (cp)
+ {
+ case 50220:
+ case 50221:
+ case 50222:
+ case 50225:
+ case 50227:
+ case 50229:
+ case CP_UTF7:
+ case 42:
+ return 0;
+ default:
+ break;
+ }
+ if (cp >= 57002 && cp <= 57011) return 0;
+ if (cp == CP_UTF8 || cp == 54936) {
+ return MB_ERR_INVALID_CHARS & ori_options;
+ }
+ return ori_options;
+ }
+ bool str_to_wstr(std::wstring& out, std::string inp, unsigned int cp) {
+ DWORD opt = getMultiByteToWideCharOptions(MB_ERR_INVALID_CHARS, cp);
+ int wlen = MultiByteToWideChar(cp, opt, inp.c_str(), inp.length(), nullptr, 0);
+ if (!wlen) {
+ return false;
+ }
+ wchar_t* wstr = (wchar_t*)malloc(wlen * sizeof(wchar_t));
+ if (wstr == nullptr) {
+ return false;
+ }
+ if (!MultiByteToWideChar(cp, opt, inp.c_str(), inp.length(), wstr, wlen)) {
+ free(wstr);
+ return false;
+ }
+ out = std::wstring(wstr, wlen);
+ free(wstr);
+ return true;
+ }
+ FILE* win32_fopen(const char* path, const char* mode) {
+ std::string p(path), m(mode);
+ FILE* f = nullptr;
+ unsigned long cps[] = { CP_UTF8, CP_ACP, CP_OEMCP };
+ for (int i = 0; i < 3; i++) {
+ std::wstring wp, wm;
+ if (str_to_wstr(wp, p, cps[i]) && str_to_wstr(wm, m, cps[i])) {
+ if ((f = _wfopen(wp.c_str(), wm.c_str()))) {
+ return f;
+ }
+ }
+ }
+ return std::fopen(path, mode);
+ }
+#endif
void BasicIo::readOrThrow(byte* buf, size_t rcount, ErrorCode err) {
const size_t nread = read(buf, rcount);
Internal::enforce(nread == rcount, err);
@@ -173,7 +231,11 @@ int FileIo::Impl::switchMode(OpMode opMode) {
}
openMode_ = "r+b";
opMode_ = opSeek;
+#if defined(__MINGW__) || (defined(WIN32) && !defined(__CYGWIN__))
+ fp_ = win32_fopen(path_.c_str(), openMode_.c_str());
+#else
fp_ = std::fopen(path_.c_str(), openMode_.c_str());
+#endif
if (!fp_)
return 1;
#ifdef _WIN32
@@ -509,7 +571,11 @@ int FileIo::open(const std::string& mode) {
close();
p_->openMode_ = mode;
p_->opMode_ = Impl::opSeek;
+#if defined(__MINGW__) || (defined(WIN32) && !defined(__CYGWIN__))
+ p_->fp_ = win32_fopen(path().c_str(), mode.c_str());
+#else
p_->fp_ = ::fopen(path().c_str(), mode.c_str());
+#endif
if (!p_->fp_)
return 1;
return 0;