OLD | NEW |
(Empty) | |
| 1 # QUIC network simulator |
| 2 |
| 3 This directory contains a discrete event network simulator which QUIC code uses |
| 4 for testing congestion control and other transmission control code that requires |
| 5 a network simulation for tests on QuicConnection level of abstraction. |
| 6 |
| 7 ## Actors |
| 8 |
| 9 The core of the simulator is the Simulator class, which maintains a virtual |
| 10 clock and an event queue. Any object in a simulation that needs to schedule |
| 11 events has to subclass Actor. Subclassing Actor involves: |
| 12 |
| 13 1. Calling the `Actor::Actor(Simulator*, std::string)` constructor to establish |
| 14 the name of the object and the simulator it is associated with. |
| 15 2. Calling `Schedule(QuicTime)` to schedule the time at which `Act()` method is |
| 16 called. `Schedule` will only cause the object to be rescheduled if the time |
| 17 for which it is currently scheduled is later than the new time. |
| 18 3. Implementing `Act()` method with the relevant logic. The actor will be |
| 19 removed from the event queue right before `Act()` is called. |
| 20 |
| 21 Here is a simple example of an object that outputs simulation time into the log |
| 22 every 100 ms. |
| 23 |
| 24 ```c++ |
| 25 class LogClock : public Actor { |
| 26 public: |
| 27 LogClock(Simulator* simulator, std::string name) : Actor(simulator, name) { |
| 28 Schedule(clock_->Now()); |
| 29 } |
| 30 ~LogClock() override {} |
| 31 |
| 32 void Act() override { |
| 33 VLOG(1) << "The current time is " << clock_->Now().ToDebuggingValue(); |
| 34 Schedule(clock_->Now() + QuicTime::Delta::FromMilliseconds(100)); |
| 35 } |
| 36 }; |
| 37 ``` |
| 38 |
| 39 A QuicAlarm object can be used to schedule events in the simulation using |
| 40 `Simulator::GetAlarmFactory()`. |
| 41 |
| 42 ## Ports |
| 43 |
| 44 The simulated network transfers packets, which are modelled as an instance of |
| 45 struct `Packet`. A packet consists of source and destination address (which are |
| 46 just plain strings), a transmission timestamp and the UDP-layer payload. |
| 47 |
| 48 The simulation uses the push model: any object that wishes to transfer a packet |
| 49 to another component in the simulation has to explicitly do it itself. Any |
| 50 object that can accept a packet is called a *port*. There are two types of |
| 51 ports: unconstrained ports, which can always accept packets, and constrained |
| 52 ports, which signal when they can accept a new packet. |
| 53 |
| 54 An endpoint is an object that is connected to the network and can both receive |
| 55 and send packets. In our model, the endpoint always receives packets as an |
| 56 unconstrained port (*RX port*), and always writes packets to a constrained port |
| 57 (*TX port*). |
| 58 |
| 59 ## Links |
| 60 |
| 61 The `SymmetricLink` class models a symmetric duplex links with finite bandwidth |
| 62 and propagation delay. It consists of a pair of identical `OneWayLink`s, which |
| 63 accept packets as a constrained port (where constrain comes from the finiteness |
| 64 of bandwidth) and outputs them into an unconstrained port. Two endpoints |
| 65 connected via a `SymmetricLink` look like this: |
| 66 |
| 67 ```none |
| 68 Endpoint A Endpoint B |
| 69 +-----------+ SymmetricLink +-----------+ |
| 70 | | +------------------------------+ | | |
| 71 | +---------+ | +------------------------+ | +---------+ | |
| 72 | | RX port <-----| OneWayLink *<-----| TX port | | |
| 73 | +---------+ | +------------------------+ | +---------+ | |
| 74 | | | | | | |
| 75 | +---------+ | +------------------------+ | +---------+ | |
| 76 | | TX port |----->* OneWayLink |-----> RX port | | |
| 77 | +---------+ | +------------------------+ | +---------+ | |
| 78 | | +------------------------------+ | | |
| 79 +-----------+ +-----------+ |
| 80 |
| 81 ( -->* denotes constrained port) |
| 82 ``` |
| 83 |
| 84 In most common scenario, one of the endpoints is going to be a QUIC endpoint, |
| 85 and another is going to be a switch port. |
| 86 |
| 87 ## Other objects |
| 88 |
| 89 Besides `SymmetricLink`, the simulator provides the following objects: |
| 90 |
| 91 * `Queue` allows to convert a constrained port into an unconstrained one by |
| 92 buffering packets upon arrival. The queue has a finite size, and once the |
| 93 queue is full, the packets are silently dropped. |
| 94 * `Switch` simulates a multi-port learning switch with a fixed queue for each |
| 95 output port. |
| 96 * `QuicEndpoint` allows QuicConnection to be run over the simulated network. |
| 97 * `QuicEndpointMultiplexer` allows multiple connections to share the same |
| 98 network endpoint. |
OLD | NEW |