diff options
author | Stephan Bergmann <sbergman@redhat.com> | 2019-09-10 10:52:57 +0200 |
---|---|---|
committer | Stephan Bergmann <sbergman@redhat.com> | 2019-09-17 15:05:11 +0200 |
commit | caa211b62048ac5037b3fd4320f3eb4dea7b639d (patch) | |
tree | cf1768b435ed71363e34b56682435628545a7293 /sal/osl/unx/uunxapi.cxx | |
parent | b9ce783a4b8ea967281ed583842ee3d931d78ac7 (diff) |
Better handling of non--UTF-8 filesystem pathnames in sal/osl/unx/
The idea is to internally in sal/osl/unx/ use OString instead of OUString to
represent pathnames, so that the OString carries the actual bytes that make up
the pathname. At the boundary of translating between pathname OStrings and file
URL OUStrings, translate sequences of bytes that are valid according to
osl_getThreadTextEncoding() into UTF-8 and translate other bytes into individual
(percent-encoded) bytes in the file URL.
This change required duplicating some of the internal functionality in
sal/osl/unx/ for both OString and OUString, and to make part of sal/rtl/uri.cxx
accessible from sal/osl/unx/ via new sal/inc/uri_internal.hxx.
Change-Id: Id1ebaebe9e7f2d21f350f6b1a07849edee54331f
Reviewed-on: https://gerrit.libreoffice.org/78798
Tested-by: Jenkins
Reviewed-by: Stephan Bergmann <sbergman@redhat.com>
Diffstat (limited to 'sal/osl/unx/uunxapi.cxx')
-rw-r--r-- | sal/osl/unx/uunxapi.cxx | 74 |
1 files changed, 55 insertions, 19 deletions
diff --git a/sal/osl/unx/uunxapi.cxx b/sal/osl/unx/uunxapi.cxx index 45de25280980..1005140a2c91 100644 --- a/sal/osl/unx/uunxapi.cxx +++ b/sal/osl/unx/uunxapi.cxx @@ -31,7 +31,7 @@ #include <osl/detail/android-bootstrap.h> #endif -static OString OUStringToOString(const OUString& s) +OString osl::OUStringToOString(const OUString& s) { return OUStringToOString(s, osl_getThreadTextEncoding()); } @@ -156,9 +156,9 @@ static OString macxp_resolveAliasAndConvert(OString const & p) } #endif /* MACOSX */ -int osl::access(const OUString& pustrPath, int mode) +int osl::access(const OString& pstrPath, int mode) { - OString fn = OUStringToOString(pustrPath); + OString fn = pstrPath; #ifdef ANDROID if (fn == "/assets" || fn.startsWith("/assets/")) { @@ -194,16 +194,29 @@ int osl::access(const OUString& pustrPath, int mode) return result; } -bool osl::realpath(const OUString& pustrFileName, OUString& ppustrResolvedName) +namespace { + +OString toOString(OString const & s) { return s; } + +OString toOString(OUString const & s) { return osl::OUStringToOString(s); } + +template<typename T> T fromOString(OString const &) = delete; + +template<> OString fromOString(OString const & s) { return s; } + +template<> OUString fromOString(OString const & s) +{ return OStringToOUString(s, osl_getThreadTextEncoding()); } + +template<typename T> bool realpath_(const T& pstrFileName, T& ppstrResolvedName) { - OString fn = OUStringToOString(pustrFileName); + OString fn = toOString(pstrFileName); #ifdef ANDROID if (fn == "/assets" || fn.startsWith("/assets/")) { - if (osl::access(pustrFileName, F_OK) == -1) + if (osl::access(fn, F_OK) == -1) return false; - ppustrResolvedName = pustrFileName; + ppstrResolvedName = pstrFileName; return true; } @@ -216,7 +229,7 @@ bool osl::realpath(const OUString& pustrFileName, OUString& ppustrResolvedName) accessFilePathState *state = prepare_to_access_file_path(fn.getStr()); char rp[PATH_MAX]; - bool bRet = ::realpath(fn.getStr(), rp); + bool bRet = realpath(fn.getStr(), rp); int saved_errno = errno; if (!bRet) SAL_INFO("sal.file", "realpath(" << fn.getStr() << "): " << UnixErrnoString(saved_errno)); @@ -227,8 +240,7 @@ bool osl::realpath(const OUString& pustrFileName, OUString& ppustrResolvedName) if (bRet) { - ppustrResolvedName = OStringToOUString(OString(static_cast<sal_Char*>(rp)), - osl_getThreadTextEncoding()); + ppstrResolvedName = fromOString<T>(OString(static_cast<sal_Char*>(rp))); } errno = saved_errno; @@ -236,6 +248,18 @@ bool osl::realpath(const OUString& pustrFileName, OUString& ppustrResolvedName) return bRet; } +} + +bool osl::realpath(const OUString& pustrFileName, OUString& ppustrResolvedName) +{ + return realpath_(pustrFileName, ppustrResolvedName); +} + +bool osl::realpath(const OString& pstrFileName, OString& ppstrResolvedName) +{ + return realpath_(pstrFileName, ppstrResolvedName); +} + int stat_c(const char* cpPath, struct stat* buf) { #ifdef ANDROID @@ -286,9 +310,11 @@ int lstat_c(const char* cpPath, struct stat* buf) return result; } -int osl::lstat(const OUString& pustrPath, struct stat& buf) +namespace { + +template<typename T> int lstat_(const T& pstrPath, struct stat& buf) { - OString fn = OUStringToOString(pustrPath); + OString fn = toOString(pstrPath); #ifdef MACOSX fn = macxp_resolveAliasAndConvert(fn); @@ -297,20 +323,30 @@ int osl::lstat(const OUString& pustrPath, struct stat& buf) return lstat_c(fn.getStr(), &buf); } -int osl::mkdir(const OUString& path, mode_t mode) +} + +int osl::lstat(const OUString& pustrPath, struct stat& buf) +{ + return lstat_(pustrPath, buf); +} + +int osl::lstat(const OString& pstrPath, struct stat& buf) { - OString fn = OUStringToOString(path); + return lstat_(pstrPath, buf); +} - accessFilePathState *state = prepare_to_access_file_path(fn.getStr()); +int osl::mkdir(const OString& path, mode_t mode) +{ + accessFilePathState *state = prepare_to_access_file_path(path.getStr()); - int result = ::mkdir(OUStringToOString(path).getStr(), mode); + int result = ::mkdir(path.getStr(), mode); int saved_errno = errno; if (result == -1) - SAL_INFO("sal.file", "mkdir(" << OUStringToOString(path).getStr() << ",0" << std::oct << mode << std::dec << "): " << UnixErrnoString(saved_errno)); + SAL_INFO("sal.file", "mkdir(" << path << ",0" << std::oct << mode << std::dec << "): " << UnixErrnoString(saved_errno)); else - SAL_INFO("sal.file", "mkdir(" << OUStringToOString(path).getStr() << ",0" << std::oct << mode << std::dec << "): OK"); + SAL_INFO("sal.file", "mkdir(" << path << ",0" << std::oct << mode << std::dec << "): OK"); - done_accessing_file_path(fn.getStr(), state); + done_accessing_file_path(path.getStr(), state); errno = saved_errno; |