Skip to content

Commit

Permalink
Add some network related device paths
Browse files Browse the repository at this point in the history
  • Loading branch information
Neverous committed Apr 23, 2022
1 parent 2d3ac0e commit fecf56e
Show file tree
Hide file tree
Showing 9 changed files with 1,283 additions and 10 deletions.
2 changes: 2 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ find_package(Qt${QT_VERSION_MAJOR}
COMPONENTS
Core
Gui
Network
Widgets
REQUIRED)

Expand All @@ -58,6 +59,7 @@ target_include_directories(${PROJECT_NAME} PRIVATE "${CMAKE_SOURCE_DIR}/include"
target_link_libraries(${PROJECT_NAME} PRIVATE
Qt::Core
Qt::Gui
Qt::Network
Qt::Widgets
)

Expand Down
1 change: 1 addition & 0 deletions icons.qrc
Original file line number Diff line number Diff line change
Expand Up @@ -18,5 +18,6 @@
<file>icons/Tango/scalable/actions/document-import.svg</file>
<file>icons/Tango/scalable/categories/preferences-system.svg</file>
<file>icons/Tango/scalable/devices/system.svg</file>
<file>icons/Tango/scalable/devices/network-wired.svg</file>
</qresource>
</RCC>
91 changes: 91 additions & 0 deletions include/bootentry.h
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// SPDX-License-Identifier: LGPL-3.0-or-later
#pragma once

#include <QHostAddress>
#include <QMetaType>
#include <QString>
#include <QUuid>
Expand Down Expand Up @@ -97,6 +98,93 @@ class Vendor
};
REGISTER_JSON_READER(Vendor);

class MACAddress
{
public:
static constexpr auto TYPE = "MSG";
static constexpr auto SUBTYPE = "MAC_ADDRESS";

private:
mutable QString string = "";

public:
QString address = "";
quint8 if_type = 0;

public:
MACAddress() = default;
MACAddress(const EFIBoot::Device_path::MAC_address &mac_address);
EFIBoot::Device_path::MAC_address toEFIBootDevicePath() const;

static std::optional<MACAddress> fromJSON(const QJsonObject &obj);
QJsonObject toJSON() const;

QString toString(bool refresh = true) const;
};
REGISTER_JSON_READER(MACAddress);

class IPv4
{
public:
static constexpr auto TYPE = "MSG";
static constexpr auto SUBTYPE = "IPV4";

private:
mutable QString string = "";

public:
QHostAddress local_ip_address = {};
QHostAddress remote_ip_address = {};
quint16 local_port = 0;
quint16 remote_port = 0;
quint16 protocol = 0;
bool static_ip_address = false;
QHostAddress gateway_ip_address = {};
QHostAddress subnet_mask = {};

public:
IPv4() = default;
IPv4(const EFIBoot::Device_path::IPv4 &ipv4);
EFIBoot::Device_path::IPv4 toEFIBootDevicePath() const;

static std::optional<IPv4> fromJSON(const QJsonObject &obj);
QJsonObject toJSON() const;

QString toString(bool refresh = true) const;
};
REGISTER_JSON_READER(IPv4);

class IPv6
{
public:
static constexpr auto TYPE = "MSG";
static constexpr auto SUBTYPE = "IPV6";

private:
mutable QString string = "";

public:
QHostAddress local_ip_address = {};
QHostAddress remote_ip_address = {};
quint16 local_port = 0;
quint16 remote_port = 0;
quint16 protocol = 0;
quint8 ip_address_origin = 0;
quint8 prefix_length = 0;
QHostAddress gateway_ip_address = {};

public:
IPv6() = default;
IPv6(const EFIBoot::Device_path::IPv6 &ipv6);
EFIBoot::Device_path::IPv6 toEFIBootDevicePath() const;

static std::optional<IPv6> fromJSON(const QJsonObject &obj);
QJsonObject toJSON() const;

QString toString(bool refresh = true) const;
};
REGISTER_JSON_READER(IPv6);

class SATA
{
public:
Expand Down Expand Up @@ -228,6 +316,9 @@ typedef std::variant<
PCI,
HID,
Vendor,
MACAddress,
IPv4,
IPv6,
SATA,
HD,
File,
Expand Down
19 changes: 14 additions & 5 deletions include/devicepathdialog.h
Original file line number Diff line number Diff line change
Expand Up @@ -66,11 +66,14 @@ class DevicePathDialog: public QDialog
PCI = 0,
HID = 1,
Vendor = 2,
SATA = 3,
HD = 4,
File = 5,
FirmwareFile = 6,
FirmwareVolume = 7,
MACAddress = 3,
IPv4 = 4,
IPv6 = 5,
SATA = 6,
HD = 7,
File = 8,
FirmwareFile = 9,
FirmwareVolume = 10,
};

