Add FileUtil and ProcessInfo classes.

This commit is contained in:
Nodir Temirkhodjaev 2017-08-26 14:39:19 +05:00
parent 0fad381aab
commit 9340d31f2d
9 changed files with 268 additions and 3 deletions

View File

@ -1,4 +1,5 @@
TEMPLATE = subdirs TEMPLATE = subdirs
SUBDIRS = \ SUBDIRS = \
fileutil \
logbuffer logbuffer

View File

@ -0,0 +1,9 @@
include(../common/Test.pri)
SOURCES += \
$$UIPATH/util/fileutil.cpp \
$$UIPATH/util/processinfo.cpp
HEADERS += \
$$UIPATH/util/fileutil.h \
$$UIPATH/util/processinfo.h

View File

@ -0,0 +1,30 @@
#include "test.h"
#include <QtTest>
#include "util/fileutil.h"
#include "util/processinfo.h"
void Test::paths()
{
const QString driveC("C:");
const QString dosNameC("\\Device\\HarddiskVolume1");
const QString subPath("\\test\\");
const QString path = driveC + subPath;
const QString dosPath = dosNameC + subPath;
QCOMPARE(FileUtil::dosNameToDrive(dosNameC), driveC);
QCOMPARE(FileUtil::driveToDosName(driveC), dosNameC);
QCOMPARE(FileUtil::dosPathToPath(dosPath), path);
QCOMPARE(FileUtil::pathToDosPath(path), dosPath);
}
void Test::process()
{
const ProcessInfo pi(ProcessInfo::currentPid());
QVERIFY(pi.isValid());
QVERIFY(!pi.dosPath().isEmpty());
}

15
src/tests/fileutil/test.h Normal file
View File

@ -0,0 +1,15 @@
#ifndef TEST_H
#define TEST_H
#include <QObject>
class Test : public QObject
{
Q_OBJECT
private slots:
void paths();
void process();
};
#endif // TEST_H

View File

