idk routing stuff i guess

This commit is contained in:
2022-02-24 19:47:27 +01:00
parent ebd9709c3d
commit c96d06653a
25 changed files with 338 additions and 399 deletions

View File

@@ -5,8 +5,6 @@ using tink.CoreApi;
import kernel.net.Package.NetworkID;
import kernel.peripherals.Peripherals.Peripheral;
import kernel.Log;
import kernel.KernelEvents;
import haxe.Exception;
import kernel.Timer;
import cc.OS;
@@ -18,145 +16,53 @@ using util.Extender.LambdaExtender;
Used to send and recceive packages.
**/
class Net {
/**
Depends on: KernelEvents
**/
public static var instance:Net;
public static inline final BRODCAST_PORT:Int = 65533;
public static inline final MESSAGE_TIMEOUT:Int = 3;
public final onNewNeigbor:Signal<Int>;
public final networkID:NetworkID = OS.getComputerID();
private final responseBus:Map<Int, Callback<Package>> = new Map();
private final protoHandlers:Map<String, Callback<Package>> = new Map();
private var allModems:Array<kernel.peripherals.Modem>;
private final routingTable:Map<NetworkID, kernel.peripherals.Modem> = new Map();
private final onNewNeigborTrigger:SignalTrigger<NetworkID> = Signal.trigger();
private var interfaces:Array<INetworkInterface>;
@:allow(kernel.Init)
private function new() {
onNewNeigbor = onNewNeigborTrigger.asSignal();
KernelEvents.instance.onModemMessage.handle(params -> {
var pack:Package = {
fromID: params.replyChannel,
toID: params.channel,
msgID: params.message.msgID,
type: params.message.type,
data: params.message.data,
};
this.interfaces = [for (e in Peripheral.instance.getModems()) e ]; // TODO: is this the way to do it?
this.interfaces.push(Loopback.instance);
handelIncomming(pack, params.addr);
});
allModems = Peripheral.instance.getModems();
open();
discoverNeighbors();
for (interf in interfaces){
interf.onMessage.handle(pack -> handle(pack,interf));
interf.listen(networkID);
interf.listen(BRODCAST_PORT);
}
}
/**
Called when a new package comes in.
**/
private function handelIncomming(pack:Package, ?addr:String) {
private function handle(pack:Package,interf: INetworkInterface) {
switch pack.type {
case Data(_):
routeToProto(pack);
case DataNoResponse(_):
case Data(_) | DataNoResponse(_):
// Let a local proccess handle it
routeToProto(pack);
case Response:
// Got a response to a send message. Invoke the callback
if (responseBus.exists(pack.msgID)) {
responseBus[pack.msgID].invoke(pack);
}
case RouteDiscover(_) | RouteDiscoverResponse(_):
handleRouteDiscover(pack, addr);
// Delegate to Routing
Routing.instance.handleRoutePackage(pack,interf);
}
}
private function newRoutDiscoverPackage():Package {
var pack:Package = {
type: RouteDiscover(getAllNeighbors()),
toID: BRODCAST_PORT,
msgID: generateMessageID(),
fromID: networkID,
data: null,
}
return pack;
}
/**
Send out discover packages on all modems.
**/
private function discoverNeighbors() {
for (modem in allModems) {
var pack = newRoutDiscoverPackage();
modem.transmit(BRODCAST_PORT, networkID, pack);
}
}
/**
Handle incomming packages that involve route discovery.
**/
private function handleRouteDiscover(pack:Package, addr:String) {
addRoute(pack.fromID, addr);
var forward = getAllNeighbors().filter(i -> i == pack.fromID);
switch pack.type{
case RouteDiscoverResponse(reachableIDs):
for (id in reachableIDs) {
addRoute(id, addr);
}
return; // Dont respond to a response
case RouteDiscover(reachableIDs):
for (id in reachableIDs) {
addRoute(id, addr);
}
default:
throw new Error("Expcted RouteDiscover or RouteDiscoverResponse type");
}
// Respond to peer
var response:Package = {
toID: pack.fromID,
fromID: networkID,
msgID: pack.msgID,
type: RouteDiscoverResponse(forward),
data: null
}
for (reponseModem in allModems.filter(m -> m.addr == addr)) {
reponseModem.transmit(pack.fromID, networkID, response);
}
}
/**
Called when a route to a client has been disoverd.
Its posible to be called multiple times with the same id but different addr.
**/
private function addRoute(toID:Int, addr:String) {
Log.info("Added new route to " + toID + " via " + addr);
routingTable.set(toID, allModems.find(item -> item.addr == addr));
this.onNewNeigborTrigger.trigger(toID);
}
public function getAllNeighbors():Array<Int> {
return routingTable.mapi((index, item) -> index);
}
private function generateMessageID():Int {
return Std.random(2147483647); // TODO: better uniqe number
}
/**
Open all wireless and wired modem.
**/
private function open() {
for (m in allModems) {
m.open(networkID);
m.open(BRODCAST_PORT);
}
}
/**
Send a message. Dont care if its reaches its destination nor it has a response.
**/
@@ -207,17 +113,8 @@ class Net {
Just send the package to the right modem.
**/
private function sendRaw(pack:Package) {
if (pack.toID == networkID) {
// Loopback
handelIncomming(pack);
} else {
if (routingTable.exists(pack.toID)) {
routingTable[pack.toID].transmit(pack.toID, pack.fromID, pack);
} else {
// Route not found
// TODO: forward package or report not reachable
}
}
Routing.instance.getIterfaceToId(pack.toID).send(pack.toID,pack.fromID,pack);
}
/**