![]() |
Q2NS dev
ns-3 module
|
Q2NS follows the standard ns-3 randomness model and standards (as of ns-3.4, described here). Simulations are deterministic by default and different outcomes are obtained by changing the global Seed and/or Run values via ns3::RngSeedManager.
Q2NS centralizes stream binding and backend seeding in NetController. In typical usage, the NetController schedules stream binding to happen at simulation time 0 upon creation so that it occurs when Simulator::Run() is called and requires no extra calls, but there are alternatives for when these are not used. This is discussed below.
This document explains when and how to use SetSeed, SetRun, and NetController::AssignStreams().
Sets the global RNG seed. This defines the overall “randomness universe.” Use a value greater than 0 or else you will get a segfault.
Selects a substream (independent replication) within the chosen seed. This is the recommended way in ns-3 to obtain independent trials while keeping a fixed seed. Use a value greater than 0 or else you will get a segfault.
Explicitly binds stream indices to Q2NS objects (channels and states) and seeds backend PRNGs using a deterministic combination of:
Calling AssignStreams() multiple times is safe. Backend RNGs are reseeded only if the (Seed, Run, stream) combination changes. Repeating the same call has no effect. Note: QState backends use process-global RNGs internally. In those cases Q2NS reseeds the backend RNG deterministically whenever (Seed, Run, stream) changes. The reseeding guard is implemented in QState to avoid redundant reseeding when the same configuration is reused.
This does not create additional randomness; it ensures that randomness is deterministic and reproducible.
Each QState backend derives its RNG seed from the ns-3 Seed, Run, and assigned stream index together with a backend-specific salt. The deterministic seed derivation and reseeding logic are implemented in the QState base class so backend implementations only need to supply a salt and reseed their internal RNG.
Current salts:
QPPK (0x5150504B)QPPD (0x51505044)STAB (0x53544142)These salts are internal implementation details but guarantee that different backends do not share identical random sequences even when all other parameters are identical. Any future backend developed should have its own unique salt.
You call Simulator::Run() (or NetController::Run()).
Steps:
SetSeed and SetRun once and early, e.g. at the very beginning of main().Simulator::Run().Example:
You do not need to call AssignStreams() explicitly. Q2NS automatically binds streams at time 0 when the simulator starts.
Change Run to obtain independent replications. Change Seed to select a different overall randomness universe–in most cases this is not necessary, but it's good to explicitly set a seed so that another person should be able to exactly reproduce your results on a different machine (up to floating point and other largely negligible differences between machines, compilers, etc.).
You do not call Simulator::Run(), but you perform operations that involve randomness (e.g., measurement, noise, random channel effects).
Steps:
SetSeed and SetRun once and early, e.g. at the very beginning of main().net.AssignStreams(0) before the first random operation (substituting nc with whatever your NetController object is called). NOTE: To properly seed the backends, it's important to set the backend with net.SetQStateBackend(...) before assigning streams.Example:
Without AssignStreams(), backend RNGs may not be seeded deterministically before the first probabilistic operation, and results may differ between program runs.
SetSeed and SetRun before:Simulator::Run().Run()), call AssignStreams() before any operation that might use randomness.Simulator::Run(), either:AssignStreams() first, orAssignStreams() may be called multiple times safely before randomness occurs. If (Seed, Run, streamBase) changes, backend RNGs will be reseeded deterministically.If you create your own UniformRandomVariable or other RandomVariableStream objects:
Avoid reusing stream indices used by Q2NS.
To perform statistically independent replications:
Seed.Run.For example:
If using immediate mode, rebuild the controller per replication and call AssignStreams() again after setting the desired Seed and Run.
AssignStreams() in immediate-mode examples.Run mid-simulation reseeds everything retroactively.Simulator::Run(): Set Seed and Run early. Do not call AssignStreams() unless you know that this offers you something specific and important.Simulator::Run() but perform random operations: Set Seed and Run early, then call net.AssignStreams(0) before the first random operation.This is sufficient for reproducible and controlled randomness in Q2NS.
If you add a new QState backend that uses randomness (measurement sampling, noise, etc.), you should implement deterministic seeding via AssignStreams().
Q2NS provides helper utilities in the QState base class so backend implementations only need to:
Each backend should use a unique 64-bit salt so different backends do not accidentally generate identical random sequences when Seed, Run, and stream match.
The Q2NS convention is to use a readable ASCII tag packed into hex when possible (example below uses "MYBA"):
The salt does not need to be secret. It just needs to be unique.
Override AssignStreams() and delegate the boring stuff to the QState helper:
QState::AssignStreamsGlobal<SALT>() handles:
Seed and Run(Seed, Run, stream, SALT)(Seed, Run, stream) did not change (for a given backend salt)1 to indicate one stream index was consumedAfter seeding, use your RNG however your backend expects (uniform draws, sampling measurement outcomes, etc.):
[1] Quantum Internet Architecture: Unlocking Quantum-Native Routing via Quantum Addressing (invited paper). Marcello Caleffi and Angela Sara Cacciapuoti – in IEEE Transactions on Communications, vol. 74, pp. 3577–3599, 2026.
[2] An Extensible Quantum Network Simulator Built on ns-3: Q2NS Design and Evaluation. Adam Pearson, Francesco Mazza, Marcello Caleffi, Angela Sara Cacciapuoti – Computer Networks (Elsevier) 2026.
[3] Q2NS: A Modular Framework for Quantum Network Simulation in ns-3 (invited paper). Adam Pearson, Francesco Mazza, Marcello Caleffi, Angela Sara Cacciapuoti – Proc. QCNC 2026.
[4] Q2NS Demo: a Quantum Network Simulator based on ns-3. Francesco Mazza, Adam Pearson, Marcello Caleffi, Angela Sara Cacciapuoti – 2026.
This work has been funded by the European Union under Horizon Europe ERC-CoG grant QNattyNet, n. 101169850. Views and opinions expressed are those of the author(s) only and do not necessarily reflect those of the European Union or the European Research Council Executive Agency. Neither the European Union nor the granting authority can be held responsible for them.