apply new project structure, fixed spelling, separate lib
parent
e3ddb73feb
commit
60dfb202fd
|
|
@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.0.0)
|
||||||
|
|
||||||
option(TESTS "Build all tests" OFF)
|
option(TESTS "Build all tests" OFF)
|
||||||
|
|
||||||
project(IntegrityCheck)
|
project(IntegrityApp)
|
||||||
|
|
||||||
include(CPack)
|
include(CPack)
|
||||||
|
|
||||||
|
|
@ -26,12 +26,10 @@ find_package(Qt5 COMPONENTS Core Gui Widgets REQUIRED)
|
||||||
set(SOURCES
|
set(SOURCES
|
||||||
src/main.cpp
|
src/main.cpp
|
||||||
src/mainwindow.cpp
|
src/mainwindow.cpp
|
||||||
src/integretychecker.cpp
|
|
||||||
)
|
)
|
||||||
|
|
||||||
set(HEADERS
|
set(HEADERS
|
||||||
inc/mainwindow.h
|
inc/mainwindow.h
|
||||||
src/integretychecker.cpp
|
|
||||||
)
|
)
|
||||||
|
|
||||||
set(FORMS
|
set(FORMS
|
||||||
|
|
@ -45,10 +43,16 @@ add_executable(${PROJECT_NAME}
|
||||||
)
|
)
|
||||||
target_include_directories(${PROJECT_NAME} PRIVATE
|
target_include_directories(${PROJECT_NAME} PRIVATE
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}
|
${CMAKE_CURRENT_SOURCE_DIR}
|
||||||
./cryptopp/
|
#./cryptopp/
|
||||||
|
./integritycheck/inc
|
||||||
)
|
)
|
||||||
target_link_libraries(${PROJECT_NAME}
|
target_link_libraries(${PROJECT_NAME}
|
||||||
${CMAKE_SOURCE_DIR}/cryptopp/libcryptopp.a
|
# ${CMAKE_SOURCE_DIR}/cryptopp/libcryptopp.a
|
||||||
|
IntegrityCheck
|
||||||
Qt5::Core
|
Qt5::Core
|
||||||
Qt5::Widgets
|
Qt5::Widgets
|
||||||
)
|
)
|
||||||
|
|
||||||
|
set(BUILD_TESTING OFF)
|
||||||
|
add_subdirectory(libs/IntegrityCheck)
|
||||||
|
add_subdirectory(libs/cryptopp)
|
||||||
|
|
@ -1,6 +1,5 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "../inc/integretychecker.h"
|
|
||||||
#include <QMainWindow>
|
#include <QMainWindow>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,22 @@
|
||||||
|
cmake_minimum_required(VERSION 3.0.0)
|
||||||
|
|
||||||
|
project(IntegrityCheck)
|
||||||
|
|
||||||
|
set( SOURCES
|
||||||
|
src/integritycheck.cpp
|
||||||
|
)
|
||||||
|
|
||||||
|
set( HEADERS
|
||||||
|
IntegrityCheck/integritycheck.h
|
||||||
|
)
|
||||||
|
|
||||||
|
add_library(${PROJECT_NAME} STATIC ${SOURCES} )
|
||||||
|
|
||||||
|
target_include_directories(${PROJECT_NAME} PUBLIC
|
||||||
|
inc
|
||||||
|
${CMAKE_CURRENT_SOURCE_DIR}/../cryptopp
|
||||||
|
)
|
||||||
|
|
||||||
|
target_link_libraries(${PROJECT_NAME} PUBLIC
|
||||||
|
cryptopp-static
|
||||||
|
)
|
||||||
|
|
@ -1,12 +1,12 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "../cryptopp/rsa.h"
|
#include "rsa.h"
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
class IntegretyCheck {
|
class IntegrityCheck {
|
||||||
public:
|
public:
|
||||||
IntegretyCheck();
|
IntegrityCheck();
|
||||||
IntegretyCheck(const std::string &appPath, bool genKeyPair);
|
IntegrityCheck(const std::string &appPath, bool genKeyPair);
|
||||||
|
|
||||||
bool loadKeyFile(const std::string &app);
|
bool loadKeyFile(const std::string &app);
|
||||||
bool saveKeyFile(const std::string &app);
|
bool saveKeyFile(const std::string &app);
|
||||||
|
|
@ -29,7 +29,15 @@ public:
|
||||||
static const std::string SIGNATURE_MARKER;
|
static const std::string SIGNATURE_MARKER;
|
||||||
static const std::string HASH_FILE_DIVIDER;
|
static const std::string HASH_FILE_DIVIDER;
|
||||||
|
|
||||||
|
enum E_STATE {
|
||||||
|
STATE_APPDIR_OK = 0x01,
|
||||||
|
STATE_PUBLIC_KEY = 0x02,
|
||||||
|
STATE_HASH_LIST = 0x04,
|
||||||
|
STATE_PRIVATE_KEY = 0x08
|
||||||
|
};
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
E_STATE m_state;
|
||||||
CryptoPP::RSA::PublicKey m_publicKey;
|
CryptoPP::RSA::PublicKey m_publicKey;
|
||||||
CryptoPP::RSA::PrivateKey m_privateKey;
|
CryptoPP::RSA::PrivateKey m_privateKey;
|
||||||
bool extractHashAndFile(const std::string &line, std::string &hash,
|
bool extractHashAndFile(const std::string &line, std::string &hash,
|
||||||
|
|
@ -1,20 +1,20 @@
|
||||||
#include "../inc/integretychecker.h"
|
#include "IntegrityCheck/integritycheck.h"
|
||||||
|
|
||||||
#include "../cryptopp/base64.h"
|
#include "base64.h"
|
||||||
#include "../cryptopp/files.h"
|
#include "files.h"
|
||||||
#include "../cryptopp/osrng.h"
|
#include "osrng.h"
|
||||||
#include "../cryptopp/rsa.h"
|
#include "rsa.h"
|
||||||
|
|
||||||
#include <filesystem>
|
#include <filesystem>
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
namespace fs = std::filesystem;
|
namespace fs = std::filesystem;
|
||||||
|
|
||||||
const int IntegretyCheck::KEY_SIZE = 2048;
|
const int IntegrityCheck::KEY_SIZE = 2048;
|
||||||
const std::string IntegretyCheck::HASH_FILE = "hashlist.sha256";
|
const std::string IntegrityCheck::HASH_FILE = "hashlist.sha256";
|
||||||
const std::string IntegretyCheck::KEY_FILE = "appKey.pub";
|
const std::string IntegrityCheck::KEY_FILE = "appKey.pub";
|
||||||
const std::string IntegretyCheck::SIGNATURE_MARKER = "### signature ###\n";
|
const std::string IntegrityCheck::SIGNATURE_MARKER = "### signature ###\n";
|
||||||
const std::string IntegretyCheck::HASH_FILE_DIVIDER = " *";
|
const std::string IntegrityCheck::HASH_FILE_DIVIDER = " *";
|
||||||
|
|
||||||
std::string string_to_hex(const std::string &input) {
|
std::string string_to_hex(const std::string &input) {
|
||||||
static const char *const lut = "0123456789ABCDEF";
|
static const char *const lut = "0123456789ABCDEF";
|
||||||
|
|
@ -30,9 +30,9 @@ std::string string_to_hex(const std::string &input) {
|
||||||
return output;
|
return output;
|
||||||
}
|
}
|
||||||
|
|
||||||
IntegretyCheck::IntegretyCheck() {}
|
IntegrityCheck::IntegrityCheck() {}
|
||||||
|
|
||||||
IntegretyCheck::IntegretyCheck(const std::string &appPath, bool genKeyPair) {
|
IntegrityCheck::IntegrityCheck(const std::string &appPath, bool genKeyPair) {
|
||||||
if (genKeyPair) {
|
if (genKeyPair) {
|
||||||
generateKeyPair();
|
generateKeyPair();
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -40,7 +40,7 @@ IntegretyCheck::IntegretyCheck(const std::string &appPath, bool genKeyPair) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IntegretyCheck::loadKeyFile(const std::string &app) {
|
bool IntegrityCheck::loadKeyFile(const std::string &app) {
|
||||||
fs::path appPath(app);
|
fs::path appPath(app);
|
||||||
if (fs::exists(appPath / KEY_FILE)) {
|
if (fs::exists(appPath / KEY_FILE)) {
|
||||||
CryptoPP::FileSource input((appPath / KEY_FILE).c_str(), true);
|
CryptoPP::FileSource input((appPath / KEY_FILE).c_str(), true);
|
||||||
|
|
@ -50,7 +50,7 @@ bool IntegretyCheck::loadKeyFile(const std::string &app) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IntegretyCheck::saveKeyFile(const std::string &app) {
|
bool IntegrityCheck::saveKeyFile(const std::string &app) {
|
||||||
///@todo https://github.com/noloader/cryptopp-pem
|
///@todo https://github.com/noloader/cryptopp-pem
|
||||||
fs::path appPath(app);
|
fs::path appPath(app);
|
||||||
CryptoPP::FileSink output((appPath / KEY_FILE).c_str());
|
CryptoPP::FileSink output((appPath / KEY_FILE).c_str());
|
||||||
|
|
@ -58,7 +58,7 @@ bool IntegretyCheck::saveKeyFile(const std::string &app) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IntegretyCheck::generateKeyPair() {
|
bool IntegrityCheck::generateKeyPair() {
|
||||||
CryptoPP::AutoSeededRandomPool rng;
|
CryptoPP::AutoSeededRandomPool rng;
|
||||||
|
|
||||||
CryptoPP::InvertibleRSAFunction params;
|
CryptoPP::InvertibleRSAFunction params;
|
||||||
|
|
@ -69,7 +69,7 @@ bool IntegretyCheck::generateKeyPair() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string IntegretyCheck::generateHashList(const std::string &app) {
|
std::string IntegrityCheck::generateHashList(const std::string &app) {
|
||||||
std::stringstream hashlist;
|
std::stringstream hashlist;
|
||||||
fs::path appPath(app);
|
fs::path appPath(app);
|
||||||
std::string p = appPath.string();
|
std::string p = appPath.string();
|
||||||
|
|
@ -94,7 +94,7 @@ std::string IntegretyCheck::generateHashList(const std::string &app) {
|
||||||
return hashlist.str();
|
return hashlist.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string IntegretyCheck::generateFileHash(const std::string &filepath) {
|
std::string IntegrityCheck::generateFileHash(const std::string &filepath) {
|
||||||
std::ifstream in(filepath);
|
std::ifstream in(filepath);
|
||||||
std::string contents((std::istreambuf_iterator<char>(in)),
|
std::string contents((std::istreambuf_iterator<char>(in)),
|
||||||
std::istreambuf_iterator<char>());
|
std::istreambuf_iterator<char>());
|
||||||
|
|
@ -108,7 +108,7 @@ std::string IntegretyCheck::generateFileHash(const std::string &filepath) {
|
||||||
std::string((char *)abDigest, CryptoPP::SHA256::DIGESTSIZE));
|
std::string((char *)abDigest, CryptoPP::SHA256::DIGESTSIZE));
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IntegretyCheck::extractHashAndFile(const std::string &line,
|
bool IntegrityCheck::extractHashAndFile(const std::string &line,
|
||||||
std::string &hash,
|
std::string &hash,
|
||||||
std::string &filename) {
|
std::string &filename) {
|
||||||
size_t divider = line.find(HASH_FILE_DIVIDER);
|
size_t divider = line.find(HASH_FILE_DIVIDER);
|
||||||
|
|
@ -123,7 +123,7 @@ bool IntegretyCheck::extractHashAndFile(const std::string &line,
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IntegretyCheck::checkHashList(const std::string &hashList,
|
bool IntegrityCheck::checkHashList(const std::string &hashList,
|
||||||
const std::string &appPath) {
|
const std::string &appPath) {
|
||||||
std::stringstream ss(hashList);
|
std::stringstream ss(hashList);
|
||||||
std::string line, hash, filename;
|
std::string line, hash, filename;
|
||||||
|
|
@ -142,12 +142,12 @@ bool IntegretyCheck::checkHashList(const std::string &hashList,
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IntegretyCheck::verifyFileHash(const std::string &filePath,
|
bool IntegrityCheck::verifyFileHash(const std::string &filePath,
|
||||||
const std::string &hash) {
|
const std::string &hash) {
|
||||||
return (generateFileHash(filePath) == hash);
|
return (generateFileHash(filePath) == hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
void IntegretyCheck::signHashList(std::string &hashList) {
|
void IntegrityCheck::signHashList(std::string &hashList) {
|
||||||
CryptoPP::AutoSeededRandomPool rng;
|
CryptoPP::AutoSeededRandomPool rng;
|
||||||
|
|
||||||
CryptoPP::RSASSA_PKCS1v15_SHA_Signer signer(m_privateKey);
|
CryptoPP::RSASSA_PKCS1v15_SHA_Signer signer(m_privateKey);
|
||||||
|
|
@ -169,7 +169,7 @@ void IntegretyCheck::signHashList(std::string &hashList) {
|
||||||
hashList.append(strHexSignature);
|
hashList.append(strHexSignature);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IntegretyCheck::verifyHashList(const std::string &signedHashList,
|
bool IntegrityCheck::verifyHashList(const std::string &signedHashList,
|
||||||
std::string &hashList) {
|
std::string &hashList) {
|
||||||
size_t startSig = signedHashList.find(SIGNATURE_MARKER);
|
size_t startSig = signedHashList.find(SIGNATURE_MARKER);
|
||||||
if (startSig == std::string::npos) {
|
if (startSig == std::string::npos) {
|
||||||
|
|
@ -203,7 +203,7 @@ bool IntegretyCheck::verifyHashList(const std::string &signedHashList,
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string IntegretyCheck::loadHashList(const std::string &app) {
|
std::string IntegrityCheck::loadHashList(const std::string &app) {
|
||||||
std::stringstream content;
|
std::stringstream content;
|
||||||
fs::path appPath(app);
|
fs::path appPath(app);
|
||||||
std::ifstream in(appPath / HASH_FILE, std::ios::in | std::ios::binary);
|
std::ifstream in(appPath / HASH_FILE, std::ios::in | std::ios::binary);
|
||||||
|
|
@ -214,7 +214,7 @@ std::string IntegretyCheck::loadHashList(const std::string &app) {
|
||||||
return content.str();
|
return content.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
void IntegretyCheck::saveHashList(const std::string &app,
|
void IntegrityCheck::saveHashList(const std::string &app,
|
||||||
const std::string &hashList) {
|
const std::string &hashList) {
|
||||||
fs::path appPath(app);
|
fs::path appPath(app);
|
||||||
std::ofstream out(appPath / HASH_FILE);
|
std::ofstream out(appPath / HASH_FILE);
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
|
|
||||||
#include "inc/mainwindow.h"
|
#include "inc/mainwindow.h"
|
||||||
#include "../ui/ui_mainwindow.h"
|
#include "../ui/ui_mainwindow.h"
|
||||||
|
#include "IntegrityCheck/integritycheck.h"
|
||||||
|
|
||||||
#include <QFile>
|
#include <QFile>
|
||||||
#include <QFileDialog>
|
#include <QFileDialog>
|
||||||
|
|
@ -39,12 +40,12 @@ void AppWindow::onAppFolderSelect_click() {
|
||||||
|
|
||||||
void AppWindow::onSign_click() {
|
void AppWindow::onSign_click() {
|
||||||
std::string dir = ui->txtFolderPath->text().toStdString();
|
std::string dir = ui->txtFolderPath->text().toStdString();
|
||||||
IntegretyCheck integretyCheck(dir, true);
|
IntegrityCheck integretyCheck(dir, true);
|
||||||
log("key pair is generated");
|
log("key pair is generated");
|
||||||
|
|
||||||
integretyCheck.saveKeyFile(dir);
|
integretyCheck.saveKeyFile(dir);
|
||||||
log("public key is saved to '" +
|
log("public key is saved to '" +
|
||||||
QString::fromStdString(IntegretyCheck::KEY_FILE) + "'");
|
QString::fromStdString(IntegrityCheck::KEY_FILE) + "'");
|
||||||
|
|
||||||
std::string hList = integretyCheck.generateHashList(dir);
|
std::string hList = integretyCheck.generateHashList(dir);
|
||||||
log("generated hash list");
|
log("generated hash list");
|
||||||
|
|
@ -54,7 +55,7 @@ void AppWindow::onSign_click() {
|
||||||
|
|
||||||
integretyCheck.saveHashList(dir, hList);
|
integretyCheck.saveHashList(dir, hList);
|
||||||
log("public key is saved to '" +
|
log("public key is saved to '" +
|
||||||
QString::fromStdString(IntegretyCheck::HASH_FILE) + "'");
|
QString::fromStdString(IntegrityCheck::HASH_FILE) + "'");
|
||||||
|
|
||||||
if (publicKeyAvailable(ui->txtFolderPath->text()) &&
|
if (publicKeyAvailable(ui->txtFolderPath->text()) &&
|
||||||
hashFileAvailable(ui->txtFolderPath->text())) {
|
hashFileAvailable(ui->txtFolderPath->text())) {
|
||||||
|
|
@ -66,14 +67,14 @@ void AppWindow::onSign_click() {
|
||||||
void AppWindow::onVerify_click() {
|
void AppWindow::onVerify_click() {
|
||||||
|
|
||||||
std::string dir = ui->txtFolderPath->text().toStdString();
|
std::string dir = ui->txtFolderPath->text().toStdString();
|
||||||
IntegretyCheck integretyCheck(dir, false);
|
IntegrityCheck integretyCheck(dir, false);
|
||||||
///@todo check for key file and create log msg
|
///@todo check for key file and create log msg
|
||||||
|
|
||||||
std::string newHashList, hList;
|
std::string newHashList, hList;
|
||||||
hList = integretyCheck.loadHashList(dir);
|
hList = integretyCheck.loadHashList(dir);
|
||||||
if (hList.empty()) {
|
if (hList.empty()) {
|
||||||
log("App modified, unable to load '" +
|
log("App modified, unable to load '" +
|
||||||
QString::fromStdString(IntegretyCheck::HASH_FILE) + "'");
|
QString::fromStdString(IntegrityCheck::HASH_FILE) + "'");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
log("loaded hash file");
|
log("loaded hash file");
|
||||||
|
|
@ -102,12 +103,12 @@ void AppWindow::log(const QString &msg) {
|
||||||
|
|
||||||
bool AppWindow::publicKeyAvailable(const QString &path) {
|
bool AppWindow::publicKeyAvailable(const QString &path) {
|
||||||
QString pubKeyFile = path + QDir::separator() +
|
QString pubKeyFile = path + QDir::separator() +
|
||||||
QString::fromStdString(IntegretyCheck::KEY_FILE);
|
QString::fromStdString(IntegrityCheck::KEY_FILE);
|
||||||
return QFileInfo::exists(pubKeyFile);
|
return QFileInfo::exists(pubKeyFile);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppWindow::hashFileAvailable(const QString &path) {
|
bool AppWindow::hashFileAvailable(const QString &path) {
|
||||||
QString hashFile = path + QDir::separator() +
|
QString hashFile = path + QDir::separator() +
|
||||||
QString::fromStdString(IntegretyCheck::HASH_FILE);
|
QString::fromStdString(IntegrityCheck::HASH_FILE);
|
||||||
return QFileInfo::exists(hashFile);
|
return QFileInfo::exists(hashFile);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue