mirror of
https://github.com/jmcorgan/fips.git
synced 2026-08-09 16:24:45 +00:00
Implement raw Ethernet transport using AF_PACKET SOCK_DGRAM on Linux with EtherType 0x88B5 (IEEE experimental range) and 1-byte frame type prefix (0x00=data, 0x01=beacon). Transport implementation: - EthernetConfig with interface, ethertype, MTU, buffer sizes, and four independent discovery knobs (discovery, announce, auto_connect, accept_connections) - PacketSocket/AsyncPacketSocket wrappers with ioctl helpers for interface index, MAC address, and MTU queries - EthernetTransport with Transport trait impl, async start/stop/send, receive loop dispatching data frames and discovery beacons - Discovery beacons (34 bytes: type + version + x-only pubkey) with DiscoveryBuffer for peer accumulation and dedup - Atomic statistics counters (frames, bytes, errors, beacons) - Platform-gated with #[cfg(target_os = "linux")] Transport-layer discovery integration: - Promote auto_connect() and accept_connections() to Transport trait with default implementations and TransportHandle dispatch - Extract initiate_connection() so both static peer config and discovery auto-connect share the same handshake initiation path - Add poll_transport_discovery() to the tick handler to drain discovery buffers and auto-connect to discovered peers - Enforce accept_connections() in handle_msg1() — transports with accept_connections=false silently drop inbound handshakes Node integration: - create_transports() handles Ethernet named instances - resolve_ethernet_addr() parses "interface/mac" address format - transport_mtu() generalized for multi-transport operation Test harness: - VethPair RAII struct for veth pair lifecycle management - Three #[ignore] integration tests requiring root/CAP_NET_RAW: two-node handshake, data exchange, mixed transport coexistence - Chaos harness: transport-aware topology model, VethManager for veth pairs between Docker containers, Ethernet-aware config gen, netem split (HTB+u32 for UDP, root netem for veth), transport-aware link flaps and node churn with veth re-setup - Container entrypoint waits for configured Ethernet interfaces before starting FIPS (handles veth creation timing) - New scenarios: ethernet-only (4-node ring), ethernet-mesh (6-node mixed UDP+Ethernet with netem and link flaps) Documentation: - fips-transport-layer.md: Ethernet section, beacon discovery, WiFi compatibility, updated discovery state, trait surface additions, implementation status table - fips-configuration.md: Ethernet parameter table, named instances, peer address format, mixed UDP+Ethernet example, complete reference - fips-wire-formats.md: Ethernet frame type prefix note
78 lines
1.7 KiB
Python
78 lines
1.7 KiB
Python
"""Generate docker-compose.yml for a simulation topology."""
|
|
|
|
from __future__ import annotations
|
|
|
|
import os
|
|
|
|
from jinja2 import Template
|
|
|
|
from .scenario import Scenario
|
|
from .topology import SimTopology
|
|
|
|
# Jinja2 template for the compose file.
|
|
# build context points back to the testing/chaos root where the Dockerfile lives.
|
|
_COMPOSE_TEMPLATE = Template(
|
|
"""\
|
|
networks:
|
|
fips-net:
|
|
driver: bridge
|
|
ipam:
|
|
config:
|
|
- subnet: {{ subnet }}
|
|
|
|
x-fips-common: &fips-common
|
|
build:
|
|
context: ../..
|
|
cap_add:
|
|
- NET_ADMIN
|
|
- NET_RAW
|
|
devices:
|
|
- /dev/net/tun:/dev/net/tun
|
|
sysctls:
|
|
- net.ipv6.conf.all.disable_ipv6=0
|
|
restart: "no"
|
|
env_file:
|
|
- ./npubs.env
|
|
environment:
|
|
- RUST_LOG={{ rust_log }}
|
|
- RUST_BACKTRACE=1
|
|
|
|
services:
|
|
{% for node in nodes %}
|
|
{{ node.node_id }}:
|
|
<<: *fips-common
|
|
container_name: fips-node-{{ node.node_id }}
|
|
hostname: {{ node.node_id }}
|
|
volumes:
|
|
- ../../resolv.conf:/etc/resolv.conf:ro
|
|
- ./{{ node.node_id }}.yaml:/etc/fips/fips.yaml:ro
|
|
networks:
|
|
fips-net:
|
|
ipv4_address: {{ node.docker_ip }}
|
|
{% endfor %}
|
|
"""
|
|
)
|
|
|
|
|
|
def generate_compose(
|
|
topology: SimTopology,
|
|
scenario: Scenario,
|
|
output_dir: str,
|
|
) -> str:
|
|
"""Render docker-compose.yml and write to output_dir. Returns the file path."""
|
|
os.makedirs(output_dir, exist_ok=True)
|
|
|
|
nodes = [topology.nodes[nid] for nid in sorted(topology.nodes)]
|
|
|
|
content = _COMPOSE_TEMPLATE.render(
|
|
subnet=scenario.topology.subnet,
|
|
rust_log=scenario.logging.rust_log,
|
|
nodes=nodes,
|
|
)
|
|
|
|
path = os.path.join(output_dir, "docker-compose.yml")
|
|
with open(path, "w") as f:
|
|
f.write(content)
|
|
|
|
return path
|