From 33c5852834229495016bc43ad2b046115dd49aa6 Mon Sep 17 00:00:00 2001 From: Kirill Polyakov Date: Tue, 13 Feb 2024 20:25:30 +0300 Subject: [PATCH 1/2] Fix bug #66436 --- DesktopEditor/common/Path.cpp | 58 +++++++++++++++++++ DesktopEditor/common/Path.h | 1 + .../raster/Metafile/svg/SvgObjects/CImage.cpp | 57 +++--------------- HtmlFile2/htmlfile2.cpp | 11 +++- 4 files changed, 77 insertions(+), 50 deletions(-) diff --git a/DesktopEditor/common/Path.cpp b/DesktopEditor/common/Path.cpp index 3df17d28f92..02dbafcbdea 100644 --- a/DesktopEditor/common/Path.cpp +++ b/DesktopEditor/common/Path.cpp @@ -31,6 +31,7 @@ */ #include "Path.h" #include "File.h" +#include #if defined(_WIN32) || defined (_WIN64) #include @@ -191,4 +192,61 @@ namespace NSSystemPath { return NormalizePathTemplate(strFileName, canHead); } + + std::wstring ShortenPath(const std::wstring &strPath, const bool& bRemoveExternalPath) + { + std::stack arStack; + std::wstring wsToken; + + for (size_t i = 0; i < strPath.size(); ++i) + { + if (L'/' == strPath[i] || L'\\' == strPath[i]) + { + if (L".." == wsToken) + { + if (!arStack.empty() && L".." != arStack.top()) + arStack.pop(); + else + arStack.push(wsToken); + } + else if (L"." != wsToken && !wsToken.empty()) + arStack.push(wsToken); + + wsToken.clear(); + } + else + wsToken += strPath[i]; + } + + if (L".." == wsToken) + { + if (!arStack.empty() && L".." == arStack.top()) + arStack.pop(); + else + arStack.push(wsToken); + } + else if (L"." != wsToken && !wsToken.empty()) + arStack.push(wsToken); + + wsToken.clear(); + + if (arStack.empty()) + return std::wstring(); + + std::wstring wsNewPath; + + while (!arStack.empty()) + { + if (bRemoveExternalPath && L".." == arStack.top()) + break; + + wsNewPath = arStack.top() + L'/' + wsNewPath; + arStack.pop(); + } + + wsNewPath.pop_back(); + + return wsNewPath; + } + } diff --git a/DesktopEditor/common/Path.h b/DesktopEditor/common/Path.h index a1dcf0d9be7..af620583744 100644 --- a/DesktopEditor/common/Path.h +++ b/DesktopEditor/common/Path.h @@ -43,6 +43,7 @@ namespace NSSystemPath KERNEL_DECL std::wstring Combine(const std::wstring& strLeft, const std::wstring& strRight); KERNEL_DECL std::string NormalizePath(const std::string& strFileName, const bool& canHead = false); KERNEL_DECL std::wstring NormalizePath(const std::wstring& strFileName, const bool& canHead = false); + KERNEL_DECL std::wstring ShortenPath(const std::wstring& strPath, const bool& bRemoveExternalPath = false); } #endif //_BUILD_PATH_CROSSPLATFORM_H_ diff --git a/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp b/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp index 68360e41bc5..7dc39c6862b 100644 --- a/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp +++ b/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp @@ -3,56 +3,11 @@ #include "../CSvgFile.h" #include "../../graphics/Image.h" #include "../../../BgraFrame.h" - -#include +#include "../../common/Path.h" +#include "../../Common/ProcessEnv.h" namespace SVG { - std::wstring ShortenPath(const std::wstring& wsPath) - { - std::stack arStack; - std::wstring wsToken; - std::wstring wsNewPath; - - std::function checkToken = [&]() - { - if (L".." == wsToken) - { - if (!arStack.empty() && L".." != arStack.top()) - arStack.pop(); - else - arStack.push(wsToken); - } - else if (L"." != wsToken && !wsToken.empty()) - arStack.push(wsToken); - - wsToken.clear(); - }; - - for (size_t i = 0; i < wsPath.size(); ++i) - { - if (L'/' == wsPath[i] || L'\\' == wsPath[i]) - checkToken(); - else - wsToken += wsPath[i]; - } - - checkToken(); - - if (arStack.empty()) - return std::wstring(); - - while (!arStack.empty()) - { - wsNewPath = arStack.top() + L'/' + wsNewPath; - arStack.pop(); - } - - wsNewPath.pop_back(); - - return wsNewPath; - } - CImage::CImage(XmlUtils::CXmlNode& oNode, CRenderedObject* pParent) : CRenderedObject(oNode, pParent) { @@ -106,9 +61,13 @@ namespace SVG } #ifndef METAFILE_DISABLE_FILESYSTEM - std::wstring wsFilePath = ShortenPath(m_wsHref); + std::wstring wsFilePath = NSSystemPath::ShortenPath(m_wsHref); + + bool bIsAllowExternalLocalFiles = true; + if (NSProcessEnv::IsPresent(NSProcessEnv::Converter::gc_allowPrivateIP)) + bIsAllowExternalLocalFiles = NSProcessEnv::GetBoolValue(NSProcessEnv::Converter::gc_allowPrivateIP); - if (!wsFilePath.empty() && L'.' != wsFilePath[0]) + if (bIsAllowExternalLocalFiles || (!wsFilePath.empty() && L'.' != wsFilePath[0])) { wsFilePath = pFile->GetWorkingDirectory() + L'/' + wsFilePath; diff --git a/HtmlFile2/htmlfile2.cpp b/HtmlFile2/htmlfile2.cpp index c56b3b2bc70..0a1e06856a5 100644 --- a/HtmlFile2/htmlfile2.cpp +++ b/HtmlFile2/htmlfile2.cpp @@ -2144,7 +2144,16 @@ class CHtmlFile2_Private size_t nHRefLen = sSVG.find(L"\"", nHRef); if(nHRefLen == std::wstring::npos) break; - std::wstring sImageName = sSVG.substr(nHRef, nHRefLen - nHRef); + + std::wstring sImageName = NSSystemPath::ShortenPath(sSVG.substr(nHRef, nHRefLen - nHRef)); + + bool bIsAllowExternalLocalFiles = true; + if (NSProcessEnv::IsPresent(NSProcessEnv::Converter::gc_allowPrivateIP)) + bIsAllowExternalLocalFiles = NSProcessEnv::GetBoolValue(NSProcessEnv::Converter::gc_allowPrivateIP); + + if (!bIsAllowExternalLocalFiles && !sImageName.empty() && L'.' == sImageName[0]) + break; + std::wstring sTIN(sImageName); sTIN.erase(std::remove_if(sTIN.begin(), sTIN.end(), [] (wchar_t ch) { return std::iswspace(ch) || (ch == L'^'); }), sTIN.end()); sTIN = NSFile::GetFileName(sTIN); From a6a73ffe3a25e0ec33b5af5809bc81ef9fa0048c Mon Sep 17 00:00:00 2001 From: Kirill Polyakov Date: Wed, 14 Feb 2024 13:20:08 +0300 Subject: [PATCH 2/2] Refactoring --- .../raster/Metafile/svg/SvgObjects/CImage.cpp | 12 +++---- HtmlFile2/htmlfile2.cpp | 36 ++++++++++++++----- 2 files changed, 33 insertions(+), 15 deletions(-) diff --git a/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp b/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp index 7dc39c6862b..62839cb9766 100644 --- a/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp +++ b/DesktopEditor/raster/Metafile/svg/SvgObjects/CImage.cpp @@ -67,13 +67,13 @@ namespace SVG if (NSProcessEnv::IsPresent(NSProcessEnv::Converter::gc_allowPrivateIP)) bIsAllowExternalLocalFiles = NSProcessEnv::GetBoolValue(NSProcessEnv::Converter::gc_allowPrivateIP); - if (bIsAllowExternalLocalFiles || (!wsFilePath.empty() && L'.' != wsFilePath[0])) - { - wsFilePath = pFile->GetWorkingDirectory() + L'/' + wsFilePath; + if (!bIsAllowExternalLocalFiles && wsFilePath.length() >= 3 && L"../" == wsFilePath.substr(0, 3)) + return true; - if (!NSFile::CFileBinary::Exists(wsFilePath) || !NSFile::CFileBinary::ReadAllBytes(wsFilePath, &pBuffer, ulSize)) - return false; - } + wsFilePath = pFile->GetWorkingDirectory() + L'/' + wsFilePath; + + if (!NSFile::CFileBinary::Exists(wsFilePath) || !NSFile::CFileBinary::ReadAllBytes(wsFilePath, &pBuffer, ulSize)) + return false; #endif if (NULL == pBuffer) diff --git a/HtmlFile2/htmlfile2.cpp b/HtmlFile2/htmlfile2.cpp index 0a1e06856a5..9326a9e5d69 100644 --- a/HtmlFile2/htmlfile2.cpp +++ b/HtmlFile2/htmlfile2.cpp @@ -102,6 +102,25 @@ std::wstring EncodeXmlString(const std::wstring& s) return sRes; } +bool GetStatusUsingExternalLocalFiles() +{ + if (NSProcessEnv::IsPresent(NSProcessEnv::Converter::gc_allowPrivateIP)) + return NSProcessEnv::GetBoolValue(NSProcessEnv::Converter::gc_allowPrivateIP); + + return true; +} + +bool CanUseThisPath(const std::wstring& wsPath, bool bIsAllowExternalLocalFiles) +{ + if (bIsAllowExternalLocalFiles) + return true; + + if (wsPath.length() >= 3 && L"../" == wsPath.substr(0, 3)) + return false; + + return true; +} + class CHtmlFile2_Private { public: @@ -1849,9 +1868,12 @@ class CHtmlFile2_Private return; } - bool bIsAllowExternalLocalFiles = true; - if (NSProcessEnv::IsPresent(NSProcessEnv::Converter::gc_allowPrivateIP)) - bIsAllowExternalLocalFiles = NSProcessEnv::GetBoolValue(NSProcessEnv::Converter::gc_allowPrivateIP); + const bool bIsAllowExternalLocalFiles = GetStatusUsingExternalLocalFiles(); + + sSrcM = NSSystemPath::ShortenPath(sSrcM); + + if (!CanUseThisPath(sSrcM, bIsAllowExternalLocalFiles)) + return; int nImageId = -1; std::wstring sImageSrc, sExtention; @@ -2145,13 +2167,9 @@ class CHtmlFile2_Private if(nHRefLen == std::wstring::npos) break; - std::wstring sImageName = NSSystemPath::ShortenPath(sSVG.substr(nHRef, nHRefLen - nHRef)); - - bool bIsAllowExternalLocalFiles = true; - if (NSProcessEnv::IsPresent(NSProcessEnv::Converter::gc_allowPrivateIP)) - bIsAllowExternalLocalFiles = NSProcessEnv::GetBoolValue(NSProcessEnv::Converter::gc_allowPrivateIP); + const std::wstring sImageName = NSSystemPath::ShortenPath(sSVG.substr(nHRef, nHRefLen - nHRef)); - if (!bIsAllowExternalLocalFiles && !sImageName.empty() && L'.' == sImageName[0]) + if (!CanUseThisPath(sImageName, GetStatusUsingExternalLocalFiles())) break; std::wstring sTIN(sImageName);