Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Don't delay the release of Lwip UDPEndPoint if there is no pending Lw… #22122

Merged
merged 5 commits into from
Aug 31, 2022
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 19 additions & 7 deletions src/inet/UDPEndPointImplLwIP.cpp
Original file line number Diff line number Diff line change
@@ -252,17 +252,20 @@ void UDPEndPointImplLwIP::CloseImpl()
mUDP = nullptr;
mLwIPEndPointType = LwIPEndPointType::Unknown;

// In case that there is a UDPEndPointImplLwIP::LwIPReceiveUDPMessage
// If there is a UDPEndPointImplLwIP::LwIPReceiveUDPMessage
// event pending in the event queue (SystemLayer::ScheduleLambda), we
// schedule a release call to the end of the queue, to ensure that the
// queued pointer to UDPEndPointImplLwIP is not dangling.
Retain();
CHIP_ERROR err = GetSystemLayer().ScheduleLambda([this] { Release(); });
if (err != CHIP_NO_ERROR)
if (mDelayReleaseCount != 0)
{
ChipLogError(Inet, "Unable scedule lambda: %" CHIP_ERROR_FORMAT, err.Format());
// There is nothing we can do here, accept the chance of racing
Release();
Retain();
CHIP_ERROR err = GetSystemLayer().ScheduleLambda([this] { Release(); });
if (err != CHIP_NO_ERROR)
{
ChipLogError(Inet, "Unable to schedule lambda: %" CHIP_ERROR_FORMAT, err.Format());
// There is nothing we can do here, accept the chance of racing
Release();
}
}
}

@@ -390,8 +393,13 @@ void UDPEndPointImplLwIP::LwIPReceiveUDPMessage(void * arg, struct udp_pcb * pcb
pktInfo->SrcPort = port;
pktInfo->DestPort = pcb->local_port;

// Increase mDelayReleaseCount to delay release of this UDP EndPoint while the HandleDataReceived call is
// pending on it.
ep->mDelayReleaseCount++;

CHIP_ERROR err = ep->GetSystemLayer().ScheduleLambda(
[ep, p = System::LwIPPacketBufferView::UnsafeGetLwIPpbuf(buf), pktInfo = pktInfo.get()] {
ep->mDelayReleaseCount--;
ep->HandleDataReceived(System::PacketBufferHandle::Adopt(p), pktInfo);
});

@@ -402,6 +410,10 @@ void UDPEndPointImplLwIP::LwIPReceiveUDPMessage(void * arg, struct udp_pcb * pcb
// Similarly, ScheduleLambda now has ownership of pktInfo.
pktInfo.release();
}
else
{
ep->mDelayReleaseCount--;
}
}

CHIP_ERROR UDPEndPointImplLwIP::SetMulticastLoopback(IPVersion aIPVersion, bool aLoopback)
1 change: 1 addition & 0 deletions src/inet/UDPEndPointImplLwIP.h
Original file line number Diff line number Diff line change
@@ -61,6 +61,7 @@ class UDPEndPointImplLwIP : public UDPEndPoint, public EndPointStateLwIP
static void LwIPReceiveUDPMessage(void * arg, struct udp_pcb * pcb, struct pbuf * p, const ip_addr_t * addr, u16_t port);

udp_pcb * mUDP; // LwIP User datagram protocol (UDP) control block.
std::atomic_int mDelayReleaseCount{ 0 };
};

using UDPEndPointImpl = UDPEndPointImplLwIP;