in Sources/NIOPosix/DatagramVectorReadManager.swift [92:143]
func readFromSocket(socket: Socket,
buffer: inout ByteBuffer,
parseControlMessages: Bool) throws -> ReadResult {
assert(buffer.readerIndex == 0, "Buffer was not cleared between calls to readFromSocket!")
let messageSize = buffer.capacity / self.messageCount
let result = try buffer.withVeryUnsafeMutableBytes { bufferPointer -> IOResult<Int> in
for i in 0..<self.messageCount {
// TODO(cory): almost all of this except for the iovec could be done at allocation time. Maybe we should?
// First we set up the iovec and save it off.
self.ioVector[i] = IOVector(iov_base: bufferPointer.baseAddress! + (i * messageSize), iov_len: numericCast(messageSize))
let controlBytes: UnsafeMutableRawBufferPointer
if parseControlMessages {
// This will be used in buildMessages below but should not be used beyond return of this function.
controlBytes = self.controlMessageStorage[i]
} else {
controlBytes = UnsafeMutableRawBufferPointer(start: nil, count: 0)
}
// Next we set up the msghdr structure. This points into the other vectors.
let msgHdr = msghdr(msg_name: self.sockaddrVector.baseAddress! + i ,
msg_namelen: socklen_t(MemoryLayout<sockaddr_storage>.size),
msg_iov: self.ioVector.baseAddress! + i,
msg_iovlen: 1, // This is weird, but each message gets only one array. Duh.
msg_control: controlBytes.baseAddress,
msg_controllen: .init(controlBytes.count),
msg_flags: 0)
self.messageVector[i] = MMsgHdr(msg_hdr: msgHdr, msg_len: 0)
// Note that we don't set up the sockaddr vector: that's because it needs no initialization,
// it's written into by the kernel.
}
// We've set up our pointers, it's time to get going. We now issue the call.
return try socket.recvmmsg(msgs: self.messageVector)
}
switch result {
case .wouldBlock(let messagesProcessed):
assert(messagesProcessed == 0)
return .none
case .processed(let messagesProcessed):
buffer.moveWriterIndex(to: messageSize * messagesProcessed)
return self.buildMessages(messageCount: messagesProcessed,
sliceSize: messageSize,
buffer: &buffer,
parseControlMessages: parseControlMessages)
}
}