Fixes net.recvFrom to work correctly with IPv6 (#14131)

* added high level sendTo and recvFrom to std/asyncnet; tests were also added.
* add .since annotation, a changelog entry and fixed to standard library style guide.
* fixes net.recvFrom to work correctly with IPv6
* raise if domain is not AF_INET or AF_INET6
* renamed template to adaptRecvFromToDomain()
This commit is contained in:
rockcavera 2020-05-04 06:54:08 -03:00 • committed by GitHub
commit 603010f8c9
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23

View file

@ -1425,11 +1425,7 @@ proc recvFrom*(socket: Socket, data: var string, length: int,
## so when ``socket`` is buffered the non-buffered implementation will be ## so when ``socket`` is buffered the non-buffered implementation will be
## used. Therefore if ``socket`` contains something in its buffer this ## used. Therefore if ``socket`` contains something in its buffer this
## function will make no effort to return it. ## function will make no effort to return it.
template adaptRecvFromToDomain(domain: Domain) =
assert(socket.protocol != IPPROTO_TCP, "Cannot `recvFrom` on a TCP socket")
# TODO: Buffered sockets
data.setLen(length)
var sockAddress: Sockaddr_in
var addrLen = sizeof(sockAddress).SockLen var addrLen = sizeof(sockAddress).SockLen
result = recvfrom(socket.fd, cstring(data), length.cint, flags.cint, result = recvfrom(socket.fd, cstring(data), length.cint, flags.cint,
cast[ptr SockAddr](addr(sockAddress)), addr(addrLen)) cast[ptr SockAddr](addr(sockAddress)), addr(addrLen))
@ -1437,10 +1433,26 @@ proc recvFrom*(socket: Socket, data: var string, length: int,
if result != -1: if result != -1:
data.setLen(result) data.setLen(result)
address = getAddrString(cast[ptr SockAddr](addr(sockAddress))) address = getAddrString(cast[ptr SockAddr](addr(sockAddress)))
when domain == AF_INET6:
port = ntohs(sockAddress.sin6_port).Port
else:
port = ntohs(sockAddress.sin_port).Port port = ntohs(sockAddress.sin_port).Port
else: else:
raiseOSError(osLastError()) raiseOSError(osLastError())
assert(socket.protocol != IPPROTO_TCP, "Cannot `recvFrom` on a TCP socket")
# TODO: Buffered sockets
data.setLen(length)
case socket.domain
of AF_INET6:
var sockAddress: Sockaddr_in6
adaptRecvFromToDomain(AF_INET6)
of AF_INET:
var sockAddress: Sockaddr_in
adaptRecvFromToDomain(AF_INET)
else:
raise newException(ValueError, "Unknown socket address family")
proc skip*(socket: Socket, size: int, timeout = -1) = proc skip*(socket: Socket, size: int, timeout = -1) =
## Skips ``size`` amount of bytes. ## Skips ``size`` amount of bytes.
## ##