
header "sys" as sys

use core
use mem

+ class AddrInfo {
    ~ data: sys:libc_addrinfo_fix

    + static fn new(host: String, port: u16) AddrInfo !fail {
        // WSA init
        #if OS == win
        core:WSA.init()
        #end

        // Get host info
        let addrinfo : ?sys:libc_addrinfo_fix = null
        let hints = @stack(<sys:libc_addrinfo_fix>)
        mem:clear(hints, size_of(<sys:libc_addrinfo_fix>))

        hints.ai_family = sys:AF_INET
        hints.ai_socktype = sys:SOCK_STREAM
        hints.ai_flags = sys:AI_PASSIVE

        let chost = host.data_cstring
        let cport = port.to_str().data_cstring
        let err = sys:getaddrinfo(chost, cport, hints, @ref(addrinfo))
        if err != 0 : throw fail
        if !isset(addrinfo) : throw fail

        return AddrInfo {
            data: addrinfo
        }
    }

    fn gc_free() {
        sys:freeaddrinfo(this.data)
    }

    + fn sock_addr() sys:libc_sockaddr {
        return this.data.ai_addr.@cast(sys:libc_sockaddr)
    }
    + fn addr_len() u32 {
        return this.data.ai_addrlen.@cast(u32)
    }
}