summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTimothy Pearson <kb9vqf@pearsoncomputing.net>2013-08-26 10:32:41 -0500
committerTimothy Pearson <kb9vqf@pearsoncomputing.net>2013-08-26 10:32:41 -0500
commit9d76cb942d54c5e8edec59d90644326219b1c4a0 (patch)
tree5f4a5474c61c923e4bbffae76ed082ae4605c452
parentcb9c3ed914b0b1578a3fcaea3e35add08cc0bdfb (diff)
downloadtdelibs-9d76cb942d54c5e8edec59d90644326219b1c4a0.tar.gz
tdelibs-9d76cb942d54c5e8edec59d90644326219b1c4a0.zip
Disable suspend/hibernate if $HOME is a network file system
This resolves Bug 1615
-rw-r--r--tdecore/tdehw/tderootsystemdevice.cpp32
-rw-r--r--tdecore/tdehw/tdestoragedevice.cpp54
-rw-r--r--tdecore/tdehw/tdestoragedevice.h7
3 files changed, 93 insertions, 0 deletions
diff --git a/tdecore/tdehw/tderootsystemdevice.cpp b/tdecore/tdehw/tderootsystemdevice.cpp
index 86a92340c..3f12b4d5a 100644
--- a/tdecore/tdehw/tderootsystemdevice.cpp
+++ b/tdecore/tdehw/tderootsystemdevice.cpp
@@ -18,6 +18,7 @@
*/
#include "tderootsystemdevice.h"
+#include "tdestoragedevice.h"
#include <unistd.h>
@@ -27,6 +28,7 @@
#include "tdeglobal.h"
#include "tdeconfig.h"
#include "tdeapplication.h"
+#include "kstandarddirs.h"
#include "config.h"
@@ -38,6 +40,16 @@
#include <tqdbusconnection.h>
#endif // defined(WITH_TDEHWLIB_DAEMONS) || defined(WITH_UPOWER) || defined(WITH_DEVKITPOWER) || defined(WITH_HAL) || defined(WITH_CONSOLEKIT)
+bool isNetworkFileSystem(TQString fileSystemType) {
+ if ((fileSystemType.startsWith("nfs"))
+ || (fileSystemType == "cifs")
+ ) {
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
TDERootSystemDevice::TDERootSystemDevice(TDEGenericDeviceType::TDEGenericDeviceType dt, TQString dn) : TDEGenericDevice(dt, dn) {
m_hibernationSpace = -1;
}
@@ -97,6 +109,12 @@ bool TDERootSystemDevice::canSetHibernationMethod() {
}
bool TDERootSystemDevice::canStandby() {
+ // Network file systems mounted on $HOME typically cause nasty suspend/resume failures
+ // See Bug 1615 for details
+ if (isNetworkFileSystem(TDEStorageDevice::determineFileSystemType(TDEGlobal::dirs()->localtdedir()))) {
+ return FALSE;
+ }
+
TQString statenode = "/sys/power/state";
int rval = access (statenode.ascii(), W_OK);
if (rval == 0) {
@@ -125,9 +143,17 @@ bool TDERootSystemDevice::canStandby() {
}
}
#endif // WITH_TDEHWLIB_DAEMONS
+
+ return FALSE;
}
bool TDERootSystemDevice::canSuspend() {
+ // Network file systems mounted on $HOME typically cause nasty suspend/resume failures
+ // See Bug 1615 for details
+ if (isNetworkFileSystem(TDEStorageDevice::determineFileSystemType(TDEGlobal::dirs()->localtdedir()))) {
+ return FALSE;
+ }
+
TQString statenode = "/sys/power/state";
int rval = access (statenode.ascii(), W_OK);
if (rval == 0) {
@@ -223,6 +249,12 @@ bool TDERootSystemDevice::canSuspend() {
}
bool TDERootSystemDevice::canHibernate() {
+ // Network file systems mounted on $HOME typically cause nasty suspend/resume failures
+ // See Bug 1615 for details
+ if (isNetworkFileSystem(TDEStorageDevice::determineFileSystemType(TDEGlobal::dirs()->localtdedir()))) {
+ return FALSE;
+ }
+
TQString statenode = "/sys/power/state";
int rval = access (statenode.ascii(), W_OK);
if (rval == 0) {
diff --git a/tdecore/tdehw/tdestoragedevice.cpp b/tdecore/tdehw/tdestoragedevice.cpp
index f13146b00..3824f488e 100644
--- a/tdecore/tdehw/tdestoragedevice.cpp
+++ b/tdecore/tdehw/tdestoragedevice.cpp
@@ -21,6 +21,7 @@
#include <unistd.h>
#include <fcntl.h>
+#include <sys/stat.h>
#include <sys/ioctl.h>
#include <linux/cdrom.h>
@@ -769,4 +770,57 @@ bool TDEStorageDevice::unmountDevice(TQString* errRet, int* retcode) {
return false;
}
+TQString TDEStorageDevice::determineFileSystemType(TQString path) {
+ TQStringList mountTable;
+ TQString prevPath = path;
+ dev_t prevDev = 0;
+ int pos;
+ struct stat directory_info;
+ if (path.startsWith("/")) {
+ stat(path.ascii(), &directory_info);
+ prevDev = directory_info.st_dev;
+ // Walk the directory tree up to the root, checking for any change in st_dev
+ // If a change is found, the previous value of path is the mount point itself
+ while (path != "/") {
+ pos = path.findRev("/", -1, TRUE);
+ if (pos < 0) {
+ break;
+ }
+ path = path.mid(0, pos);
+ if (path == "") {
+ path = "/";
+ }
+ stat(path.ascii(), &directory_info);
+ if (directory_info.st_dev != prevDev) {
+ break;
+ }
+ prevPath = path;
+ prevDev = directory_info.st_dev;
+ }
+ }
+
+ // Read in mount table
+ mountTable.clear();
+ TQFile file( "/proc/mounts" );
+ if ( file.open( IO_ReadOnly ) ) {
+ TQTextStream stream( &file );
+ while ( !stream.atEnd() ) {
+ mountTable.append(stream.readLine());
+ }
+ file.close();
+ }
+
+ // Parse mount table
+ TQStringList::Iterator it;
+ for ( it = mountTable.begin(); it != mountTable.end(); ++it ) {
+ TQStringList mountInfo = TQStringList::split(" ", (*it), true);
+ if ((*mountInfo.at(1)) == prevPath) {
+ return (*mountInfo.at(2));
+ }
+ }
+
+ // Unknown file system type
+ return TQString::null;
+}
+
#include "tdestoragedevice.moc"
diff --git a/tdecore/tdehw/tdestoragedevice.h b/tdecore/tdehw/tdestoragedevice.h
index 6e6270f9e..1199510a4 100644
--- a/tdecore/tdehw/tdestoragedevice.h
+++ b/tdecore/tdehw/tdestoragedevice.h
@@ -290,6 +290,13 @@ class TDECORE_EXPORT TDEStorageDevice : public TDEGenericDevice
*/
bool ejectDrive();
+ /**
+ * @param path Full path to arbitrary file or directory
+ * @return TQString with type of file system containing the given file,
+ * or TQString::null if file system type unknown
+ */
+ static TQString determineFileSystemType(TQString path);
+
protected:
/**
* @param a TQString with the disk or partition label, if any