@ -11,12 +11,16 @@ SOURCES += \
main.cpp \ main.cpp \
firewallLog/logbuffer.cpp \ firewallLog/logbuffer.cpp \
firewallLog/logentry.cpp \ firewallLog/logentry.cpp \
fortcommon.cpp fortcommon.cpp \
util/fileutil.cpp \
util/processinfo.cpp
HEADERS += \ HEADERS += \
firewallLog/logbuffer.h \ firewallLog/logbuffer.h \
firewallLog/logentry.h \ firewallLog/logentry.h \
fortcommon.h fortcommon.h \
util/fileutil.h \
util/processinfo.h
QML_FILES += \ QML_FILES += \
qml/*.qml qml/*.qml
@ -35,7 +39,7 @@ RESOURCES += fort_i18n.qrc
RESOURCES += fort_ini.qrc RESOURCES += fort_ini.qrc
# Windows # Windows
LIBS += -lfwpuclnt -lkernel32 -luser32 -luuid LIBS += -lfwpuclnt -lkernel32 -lpsapi -luser32 -luuid
RC_FILE = fort.rc RC_FILE = fort.rc
# Kernel Driver # Kernel Driver

70
src/ui/util/fileutil.cpp Normal file
View File

@ -0,0 +1,70 @@
#include "fileutil.h"
#include <QDir>
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
FileUtil::FileUtil(QObject *parent) :
QObject(parent)
{
Q_ASSERT(sizeof(wchar_t) == sizeof(QChar));
}
// Convert "\\Device\\HarddiskVolume1" to "C:"
QString FileUtil::dosNameToDrive(const QString &dosName)
{
const QString dosNameLower = dosName.toLower();
foreach (const QFileInfo &fi, QDir::drives()) {
const QString driveName = fi.path().left(2);
const QString driveDosName = driveToDosName(driveName);
if (dosNameLower == driveDosName.toLower()) {
return driveName;
}
}
return QString();
}
// Convert "C:" to "\\Device\\HarddiskVolume1"
QString FileUtil::driveToDosName(const QString &drive)
{
char driveName[3] = {drive.at(0).toLatin1(), ':', '\0'};
char buf[MAX_PATH];
const int len = QueryDosDeviceA((LPCSTR) driveName,
buf, MAX_PATH);
return (len > 0) ? QString::fromLatin1(buf)
: QString();
}
// Convert "\\Device\\HarddiskVolume1\\path" to "C:\\path"
QString FileUtil::dosPathToPath(const QString &dosPath)
{
const QLatin1Char sep('\\');
if (dosPath.startsWith(sep)) {
const int sepPos1 = dosPath.indexOf(sep, 1);
if (sepPos1 > 0) {
const int sepPos2 = dosPath.indexOf(sep, sepPos1 + 1);
if (sepPos2 > 0) {
const QString dosName = dosPath.left(sepPos2);
return dosNameToDrive(dosName) + dosPath.mid(sepPos2);
}
}
}
return dosPath;
}
// Convert "C:\\path" to "\\Device\\HarddiskVolume1\\path"
QString FileUtil::pathToDosPath(const QString &path)
{
const QString drive = path.left(2);
if (drive.at(0).isLetter() && drive.at(1) == QLatin1Char(':')) {
return driveToDosName(drive) + path.mid(2);
}
return path;
}

29
src/ui/util/fileutil.h Normal file
View File

@ -0,0 +1,29 @@
#ifndef FILEUTIL_H
#define FILEUTIL_H
#include <QObject>
#include <QHash>
class FileUtil : public QObject
{
Q_OBJECT
public:
explicit FileUtil(QObject *parent = nullptr);
// Convert DOS device name to drive letter (A: .. Z:)
static QString dosNameToDrive(const QString &dosName);
// Convert drive letter (A: .. Z:) to DOS device name
static QString driveToDosName(const QString &drive);
// Convert Native path to Win32 path
static QString dosPathToPath(const QString &dosPath);
// Convert Win32 path to Native path
static QString pathToDosPath(const QString &path);
private:
};
#endif // FILEUTIL_H

View File

@ -0,0 +1,63 @@
#include "processinfo.h"
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <psapi.h> /* GetProcessImageFileName */
#define PROC_PATH_MAX 65536
ProcessInfo::ProcessInfo(quint32 pid, QObject *parent) :
QObject(parent),
m_pid(pid),
m_handle(PROC_INVALID_HANDLE)
{
openProcess();
}
ProcessInfo::~ProcessInfo()
{
closeProcess();
}
quint32 ProcessInfo::currentPid()
{
return GetCurrentProcessId();
}
void ProcessInfo::openProcess()
{
if (m_pid == PROC_INVALID_PID)
return;
if (m_pid == currentPid()) {
m_handle = GetCurrentProcess();
} else {
const DWORD access = (PROCESS_QUERY_INFORMATION | PROCESS_VM_READ);
m_handle = OpenProcess(access, FALSE, m_pid);
}
}
void ProcessInfo::closeProcess()
{
if (isValid()) {
CloseHandle(m_handle);
m_handle = PROC_INVALID_HANDLE;
}
}
QString ProcessInfo::dosPath() const
{
if (isValid()) {
QByteArray buf(PROC_PATH_MAX * sizeof(wchar_t), Qt::Uninitialized);
wchar_t *p = (wchar_t *) buf.data();
const DWORD len = GetProcessImageFileNameW(
m_handle, (LPWSTR) p, PROC_PATH_MAX);
if (len) {
return QString::fromWCharArray(p, len);
}
}
return QString();
}

44
src/ui/util/processinfo.h Normal file
View File

@ -0,0 +1,44 @@
#ifndef PROCESSINFO_H
#define PROCESSINFO_H
#include <QObject>
typedef void *phandle_t;
#define PROC_INVALID_PID -1
#define PROC_INVALID_HANDLE nullptr
class ProcessInfo : public QObject
{
Q_OBJECT
Q_PROPERTY(quint32 pid READ pid CONSTANT)
public:
explicit ProcessInfo(quint32 pid = PROC_INVALID_PID,
QObject *parent = nullptr);
virtual ~ProcessInfo();
quint32 pid() const { return m_pid; }
bool isValid() const {
return m_pid != PROC_INVALID_PID
&& m_handle != PROC_INVALID_HANDLE;
}
static quint32 currentPid();
signals:
public slots:
QString dosPath() const;
private:
void openProcess();
void closeProcess();
private:
quint32 m_pid;
phandle_t m_handle;
};
#endif // PROCESSINFO_H