enum VendorDataFormat
Expand All @@ -97,6 +100,9 @@ class DevicePathDialog: public QDialog
void setPCIForm(const Device_path::PCI &pci);
void setHIDForm(const Device_path::HID &hid);
void setVendorForm(const Device_path::Vendor &vendor);
void setMACAddressForm(const Device_path::MACAddress &mac_address);
void setIPv4Form(const Device_path::IPv4 &ipv4);
void setIPv6Form(const Device_path::IPv6 &ipv6);
void setSATAForm(const Device_path::SATA &sata);
void setHDForm(const Device_path::HD &hd);
void setFileForm(const Device_path::File &file);
Expand All @@ -109,6 +115,9 @@ class DevicePathDialog: public QDialog
void resetHIDForm();
QByteArray getVendorData(int format) const;
void resetVendorForm();
void resetMACAddressForm();
void resetIPv4Form();
void resetIPv6Form();
void resetSATAForm();
void resetHDForm();
void resetFileForm();
Expand Down
180 changes: 180 additions & 0 deletions include/efiboot.h
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,48 @@ struct Vendor
};
REGISTER_DESERIALIZER(Vendor);

struct MAC_address
{
static const uint8_t TYPE = MSG;
static const uint8_t SUBTYPE = 0x0b;

std::array<uint8_t, 32> address = {};
uint8_t if_type = 0;
};
REGISTER_DESERIALIZER(MAC_address);

struct IPv4
{
static const uint8_t TYPE = MSG;
static const uint8_t SUBTYPE = 0x0c;

std::array<uint8_t, 4> local_ip_address = {};
std::array<uint8_t, 4> remote_ip_address = {};
uint16_t local_port = 0;
uint16_t remote_port = 0;
uint16_t protocol = 0;
bool static_ip_address = false;
std::array<uint8_t, 4> gateway_ip_address = {};
std::array<uint8_t, 4> subnet_mask = {};
};
REGISTER_DESERIALIZER(IPv4);

struct IPv6
{
static const uint8_t TYPE = MSG;
static const uint8_t SUBTYPE = 0x0d;

std::array<uint8_t, 16> local_ip_address = {};
std::array<uint8_t, 16> remote_ip_address = {};
uint16_t local_port = 0;
uint16_t remote_port = 0;
uint16_t protocol = 0;
uint8_t ip_address_origin = 0;
uint8_t prefix_length = 0;
std::array<uint8_t, 16> gateway_ip_address = {};
};
REGISTER_DESERIALIZER(IPv6);

struct SATA
{
static const uint8_t TYPE = MSG;
Expand Down Expand Up @@ -165,6 +207,9 @@ typedef std::variant<
PCI,
HID,
Vendor,
MAC_address,
IPv4,
IPv6,
SATA,
HD,
File,
Expand Down Expand Up @@ -615,6 +660,141 @@ inline size_t serialize(Raw_data &output, const Device_path::Vendor &vendor)
return bytes;
}

template <>
inline std::optional<Device_path::MAC_address> deserialize(const void *data, size_t data_size)
{
const efidp_mac_address *dp = static_cast<const efidp_mac_address *>(data);
if(dp->header.length != data_size)
return std::nullopt;

if(dp->header.type != Device_path::TYPE::MSG)
return std::nullopt;

if(dp->header.subtype != Device_path::MAC_address::SUBTYPE)
return std::nullopt;

Device_path::MAC_address value;
std::copy(std::begin(dp->address), std::end(dp->address), std::begin(value.address));
value.if_type = dp->if_type;
return {value};
}

template <>
inline size_t serialize(Raw_data &output, const Device_path::MAC_address &mac_address)
{
size_t bytes = 0;
uint8_t type = Device_path::TYPE::MSG;
bytes += serialize(output, type);
uint8_t subtype = Device_path::MAC_address::SUBTYPE;
bytes += serialize(output, subtype);
size_t pos = output.size();
uint16_t length = 0;
bytes += serialize(output, length);
bytes += serialize(output, mac_address.address);
bytes += serialize(output, mac_address.if_type);
length = static_cast<uint16_t>(bytes);
memcpy(&output[pos], &length, sizeof(length));
return bytes;
}

