mirror of
https://github.com/RGBCube/serenity
synced 2025-07-25 17:17:44 +00:00
IPv4: Split IPv4Socket::recvfrom() into packet/byte buffered functions
This code was really hard to follow since it handles two separate modes of buffering the data.
This commit is contained in:
parent
00d8ec3ead
commit
48f13f2a81
2 changed files with 45 additions and 33 deletions
|
@ -234,45 +234,37 @@ ssize_t IPv4Socket::sendto(FileDescription&, const void* data, size_t data_lengt
|
||||||
return nsent;
|
return nsent;
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t IPv4Socket::recvfrom(FileDescription& description, void* buffer, size_t buffer_length, int flags, sockaddr* addr, socklen_t* addr_length)
|
ssize_t IPv4Socket::receive_byte_buffered(FileDescription& description, void* buffer, size_t buffer_length, int, sockaddr*, socklen_t*)
|
||||||
{
|
{
|
||||||
if (addr_length && *addr_length < sizeof(sockaddr_in))
|
if (m_receive_buffer.is_empty()) {
|
||||||
return -EINVAL;
|
if (protocol_is_disconnected())
|
||||||
|
return 0;
|
||||||
|
if (!description.is_blocking())
|
||||||
|
return -EAGAIN;
|
||||||
|
|
||||||
#ifdef IPV4_SOCKET_DEBUG
|
auto res = current->block<Thread::ReadBlocker>(description);
|
||||||
kprintf("recvfrom: type=%d, local_port=%u\n", type(), local_port());
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if (buffer_mode() == BufferMode::Bytes) {
|
LOCKER(lock());
|
||||||
if (m_receive_buffer.is_empty()) {
|
if (!m_can_read) {
|
||||||
if (protocol_is_disconnected()) {
|
if (res != Thread::BlockResult::WokeNormally)
|
||||||
return 0;
|
return -EINTR;
|
||||||
}
|
|
||||||
if (!description.is_blocking()) {
|
|
||||||
return -EAGAIN;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto res = current->block<Thread::ReadBlocker>(description);
|
// Unblocked due to timeout.
|
||||||
|
return -EAGAIN;
|
||||||
LOCKER(lock());
|
|
||||||
if (!m_can_read) {
|
|
||||||
if (res != Thread::BlockResult::WokeNormally)
|
|
||||||
return -EINTR;
|
|
||||||
|
|
||||||
// Unblocked due to timeout.
|
|
||||||
return -EAGAIN;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ASSERT(!m_receive_buffer.is_empty());
|
|
||||||
int nreceived = m_receive_buffer.read((u8*)buffer, buffer_length);
|
|
||||||
if (nreceived > 0)
|
|
||||||
current->did_ipv4_socket_read((size_t)nreceived);
|
|
||||||
|
|
||||||
m_can_read = !m_receive_buffer.is_empty();
|
|
||||||
return nreceived;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ASSERT(!m_receive_buffer.is_empty());
|
||||||
|
int nreceived = m_receive_buffer.read((u8*)buffer, buffer_length);
|
||||||
|
if (nreceived > 0)
|
||||||
|
current->did_ipv4_socket_read((size_t)nreceived);
|
||||||
|
|
||||||
|
m_can_read = !m_receive_buffer.is_empty();
|
||||||
|
return nreceived;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssize_t IPv4Socket::receive_packet_buffered(FileDescription& description, void* buffer, size_t buffer_length, int flags, sockaddr* addr, socklen_t* addr_length)
|
||||||
|
{
|
||||||
ReceivedPacket packet;
|
ReceivedPacket packet;
|
||||||
{
|
{
|
||||||
LOCKER(lock());
|
LOCKER(lock());
|
||||||
|
@ -338,7 +330,24 @@ ssize_t IPv4Socket::recvfrom(FileDescription& description, void* buffer, size_t
|
||||||
return ipv4_packet.payload_size();
|
return ipv4_packet.payload_size();
|
||||||
}
|
}
|
||||||
|
|
||||||
int nreceived = protocol_receive(packet.data.value(), buffer, buffer_length, flags);
|
return protocol_receive(packet.data.value(), buffer, buffer_length, flags);
|
||||||
|
}
|
||||||
|
|
||||||
|
ssize_t IPv4Socket::recvfrom(FileDescription& description, void* buffer, size_t buffer_length, int flags, sockaddr* addr, socklen_t* addr_length)
|
||||||
|
{
|
||||||
|
if (addr_length && *addr_length < sizeof(sockaddr_in))
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
#ifdef IPV4_SOCKET_DEBUG
|
||||||
|
kprintf("recvfrom: type=%d, local_port=%u\n", type(), local_port());
|
||||||
|
#endif
|
||||||
|
|
||||||
|
ssize_t nreceived = 0;
|
||||||
|
if (buffer_mode() == BufferMode::Bytes)
|
||||||
|
nreceived = receive_byte_buffered(description, buffer, buffer_length, flags, addr, addr_length);
|
||||||
|
else
|
||||||
|
nreceived = receive_packet_buffered(description, buffer, buffer_length, flags, addr, addr_length);
|
||||||
|
|
||||||
if (nreceived > 0)
|
if (nreceived > 0)
|
||||||
current->did_ipv4_socket_read(nreceived);
|
current->did_ipv4_socket_read(nreceived);
|
||||||
return nreceived;
|
return nreceived;
|
||||||
|
|
|
@ -105,6 +105,9 @@ protected:
|
||||||
private:
|
private:
|
||||||
virtual bool is_ipv4() const override { return true; }
|
virtual bool is_ipv4() const override { return true; }
|
||||||
|
|
||||||
|
ssize_t receive_byte_buffered(FileDescription&, void* buffer, size_t buffer_length, int flags, sockaddr*, socklen_t*);
|
||||||
|
ssize_t receive_packet_buffered(FileDescription&, void* buffer, size_t buffer_length, int flags, sockaddr*, socklen_t*);
|
||||||
|
|
||||||
IPv4Address m_local_address;
|
IPv4Address m_local_address;
|
||||||
IPv4Address m_peer_address;
|
IPv4Address m_peer_address;
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue