summaryrefslogtreecommitdiff
path: root/sal
diff options
context:
space:
mode:
authorTor Lillqvist <tml@iki.fi>2013-08-24 22:01:18 +0300
committerTor Lillqvist <tml@iki.fi>2013-08-25 00:29:18 +0300
commitfa9ef668fb8b0abfdf85d641048580fa7c2fee3e (patch)
tree44ec2474ab4842628c4906ae20cf1e1397b73d30 /sal
parent2599bc9d6723daee921e3bf65124928bf56c8241 (diff)
More work on a sandboxed LibreOffice on OS X
In particular, surround also the ftruncate() operation that osl_setFileSize() does with access through a security scope bookmark for the file, if available. This fixes file saving in a sandboxed LibreOffice. (But oh boy, does simply saving an ODT document go though a weird dance of file operations.) Luckily the C++ oslFileHandle abstraction keeps the pathname that the file was opened with, so even if ftruncate() as such takes only the file descriptor, we can get at the pathname to retrieve our security scope bookmark. Change-Id: I8acb1b2f3fb3ec0cea833697b7f1d4a1912ed551
Diffstat (limited to 'sal')
-rw-r--r--sal/osl/unx/file.cxx2
-rw-r--r--sal/osl/unx/uunxapi.cxx59
-rw-r--r--sal/osl/unx/uunxapi.h4
3 files changed, 50 insertions, 15 deletions
diff --git a/sal/osl/unx/file.cxx b/sal/osl/unx/file.cxx
index 9ed1892dc031..a0ef50eae0e7 100644
--- a/sal/osl/unx/file.cxx
+++ b/sal/osl/unx/file.cxx
@@ -307,7 +307,7 @@ sal_uInt64 FileHandle_Impl::getSize() const
oslFileError FileHandle_Impl::setSize (sal_uInt64 uSize)
{
off_t const nSize = sal::static_int_cast< off_t >(uSize);
- if (-1 == ftruncate (m_fd, nSize))
+ if (-1 == ftruncate_with_name (m_fd, nSize, m_strFilePath))
{
/* Failure. Save original result. Try fallback algorithm */
oslFileError result = oslTranslateFileError (OSL_FET_ERROR, errno);
diff --git a/sal/osl/unx/uunxapi.cxx b/sal/osl/unx/uunxapi.cxx
index 9b40644e8b27..7eb2ed910467 100644
--- a/sal/osl/unx/uunxapi.cxx
+++ b/sal/osl/unx/uunxapi.cxx
@@ -127,7 +127,6 @@ static rtl::OString macxp_resolveAliasAndConvert(rtl::OString p)
int access_u(const rtl_uString* pustrPath, int mode)
{
rtl::OString fn = OUStringToOString(pustrPath);
-#ifndef MACOSX
#ifdef ANDROID
if (strncmp(fn.getStr(), "/assets", sizeof("/assets")-1) == 0 &&
(fn.getStr()[sizeof("/assets")-1] == '\0' ||
@@ -144,18 +143,18 @@ int access_u(const rtl_uString* pustrPath, int mode)
return 0;
}
#endif
- return access(fn.getStr(), mode);
-#else
+
+#ifdef MACOSX
+ fn = macxp_resolveAliasAndConvert(fn);
+#endif
accessFilePathState *state = prepare_to_access_file_path(fn.getStr());
- int result = access(macxp_resolveAliasAndConvert(fn).getStr(), mode);
+ int result = access(fn.getStr(), mode);
done_accessing_file_path(fn.getStr(), state);
return result;
-
-#endif
}
sal_Bool realpath_u(const rtl_uString* pustrFileName, rtl_uString** ppustrResolvedName)
@@ -176,12 +175,12 @@ sal_Bool realpath_u(const rtl_uString* pustrFileName, rtl_uString** ppustrResolv
}
#endif
- accessFilePathState *state = prepare_to_access_file_path(fn.getStr());
-
#ifdef MACOSX
fn = macxp_resolveAliasAndConvert(fn);
#endif
+ accessFilePathState *state = prepare_to_access_file_path(fn.getStr());
+
char rp[PATH_MAX];
bool bRet = realpath(fn.getStr(), rp);
@@ -205,7 +204,14 @@ int stat_c(const char* cpPath, struct stat* buf)
cpPath[sizeof("/assets")-1] == '/'))
return lo_apk_lstat(cpPath, buf);
#endif
- return stat(cpPath, buf);
+
+ accessFilePathState *state = prepare_to_access_file_path(cpPath);
+
+ int result = stat(cpPath, buf);
+
+ done_accessing_file_path(cpPath, state);
+
+ return result;
}
int lstat_c(const char* cpPath, struct stat* buf)
@@ -229,11 +235,12 @@ int lstat_c(const char* cpPath, struct stat* buf)
int lstat_u(const rtl_uString* pustrPath, struct stat* buf)
{
rtl::OString fn = OUStringToOString(pustrPath);
-#ifndef MACOSX
- return lstat_c(fn.getStr(), buf);
-#else
- return lstat(macxp_resolveAliasAndConvert(fn).getStr(), buf);
+
+#ifdef MACOSX
+ fn = macxp_resolveAliasAndConvert(fn);
#endif
+
+ return lstat_c(fn.getStr(), buf);
}
int mkdir_u(const rtl_uString* path, mode_t mode)
@@ -271,4 +278,30 @@ int utime_c(const char *cpPath, struct utimbuf *times)
return result;
}
+int ftruncate_with_name(int fd, sal_uInt64 uSize, rtl_String* path)
+{
+ /* When sandboxed on OS X, ftruncate(), even if it takes an
+ * already open file descriptor which was retuned from an open()
+ * call already checked by the sandbox, still requires a security
+ * scope bookmark for the file to be active in case the file is
+ * one that the sandbox doesn't otherwise allow access to. Luckily
+ * LibreOffice usually calls ftruncate() through the helpful C++
+ * abstraction layer that keeps the pathname around.
+ */
+
+ rtl::OString fn = rtl::OString(path);
+
+#ifdef MACOSX
+ fn = macxp_resolveAliasAndConvert(fn);
+#endif
+
+ accessFilePathState *state = prepare_to_access_file_path(fn.getStr());
+
+ int result = ftruncate(fd, uSize);
+
+ done_accessing_file_path(fn.getStr(), state);
+
+ return result;
+}
+
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sal/osl/unx/uunxapi.h b/sal/osl/unx/uunxapi.h
index 0e4106e70742..3b431ad292e2 100644
--- a/sal/osl/unx/uunxapi.h
+++ b/sal/osl/unx/uunxapi.h
@@ -45,7 +45,7 @@ int access_u(const rtl_uString* pustrPath, int mode);
**********************************/
sal_Bool realpath_u(
const rtl_uString* pustrFileName,
- rtl_uString** ppustrResolvedName);
+ rtl_uString** ppustrResolvedName);
int stat_c(const char *cpPath, struct stat* buf);
@@ -59,6 +59,8 @@ int open_c(const char *cpPath, int oflag, int mode);
int utime_c(const char *cpPath, struct utimbuf *times);
+int ftruncate_with_name(int fd, sal_uInt64 uSize, rtl_String* path);
+
#ifdef __cplusplus
}
#endif