template <>
inline std::optional<Device_path::IPv4> deserialize(const void *data, size_t data_size)
{
const efidp_ipv4 *dp = static_cast<const efidp_ipv4 *>(data);
if(dp->header.length != data_size)
return std::nullopt;

if(dp->header.type != Device_path::TYPE::MSG)
return std::nullopt;

if(dp->header.subtype != Device_path::IPv4::SUBTYPE)
return std::nullopt;

Device_path::IPv4 value;
std::copy(std::begin(dp->local_ip_address), std::end(dp->local_ip_address), std::begin(value.local_ip_address));
std::copy(std::begin(dp->remote_ip_address), std::end(dp->remote_ip_address), std::begin(value.remote_ip_address));
value.local_port = dp->local_port;
value.remote_port = dp->remote_port;
value.protocol = dp->protocol;
value.static_ip_address = dp->static_ip_address;
std::copy(std::begin(dp->gateway_ip_address), std::end(dp->gateway_ip_address), std::begin(value.gateway_ip_address));
std::copy(std::begin(dp->subnet_mask), std::end(dp->subnet_mask), std::begin(value.subnet_mask));
return {value};
}

template <>
inline size_t serialize(Raw_data &output, const Device_path::IPv4 &ipv4)
{
size_t bytes = 0;
uint8_t type = Device_path::TYPE::MSG;
bytes += serialize(output, type);
uint8_t subtype = Device_path::IPv4::SUBTYPE;
bytes += serialize(output, subtype);
size_t pos = output.size();
uint16_t length = 0;
bytes += serialize(output, length);
bytes += serialize(output, ipv4.local_ip_address);
bytes += serialize(output, ipv4.remote_ip_address);
bytes += serialize(output, ipv4.local_port);
bytes += serialize(output, ipv4.remote_port);
bytes += serialize(output, ipv4.protocol);
bytes += serialize(output, ipv4.static_ip_address);
bytes += serialize(output, ipv4.gateway_ip_address);
bytes += serialize(output, ipv4.subnet_mask);
length = static_cast<uint16_t>(bytes);
memcpy(&output[pos], &length, sizeof(length));
return bytes;
}

template <>
inline std::optional<Device_path::IPv6> deserialize(const void *data, size_t data_size)
{
const efidp_ipv6 *dp = static_cast<const efidp_ipv6 *>(data);
if(dp->header.length != data_size)
return std::nullopt;

if(dp->header.type != Device_path::TYPE::MSG)
return std::nullopt;

if(dp->header.subtype != Device_path::IPv6::SUBTYPE)
return std::nullopt;

Device_path::IPv6 value;
std::copy(std::begin(dp->local_ip_address), std::end(dp->local_ip_address), std::begin(value.local_ip_address));
std::copy(std::begin(dp->remote_ip_address), std::end(dp->remote_ip_address), std::begin(value.remote_ip_address));
value.local_port = dp->local_port;
value.remote_port = dp->remote_port;
value.protocol = dp->protocol;
value.ip_address_origin = dp->ip_address_origin;
value.prefix_length = dp->prefix_length;
std::copy(std::begin(dp->gateway_ip_address), std::end(dp->gateway_ip_address), std::begin(value.gateway_ip_address));
return {value};
}

template <>
inline size_t serialize(Raw_data &output, const Device_path::IPv6 &ipv6)
{
size_t bytes = 0;
uint8_t type = Device_path::TYPE::MSG;
bytes += serialize(output, type);
uint8_t subtype = Device_path::IPv6::SUBTYPE;
bytes += serialize(output, subtype);
size_t pos = output.size();
uint16_t length = 0;
bytes += serialize(output, length);
bytes += serialize(output, ipv6.local_ip_address);
bytes += serialize(output, ipv6.remote_ip_address);
bytes += serialize(output, ipv6.local_port);
bytes += serialize(output, ipv6.remote_port);
bytes += serialize(output, ipv6.protocol);
bytes += serialize(output, ipv6.ip_address_origin);
bytes += serialize(output, ipv6.prefix_length);
bytes += serialize(output, ipv6.gateway_ip_address);
length = static_cast<uint16_t>(bytes);
memcpy(&output[pos], &length, sizeof(length));
return bytes;
}

template <>
inline std::optional<Device_path::SATA> deserialize(const void *data, size_t data_size)
{
Expand Down
Loading

0 comments on commit fecf56e

Please sign in to comment.