summaryrefslogtreecommitdiffstats
path: root/src/corelib/io/qstandardpaths.cpp
diff options
context:
space:
mode:
authorDavid Faure <faure@kde.org>2011-10-21 20:57:31 +0200
committerQt by Nokia <qt-info@nokia.com>2011-10-23 00:56:51 +0200
commit4b72c3f4347bfb8493e877d26f172f2e18c69a83 (patch)
tree636fc5ca4a92678ae1c11b0d48483b23b1d1127f /src/corelib/io/qstandardpaths.cpp
parentfa0ad643a6f0018544197e4eb80e8cf2cbf700cf (diff)
Add QStandardPaths::findExecutable.
Change-Id: If30a83622e2ac5af48e47a38b8f70fce73044d74 Reviewed-by: Thiago Macieira (Intel) <thiago.macieira@intel.com>
Diffstat (limited to 'src/corelib/io/qstandardpaths.cpp')
-rw-r--r--src/corelib/io/qstandardpaths.cpp87
1 files changed, 87 insertions, 0 deletions
diff --git a/src/corelib/io/qstandardpaths.cpp b/src/corelib/io/qstandardpaths.cpp
index 58a6ab13eb..86d0f7424d 100644
--- a/src/corelib/io/qstandardpaths.cpp
+++ b/src/corelib/io/qstandardpaths.cpp
@@ -176,6 +176,93 @@ QStringList QStandardPaths::locateAll(StandardLocation type, const QString &file
return result;
}
+#ifdef Q_OS_WIN
+static QStringList executableExtensions()
+{
+ QStringList ret = QString::fromLocal8Bit(qgetenv("PATHEXT")).split(QLatin1Char(';'));
+ if (!ret.contains(QLatin1String(".exe"), Qt::CaseInsensitive)) {
+ // If %PATHEXT% does not contain .exe, it is either empty, malformed, or distorted in ways that we cannot support, anyway.
+ ret.clear();
+ ret << QLatin1String(".exe")
+ << QLatin1String(".com")
+ << QLatin1String(".bat")
+ << QLatin1String(".cmd");
+ }
+ return ret;
+}
+#endif
+
+static QString checkExecutable(const QString &path)
+{
+ const QFileInfo info(path);
+ if (info.isBundle())
+ return info.bundleName();
+ if (info.isFile() && info.isExecutable())
+ return QDir::cleanPath(path);
+ return QString();
+}
+
+/*!
+ Finds the executable named \a executableName in the paths specified by \a paths,
+ or the system paths if \a paths is empty.
+
+ On most operating systems the system path is determined by the PATH environment variable.
+
+ The directories where to search for the executable can be set in the \a paths argument.
+ To search in both your own paths and the system paths, call findExecutable twice, once with
+ \a paths set and once with \a paths empty.
+
+ Symlinks are not resolved, in order to preserve behavior for the case of executables
+ whose behavior depends on the name they are invoked with.
+
+ \note On Windows, the usual executable extensions (from the PATHEXT environment variable)
+ are automatically appended, so that for instance findExecutable("foo") will find foo.exe
+ or foo.bat if present.
+
+ Returns the absolute file path to the executable, or an empty string if not found.
+ */
+QString QStandardPaths::findExecutable(const QString &executableName, const QStringList &paths)
+{
+ if (QFileInfo(executableName).isAbsolute())
+ return checkExecutable(executableName);
+
+ QStringList searchPaths = paths;
+ if (paths.isEmpty()) {
+ QByteArray pEnv = qgetenv("PATH");
+#if defined(Q_OS_WIN) || defined(Q_OS_SYMBIAN)
+ const QLatin1Char pathSep(';');
+#else
+ const QLatin1Char pathSep(':');
+#endif
+ searchPaths = QString::fromLocal8Bit(pEnv.constData()).split(pathSep, QString::SkipEmptyParts);
+ }
+
+ QDir currentDir = QDir::current();
+ QString absPath;
+#ifdef Q_OS_WIN
+ static QStringList executable_extensions = executableExtensions();
+#endif
+
+ for (QStringList::const_iterator p = searchPaths.constBegin(); p != searchPaths.constEnd(); ++p) {
+ const QString candidate = currentDir.absoluteFilePath(*p + QLatin1Char('/') + executableName);
+#ifdef Q_OS_WIN
+ const QString extension = QLatin1Char('.') + QFileInfo(executableName).suffix();
+ if (!executable_extensions.contains(extension, Qt::CaseInsensitive)) {
+ foreach (const QString &extension, executable_extensions) {
+ absPath = checkExecutable(candidate + extension.toLower());
+ if (!absPath.isEmpty())
+ break;
+ }
+ }
+#endif
+ absPath = checkExecutable(candidate);
+ if (!absPath.isEmpty()) {
+ break;
+ }
+ }
+ return absPath;
+}
+
/*!
\fn QString QStandardPaths::displayName(StandardLocation type)