From ece6c54f1b4db27abac52ee3c627f619d1090544 Mon Sep 17 00:00:00 2001 From: euxane Date: Sun, 24 Nov 2024 17:17:02 +0100 Subject: ping: add hostname resolution --- ping.nim | 34 ++++++++++++++++++++++++++++++++++ 1 file changed, 34 insertions(+) (limited to 'ping.nim') diff --git a/ping.nim b/ping.nim index c99da96..b09d5f1 100644 --- a/ping.nim +++ b/ping.nim @@ -167,6 +167,40 @@ proc receiveReply(sock: Socket, timeout: Duration): seq[uint8] = stripIPHeader(ipAddr.family, cast[seq[uint8]](buffer)) +func toIpAddress(info: ptr AddrInfo): IpAddress = + case info.ai_family: + of posix.AF_INET6: + let sockAddr = cast[ptr posix.SockAddr_in6](info.ai_addr)[] + IpAddress( + family: IPv6, + address_v6: cast[array[0..15, uint8]](sockAddr.sin6_addr.s6_addr), + ) + of posix.AF_INET: + let sockAddr = cast[ptr posix.SockAddr_in](info.ai_addr)[] + IpAddress( + family: IPv4, + address_v4: cast[array[0..3, uint8]](sockAddr.sin_addr.s_addr), + ) + else: + raise newException(ValueError, "Invalid address info") + +func splitDomainHostname(target: string): (Domain, string) = + let parts = target.split('/', 1) + case parts[0]: + of "6": (AF_INET6, parts[1]) + of "4": (AF_INET, parts[1]) + else: (AF_UNSPEC, target) + +proc resolve*(target: string): IpAddress = + try: + parseIpAddress(target) + except ValueError: + let (domain, hostname) = splitDomainHostname(target) + let addrInfo = getAddrInfo(hostname, Port 0, domain) + defer: freeAddrInfo(addrInfo) + addrInfo.toIpAddress + + type PingMonitor = ref object socket: Socket target: IpAddress -- cgit v1.2.3