Skip to content

Commit 3afb5d3

Browse files
Merge pull request RustPython#850 from palaviv/socket-fileno
Socket.fileno
2 parents 01f143e + f42c2a6 commit 3afb5d3

File tree

2 files changed

+53
-0
lines changed

2 files changed

+53
-0
lines changed

tests/snippets/stdlib_socket.py

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import socket
2+
import os
23
from testutils import assertRaises
34

45
MESSAGE_A = b'aaaa'
@@ -21,6 +22,18 @@
2122
recv_b = connector.recv(len(MESSAGE_B))
2223
assert recv_a == MESSAGE_A
2324
assert recv_b == MESSAGE_B
25+
26+
# fileno
27+
if os.name == "posix":
28+
connector_fd = connector.fileno()
29+
connection_fd = connection.fileno()
30+
os.write(connector_fd, MESSAGE_A)
31+
connection.send(MESSAGE_B)
32+
recv_a = connection.recv(len(MESSAGE_A))
33+
recv_b = os.read(connector_fd, (len(MESSAGE_B)))
34+
assert recv_a == MESSAGE_A
35+
assert recv_b == MESSAGE_B
36+
2437
connection.close()
2538
connector.close()
2639
listener.close()

vm/src/stdlib/socket.rs

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,33 @@ impl Connection {
8686
_ => Err(io::Error::new(io::ErrorKind::Other, "oh no!")),
8787
}
8888
}
89+
90+
#[cfg(unix)]
91+
fn fileno(&self) -> i64 {
92+
use std::os::unix::io::AsRawFd;
93+
let raw_fd = match self {
94+
Connection::TcpListener(con) => con.as_raw_fd(),
95+
Connection::UdpSocket(con) => con.as_raw_fd(),
96+
Connection::TcpStream(con) => con.as_raw_fd(),
97+
};
98+
raw_fd as i64
99+
}
100+
101+
#[cfg(windows)]
102+
fn fileno(&self) -> i64 {
103+
use std::os::windows::io::AsRawSocket;
104+
let raw_fd = match self {
105+
Connection::TcpListener(con) => con.as_raw_socket(),
106+
Connection::UdpSocket(con) => con.as_raw_socket(),
107+
Connection::TcpStream(con) => con.as_raw_socket(),
108+
};
109+
raw_fd as i64
110+
}
111+
112+
#[cfg(all(not(unix), not(windows)))]
113+
fn fileno(&self) -> i64 {
114+
unimplemented!();
115+
}
89116
}
90117

91118
impl Read for Connection {
@@ -387,6 +414,18 @@ fn socket_close(vm: &VirtualMachine, args: PyFuncArgs) -> PyResult {
387414
Ok(vm.get_none())
388415
}
389416

417+
fn socket_fileno(vm: &VirtualMachine, args: PyFuncArgs) -> PyResult {
418+
arg_check!(vm, args, required = [(zelf, None)]);
419+
420+
let socket = get_socket(zelf);
421+
422+
let fileno = match socket.con.borrow_mut().as_mut() {
423+
Some(v) => v.fileno(),
424+
None => return Err(vm.new_type_error("".to_string())),
425+
};
426+
Ok(vm.ctx.new_int(fileno))
427+
}
428+
390429
fn socket_getsockname(vm: &VirtualMachine, args: PyFuncArgs) -> PyResult {
391430
arg_check!(vm, args, required = [(zelf, None)]);
392431
let socket = get_socket(zelf);
@@ -424,6 +463,7 @@ pub fn make_module(vm: &VirtualMachine) -> PyObjectRef {
424463
"getsockname" => ctx.new_rustfunc(socket_getsockname),
425464
"sendto" => ctx.new_rustfunc(socket_sendto),
426465
"recvfrom" => ctx.new_rustfunc(socket_recvfrom),
466+
"fileno" => ctx.new_rustfunc(socket_fileno),
427467
});
428468

429469
py_module!(vm, "socket", {

0 commit comments

Comments
 (0)