Index: src/resolver.cr ================================================================== --- src/resolver.cr +++ src/resolver.cr @@ -141,12 +141,13 @@ end end end def handle_packet(packet : Bytes, sender : Socket::IPAddress) : Nil + io = IO::Memory.new(packet, writeable: false) begin - id = packet[0].to_u16 << 8 | packet[1] + id = io.read_bytes(UInt16, IO::ByteFormat::BigEndian) begin context = @queries[id] rescue KeyError return @@ -154,23 +155,24 @@ return if sender != context.used_ns @queries.delete(id) - if packet[2] & 0x80 == 0 || # QR - packet[2] & 0x78 != context.raw_data[2] & 0x78 # Opcode + byte = io.read_bytes(UInt8) + if byte & 0x80 == 0 || # QR + byte & 0x78 != context.raw_data[2] & 0x78 # Opcode context.block.call(Error::INVALID_REPLY) return end - if packet[2] & 0x02 != 0 # TC + if byte & 0x02 != 0 # TC # TODO: Switch to TCP context.block.call(Error::TRUNCATED) return end - case packet[3] & 0x0F # RCODE + case io.read_bytes(UInt8) & 0x0F # RCODE when 0 error = nil try_next_ns = false when 1 error = Error::SERVER_INVALID_FORMAT @@ -203,16 +205,14 @@ if error context.block.call(error) return end - io = IO::Memory.new(packet[4, packet.size - 4], writeable: false) qdcount = io.read_bytes(UInt16, IO::ByteFormat::BigEndian) adcount = io.read_bytes(UInt16, IO::ByteFormat::BigEndian) nscount = io.read_bytes(UInt16, IO::ByteFormat::BigEndian) arcount = io.read_bytes(UInt16, IO::ByteFormat::BigEndian) - rescue IndexError rescue IO::EOFError end end def stop : Nil