MCPcopy Create free account
hub / github.com/Haivision/srt / worker_TryAsyncRend_OrStore

Method worker_TryAsyncRend_OrStore

srtcore/queue.cpp:1546–1674  ·  view source on GitHub ↗

This function responds to the fact that a packet has come for a socket that does not expect to receive a normal connection request. This can be then: - a normal packet of whatever kind, just to be processed by the message loop - a rendezvous connection This function then tries to manage the packet as a rendezvous connection request in ASYNC mode; when this is not applicable, it stores the packet i

Source from the content-addressed store, hash-verified

1544// request in ASYNC mode; when this is not applicable, it stores the packet
1545// in the "receiving queue" so that it will be picked up in the "main" thread.
1546srt::EConnectStatus srt::CRcvQueue::worker_TryAsyncRend_OrStore(int32_t id, CUnit* unit, const sockaddr_any& addr)
1547{
1548 // This 'retrieve' requires that 'id' be either one of those
1549 // stored in the rendezvous queue (see CRcvQueue::registerConnector)
1550 // or simply 0, but then at least the address must match one of these.
1551 // If the id was 0, it will be set to the actual socket ID of the returned CUDT.
1552 CUDT* u = m_pRendezvousQueue->retrieve(addr, (id));
1553 if (!u)
1554 {
1555 // this socket is then completely unknown to the system.
1556 // Note that this situation may also happen at a very unfortunate
1557 // coincidence that the socket is already bound, but the registerConnector()
1558 // has not yet started. In case of rendezvous this may mean that the other
1559 // side just started sending its handshake packets, the local side has already
1560 // run the CRcvQueue::worker thread, and this worker thread is trying to dispatch
1561 // the handshake packet too early, before the dispatcher has a chance to see
1562 // this socket registered in the RendezvousQueue, which causes the packet unable
1563 // to be dispatched. Therefore simply treat every "out of band" packet (with socket
1564 // not belonging to the connection and not registered as rendezvous) as "possible
1565 // attack" and ignore it. This also should better protect the rendezvous socket
1566 // against a rogue connector.
1567 if (id == 0)
1568 {
1569 HLOGC(cnlog.Debug,
1570 log << CONID() << "AsyncOrRND: no sockets expect connection from " << addr.str()
1571 << " - POSSIBLE ATTACK, ignore packet");
1572 }
1573 else
1574 {
1575 HLOGC(cnlog.Debug,
1576 log << CONID() << "AsyncOrRND: no sockets expect socket " << id << " from " << addr.str()
1577 << " - POSSIBLE ATTACK, ignore packet");
1578 }
1579 return CONN_AGAIN; // This means that the packet should be ignored.
1580 }
1581
1582 // asynchronous connect: call connect here
1583 // otherwise wait for the UDT socket to retrieve this packet
1584 if (!u->m_config.bSynRecving)
1585 {
1586 HLOGC(cnlog.Debug, log << "AsyncOrRND: packet RESOLVED TO @" << id << " -- continuing as ASYNC CONNECT");
1587 // This is practically same as processConnectResponse, just this applies
1588 // appropriate mutex lock - which can't be done here because it's intentionally private.
1589 // OTOH it can't be applied to processConnectResponse because the synchronous
1590 // call to this method applies the lock by itself, and same-thread-double-locking is nonportable (crashable).
1591 EConnectStatus cst = u->processAsyncConnectResponse(unit->m_Packet);
1592
1593 if (cst == CONN_CONFUSED)
1594 {
1595 LOGC(cnlog.Warn, log << "AsyncOrRND: PACKET NOT HANDSHAKE - re-requesting handshake from peer");
1596 storePktClone(id, unit->m_Packet);
1597 if (!u->processAsyncConnectRequest(RST_AGAIN, CONN_CONTINUE, &unit->m_Packet, u->m_PeerAddr))
1598 {
1599 // Reuse previous behavior to reject a packet
1600 cst = CONN_REJECT;
1601 }
1602 else
1603 {

Callers

nothing calls this directly

Calls 6

retrieveMethod · 0.80
isControlMethod · 0.80
strMethod · 0.45
insertMethod · 0.45

Tested by

no test coverage detected