1
0
mirror of https://github.com/vlang/v.git synced 2023-08-10 21:13:21 +03:00

net: allow more fine grained control over socket shutdowns

This commit is contained in:
Delyan Angelov 2023-01-25 12:32:05 +02:00
parent b34c55ffd6
commit d2e5c721a0
No known key found for this signature in database
GPG Key ID: 66886C0F12D595ED
7 changed files with 49 additions and 33 deletions

View File

@ -16,13 +16,36 @@ pub const no_timeout = time.Duration(0)
// only ever return with data) // only ever return with data)
pub const infinite_timeout = time.infinite pub const infinite_timeout = time.infinite
// Shutdown shutsdown a socket and closes it // ShutdownDirection is used by `net.shutdown`, for specifying the direction for which the
fn shutdown(handle int) ! { // communication will be cut.
pub enum ShutdownDirection {
read
write
read_and_write
}
[params]
pub struct ShutdownConfig {
how ShutdownDirection = .read_and_write
}
// shutdown shutsdown a socket, given its file descriptor `handle`.
// By default it shuts it down in both directions, both for reading
// and for writing. You can change that using `net.shutdown(handle, how: .read)`
// or `net.shutdown(handle, how: .write)`
pub fn shutdown(handle int, config ShutdownConfig) int {
$if windows {
return C.shutdown(handle, int(config.how))
} $else {
return C.shutdown(handle, int(config.how))
}
}
// close a socket, given its file descriptor `handle`.
pub fn close(handle int) ! {
$if windows { $if windows {
C.shutdown(handle, C.SD_BOTH)
socket_error(C.closesocket(handle))! socket_error(C.closesocket(handle))!
} $else { } $else {
C.shutdown(handle, C.SHUT_RDWR)
socket_error(C.close(handle))! socket_error(C.close(handle))!
} }
} }

View File

@ -89,13 +89,8 @@ pub fn (mut s SSLConn) shutdown() ! {
C.mbedtls_ssl_free(&s.ssl) C.mbedtls_ssl_free(&s.ssl)
C.mbedtls_ssl_config_free(&s.conf) C.mbedtls_ssl_config_free(&s.conf)
if s.owns_socket { if s.owns_socket {
$if windows { net.shutdown(s.handle)
C.shutdown(s.handle, C.SD_BOTH) net.close(s.handle)!
net.socket_error(C.closesocket(s.handle))!
} $else {
C.shutdown(s.handle, C.SHUT_RDWR)
net.socket_error(C.close(s.handle))!
}
} }
} }

View File

@ -104,13 +104,8 @@ pub fn (mut s SSLConn) shutdown() ! {
C.SSL_CTX_free(s.sslctx) C.SSL_CTX_free(s.sslctx)
} }
if s.owns_socket { if s.owns_socket {
$if windows { net.shutdown(s.handle)
C.shutdown(s.handle, C.SD_BOTH) net.close(s.handle)!
net.socket_error(C.closesocket(s.handle))!
} $else {
C.shutdown(s.handle, C.SHUT_RDWR)
net.socket_error(C.close(s.handle))!
}
} }
} }

View File

@ -454,7 +454,8 @@ pub fn (mut s TcpSocket) bind(addr string) ! {
} }
fn (mut s TcpSocket) close() ! { fn (mut s TcpSocket) close() ! {
return shutdown(s.handle) shutdown(s.handle)
return close(s.handle)
} }
fn (mut s TcpSocket) @select(test Select, timeout time.Duration) !bool { fn (mut s TcpSocket) @select(test Select, timeout time.Duration) !bool {

View File

@ -278,7 +278,8 @@ pub fn (mut s UdpSocket) set_dualstack(on bool) ! {
} }
fn (mut s UdpSocket) close() ! { fn (mut s UdpSocket) close() ! {
return shutdown(s.handle) shutdown(s.handle)
return close(s.handle)
} }
fn (mut s UdpSocket) @select(test Select, timeout time.Duration) !bool { fn (mut s UdpSocket) @select(test Select, timeout time.Duration) !bool {

View File

@ -3,23 +3,23 @@ module unix
import time import time
import net import net
const ( const error_ewouldblock = C.EWOULDBLOCK
error_ewouldblock = C.EWOULDBLOCK
)
fn C.SUN_LEN(ptr &C.sockaddr_un) int fn C.SUN_LEN(ptr &C.sockaddr_un) int
fn C.strncpy(&char, &char, int) fn C.strncpy(&char, &char, int)
// Shutdown shutsdown a socket and closes it // shutdown shutsdown a socket, given its file descriptor `handle`.
fn shutdown(handle int) ! { // By default it shuts it down in both directions, both for reading
$if windows { // and for writing. You can change that using `net.shutdown(handle, how: .read)`
C.shutdown(handle, C.SD_BOTH) // or `net.shutdown(handle, how: .write)`
net.socket_error(C.closesocket(handle))! pub fn shutdown(handle int, config net.ShutdownConfig) int {
} $else { return net.shutdown(handle, config)
C.shutdown(handle, C.SHUT_RDWR) }
net.socket_error(C.close(handle))!
} // close a socket, given its file descriptor `handle`.
pub fn close(handle int) ! {
net.close(handle)!
} }
// Select waits for an io operation (specified by parameter `test`) to be available // Select waits for an io operation (specified by parameter `test`) to be available

View File

@ -49,7 +49,8 @@ fn new_stream_socket() !StreamSocket {
} }
fn (mut s StreamSocket) close() ! { fn (mut s StreamSocket) close() ! {
return shutdown(s.handle) shutdown(s.handle)
return close(s.handle)
} }
fn (mut s StreamSocket) @select(test Select, timeout time.Duration) !bool { fn (mut s StreamSocket) @select(test Select, timeout time.Duration) !bool {