3

I have simple UDPServer class, which is fetching some data, and I can setup what size of each packet do I need. When I set packetSize = 1024(this property set on Windows desktop application) everything seems work fine, but when it's more, for example 2048, i have weird logs like this:

[] udp_validate_cksum_internal [C6:1] udp incorrect IPv4-UDP non-offload checksum 0xf3ff ulen 1506

[] nw_protocol_ipv4_get_input_frames_block_invoke [C6:2] Dropping unused IPv4 extra fragment


Devices: iPhone 11, 11 Pro with iOS 13 - logs appear

On simulators: iOS 12 and 13 - no logs

My UDPServer:

final class UDPServer {
        
    var frameReceivedHandler: ((Data) -> Void)?
    
    private let listener: NWListener
    private let queue: DispatchQueue
    private var connection: NWConnection? {
        didSet { establishNewConnection(connection) }
    }
    
    deinit {
        stopListening()
    }
    
    init(port: UInt16) {
        self.queue = DispatchQueue(label: "UDP Server Queue")
        self.listener = try! NWListener(using: .udp,
                                        on: NWEndpoint.Port(integerLiteral: port))
    }
    
    // MARK: Public API
    
    func startListening() {
        listener.newConnectionHandler = { [weak self] newConnection in
            guard let self = self else { return }
            self.connection = newConnection
        }
        listener.start(queue: queue)
    }
    
    func stopListening() {
        listener.cancel()
        connection?.cancel()
    }
    
    // MARK: Private API
    
    private func establishNewConnection(_ newConnection: NWConnection?) {
        debugPrint(" New connection: \(String(describing: newConnection?.endpoint)) establish")
        newConnection?.stateUpdateHandler = { [weak self] connectionState in
            guard let self = self else { return }
            switch connectionState {
            case .ready:
                debugPrint("Connection: ✅ ready to receive")
                self.receive(on: newConnection)
            case .failed(let error): debugPrint("❌ Connection: failed: \(error)")
            case .cancelled: debugPrint("❌ Connection: cancelled")
            default: break
            }
        }
        newConnection?.start(queue: .main)
    }
    
    private func receive(on connection: NWConnection?) {
        connection?.receiveMessage { [weak self] content, context, isCompleted, error in
            guard let self = self else { return }
            if let frame = content {
                self.frameReceivedHandler?(frame)
            }
            self.receive(on: connection)
        }
    }
    
}

My usage example:

udpVideoServer = UDPServer(port: /*port*/)
udpVideoServer.frameReceivedHandler = { [weak self] data in
    guard let self = self else { return }
    ...
}
udpVideoServer.startListening()

I didn't find any useful information or explanation on the Internet

Thank you!

vpoltave
  • 1,612
  • 3
  • 14
  • 31

0 Answers0