Add the unix socket support for sendto system call

This commit is contained in:
He Sun 2020-05-28 19:42:05 +08:00
parent 987e06a458
commit eb4bb860ce
3 changed files with 45 additions and 15 deletions

@ -278,12 +278,14 @@ pub fn do_sendto(
addr_len: libc::socklen_t, addr_len: libc::socklen_t,
) -> Result<isize> { ) -> Result<isize> {
debug!( debug!(
"sendto: fd: {}, base: {:?}, len: {}, addr: {:?}, addr_len: {}", "sendto: fd: {}, base: {:?}, len: {}, flags: {} addr: {:?}, addr_len: {}",
fd, base, len, addr, addr_len fd, base, len, flags, addr, addr_len
); );
let file_ref = current!().file(fd as FileDesc)?; from_user::check_array(base as *const u8, len)?;
let socket = file_ref.as_socket()?;
let file_ref = current!().file(fd as FileDesc)?;
if let Ok(socket) = file_ref.as_socket() {
// TODO: check addr and addr_len according to connection mode
let ret = try_libc!(libc::ocall::sendto( let ret = try_libc!(libc::ocall::sendto(
socket.fd(), socket.fd(),
base, base,
@ -293,6 +295,20 @@ pub fn do_sendto(
addr_len addr_len
)); ));
Ok(ret as isize) Ok(ret as isize)
} else if let Ok(unix) = file_ref.as_unix_socket() {
if !addr.is_null() || addr_len != 0 {
return_errno!(EISCONN, "Only connection-mode socket is supported");
}
if !unix.is_connected() {
return_errno!(ENOTCONN, "the socket has not been connected yet");
}
let data = unsafe { std::slice::from_raw_parts(base as *const u8, len) };
unix.write(data).map(|u| u as isize)
} else {
return_errno!(EBADF, "unsupported file type");
}
} }
pub fn do_recvfrom( pub fn do_recvfrom(

@ -150,6 +150,14 @@ impl UnixSocketFile {
} }
} }
} }
pub fn is_connected(&self) -> bool {
if let Status::Connected(_) = self.inner.lock().unwrap().status {
true
} else {
false
}
}
} }
impl Debug for UnixSocketFile { impl Debug for UnixSocketFile {

@ -101,9 +101,15 @@ int verify_connection(int src_sock, int dest_sock) {
char buf[1024]; char buf[1024];
int i; int i;
for (i = 0; i < 100; i++) { for (i = 0; i < 100; i++) {
if (i % 2 == 0) {
if (write(src_sock, ECHO_MSG, sizeof(ECHO_MSG)) < 0) { if (write(src_sock, ECHO_MSG, sizeof(ECHO_MSG)) < 0) {
THROW_ERROR("writing server message"); THROW_ERROR("writing server message");
} }
} else {
if (sendto(src_sock, ECHO_MSG, sizeof(ECHO_MSG), 0, NULL, 0) < 0) {
THROW_ERROR("sendto server message");
}
}
if (read(dest_sock, buf, 1024) < 0) { if (read(dest_sock, buf, 1024) < 0) {
THROW_ERROR("reading server message"); THROW_ERROR("reading server message");