mirror of
https://github.com/cesanta/mongoose.git
synced 2026-11-06 15:51:25 +00:00
110 lines
4.0 KiB
C
110 lines
4.0 KiB
C
// Copyright (c) 2026 Cesanta Software Limited
|
|
// All rights reserved
|
|
|
|
#pragma once
|
|
|
|
#define MG_ENABLE_TCPIP 1
|
|
|
|
#include "mongoose.h"
|
|
|
|
extern const struct mg_mesh mg_mesh_a;
|
|
|
|
// A position in metres
|
|
struct pos {
|
|
double x, y, z; // Coordinates
|
|
};
|
|
|
|
struct simulator;
|
|
|
|
// Private state of the simulated radio driver.
|
|
struct radio_port {
|
|
struct simulator *sim;
|
|
struct mg_tcpip_if *lan; // Bridge LAN interface, NULL for a node
|
|
const struct pos *pos; // Location of the radio
|
|
uint64_t tx_until; // Latest transmission end, us
|
|
uint64_t tx_ready_at; // Inter-frame wait ends, us
|
|
uint64_t rx_off_until; // Latest backoff/sensing/turnaround/TX end, us
|
|
struct mg_mesh_node *mesh; // Mesh state owned by the driver
|
|
struct mg_queue rx;
|
|
uint32_t random; // Driver backoff PRNG
|
|
uint16_t address; // Preassigned radio address
|
|
};
|
|
|
|
// A bridge: forwards frames between the LAN and the radio, no IP stack
|
|
struct bridge {
|
|
struct bridge *next; // Next in simulator::bridges
|
|
struct pos pos; // Where it is
|
|
struct mg_mgr mgr; // Polls the raw radio driver
|
|
struct mg_tcpip_if lif; // LAN side: LAN driver, gets every LAN frame
|
|
struct mg_tcpip_if rif; // Radio side: radio driver, gets every frame
|
|
struct radio_port radio;
|
|
};
|
|
|
|
// A radio node: Mongoose on a radio interface
|
|
struct radio_node {
|
|
struct radio_node *next; // Next in simulator::nodes
|
|
struct pos pos; // Where it is
|
|
struct mg_mgr mgr; // Mongoose event manager
|
|
struct mg_tcpip_if rif; // Radio interface. rif.ip from DHCP, 0: none yet
|
|
struct radio_port radio;
|
|
};
|
|
|
|
struct simulator;
|
|
|
|
// LAN node: a DHCP server, 10.0.0.1. Gives each client an address made
|
|
// from its MAC, see node_ip()
|
|
struct lan_dhcp_server {
|
|
struct mg_tcpip_if lif; // Its LAN interface, no Mongoose on it
|
|
};
|
|
|
|
// LAN node: the test node, 10.0.0.2, a Mongoose instance. Waits for
|
|
// the mesh to settle, then cycles GET / through nodes until 5 s before the end
|
|
struct lan_tester {
|
|
struct mg_mgr mgr; // Its Mongoose
|
|
struct mg_tcpip_if lif; // Its LAN interface
|
|
uint64_t wait; // Mesh settle time: start requests then, us
|
|
struct radio_node *next; // Node to request next, wraps at the end
|
|
struct mg_connection *c; // Request on the way, NULL: none
|
|
uint64_t start; // When it started, us
|
|
int ok, failed; // Requests done, by result
|
|
double min, max, sum; // Times of successful requests, ms
|
|
};
|
|
|
|
enum { RADIO_BACKOFF, RADIO_CCA, RADIO_START, RADIO_END };
|
|
|
|
// One radio frame waiting on the simulated radio channel
|
|
struct radio_frame {
|
|
struct radio_frame *next;
|
|
struct mg_tcpip_if *from;
|
|
uint64_t due; // Next radio event, us
|
|
uint64_t start; // Transmission start, for receive overlap checks
|
|
uint8_t state, backoff;
|
|
bool collided;
|
|
size_t len;
|
|
uint8_t buf[1540];
|
|
};
|
|
|
|
uint64_t radio_airtime(size_t len);
|
|
|
|
// Simulator state
|
|
struct simulator {
|
|
struct radio_frame *air_head; // Pending and active frames, singly linked
|
|
uint64_t air_busy_until; // Last transmission end, for channel sensing
|
|
unsigned long air_sent, air_collisions;
|
|
unsigned long air_lost; // Receptions lost to range, random loss or TX overlap
|
|
double radio_range; // Maximum reception distance, metres
|
|
double radio_loss; // In-range reception loss probability, percent
|
|
uint32_t loss_random; // Reception-loss PRNG state
|
|
bool work_pending; // Drain immediate work before advancing time
|
|
struct pos area; // A box: all positions inside
|
|
struct bridge *bridges; // Bridges, a list
|
|
struct radio_node *nodes; // Radio nodes, a list
|
|
int num_bridges, num_nodes; // How many
|
|
uint64_t now; // Virtual time, us since the start
|
|
uint64_t duration; // Run this long, us
|
|
uint32_t last_mac; // Low 3 bytes of the last MAC given
|
|
int request_timeout_ms; // A request that takes longer failed
|
|
struct lan_dhcp_server dhcp; // DHCP server on the LAN
|
|
struct lan_tester tester; // Test node on the LAN
|
|
};
|