137 return ns3::Ipv4Address::GetAny();
139 for (uint32_t i = 0; i < ipv4->GetNInterfaces(); ++i) {
140 for (uint32_t j = 0; j < ipv4->GetNAddresses(i); ++j) {
141 auto ifaddr = ipv4->GetAddress(i, j);
142 auto addr = ifaddr.GetLocal();
143 if (addr != ns3::Ipv4Address(
"127.0.0.1") && addr != ns3::Ipv4Address::GetZero()) {
148 return ns3::Ipv4Address::GetAny();
152 NS_LOG_INFO(
"Building " << spec.
classicalEdges.size() <<
" classical links");
155 ns3::Ipv4AddressHelper ip;
162 NS_LOG_ERROR(
"Classical edge refers to unknown nodes: " << e.u <<
" - " << e.v);
166 ns3::NodeContainer pair(itU->second, itV->second);
169 ns3::PointToPointHelper p2p;
170 std::ostringstream dr;
171 dr << e.mbps <<
"Mbps";
172 p2p.SetDeviceAttribute(
"DataRate", ns3::StringValue(dr.str()));
174 double delayNs = e.delayNsPerKm * e.distanceKm;
175 std::ostringstream dl;
176 dl << delayNs <<
"ns";
177 p2p.SetChannelAttribute(
"Delay", ns3::StringValue(dl.str()));
180 std::string qmax = e.queueMax.empty() ?
m_defaultQueue : e.queueMax;
181 p2p.SetQueue(
"ns3::DropTailQueue<Packet>",
"MaxSize",
182 ns3::QueueSizeValue(ns3::QueueSize(qmax)));
184 auto devices = p2p.Install(pair);
188 uint8_t a =
static_cast<uint8_t
>((netId >> 8) & 0xFF);
189 uint8_t b =
static_cast<uint8_t
>(netId & 0xFF);
190 std::ostringstream base;
191 base <<
"10." << unsigned(a) <<
"." << unsigned(b) <<
".0";
192 ip.SetBase(ns3::Ipv4Address(base.str().c_str()),
"255.255.255.252");
202 NS_LOG_INFO(
"Quantum edges: " << spec.
quantumEdges.size());
207 NS_LOG_WARN(
"Quantum edge refers to unknown nodes: " << e.u <<
" - " << e.v <<
"\n");
210 auto a = ns3::DynamicCast<q2ns::QNode>(itU->second);
211 auto b = ns3::DynamicCast<q2ns::QNode>(itV->second);
213 NS_LOG_ERROR(
"Quantum edge endpoints are not QNodes: " << e.u <<
" - " << e.v <<
"\n");
216 const double delayNs = e.delayNsPerKm * e.distanceKm;
217 ns3::Time oneWay = ns3::NanoSeconds(
static_cast<uint64_t
>(std::max(0.0, delayNs)));
219 ch->SetAttribute(
"Delay", ns3::TimeValue(oneWay));
225 NS_LOG_INFO(
"Installing " << spec.
sessions.size() <<
" teleportation sessions");
228 std::unordered_set<uint64_t> usedPortKey;
229 auto keyOf = [&](ns3::Ptr<ns3::Node> n, uint16_t p) -> uint64_t {
230 return (
static_cast<uint64_t
>(n->GetId()) << 32) |
static_cast<uint64_t
>(p);
233 for (
const auto& s : spec.
sessions) {
235 NS_LOG_ERROR(
"Session refers to unknown nodes: " << s.src <<
" -> " << s.dst);
240 auto dstQ = ns3::DynamicCast<q2ns::QNode>(dstNode);
244 if (dstAddr == ns3::Ipv4Address::GetAny()) {
245 NS_LOG_WARN(
"Destination node " << s.dst <<
" has no IPv4 address yet");
249 uint16_t ctrlPort = s.ctrlPort ? s.ctrlPort :
AllocatePort(s.sessionId);
251 uint64_t k = keyOf(dstNode, ctrlPort);
252 if (usedPortKey.count(k)) {
253 NS_LOG_WARN(
"Two sessions target dst=" << s.dst <<
" with the same CtrlPort=" << ctrlPort
254 <<
" -- PacketSink bind conflict likely.");
256 usedPortKey.insert(k);
261 std::string proto = s.protocol;
266 if ((e.u == s.src && e.v == s.dst) || (e.u == s.dst && e.v == s.src)) {
277 std::ostringstream tag;
278 tag <<
"teleport_target_s" << s.sessionId;
282 auto app = ns3::CreateObject<TeleportationApp>();
283 srcNode->AddApplication(app);
284 app->SetAttribute(
"Role", ns3::StringValue(
"source"));
285 app->SetAttribute(
"Peer", ns3::Ipv4AddressValue(dstAddr));
286 app->SetAttribute(
"CtrlPort", ns3::UintegerValue(ctrlPort));
287 app->SetAttribute(
"ClassicalProtocol", ns3::StringValue(proto));
288 app->SetAttribute(
"Backend", ns3::StringValue(backend));
289 app->SetAttribute(
"TargetQubitTag", ns3::StringValue(tag.str()));
290 app->SetAttribute(
"SessionId", ns3::UintegerValue(s.sessionId));
291 app->SetAttribute(
"SessionStartTime", ns3::TimeValue(ns3::Seconds(s.start_s)));
293 app->SetAttribute(
"PeerQNode", ns3::PointerValue(dstQ));
295 app->SetNetController(
m_nc);
299 app->SetStartTime(ns3::Seconds(0.0));
300 app->SetStopTime(ns3::Seconds(1e9));
305 auto app = ns3::CreateObject<TeleportationApp>();
306 dstNode->AddApplication(app);
307 app->SetAttribute(
"Role", ns3::StringValue(
"sink"));
308 app->SetAttribute(
"Peer",
309 ns3::Ipv4AddressValue(ns3::Ipv4Address::GetAny()));
310 app->SetAttribute(
"CtrlPort", ns3::UintegerValue(ctrlPort));
311 app->SetAttribute(
"ClassicalProtocol", ns3::StringValue(proto));
312 app->SetAttribute(
"Backend", ns3::StringValue(backend));
313 app->SetAttribute(
"TargetQubitTag", ns3::StringValue(tag.str()));
314 app->SetAttribute(
"SessionId", ns3::UintegerValue(s.sessionId));
315 app->SetAttribute(
"SessionStartTime", ns3::TimeValue(ns3::Seconds(s.start_s)));
316 app->SetNetController(
m_nc);
320 app->SetStartTime(ns3::Seconds(0.0));
321 app->SetStopTime(ns3::Seconds(1e9));