Files
GUI/src/device/networkmanager.cpp

297 lines
8.4 KiB
C++
Raw Normal View History

#include "networkmanager.h"
#include "json/jsonobject.h"
#include <QProcess>
#include <QDebug>
#include <QRegularExpression>
2023-09-20 10:09:57 +08:00
#include <QNetworkSession>
#include <QHostAddress>
#include <QNetworkInterface>
2023-09-20 10:09:57 +08:00
namespace
{
unsigned int ipToUInt(const std::string& ip) {
unsigned int result = 0;
int start = 0;
for (int i = 0; i < 4; ++i) {
int end = ip.find('.', start);
if (end == std::string::npos) end = ip.length();
int octet = stoi(ip.substr(start, end - start));
result = (result << 8) | octet;
start = end + 1;
}
return result;
}
QString cidrFromSubnet(const QString& subnet) {
unsigned int subnetMask = ipToUInt(subnet.toStdString());
int cidr = 0;
while (subnetMask != 0) {
subnetMask = (subnetMask << 1) & 0xFFFFFFFF;
cidr++;
}
return QString::number(cidr);
}
}
2023-09-20 10:09:57 +08:00
NetworkManager* NetworkManager::getInstance()
{
static NetworkManager instance;
return &instance;
}
2023-09-20 10:09:57 +08:00
NetworkManager::NetworkManager(QObject* aParent)
: QObject(aParent)
, mIsDHCP()
, mIpAddress()
, mSubNetMask()
{
initNetworkInfo();
}
2023-09-20 10:09:57 +08:00
void NetworkManager::initNetworkInfo()
{
QList<QNetworkInterface> interfaces = QNetworkInterface::allInterfaces();
for (const QNetworkInterface &interface : interfaces)
{
if (!(interface.flags() & QNetworkInterface::IsLoopBack))
{
QList<QNetworkAddressEntry> entries = interface.addressEntries();
for (const QNetworkAddressEntry &entry : entries)
{
if (entry.ip().protocol() == QAbstractSocket::IPv4Protocol)
{
mIsDHCP = !entry.isPermanent();
mIpAddress = entry.ip().toString();
mSubNetMask = entry.netmask().toString();
return;
}
}
}
}
}
2021-12-28 18:23:02 +08:00
host NetworkManager::getLocalHost()
{
return JsonObject::Instance()->getServer(JsonObject::LOCAL);
}
2021-12-28 18:23:02 +08:00
bool NetworkManager::setLocalHost(const host& h)
{
JsonObject::Instance()->setServer(JsonObject::LOCAL, h);
return true;
}
QString NetworkManager::interfaceName()
{
return JsonObject::Instance()->interfaceName();
}
bool NetworkManager::isDHCP()
{
2023-09-20 10:09:57 +08:00
return mIsDHCP;
}
IpAddr NetworkManager::getDefaultIpAddr()
{
2023-09-20 10:09:57 +08:00
return IpAddr{mIpAddress, mSubNetMask};
}
QList<QStringList> NetworkManager::getIpAddrList()
{
return JsonObject::Instance()->getIpAddrList();
}
QString NetworkManager::getDefaultGateway()
{
return JsonObject::Instance()->getDefaultGateway();
}
QList<QStringList> NetworkManager::getIpRouteList()
{
return JsonObject::Instance()->getIpRouteList();
}
2023-09-20 10:09:57 +08:00
bool NetworkManager::setDHCP()
{
2023-09-20 10:09:57 +08:00
QString pwd = JsonObject::Instance()->passWord();
qDebug()<< pwd;
QString dhcpCommand = QString("echo %1 | sudo -S nmcli con mod usct ipv4.method auto ipv4.address \"\" ipv4.gateway \"\"").arg(pwd);
QString networkUpdateCommand = QString("echo %1 | sudo -S nmcli con up usct").arg(pwd);
QProcess settingProcess;
settingProcess.start("/bin/bash" , QStringList() << "-c" << dhcpCommand);
settingProcess.waitForFinished();
if (settingProcess.exitStatus() != QProcess::NormalExit || settingProcess.exitCode() != 0)
{
return false;
}
QProcess restartProcess;
restartProcess.start("/bin/bash", QStringList() << "-c" << networkUpdateCommand);
restartProcess.waitForFinished();
if (restartProcess.exitStatus() != QProcess::NormalExit && restartProcess.exitCode() != 0)
{
return false;
}
mIsDHCP = true;
JsonObject::Instance()->autoDHCP(true);
return true;
}
2023-09-20 10:09:57 +08:00
bool NetworkManager::setIpAddr(const IpAddr& addr, const QString& aGateWay, QString& err_info)
{
2023-09-20 10:09:57 +08:00
QString pwd = JsonObject::Instance()->passWord();
QString ipaddr = NewExp(addr.ip, addr.mask);
2023-09-20 10:09:57 +08:00
QProcess settingProcess;
QString setIpCommand = QString("echo %1 | sudo -S nmcli con mod usct ipv4.method manual ipv4.address %2 ipv4.gateway %3").arg(pwd).arg(ipaddr).arg(aGateWay);
QStringList args;
2023-09-20 10:09:57 +08:00
args << "-c" << setIpCommand;
settingProcess.start("/bin/sh", args);
settingProcess.waitForFinished();
if (settingProcess.exitStatus() != QProcess::NormalExit || settingProcess.exitCode() != 0)
{
return false;
}
QString networkUpdateCommand = QString("echo %1 | sudo -S nmcli con up usct").arg(pwd);
QProcess restartProcess;
restartProcess.start("/bin/bash", QStringList() << "-c" << networkUpdateCommand);
restartProcess.waitForFinished();
if (restartProcess.exitStatus() != QProcess::NormalExit && restartProcess.exitCode() != 0)
{
return false;
}
JsonObject::Instance()->setDefaultIpAddr(addr);
JsonObject::Instance()->autoDHCP(false);
return true;
}
bool NetworkManager::validate(const QString& addr)
{
QRegularExpression ipFormat("^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$");
QRegularExpressionMatch mre = ipFormat.match(addr);
if (mre.hasMatch())
{
return true;
}
return false;
}
QString NetworkManager::NewExp(QString ip, QString mask)
{
QString temp = "";
2023-09-20 10:09:57 +08:00
temp.append(ip).append("/").append(cidrFromSubnet(mask));
return temp;
}
bool NetworkManager::setIpAddrList(const QList<QStringList>& list, QString& err_info)
{
QProcess* myProcess = new QProcess;
QString inface = JsonObject::Instance()->interfaceName();
QString pwd = JsonObject::Instance()->passWord();
QString cmd = QString("echo %1 | ").arg(pwd);
for (QStringList addr : list)
{
QString ipaddr = NewExp(addr[0], addr[1]);
cmd.append(QString("sudo -S ip addr add %1 dev %2;").arg(ipaddr).arg(inface));
}
QStringList args;
args << "-c" << cmd;
connect(myProcess, SIGNAL(finished(int)), myProcess, SLOT(deleteLater()));
myProcess->start("/bin/sh", args);
if (!myProcess->waitForFinished()) {
err_info.append("failed...\n");
return false;
}
if (myProcess->exitCode() == 0) {
JsonObject::Instance()->setIpAddrList(list);
err_info.append("success...\n");
return true;
}
else {
err_info.append(myProcess->readAllStandardError());
return false;
}
}
bool NetworkManager::setDefaultGateway(const QString& gw, QString& err_info)
{
QProcess* myProcess = new QProcess;
QString pwd = JsonObject::Instance()->passWord();
QString cmd = QString("echo %1 | sudo -S ip route replace default via %2").arg(pwd).arg(gw);
QStringList args;
args << "-c" << cmd;
connect(myProcess, SIGNAL(finished(int)), myProcess, SLOT(deleteLater()));
//qDebug()<<args;
myProcess->start("/bin/sh", args);
if (!myProcess->waitForFinished()) {
err_info.append("failed...\n");
return false;
}
if (myProcess->exitCode() == 0) {
JsonObject::Instance()->setDefaultGateway(gw);
err_info.append("success...\n");
return true;
}
else {
err_info.append(myProcess->readAllStandardError());
return false;
}
}
2021-12-28 18:23:02 +08:00
bool NetworkManager::checkPassWord(const QString& pwd, QString& err_info)
2021-12-28 10:43:59 +08:00
{
QProcess* myProcess = new QProcess;
2021-12-28 18:23:02 +08:00
//QString pwd = JsonObject::Instance()->passWord();
QString cmd = QString("echo %1 | sudo -S -k whoami").arg(pwd);
2021-12-28 10:43:59 +08:00
QStringList args;
args << "-c" << cmd;
connect(myProcess, SIGNAL(finished(int)), myProcess, SLOT(deleteLater()));
//qDebug()<<args;
myProcess->start("/bin/sh", args);
if (!myProcess->waitForFinished()) {
err_info.append("failed...\n");
return false;
}
if (myProcess->exitCode() == 0) {
err_info.append("success...\n");
return true;
}
else {
err_info.append(myProcess->readAllStandardError());
return false;
}
}
bool NetworkManager::setIpRouteList(const QList<QStringList>& list, QString& err_info)
{
QProcess* myProcess = new QProcess;
QString inface = JsonObject::Instance()->interfaceName();
QString pwd = JsonObject::Instance()->passWord();
QString cmd = QString("echo %1 | ").arg(pwd);
for (QStringList route : list)
{
QString ipaddr = NewExp(route[0], route[1]);
cmd.append(QString("sudo -S ip route replace %1 via %2 dev %3;").arg(ipaddr).arg(route[2]).arg(inface));
}
QStringList args;
args << "-c" << cmd;
connect(myProcess, SIGNAL(finished(int)), myProcess, SLOT(deleteLater()));
myProcess->start("/bin/sh", args);
if (!myProcess->waitForFinished()) {
err_info.append("failed...\n");
return false;
}
if (myProcess->exitCode() == 0) {
JsonObject::Instance()->setIpRouteList(list);
err_info.append("success...\n");
return true;
}
else {
err_info.append(cmd);
err_info.append("\n");
err_info.append(myProcess->readAllStandardError());
return false;
}
}