From a036160515ccfb4c1573df4a0482db8a074c2697 Mon Sep 17 00:00:00 2001 From: Chris McCarthy Date: Thu, 8 Feb 2024 22:37:21 +0000 Subject: [PATCH] #2248 - Enhances the PrimAITE documentation, covering the Node, network interfaces, Session Manager, Software Manager, PCAP service, SysLog functionality, and network devices like Routers, Switches, Computers, and Switch Nodes. It details their roles, workflows, and integration within the simulation, focusing on frame processing, software management, and logging. The documentation also clarifies the frame reception process, including port checks and application-level dispatching, ensuring a thorough understanding of network operations within the simulation --- CHANGELOG.md | 4 + docs/source/simulation.rst | 8 +- .../network/base_hardware.rst | 740 +----------------- .../simulation_components/network/network.rst | 8 +- .../network/network_interfaces.rst | 118 +++ .../network/nodes/host_node.rst | 47 ++ .../network/nodes/network_node.rst | 41 + .../network/nodes/router.rst | 41 + .../network/nodes/switch.rst | 29 + .../primaite_network_interface_model.png | Bin 0 -> 46770 bytes .../simulation_components/network/router.rst | 73 -- .../system/data_manipulation_bot.rst | 2 +- .../system/ftp_client_server.rst | 2 +- .../node_session_software_model_example.png | Bin 0 -> 52428 bytes .../simulation_components/system/pcap.rst | 51 ++ .../system/session_and_software_manager.rst | 90 +++ .../simulation_components/system/sys_log.rst | 51 ++ .../web_browser_and_web_server_service.rst | 2 +- .../wireless/wireless_access_point.py | 9 +- .../wireless/wireless_nic.py | 9 +- .../network/hardware/nodes/network/router.py | 41 - 21 files changed, 529 insertions(+), 837 deletions(-) create mode 100644 docs/source/simulation_components/network/network_interfaces.rst create mode 100644 docs/source/simulation_components/network/nodes/host_node.rst create mode 100644 docs/source/simulation_components/network/nodes/network_node.rst create mode 100644 docs/source/simulation_components/network/nodes/router.rst create mode 100644 docs/source/simulation_components/network/nodes/switch.rst create mode 100644 docs/source/simulation_components/network/primaite_network_interface_model.png delete mode 100644 docs/source/simulation_components/network/router.rst create mode 100644 docs/source/simulation_components/system/node_session_software_model_example.png create mode 100644 docs/source/simulation_components/system/pcap.rst create mode 100644 docs/source/simulation_components/system/session_and_software_manager.rst create mode 100644 docs/source/simulation_components/system/sys_log.rst diff --git a/CHANGELOG.md b/CHANGELOG.md index 94c6aff0..9716fd0e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -67,6 +67,10 @@ SessionManager. - Created the `ARP` and `ICMP` service classes to handle Address Resolution Protocol operations and Internet Control Message Protocol messages, respectively, with `RouterARP` and `RouterICMP` for router-specific implementations. - Created `HostNode` as a subclass of `Node`, extending its functionality with host-specific services and applications. This class is designed to represent end-user devices like computers or servers that can initiate and respond to network communications. - Introduced a new `IPV4Address` type in the Pydantic model for enhanced validation and auto-conversion of IPv4 addresses from strings using an `ipv4_validator`. +- Comprehensive documentation for the Node and its network interfaces, detailing the operational workflow from frame reception to application-level processing. +- Detailed descriptions of the Session Manager and Software Manager functionalities, including their roles in managing sessions, software services, and applications within the simulation. +- Documentation for the Packet Capture (PCAP) service and SysLog functionality, highlighting their importance in logging network frames and system events, respectively. +- Expanded documentation on network devices such as Routers, Switches, Computers, and Switch Nodes, explaining their specific processing logic and protocol support. ### Changed diff --git a/docs/source/simulation.rst b/docs/source/simulation.rst index e5c0d2c8..d85a1449 100644 --- a/docs/source/simulation.rst +++ b/docs/source/simulation.rst @@ -17,9 +17,15 @@ Contents simulation_structure simulation_components/network/base_hardware + simulation_components/network/network_interfaces simulation_components/network/transport_to_data_link_layer - simulation_components/network/router + simulation_components/network/nodes/host_node + simulation_components/network/nodes/network_node + simulation_components/network/nodes/router simulation_components/network/switch simulation_components/network/network simulation_components/system/internal_frame_processing + simulation_components/system/sys_log + simulation_components/system/pcap + simulation_components/system/session_and_software_manager simulation_components/system/software diff --git a/docs/source/simulation_components/network/base_hardware.rst b/docs/source/simulation_components/network/base_hardware.rst index 01c68036..10ed59c6 100644 --- a/docs/source/simulation_components/network/base_hardware.rst +++ b/docs/source/simulation_components/network/base_hardware.rst @@ -6,719 +6,41 @@ Base Hardware ############# -The physical layer components are models of a NIC (Network Interface Card), SwitchPort, Node, Switch, and a Link. -These components allow modelling of layer 1 (physical layer) in the OSI model and the nodes that connect to and -transmit across layer 1. +The ``base.py`` module in ``primaite.simulator.network.hardware`` provides foundational components, interfaces, and classes for +modeling network hardware within PrimAITE simulations. It establishes core building blocks and abstractions that more +complex, specialized hardware components inherit from and build upon. -=== -NIC -=== +The key elements defined in ``base.py`` are: -The NIC class provides a realistic model of a Network Interface Card. The NIC acts as the interface between a Node and -a Link, handling IP and MAC addressing, status, and sending/receiving frames. +NetworkInterface +================ ----------- -Addressing ----------- +- Abstract base class for network interfaces like NICs. Defines common attributes like MAC address, speed, MTU. +- Requires subclasses to implement ``enable()``, ``disable()``, ``send_frame()`` and ``receive_frame()``. +- Provides basic state description and request handling capabilities. -A NIC has both an IPv4 address and MAC address assigned: - -- **ip_address** - The IPv4 address assigned to the NIC for communication on an IP network. -- **subnet_mask** - The subnet mask that defines the network subnet. -- **gateway** - The default gateway IP address for routing traffic beyond the local network. -- **mac_address** - A unique MAC address assigned to the NIC by the manufacturer. - - ------- -Status ------- - -The status of the NIC is represented by: - -- **enabled** - Indicates if the NIC is active/enabled or disabled/down. It must be enabled to send/receive frames. -- **connected_node** - The Node instance the NIC is attached to. -- **connected_link** - The Link instance the NIC is wired to. - - --------------- -Packet Capture --------------- - -- **pcap** - A PacketCapture instance attached to the NIC for capturing all frames sent and received. This allows packet -capture and analysis. - ------------------------- -Sending/Receiving Frames ------------------------- - -The NIC can send and receive Frames to/from the connected Link: - -- **send_frame()** - Sends a Frame through the NIC onto the attached Link. -- **receive_frame()** - Receives a Frame from the attached Link and processes it. - -This allows a NIC to handle sending, receiving, and forwarding of network traffic at layer 2 of the OSI model. -The Frames contain network data encapsulated with various protocol headers. - ------------ -Basic Usage ------------ - -.. code-block:: python - - nic1 = NIC( - ip_address="192.168.0.100", - subnet_mask="255.255.255.0", - gateway="192.168.0.1" - ) - nic1.enable() - frame = Frame(...) - nic1.send_frame(frame) - -========== -SwitchPort -========== - -The SwitchPort models a port on a network switch. It has similar attributes and methods to NIC for addressing, status, -packet capture, sending/receiving frames, etc. - -Key attributes: - -- **port_num**: The port number on the switch. -- **connected_switch**: The switch to which this port belongs. - -==== Node ==== -The Node class represents a base node that communicates on the Network. - -Nodes take more than 1 time step to power on (3 time steps by default). -To create a Node that is already powered on, the Node's operating state can be overriden. -Otherwise, the node ``start_up_duration`` (and ``shut_down_duration``) can be set to 0 if -the node will be powered off or on multiple times. This will still need ``power_on()`` to -be called to turn the node on. - -e.g. - -.. code-block:: python - - active_node = Node(hostname='server1', operating_state=NodeOperatingState.ON) - # node is already on, no need to call power_on() - - - instant_start_node = Node(hostname="client", start_up_duration=0, shut_down_duration=0) - instant_start_node.power_on() # node will still need to be powered on - -.. _Node Start up and Shut down: - ---------------------------- -Node Start up and Shut down ---------------------------- - -Nodes are powered on and off over multiple timesteps. By default, the node ``start_up_duration`` and ``shut_down_duration`` is 3 timesteps. - -Example code where a node is turned on: - -.. code-block:: python - - from primaite.simulator.network.hardware.base import Node - from primaite.simulator.network.hardware.node_operating_state import NodeOperatingState - - node = Node(hostname="pc_a") - - assert node.operating_state is NodeOperatingState.OFF # By default, node is instantiated in an OFF state - - node.power_on() # power on the node - - assert node.operating_state is NodeOperatingState.BOOTING # node is booting up - - for i in range(node.start_up_duration + 1): - # apply timestep until the node start up duration - node.apply_timestep(timestep=i) - - assert node.operating_state is NodeOperatingState.ON # node is in ON state - - -If the node needs to be instantiated in an on state: - - -.. code-block:: python - - from primaite.simulator.network.hardware.base import Node - from primaite.simulator.network.hardware.node_operating_state import NodeOperatingState - - node = Node(hostname="pc_a", operating_state=NodeOperatingState.ON) - - assert node.operating_state is NodeOperatingState.ON # node is in ON state - -Setting ``start_up_duration`` and/or ``shut_down_duration`` to ``0`` will allow for the ``power_on`` and ``power_off`` methods to be completed instantly without applying timesteps: - -.. code-block:: python - - from primaite.simulator.network.hardware.base import Node - from primaite.simulator.network.hardware.node_operating_state import NodeOperatingState - - node = Node(hostname="pc_a", start_up_duration=0, shut_down_duration=0) - - assert node.operating_state is NodeOperatingState.OFF # node is in OFF state - - node.power_on() - - assert node.operating_state is NodeOperatingState.ON # node is in ON state - - node.power_off() - - assert node.operating_state is NodeOperatingState.OFF # node is in OFF state - ------------------- -Network Interfaces ------------------- - -A Node will typically have one or more NICs attached to it for network connectivity: - -- **network_interfaces** - A dictionary containing the NIC instances attached to the Node. NICs can be added/removed. - -------------- -Configuration -------------- - -- **hostname** - Configured hostname of the Node. -- **operating_state** - Current operating state like ON or OFF. The NICs will be enabled/disabled based on this. - ----------------- -Network Services ----------------- - -A Node runs various network services and components for handling traffic: - -- **session_manager** - Handles establishing sessions to/from the Node. -- **software_manager** - Manages software and applications on the Node. -- **arp** - ARP cache for resolving IP addresses to MAC addresses. -- **icmp** - ICMP service for responding to pings and echo requests. -- **sys_log** - System log service for logging internal events and messages. - -The SysLog provides a logging mechanism for the Node: - -The SysLog records informational, warning, and error events that occur on the Node during simulation. This allows -debugging and tracing program execution and network activity for each simulated Node. Other Node services like ARP and -ICMP, along with custom Applications, services, and Processes will log to the SysLog. - ------------------ -Sending/Receiving ------------------ - -The Node handles sending and receiving Frames via its attached NICs: - -- **send_frame()** - Sends a Frame to the network through one of the Node's NICs. -- **receive_frame()** - Receives a Frame from the network through a NIC. The Node then processes it appropriately based -on the protocols and payload. - ------------ -Basic Usage ------------ - -.. code-block:: python - - node1 = Node(hostname='server1') - node1.operating_state = NodeOperatingState.ON - - nic1 = NIC() - node1.connect_nic(nic1) - - Send a frame - frame = Frame(...) - node1.send_frame(frame) - -The Node class brings together the NICs, configuration, and services to model a full network node that can send, -receive, process, and forward traffic on a simulated network. - -====== -Switch -====== - -The Switch subclass models a network switch. It inherits from Node and acts at layer 2 of the OSI model to forward -frames based on MAC addresses. - --------------------------- -Inherits Node Capabilities --------------------------- - -Since Switch subclasses Node, it inherits all capabilities from Node like: - -- **Managing NICs** -- **Running network services like ARP, ICMP** -- **Sending and receiving frames** -- **Maintaining system logs** - ------ -Ports ------ - -A Switch has multiple ports implemented using SwitchPort instances: - -- **switch_ports** - A dictionary mapping port numbers to SwitchPort instances. -- **num_ports** - The number of ports the Switch has. - ----------- -Forwarding ----------- - -A Switch forwards frames between ports based on the destination MAC: - -- **dst_mac_table** - MAC address table that maps MACs to SwitchPorts. -- **forward_frame()** - Forwards a frame out the port associated with the destination MAC. - -When a frame is received on a SwitchPort: - -1. The source MAC address is extracted from the frame. -2. An entry is added to dst_mac_table that maps this source MAC to the SwitchPort it was received on. -3. When a frame with that destination MAC is received in the future, it will be forwarded out this SwitchPort. - -This allows the Switch to dynamically build up a mapping table between MAC addresses and SwitchPorts based on traffic -received. If no entry exists for a destination MAC, it floods the frame out all ports. - -==== -Link -==== - -The Link class represents a physical link or connection between two network endpoints like NICs or SwitchPorts. - ---------- -Endpoints ---------- - -A Link connects two endpoints: - -- **endpoint_a** - The first endpoint, a NIC or SwitchPort. -- **endpoint_b** - The second endpoint, a NIC or SwitchPort. - ------------- -Transmission ------------- - -Links transmit Frames between the endpoints: - -- **transmit_frame()** - Sends a Frame from one endpoint to the other. - -Uses bandwidth/load properties to determine if transmission is possible. - ----------------- -Bandwidth & Load ----------------- - -- **bandwidth** - The total capacity of the Link in Mbps. -- **current_load** - The current bandwidth utilization of the Link in Mbps. - -As Frames are sent over the Link, the load increases. The Link tracks if there is enough unused capacity to transmit a -Frame based on its size and the current load. - ------- -Status ------- - -- **up** - Boolean indicating if the Link is currently up/active based on the endpoint status. -- **endpoint_up()/down()** - Notifies the Link when an endpoint goes up or down. - -This allows the Link to realistically model the connection and transmission characteristics between two endpoints. - -======================= -Putting it all Together -======================= - -We'll now demonstrate how the nodes, NICs, switches, and links connect in a network, including full code examples and -syslog extracts to illustrate the step-by-step process. - -To demonstrate successful network communication between nodes and switches, we'll model a standard network with four -PC's and two switches. - - -.. image:: ../../../_static/four_node_two_switch_network.png - -------------------- -Create Nodes & NICs -------------------- - -First, we'll create the four nodes, each with a single NIC. - -.. code-block:: python - - from primaite.simulator.network.hardware.base import Node, NodeOperatingState, NIC - - pc_a = Node(hostname="pc_a", operating_state=NodeOperatingState.ON) - nic_a = NIC(ip_address="192.168.0.10", subnet_mask="255.255.255.0", gateway="192.168.0.1") - pc_a.connect_nic(nic_a) - - pc_b = Node(hostname="pc_b", operating_state=NodeOperatingState.ON) - nic_b = NIC(ip_address="192.168.0.11", subnet_mask="255.255.255.0", gateway="192.168.0.1") - pc_b.connect_nic(nic_b) - - pc_c = Node(hostname="pc_c", operating_state=NodeOperatingState.ON) - nic_c = NIC(ip_address="192.168.0.12", subnet_mask="255.255.255.0", gateway="192.168.0.1") - pc_c.connect_nic(nic_c) - - pc_d = Node(hostname="pc_d", operating_state=NodeOperatingState.ON) - nic_d = NIC(ip_address="192.168.0.13", subnet_mask="255.255.255.0", gateway="192.168.0.1") - pc_d.connect_nic(nic_d) - -Creating the four nodes results in: - -**node_a NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+----------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+==========+ -| 80:af:f2:f6:58:b7 | 102.169.0.10 | 255.255.255.0 | 192.168.0.1 | 100 | Disabled | -+-------------------+--------------+---------------+-----------------+--------------+----------+ - -**node_a sys log** - -.. code-block:: - - 2023-08-08 15:50:08,355 INFO: Connected NIC 80:af:f2:f6:58:b7/192.168.0.10 - -**node_b NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+----------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+==========+ -| 98:ad:eb:7c:dc:cb | 102.169.0.11 | 255.255.255.0 | 192.168.0.1 | 100 | Disabled | -+-------------------+--------------+---------------+-----------------+--------------+----------+ - -**node_b sys log** - -.. code-block:: - - 2023-08-08 15:50:08,357 INFO: Connected NIC 98:ad:eb:7c:dc:cb/192.168.0.11 - -**node_c NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+----------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+==========+ -| bc:72:82:5d:82:a4 | 102.169.0.12 | 255.255.255.0 | 192.168.0.1 | 100 | Disabled | -+-------------------+--------------+---------------+-----------------+--------------+----------+ - -**node_c sys log** - -.. code-block:: - - 2023-08-08 15:50:08,358 INFO: Connected NIC bc:72:82:5d:82:a4/192.168.0.12 - -**node_d NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+----------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+==========+ -| 84:20:7c:ec:a5:c6 | 102.169.0.13 | 255.255.255.0 | 192.168.0.1 | 100 | Disabled | -+-------------------+--------------+---------------+-----------------+--------------+----------+ - -**node_d sys log** - -.. code-block:: - - 2023-08-08 15:50:08,359 INFO: Connected NIC 84:20:7c:ec:a5:c6/192.168.0.13 - ---------------- -Create Switches ---------------- - -Next, we'll create two six-port switches: - -.. code-block:: python - - switch_1 = Switch(hostname="switch_1", num_ports=6, operating_state=NodeOperatingState.ON) - - switch_2 = Switch(hostname="switch_2", num_ports=6, operating_state=NodeOperatingState.ON) - -This produces: - -**switch_1 MAC table** - -+------+-------------------+--------------+----------+ -| Port | MAC Address | Speed (Mbps) | Status | -+======+===================+==============+==========+ -| 1 | 9d:ac:59:a0:05:13 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 2 | 45:f5:8e:b6:f5:d3 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 3 | ef:f5:b9:28:cb:ae | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 4 | 88:76:0a:72:fc:14 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 5 | 79:de:da:bd:e2:ba | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 6 | 91:d5:83:a0:02:f2 | 100 | Disabled | -+------+-------------------+--------------+----------+ - -**switch_1 sys log** - -.. code-block:: - - 2023-08-08 15:50:08,373 INFO: Turned on - -**switch_2 MAC table** - -+------+-------------------+--------------+----------+ -| Port | MAC Address | Speed (Mbps) | Status | -+======+===================+==============+==========+ -| 1 | aa:58:fa:66:d7:be | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 2 | 72:d2:1e:88:e9:45 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 3 | 8a:fc:2a:56:d5:c5 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 4 | fb:b5:9a:04:4a:49 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 5 | 88:aa:48:d0:21:9e | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 6 | 96:77:39:d1:de:44 | 100 | Disabled | -+------+-------------------+--------------+----------+ - -**switch_2 sys log** - -.. code-block:: - - 2023-08-08 15:50:08,374 INFO: Turned on - ------------- -Create Links ------------- - -Finally, we'll create the five links that connect the nodes and the switches: - -.. code-block:: python - - link_nic_a_switch_1 = Link(endpoint_a=nic_a, endpoint_b=switch_1.switch_ports[1]) - link_nic_b_switch_1 = Link(endpoint_a=nic_b, endpoint_b=switch_1.switch_ports[2]) - link_nic_c_switch_2 = Link(endpoint_a=nic_c, endpoint_b=switch_2.switch_ports[1]) - link_nic_d_switch_2 = Link(endpoint_a=nic_d, endpoint_b=switch_2.switch_ports[2]) - link_switch_1_switch_2 = Link( - endpoint_a=switch_1.switch_ports[6], endpoint_b=switch_2.switch_ports[6] - ) - -This produces: - -**node_a NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+---------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+=========+ -| 80:af:f2:f6:58:b7 | 102.169.0.10 | 255.255.255.0 | 192.168.0.1 | 100 | Enabled | -+-------------------+--------------+---------------+-----------------+--------------+---------+ - -**node_a sys log** - -.. code-block:: - - 2023-08-08 15:50:08,355 INFO: Connected NIC 80:af:f2:f6:58:b7/192.168.0.10 - 2023-08-08 15:50:08,355 INFO: Turned on - 2023-08-08 15:50:08,355 INFO: NIC 80:af:f2:f6:58:b7/192.168.0.10 enabled - -**node_b NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+---------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+=========+ -| 98:ad:eb:7c:dc:cb | 102.169.0.11 | 255.255.255.0 | 192.168.0.1 | 100 | Enabled | -+-------------------+--------------+---------------+-----------------+--------------+---------+ - -**node_b sys log** - -.. code-block:: - - 2023-08-08 15:50:08,357 INFO: Connected NIC 98:ad:eb:7c:dc:cb/192.168.0.11 - 2023-08-08 15:50:08,357 INFO: Turned on - 2023-08-08 15:50:08,357 INFO: NIC 98:ad:eb:7c:dc:cb/192.168.0.11 enabled - -**node_c NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+---------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+=========+ -| bc:72:82:5d:82:a4 | 102.169.0.12 | 255.255.255.0 | 192.168.0.1 | 100 | Enabled | -+-------------------+--------------+---------------+-----------------+--------------+---------+ - -**node_c sys log** - -.. code-block:: - - 2023-08-08 15:50:08,358 INFO: Connected NIC bc:72:82:5d:82:a4/192.168.0.12 - 2023-08-08 15:50:08,358 INFO: Turned on - 2023-08-08 15:50:08,358 INFO: NIC bc:72:82:5d:82:a4/192.168.0.12 enabled - -**node_d NIC table** - -+-------------------+--------------+---------------+-----------------+--------------+---------+ -| MAC Address | IP Address | Subnet Mask | Default Gateway | Speed (Mbps) | Status | -+===================+==============+===============+=================+==============+=========+ -| 84:20:7c:ec:a5:c6 | 102.169.0.13 | 255.255.255.0 | 192.168.0.1 | 100 | Enabled | -+-------------------+--------------+---------------+-----------------+--------------+---------+ - -**node_d sys log** - -.. code-block:: - - 2023-08-08 15:50:08,359 INFO: Connected NIC 84:20:7c:ec:a5:c6/192.168.0.13 - 2023-08-08 15:50:08,360 INFO: Turned on - 2023-08-08 15:50:08,360 INFO: NIC 84:20:7c:ec:a5:c6/192.168.0.13 enabled - -**switch_1 MAC table** - -+------+-------------------+--------------+----------+ -| Port | MAC Address | Speed (Mbps) | Status | -+======+===================+==============+==========+ -| 1 | 9d:ac:59:a0:05:13 | 100 | Enabled | -+------+-------------------+--------------+----------+ -| 2 | 45:f5:8e:b6:f5:d3 | 100 | Enabled | -+------+-------------------+--------------+----------+ -| 3 | ef:f5:b9:28:cb:ae | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 4 | 88:76:0a:72:fc:14 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 5 | 79:de:da:bd:e2:ba | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 6 | 91:d5:83:a0:02:f2 | 100 | Enabled | -+------+-------------------+--------------+----------+ - - -**switch_1 sys log** - -.. code-block:: - - 2023-08-08 15:50:08,373 INFO: Turned on - 2023-08-08 15:50:08,378 INFO: SwitchPort 9d:ac:59:a0:05:13 enabled - 2023-08-08 15:50:08,380 INFO: SwitchPort 45:f5:8e:b6:f5:d3 enabled - 2023-08-08 15:50:08,384 INFO: SwitchPort 91:d5:83:a0:02:f2 enabled - - -**switch_2 MAC table** - -+------+-------------------+--------------+----------+ -| Port | MAC Address | Speed (Mbps) | Status | -+======+===================+==============+==========+ -| 1 | aa:58:fa:66:d7:be | 100 | Enabled | -+------+-------------------+--------------+----------+ -| 2 | 72:d2:1e:88:e9:45 | 100 | Enabled | -+------+-------------------+--------------+----------+ -| 3 | 8a:fc:2a:56:d5:c5 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 4 | fb:b5:9a:04:4a:49 | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 5 | 88:aa:48:d0:21:9e | 100 | Disabled | -+------+-------------------+--------------+----------+ -| 6 | 96:77:39:d1:de:44 | 100 | Enabled | -+------+-------------------+--------------+----------+ - - -**switch_2 sys log** - -.. code-block:: - - 2023-08-08 15:50:08,374 INFO: Turned on - 2023-08-08 15:50:08,381 INFO: SwitchPort aa:58:fa:66:d7:be enabled - 2023-08-08 15:50:08,383 INFO: SwitchPort 72:d2:1e:88:e9:45 enabled - 2023-08-08 15:50:08,384 INFO: SwitchPort 96:77:39:d1:de:44 enabled - - ------------- -Perform Ping ------------- - -Now with the network setup and operational, we can perform a ping to confirm that communication between nodes over a -switched network is possible. In the below example, we ping 192.168.0.13 (node_d) from node_a: - -.. code-block:: python - - pc_a.ping("192.168.0.13") - - -This produces: - -**node_a sys log** - -.. code-block:: - - 2023-08-08 15:50:08,355 INFO: Connected NIC 80:af:f2:f6:58:b7/192.168.0.10 - 2023-08-08 15:50:08,355 INFO: Turned on - 2023-08-08 15:50:08,355 INFO: NIC 80:af:f2:f6:58:b7/192.168.0.10 enabled - 2023-08-08 15:50:08,406 INFO: Attempting to ping 192.168.0.13 - 2023-08-08 15:50:08,406 INFO: No entry in ARP cache for 192.168.0.13 - 2023-08-08 15:50:08,406 INFO: Sending ARP request from NIC 80:af:f2:f6:58:b7/192.168.0.10 for ip 192.168.0.13 - 2023-08-08 15:50:08,413 INFO: Received ARP response for 192.168.0.13 from 84:20:7c:ec:a5:c6 via NIC 80:af:f2:f6:58:b7/192.168.0.10 - 2023-08-08 15:50:08,413 INFO: Adding ARP cache entry for 84:20:7c:ec:a5:c6/192.168.0.13 via NIC 80:af:f2:f6:58:b7/192.168.0.10 - 2023-08-08 15:50:08,415 INFO: Sending echo request to 192.168.0.13 - 2023-08-08 15:50:08,417 INFO: Received echo reply from 192.168.0.13 - 2023-08-08 15:50:08,419 INFO: Sending echo request to 192.168.0.13 - 2023-08-08 15:50:08,421 INFO: Received echo reply from 192.168.0.13 - 2023-08-08 15:50:08,422 INFO: Sending echo request to 192.168.0.13 - 2023-08-08 15:50:08,424 INFO: Received echo reply from 192.168.0.13 - 2023-08-08 15:50:08,425 INFO: Sending echo request to 192.168.0.13 - 2023-08-08 15:50:08,427 INFO: Received echo reply from 192.168.0.13 - - -**node_b sys log** - -.. code-block:: - - 2023-08-08 15:50:08,357 INFO: Connected NIC 98:ad:eb:7c:dc:cb/192.168.0.11 - 2023-08-08 15:50:08,357 INFO: Turned on - 2023-08-08 15:50:08,357 INFO: NIC 98:ad:eb:7c:dc:cb/192.168.0.11 enabled - 2023-08-08 15:50:08,410 INFO: Received ARP request for 192.168.0.13 from 80:af:f2:f6:58:b7/192.168.0.10 - 2023-08-08 15:50:08,410 INFO: Ignoring ARP request for 192.168.0.13 - - -**node_c sys log** - -.. code-block:: - - 2023-08-08 15:50:08,358 INFO: Connected NIC bc:72:82:5d:82:a4/192.168.0.12 - 2023-08-08 15:50:08,358 INFO: Turned on - 2023-08-08 15:50:08,358 INFO: NIC bc:72:82:5d:82:a4/192.168.0.12 enabled - 2023-08-08 15:50:08,411 INFO: Received ARP request for 192.168.0.13 from 80:af:f2:f6:58:b7/192.168.0.10 - 2023-08-08 15:50:08,411 INFO: Ignoring ARP request for 192.168.0.13 - - -**node_d sys log** - -.. code-block:: - - 2023-08-08 15:50:08,359 INFO: Connected NIC 84:20:7c:ec:a5:c6/192.168.0.13 - 2023-08-08 15:50:08,360 INFO: Turned on - 2023-08-08 15:50:08,360 INFO: NIC 84:20:7c:ec:a5:c6/192.168.0.13 enabled - 2023-08-08 15:50:08,412 INFO: Received ARP request for 192.168.0.13 from 80:af:f2:f6:58:b7/192.168.0.10 - 2023-08-08 15:50:08,412 INFO: Adding ARP cache entry for 80:af:f2:f6:58:b7/192.168.0.10 via NIC 84:20:7c:ec:a5:c6/192.168.0.13 - 2023-08-08 15:50:08,412 INFO: Sending ARP reply from 84:20:7c:ec:a5:c6/192.168.0.13 to 192.168.0.10/80:af:f2:f6:58:b7 - 2023-08-08 15:50:08,416 INFO: Received echo request from 192.168.0.10 - 2023-08-08 15:50:08,417 INFO: Sending echo reply to 192.168.0.10 - 2023-08-08 15:50:08,420 INFO: Received echo request from 192.168.0.10 - 2023-08-08 15:50:08,420 INFO: Sending echo reply to 192.168.0.10 - 2023-08-08 15:50:08,423 INFO: Received echo request from 192.168.0.10 - 2023-08-08 15:50:08,423 INFO: Sending echo reply to 192.168.0.10 - 2023-08-08 15:50:08,426 INFO: Received echo request from 192.168.0.10 - 2023-08-08 15:50:08,426 INFO: Sending echo reply to 192.168.0.10 - - - -**switch_1 sys log** - -.. code-block:: - - 2023-08-08 15:50:08,373 INFO: Turned on - 2023-08-08 15:50:08,378 INFO: SwitchPort 9d:ac:59:a0:05:13 enabled - 2023-08-08 15:50:08,380 INFO: SwitchPort 45:f5:8e:b6:f5:d3 enabled - 2023-08-08 15:50:08,384 INFO: SwitchPort 91:d5:83:a0:02:f2 enabled - 2023-08-08 15:50:08,409 INFO: Added MAC table entry: Port 1 -> 80:af:f2:f6:58:b7 - 2023-08-08 15:50:08,413 INFO: Added MAC table entry: Port 6 -> 84:20:7c:ec:a5:c6 - - - -**switch_2 sys log** - -.. code-block:: - - 2023-08-08 15:50:08,374 INFO: Turned on - 2023-08-08 15:50:08,381 INFO: SwitchPort aa:58:fa:66:d7:be enabled - 2023-08-08 15:50:08,383 INFO: SwitchPort 72:d2:1e:88:e9:45 enabled - 2023-08-08 15:50:08,384 INFO: SwitchPort 96:77:39:d1:de:44 enabled - 2023-08-08 15:50:08,411 INFO: Added MAC table entry: Port 6 -> 80:af:f2:f6:58:b7 - 2023-08-08 15:50:08,412 INFO: Added MAC table entry: Port 2 -> 84:20:7c:ec:a5:c6 +The Node class is the most crucial component defined in base.py, serving as the parent class for all nodes within a +PrimAITE network simulation. + +It encapsulates the following key attributes and behaviors: + +- ``hostname`` - The node's hostname on the network. +- ``network_interfaces`` - Dict of NetworkInterface objects attached to the node. +- ``operating_state`` - The hardware state (on/off) of the node. +- ``sys_log`` - System log to record node events. +- ``session_manager`` - Manages user sessions on the node. +- ``software_manager`` - Manages software and services installed on the node. +- ``connect_nic()`` - Connects a NetworkInterface to the node. +- ``disconnect_nic()`` - Disconnects a NetworkInterface from the node. +- ``receive_frame()`` - Receive and process an incoming network frame. +- ``apply_timestep()`` - Progresses node state for a simulation timestep. +- ``power_on()`` - Powers on the node and enables NICs. +- ``power_off()`` - Powers off the node and disables NICs. + + +The Node class handles installation of system software, network connectivity, frame processing, system logging, and +power states. It establishes baseline functionality while allowing subclassing to model specific node types like hosts, +routers, firewalls etc. The flexible architecture enables composing complex network topologies. diff --git a/docs/source/simulation_components/network/network.rst b/docs/source/simulation_components/network/network.rst index cb6d9392..533a15f2 100644 --- a/docs/source/simulation_components/network/network.rst +++ b/docs/source/simulation_components/network/network.rst @@ -66,9 +66,9 @@ we'll use the following Network that has a client, server, two switches, and a r .. code-block:: python - network.connect(endpoint_a=router_1.ethernet_ports[1], endpoint_b=switch_1.switch_ports[6]) + network.connect(endpoint_a=router_1.network_interfaces[1], endpoint_b=switch_1.network_interface[6]) router_1.enable_port(1) - network.connect(endpoint_a=router_1.ethernet_ports[2], endpoint_b=switch_2.switch_ports[6]) + network.connect(endpoint_a=router_1.network_interfaces[2], endpoint_b=switch_2.network_interface[6]) router_1.enable_port(2) 6. Create the Client and Server nodes. @@ -94,8 +94,8 @@ we'll use the following Network that has a client, server, two switches, and a r .. code-block:: python - network.connect(endpoint_a=switch_2.switch_ports[1], endpoint_b=client_1.ethernet_port[1]) - network.connect(endpoint_a=switch_1.switch_ports[1], endpoint_b=server_1.ethernet_port[1]) + network.connect(endpoint_a=switch_2.network_interface[1], endpoint_b=client_1.network_interface[1]) + network.connect(endpoint_a=switch_1.network_interface[1], endpoint_b=server_1.network_interface[1]) 8. Add ACL rules on the Router to allow ARP and ICMP traffic. diff --git a/docs/source/simulation_components/network/network_interfaces.rst b/docs/source/simulation_components/network/network_interfaces.rst new file mode 100644 index 00000000..9e1ad80a --- /dev/null +++ b/docs/source/simulation_components/network/network_interfaces.rst @@ -0,0 +1,118 @@ +.. only:: comment + + © Crown-owned copyright 2023, Defence Science and Technology Laboratory UK + +################################# +Network Interface Hierarchy Model +################################# + +The network interface hierarchy model is designed to represent the various types of network interfaces and their +functionalities within a networking system. This model is organised into five distinct layers, each serving a specific +purpose in the abstraction, implementation, and utilisation of network interfaces. This hierarchical structure +facilitates modular development, enhances maintainability, and supports scalability by clearly separating concerns and +allowing for focused enhancements within each layer. + +.. image:: primaite_network_interface_model.png + +Layer Descriptions +================== + +#. **Base Layer** + + * **Purpose:** Serves as the foundation of the hierarchy, defining the most abstract properties and behaviours common + to all network interfaces. + * **Content:** Contains the NetworkInterface class, which abstracts basic functionalities such as enabling/disabling + the interface, sending, and receiving frames. + * **Significance:** Ensures that core functionalities are universally available across all types of network + interfaces, promoting code reuse and consistency. + +#. **Connection Type Layer** + + * **Purpose:** Differentiates network interfaces based on their physical connection type: wired or wireless. + * **Content:** Includes ``WiredNetworkInterface`` and ``WirelessNetworkInterface`` classes, each tailoring the base + functionalities to specific mediums. + * **Significance:** Allows the development of medium-specific features (e.g., handling point-to-point links in + wired devices) while maintaining a clear separation from IP-related functionalities. + +#. **IP Layer** + + * **Purpose:** Introduces Internet Protocol (IP) capabilities to network interfaces, enabling IP-based networking. + * **Content:** Includes ``IPWiredNetworkInterface`` and ``IPWirelessNetworkInterface`` classes, extending connection + type-specific classes with IP functionalities. + * **Significance:** Facilitates the implementation of IP address assignment, subnetting, and other Layer 3 + networking features, crucial for modern networking applications. + +#. **Interface Layer** + + * **Purpose:** Defines concrete implementations of network interfaces for specific devices or roles within a network. + * **Content:** Includes ``NIC``, ``RouterInterface``, ``SwitchPort``, ``WirelessNIC``, and ``WirelessAccessPoint`` + classes, each designed for a particular networking function or device. + * **Significance:** This layer allows developers to directly utilise or extend pre-built interfaces tailored to + specific networking tasks, enhancing development efficiency and clarity. + +#. **Device Layer** + + * **Purpose:** Maps the concrete interface implementations to their respective devices within a network, + illustrating practical usage scenarios. + * **Content:** Conceptually groups devices such as ``Computer``, ``Server``, ``Switch``, ``Router``, and ``Firewall`` + with the interfaces they utilise (e.g., ``Computer`` might use ``NIC`` or ``WirelessNIC``). + * **Significance:** Provides a clear understanding of how various network interfaces are applied in real-world + devices, aiding in system design and architecture planning. + + +Network Interface Classes +========================= + +**NetworkInterface (Base Layer)** + +Abstract base class defining core interface properties like MAC address, speed, MTU. +Requires subclasses implement key methods like send/receive frames, enable/disable interface. +Establishes universal network interface capabilities. + +**WiredNetworkInterface (Connection Type Layer)** + +- Extends NetworkInterface for wired connection interfaces. +- Adds notions of physical/logical connectivity and link management. +- Mandates subclasses implement wired-specific methods. + +**WirelessNetworkInterface (Connection Type Layer)** + +- Extends NetworkInterface for wireless interfaces. +- Encapsulates wireless-specific behaviours like signal strength handling. +- Requires wireless-specific methods in subclasses. + +**Layer3Interface (IP Layer)** + +- Introduces IP addressing abilities with ip_address and subnet_mask. +- Validates address configuration. +- Enables participation in IP networking. + +**IPWiredNetworkInterface (IP Layer)** + +- Merges Layer3Interface and WiredNetworkInterface. +- Defines wired interfaces with IP capabilities. +- Meant to be extended, doesn't implement methods. + +**IPWirelessNetworkInterface (IP Layer)** + +- Combines Layer3Interface and WirelessNetworkInterface. +- Represents wireless interfaces with IP capabilities. +- Intended to be extended and specialised. + +**NIC (Interface Layer)** + +- Concrete wired NIC implementation combining IPWiredNetworkInterface and Layer3Interface. +- Provides network connectivity for host nodes. +- Manages MAC and IP addressing, frame processing. + +**WirelessNIC (Interface Layer)** + +- Concrete wireless NIC implementation combining IPWirelessNetworkInterface and Layer3Interface. +- Delivers wireless connectivity with IP for hosts. +- Handles wireless transmission/reception. + +**WirelessAccessPoint (Interface Layer)** + +- Concrete wireless access point implementation using IPWirelessNetworkInterface and Layer3Interface. +- Bridges wireless and wired networks. +- Manages wireless network. diff --git a/docs/source/simulation_components/network/nodes/host_node.rst b/docs/source/simulation_components/network/nodes/host_node.rst new file mode 100644 index 00000000..bc3c13a5 --- /dev/null +++ b/docs/source/simulation_components/network/nodes/host_node.rst @@ -0,0 +1,47 @@ + +######### +Host Node +######### + +The ``host_node.py`` module is a core component of the PrimAITE project, aimed at simulating network host. It +encapsulates the functionality necessary for modelling the behaviour, communication capabilities, and interactions of +hosts in a networked environment. + + +HostNode Class +============== + +The ``HostNode`` class acts as a foundational representation of a networked device or computer, capable of both +initiating and responding to network communications. + +**Attributes:** + +- Manages IP addressing with support for IPv4. +- Employs ``NIC`` or ``WirelessNIC`` (subclasses of``IPWiredNetworkInterface``) to simulate wired network connections. +- Integrates with ``SysLog`` for logging operational events, aiding in debugging and monitoring the host node's + behaviour. + +**Key Methods:** + +- Facilitates the sending and receiving of ``Frame`` objects to simulate data link layer communications. +- Manages a variety of network services and applications, enhancing the simulation's realism and functionality. + +Default Services and Applications +================================= + +Both the ``HostNode`` and its subclasses come equipped with a suite of default services and applications critical for +fundamental network operations: + +1. **ARP (Address Resolution Protocol):** The ``HostARP`` subclass enhances ARP functionality for host-specific + operations. + +2. **DNS (Domain Name System) Client:** Facilitates domain name resolution to IP addresses, enabling web navigation. + +3. **FTP (File Transfer Protocol) Client:** Supports file transfers across the network. + +4. **ICMP (Internet Control Message Protocol):** Utilised for network diagnostics and control, such as executing ping + requests. + +5. **NTP (Network Time Protocol) Client:** Synchronises the host's clock with network time servers. + +6. **Web Browser:** A simulated application that allows the host to request and display web content. diff --git a/docs/source/simulation_components/network/nodes/network_node.rst b/docs/source/simulation_components/network/nodes/network_node.rst new file mode 100644 index 00000000..eb9997ba --- /dev/null +++ b/docs/source/simulation_components/network/nodes/network_node.rst @@ -0,0 +1,41 @@ +.. only:: comment + + © Crown-owned copyright 2023, Defence Science and Technology Laboratory UK + +############ +Network Node +############ + + +The ``network_node.py`` module within the PrimAITE project is pivotal for simulating network nodes like routers and +switches, which are integral to network traffic management. This module establishes the framework for these devices, +enabling them to receive and process network frames effectively. + +Overview +======== + +The module defines the ``NetworkNode`` class, an abstract base class that outlines essential behaviours for network +devices tasked with handling network traffic. It is designed to be extended by more specific device simulations that +implement these foundational capabilities. + +NetworkNode Class +================= + +The ``NetworkNode`` class is at the heart of the module, providing an interface for network devices that participate +in the transmission and routing of data within the simulated environment. + +**Key Features:** + +- **Frame Processing:** Central to the class is the ability to receive and process network frames, facilitating the +simulation of data flow through network devices. + +- **Abstract Methods:** Includes abstract methods such as ``receive_frame``, which subclasses must implement to specify + how devices handle incoming traffic. + +- **Extensibility:** Designed for extension, allowing for the creation of specific device simulations, such as router + and switch classes, that embody unique behaviours and functionalities. + + +The ``network_node.py`` module's abstract approach to defining network devices allows the PrimAITE project to simulate +a wide range of network behaviours and scenarios comprehensively. By providing a common framework for all network +nodes, it facilitates the development of a modular and scalable simulation environment. diff --git a/docs/source/simulation_components/network/nodes/router.rst b/docs/source/simulation_components/network/nodes/router.rst new file mode 100644 index 00000000..7679baa0 --- /dev/null +++ b/docs/source/simulation_components/network/nodes/router.rst @@ -0,0 +1,41 @@ +.. only:: comment + + © Crown-owned copyright 2023, Defence Science and Technology Laboratory UK + +###### +Router +###### + +The ``router.py`` module is a pivotal component of the PrimAITE, designed to simulate the complex functionalities of a +router within a network simulation. Routers are essential for directing traffic between different network segments, +and this module provides the tools necessary to model these devices' behaviour and capabilities accurately. + +Router Class +------------ + +The ``Router`` class embodies the core functionalities of a network router, extending the ``NetworkNode`` class to +incorporate routing-specific behaviours. + +**Key Features:** + +- **IP Routing:** Supports dynamic handling of IP packets, including forwarding based on destination IP addresses and + subnetting. +- **Routing Table:** Maintains a routing table to determine the best path for forwarding packets. +- **Protocol Support:** Implements support for key networking protocols, including ARP for address resolution and ICMP + for diagnostic messages. +- **Interface Management:** Manages multiple ``RouterInterface`` instances, enabling connections to different network + segments. +- **Network Interface Configuration:** Tools for configuring router interfaces, including setting IP addresses, subnet + masks, and enabling/disabling interfaces. +- **Logging and Monitoring:** Integrates with ``SysLog`` for logging operational events, aiding in debugging and + monitoring router behaviour. + +**Operations:** + +- **Packet Forwarding:** Utilises the routing table to forward packets to their correct destination across + interconnected networks. +- **ARP Handling:** Responds to ARP requests for any IP addresses configured on its interfaces, facilitating + communication within local networks. +- **ICMP Processing:** Generates and processes ICMP packets, such as echo requests and replies, for network diagnostics. + +The ``router.py`` module offers a comprehensive simulation of router functionalities. By providing detailed modelling of router operations, including packet forwarding, interface management, and protocol handling, PrimAITE enables the exploration of advanced network topologies and routing scenarios. diff --git a/docs/source/simulation_components/network/nodes/switch.rst b/docs/source/simulation_components/network/nodes/switch.rst new file mode 100644 index 00000000..0595f363 --- /dev/null +++ b/docs/source/simulation_components/network/nodes/switch.rst @@ -0,0 +1,29 @@ +.. only:: comment + + © Crown-owned copyright 2023, Defence Science and Technology Laboratory UK + +###### +Switch +###### + +The ``switch.py`` module is a crucial component of the PrimAITE, aimed at simulating network switches within a network simulation environment. Network switches play a vital role in managing data flow within local area networks (LANs) by forwarding frames based on MAC addresses. This module provides a comprehensive framework for modelling switch operations and behaviours. + +Switch Class Overview +--------------------- + +The module introduces the concept of switch ports through the ``SwitchPort`` class, which extends the functionality of ``WiredNetworkInterface`` to simulate the operation of switch ports in a network. + +**Key Features:** + +- **Data Link Layer Operation:** Operates at the data link layer (Layer 2) of the OSI model, handling the reception and forwarding of frames based on MAC addresses. +- **Port Management:** Tools for configuring switch ports, including enabling/disabling ports, setting port speeds, and managing port security features. +- **Logging and Monitoring:** Integrates with ``SysLog`` for logging operational events, aiding in debugging and + monitoring switch behaviour. + +Functionality and Implementation +--------------------------------- + +- **MAC Address Learning:** Dynamically learns and associates MAC addresses with switch ports, enabling intelligent frame forwarding. +- **Frame Forwarding:** Utilises the learned MAC address table to forward frames only to the specific port associated with the destination MAC address, minimising unnecessary network traffic. + +The ``switch.py`` module offers a realistic and configurable representation of switch operations. By detailing the functionalities of the ``SwitchPort`` class, the module lays the foundation for simulating complex network topologies. diff --git a/docs/source/simulation_components/network/primaite_network_interface_model.png b/docs/source/simulation_components/network/primaite_network_interface_model.png new file mode 100644 index 0000000000000000000000000000000000000000..68b052936ca54a5610520d0af17323216e1e5eb0 GIT binary patch literal 46770 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 bI60eQ9R7P5h0Ll9RA6y3Ihl59n=h>9pm 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 bool: - """ - Receive and process a network frame from the connected link, provided the NIC is enabled. - - This method is tailored for router behavior. It decrements the frame's Time To Live (TTL), checks for TTL - expiration, and captures the frame using PCAP (Packet Capture). The frame is accepted if it is destined for - this NIC's MAC address or is a broadcast frame. - - Key Differences from Standard NIC: - - Does not perform Layer 3 (IP-based) broadcast checks. - - Only checks for Layer 2 (Ethernet) destination MAC address and broadcast frames. - - :param frame: The network frame being received. This should be an instance of the Frame class. - :return: Returns True if the frame is processed and passed to the connected node, False otherwise. - """ - if self.enabled: - frame.decrement_ttl() - if frame.ip and frame.ip.ttl < 1: - self._connected_node.sys_log.info("Frame discarded as TTL limit reached") - return False - frame.set_received_timestamp() - self.pcap.capture_inbound(frame) - # If this destination or is broadcast - if frame.ethernet.dst_mac_addr == self.mac_address or frame.ethernet.dst_mac_addr == "ff:ff:ff:ff:ff:ff": - self._connected_node.receive_frame(frame=frame, from_network_interface=self) - return True - return False - - def __str__(self) -> str: - return f"{self.mac_address}/{self.ip_address}" - - class RouterInterface(IPWiredNetworkInterface): """ Represents a Router Interface.