feat: scheduling, usermode, shell

This commit is contained in:
2026-02-17 19:17:01 +01:00
parent 20fa8a9be2
commit f384d4cf75
45 changed files with 2622 additions and 98 deletions
+61 -27
View File
@@ -15,7 +15,6 @@
#include <Libraries/Memory.hpp>
#include <Terminal/Terminal.hpp>
#include <CppLib/Stream.hpp>
#include <Timekeeping/ApicTimer.hpp>
using namespace Kt;
@@ -23,6 +22,18 @@ namespace Net::Ipv4 {
static uint16_t g_identification = 0;
// Deferred packet queue for packets awaiting ARP resolution
struct PendingPacket {
uint32_t DestIp;
uint8_t Protocol;
uint8_t Data[Ethernet::MAX_PAYLOAD_SIZE - HEADER_SIZE];
uint16_t Length;
bool Active;
};
static constexpr uint32_t PENDING_QUEUE_SIZE = 8;
static PendingPacket g_pendingQueue[PENDING_QUEUE_SIZE] = {};
void Initialize() {
g_identification = 0;
KernelLogStream(OK, "Net") << "IPv4 initialized, IP: "
@@ -138,30 +149,9 @@ namespace Net::Ipv4 {
}
}
bool Send(uint32_t destIp, uint8_t protocol, const uint8_t* payload, uint16_t payloadLen) {
if (payloadLen > (Ethernet::MAX_PAYLOAD_SIZE - HEADER_SIZE)) {
return false;
}
// Determine next-hop IP and resolve MAC
uint32_t nextHop = GetNextHop(destIp);
uint8_t destMac[6];
if (!Arp::Resolve(nextHop, destMac)) {
// ARP request sent, wait briefly and retry
for (int attempt = 0; attempt < 3; attempt++) {
Timekeeping::Sleep(50);
if (Arp::Resolve(nextHop, destMac)) {
break;
}
}
// Final check
if (!Arp::Resolve(nextHop, destMac)) {
return false;
}
}
// Build IP packet
// Build and send an IP packet over Ethernet (MAC already resolved)
static bool SendDirect(uint32_t destIp, uint8_t protocol, const uint8_t* destMac,
const uint8_t* payload, uint16_t payloadLen) {
uint8_t packet[Ethernet::MAX_PAYLOAD_SIZE];
Header* hdr = (Header*)packet;
@@ -176,13 +166,57 @@ namespace Net::Ipv4 {
hdr->SrcIp = GetIpAddress();
hdr->DstIp = destIp;
// Calculate header checksum
hdr->Checksum = Checksum(hdr, HEADER_SIZE);
// Copy payload
memcpy(packet + HEADER_SIZE, payload, payloadLen);
return Ethernet::Send(destMac, Ethernet::ETHERTYPE_IPV4, packet, HEADER_SIZE + payloadLen);
}
bool Send(uint32_t destIp, uint8_t protocol, const uint8_t* payload, uint16_t payloadLen) {
if (payloadLen > (Ethernet::MAX_PAYLOAD_SIZE - HEADER_SIZE)) {
return false;
}
// Determine next-hop IP and resolve MAC
uint32_t nextHop = GetNextHop(destIp);
uint8_t destMac[6];
if (Arp::Resolve(nextHop, destMac)) {
return SendDirect(destIp, protocol, destMac, payload, payloadLen);
}
// ARP request already sent by Resolve(), queue the packet for later
for (uint32_t i = 0; i < PENDING_QUEUE_SIZE; i++) {
if (!g_pendingQueue[i].Active) {
g_pendingQueue[i].DestIp = destIp;
g_pendingQueue[i].Protocol = protocol;
g_pendingQueue[i].Length = payloadLen;
memcpy(g_pendingQueue[i].Data, payload, payloadLen);
g_pendingQueue[i].Active = true;
return true;
}
}
// Queue full, drop the packet
return false;
}
void FlushPending() {
for (uint32_t i = 0; i < PENDING_QUEUE_SIZE; i++) {
if (!g_pendingQueue[i].Active) {
continue;
}
uint32_t nextHop = GetNextHop(g_pendingQueue[i].DestIp);
uint8_t destMac[6];
if (Arp::Resolve(nextHop, destMac)) {
SendDirect(g_pendingQueue[i].DestIp, g_pendingQueue[i].Protocol,
destMac, g_pendingQueue[i].Data, g_pendingQueue[i].Length);
g_pendingQueue[i].Active = false;
}
}
}
}