Kernel: Implement barebones arp table
This commit is contained in:
27
kernel/kernel/Networking/ARPTable.cpp
Normal file
27
kernel/kernel/Networking/ARPTable.cpp
Normal file
@@ -0,0 +1,27 @@
|
||||
#include <kernel/Networking/ARPTable.h>
|
||||
|
||||
namespace Kernel
|
||||
{
|
||||
|
||||
static constexpr BAN::IPv4Address s_broadcast_ipv4 { 0xFFFFFFFF };
|
||||
static constexpr BAN::MACAddress s_broadcast_mac {{ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }};
|
||||
|
||||
BAN::ErrorOr<BAN::UniqPtr<ARPTable>> ARPTable::create()
|
||||
{
|
||||
return TRY(BAN::UniqPtr<ARPTable>::create());
|
||||
}
|
||||
|
||||
ARPTable::ARPTable()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
BAN::ErrorOr<BAN::MACAddress> ARPTable::get_mac_from_ipv4(BAN::IPv4Address ipv4_address)
|
||||
{
|
||||
if (ipv4_address == s_broadcast_ipv4)
|
||||
return s_broadcast_mac;
|
||||
dprintln("No MAC for IPv4 {}", ipv4_address);
|
||||
return BAN::Error::from_errno(ENOTSUP);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -19,6 +19,7 @@ namespace Kernel
|
||||
if (manager_ptr == nullptr)
|
||||
return BAN::Error::from_errno(ENOMEM);
|
||||
auto manager = BAN::UniqPtr<NetworkManager>::adopt(manager_ptr);
|
||||
manager->m_arp_table = TRY(ARPTable::create());
|
||||
TRY(manager->TmpFileSystem::initialize(0777, 0, 0));
|
||||
s_instance = BAN::move(manager);
|
||||
return {};
|
||||
|
||||
@@ -58,16 +58,12 @@ namespace Kernel
|
||||
auto* destination = reinterpret_cast<const sockaddr_in*>(arguments->dest_addr);
|
||||
auto message = BAN::ConstByteSpan((const uint8_t*)arguments->message, arguments->length);
|
||||
|
||||
if (destination->sin_port == PORT_NONE)
|
||||
uint16_t dst_port = destination->sin_port;
|
||||
if (dst_port == PORT_NONE)
|
||||
return BAN::Error::from_errno(EINVAL);
|
||||
|
||||
if (destination->sin_addr.s_addr != 0xFFFFFFFF)
|
||||
{
|
||||
dprintln("Only broadcast ip supported");
|
||||
return BAN::Error::from_errno(EINVAL);
|
||||
}
|
||||
|
||||
static BAN::MACAddress dest_mac {{ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }};
|
||||
auto dst_addr = BAN::IPv4Address(destination->sin_addr.s_addr);
|
||||
auto dst_mac = TRY(NetworkManager::get().arp_table().get_mac_from_ipv4(dst_addr));
|
||||
|
||||
const size_t interface_header_offset = 0;
|
||||
const size_t interface_header_size = m_interface->interface_header_size();
|
||||
@@ -87,9 +83,9 @@ namespace Kernel
|
||||
BAN::ByteSpan packet_bytespan { full_packet.span() };
|
||||
|
||||
memcpy(full_packet.data() + payload_offset, message.data(), payload_size);
|
||||
add_protocol_header(packet_bytespan.slice(protocol_header_offset), m_port, destination->sin_port);
|
||||
add_ipv4_header(packet_bytespan.slice(ipv4_header_offset), m_interface->get_ipv4_address(), destination->sin_addr.s_addr, protocol());
|
||||
m_interface->add_interface_header(packet_bytespan.slice(interface_header_offset), dest_mac);
|
||||
add_protocol_header(packet_bytespan.slice(protocol_header_offset), m_port, dst_port);
|
||||
add_ipv4_header(packet_bytespan.slice(ipv4_header_offset), m_interface->get_ipv4_address(), dst_addr, protocol());
|
||||
m_interface->add_interface_header(packet_bytespan.slice(interface_header_offset), dst_mac);
|
||||
TRY(m_interface->send_raw_bytes(packet_bytespan));
|
||||
|
||||
return arguments->length;
|
||||
|
||||
Reference in New Issue
Block a user