From ff13f9f6225b6404f6683a9addf850c0d502047b Mon Sep 17 00:00:00 2001 From: Samuel Dai Date: Thu, 7 Nov 2024 14:38:31 +0800 Subject: [PATCH] fix(net): TCP Resources and add syscall print, change to use latest smoltcp (#1032) * change to smoltcp * add syscall, fix wront accept-listen logic * add version and resource close --- kernel/Cargo.toml | 2 +- kernel/src/arch/x86_64/syscall/mod.rs | 75 ++-- kernel/src/arch/x86_64/syscall/nr.rs | 378 ++++++++++++++++++ kernel/src/driver/net/e1000e/e1000e_driver.rs | 6 +- kernel/src/driver/net/loopback.rs | 35 +- kernel/src/driver/net/mod.rs | 26 +- kernel/src/driver/net/virtio_net.rs | 6 +- kernel/src/net/posix.rs | 41 +- kernel/src/net/socket/inet/common/mod.rs | 22 +- kernel/src/net/socket/inet/stream/inner.rs | 72 ++-- kernel/src/net/socket/inet/stream/mod.rs | 26 +- kernel/src/net/socket/inet/syscall.rs | 13 +- 12 files changed, 569 insertions(+), 133 deletions(-) diff --git a/kernel/Cargo.toml b/kernel/Cargo.toml index 18781dbd3..f989c8cf7 100644 --- a/kernel/Cargo.toml +++ b/kernel/Cargo.toml @@ -48,7 +48,7 @@ linkme = "=0.3.27" num = { version = "=0.4.0", default-features = false } num-derive = "=0.3" num-traits = { git = "https://git.mirrors.dragonos.org.cn/DragonOS-Community/num-traits.git", rev="1597c1c", default-features = false } -smoltcp = { version = "=0.11.0", default-features = false, features = ["log", "alloc", "socket-raw", "socket-udp", "socket-tcp", "socket-icmp", "socket-dhcpv4", "socket-dns", "proto-ipv4", "proto-ipv6"]} +smoltcp = { git = "https://git.mirrors.dragonos.org.cn/DragonOS-Community/smoltcp.git", rev = "3e61c909fd540d05575068d16dc4574e196499ed", default-features = false, features = ["log", "alloc", "socket-raw", "socket-udp", "socket-tcp", "socket-icmp", "socket-dhcpv4", "socket-dns", "proto-ipv4", "proto-ipv6"]} system_error = { path = "crates/system_error" } uefi = { version = "=0.26.0", features = ["alloc"] } uefi-raw = "=0.5.0" diff --git a/kernel/src/arch/x86_64/syscall/mod.rs b/kernel/src/arch/x86_64/syscall/mod.rs index 4ed274c23..ef9ee600b 100644 --- a/kernel/src/arch/x86_64/syscall/mod.rs +++ b/kernel/src/arch/x86_64/syscall/mod.rs @@ -1,7 +1,7 @@ use crate::{ arch::{ ipc::signal::X86_64SignalArch, - syscall::nr::{SYS_ARCH_PRCTL, SYS_RT_SIGRETURN}, + syscall::nr::{SysCall, SYS_ARCH_PRCTL, SYS_RT_SIGRETURN}, CurrentIrqArch, }, exception::InterruptArch, @@ -11,7 +11,6 @@ use crate::{ process::ProcessManager, syscall::{Syscall, SYS_SCHED}, }; -use log::debug; use system_error::SystemError; use super::{ @@ -53,7 +52,7 @@ macro_rules! syscall_return { if $show { let pid = ProcessManager::current_pcb().pid(); - debug!("syscall return:pid={:?},ret= {:?}\n", pid, ret as isize); + log::debug!("[SYS] [Pid: {:?}] [Retn: {:?}]", pid, ret as i64); } unsafe { @@ -63,6 +62,24 @@ macro_rules! syscall_return { }}; } +macro_rules! normal_syscall_return { + ($val:expr, $regs:expr, $show:expr) => {{ + let ret = $val; + + if $show { + let pid = ProcessManager::current_pcb().pid(); + log::debug!("[SYS] [Pid: {:?}] [Retn: {:?}]", pid, ret); + } + + $regs.rax = ret.unwrap_or_else(|e| e.to_posix_errno() as usize) as u64; + + unsafe { + CurrentIrqArch::interrupt_disable(); + } + return; + }}; +} + #[no_mangle] pub extern "sysv64" fn syscall_handler(frame: &mut TrapFrame) { let syscall_num = frame.rax as usize; @@ -87,15 +104,37 @@ pub extern "sysv64" fn syscall_handler(frame: &mut TrapFrame) { ]; mfence(); let pid = ProcessManager::current_pcb().pid(); - let show = false; - // let show = if syscall_num != SYS_SCHED && pid.data() >= 7 { - // true - // } else { - // false - // }; + let mut show = (syscall_num != SYS_SCHED) && (pid.data() >= 7); + // let mut show = true; - if show { - debug!("syscall: pid: {:?}, num={:?}\n", pid, syscall_num); + let to_print = SysCall::try_from(syscall_num); + if let Ok(to_print) = to_print { + use SysCall::*; + match to_print { + SYS_ACCEPT | SYS_ACCEPT4 | SYS_BIND | SYS_CONNECT | SYS_SHUTDOWN | SYS_LISTEN => { + // show &= false; + } + SYS_RECVFROM | SYS_SENDTO | SYS_SENDMSG | SYS_RECVMSG => { + show &= false; + } + SYS_SOCKET | SYS_GETSOCKNAME | SYS_GETPEERNAME | SYS_SOCKETPAIR | SYS_SETSOCKOPT + | SYS_GETSOCKOPT => { + show &= false; + } + SYS_OPEN | SYS_OPENAT | SYS_CREAT | SYS_CLOSE => { + show &= false; + } + SYS_READ | SYS_WRITE | SYS_READV | SYS_WRITEV | SYS_PREAD64 | SYS_PWRITE64 + | SYS_PREADV | SYS_PWRITEV | SYS_PREADV2 => { + show &= false; + } + _ => { + show &= false; + } + } + if show { + log::debug!("[SYS] [Pid: {:?}] [Call: {:?}]", pid, to_print); + } } // Arch specific syscall @@ -108,21 +147,11 @@ pub extern "sysv64" fn syscall_handler(frame: &mut TrapFrame) { ); } SYS_ARCH_PRCTL => { - syscall_return!( - Syscall::arch_prctl(args[0], args[1]) - .unwrap_or_else(|e| e.to_posix_errno() as usize), - frame, - show - ); + normal_syscall_return!(Syscall::arch_prctl(args[0], args[1]), frame, show); } _ => {} } - syscall_return!( - Syscall::handle(syscall_num, &args, frame).unwrap_or_else(|e| e.to_posix_errno() as usize) - as u64, - frame, - show - ); + normal_syscall_return!(Syscall::handle(syscall_num, &args, frame), frame, show); } /// 系统调用初始化 diff --git a/kernel/src/arch/x86_64/syscall/nr.rs b/kernel/src/arch/x86_64/syscall/nr.rs index c37dc36cd..f3c4c895c 100644 --- a/kernel/src/arch/x86_64/syscall/nr.rs +++ b/kernel/src/arch/x86_64/syscall/nr.rs @@ -355,3 +355,381 @@ pub const SYS_WAIT4: usize = 61; pub const SYS_WAITID: usize = 247; pub const SYS_WRITE: usize = 1; pub const SYS_WRITEV: usize = 20; + +use num_traits::{FromPrimitive, ToPrimitive}; +use system_error::SystemError; +#[allow(non_camel_case_types)] +#[derive(Debug, Clone, Copy, FromPrimitive, ToPrimitive, PartialEq, Eq)] +pub enum SysCall { + SYS__SYSCTL = 156, + SYS_ACCEPT = 43, + SYS_ACCEPT4 = 288, + SYS_ACCESS = 21, + SYS_ACCT = 163, + SYS_ADD_KEY = 248, + SYS_ADJTIMEX = 159, + SYS_AFS_SYSCALL = 183, + SYS_ALARM = 37, + SYS_ARCH_PRCTL = 158, + SYS_BIND = 49, + SYS_BPF = 321, + SYS_BRK = 12, + SYS_CAPGET = 125, + SYS_CAPSET = 126, + SYS_CHDIR = 80, + SYS_CHMOD = 90, + SYS_CHOWN = 92, + SYS_CHROOT = 161, + SYS_CLOCK_ADJTIME = 305, + SYS_CLOCK_GETRES = 229, + SYS_CLOCK_GETTIME = 228, + SYS_CLOCK_NANOSLEEP = 230, + SYS_CLOCK_SETTIME = 227, + SYS_CLONE = 56, + SYS_CLONE3 = 435, + SYS_CLOSE = 3, + SYS_CLOSE_RANGE = 436, + SYS_CONNECT = 42, + SYS_COPY_FILE_RANGE = 326, + SYS_CREAT = 85, + SYS_CREATE_MODULE = 174, + SYS_DELETE_MODULE = 176, + SYS_DUP = 32, + SYS_DUP2 = 33, + SYS_DUP3 = 292, + SYS_EPOLL_CREATE = 213, + SYS_EPOLL_CREATE1 = 291, + SYS_EPOLL_CTL = 233, + SYS_EPOLL_CTL_OLD = 214, + SYS_EPOLL_PWAIT = 281, + SYS_EPOLL_PWAIT2 = 441, + SYS_EPOLL_WAIT = 232, + SYS_EPOLL_WAIT_OLD = 215, + SYS_EVENTFD = 284, + SYS_EVENTFD2 = 290, + SYS_EXECVE = 59, + SYS_EXECVEAT = 322, + SYS_EXIT = 60, + SYS_EXIT_GROUP = 231, + SYS_FACCESSAT = 269, + SYS_FACCESSAT2 = 439, + SYS_FADVISE64 = 221, + SYS_FALLOCATE = 285, + SYS_FANOTIFY_INIT = 300, + SYS_FANOTIFY_MARK = 301, + SYS_FCHDIR = 81, + SYS_FCHMOD = 91, + SYS_FCHMODAT = 268, + SYS_FCHOWN = 93, + SYS_FCHOWNAT = 260, + SYS_FCNTL = 72, + SYS_FDATASYNC = 75, + SYS_FGETXATTR = 193, + SYS_FINIT_MODULE = 313, + SYS_FLISTXATTR = 196, + SYS_FLOCK = 73, + SYS_FORK = 57, + SYS_FREMOVEXATTR = 199, + SYS_FSCONFIG = 431, + SYS_FSETXATTR = 190, + SYS_FSMOUNT = 432, + SYS_FSOPEN = 430, + SYS_FSPICK = 433, + SYS_FSTAT = 5, + SYS_FSTATFS = 138, + SYS_FSYNC = 74, + SYS_FTRUNCATE = 77, + SYS_FUTEX = 202, + SYS_FUTIMESAT = 261, + SYS_GET_KERNEL_SYMS = 177, + SYS_GET_MEMPOLICY = 239, + SYS_GET_ROBUST_LIST = 274, + SYS_GET_THREAD_AREA = 211, + SYS_GETCPU = 309, + SYS_GETCWD = 79, + SYS_GETDENTS = 78, + SYS_GETDENTS64 = 217, + SYS_GETEGID = 108, + SYS_GETEUID = 107, + SYS_GETGID = 104, + SYS_GETGROUPS = 115, + SYS_GETITIMER = 36, + SYS_GETPEERNAME = 52, + SYS_GETPGID = 121, + SYS_GETPGRP = 111, + SYS_GETPID = 39, + SYS_GETPMSG = 181, + SYS_GETPPID = 110, + SYS_GETPRIORITY = 140, + SYS_GETRANDOM = 318, + SYS_GETRESGID = 120, + SYS_GETRESUID = 118, + SYS_GETRLIMIT = 97, + SYS_GETRUSAGE = 98, + SYS_GETSID = 124, + SYS_GETSOCKNAME = 51, + SYS_GETSOCKOPT = 55, + SYS_GETTID = 186, + SYS_GETTIMEOFDAY = 96, + SYS_GETUID = 102, + SYS_GETXATTR = 191, + SYS_INIT_MODULE = 175, + SYS_INOTIFY_ADD_WATCH = 254, + SYS_INOTIFY_INIT = 253, + SYS_INOTIFY_INIT1 = 294, + SYS_INOTIFY_RM_WATCH = 255, + SYS_IO_CANCEL = 210, + SYS_IO_DESTROY = 207, + SYS_IO_GETEVENTS = 208, + SYS_IO_PGETEVENTS = 333, + SYS_IO_SETUP = 206, + SYS_IO_SUBMIT = 209, + SYS_IO_URING_ENTER = 426, + SYS_IO_URING_REGISTER = 427, + SYS_IO_URING_SETUP = 425, + SYS_IOCTL = 16, + SYS_IOPERM = 173, + SYS_IOPL = 172, + SYS_IOPRIO_GET = 252, + SYS_IOPRIO_SET = 251, + SYS_KCMP = 312, + SYS_KEXEC_FILE_LOAD = 320, + SYS_KEXEC_LOAD = 246, + SYS_KEYCTL = 250, + SYS_KILL = 62, + SYS_LCHOWN = 94, + SYS_LGETXATTR = 192, + SYS_LINK = 86, + SYS_LINKAT = 265, + SYS_LISTEN = 50, + SYS_LISTXATTR = 194, + SYS_LLISTXATTR = 195, + SYS_LOOKUP_DCOOKIE = 212, + SYS_LREMOVEXATTR = 198, + SYS_LSEEK = 8, + SYS_LSETXATTR = 189, + SYS_LSTAT = 6, + SYS_MADVISE = 28, + SYS_MBIND = 237, + SYS_MEMBARRIER = 324, + SYS_MEMFD_CREATE = 319, + SYS_MIGRATE_PAGES = 256, + SYS_MINCORE = 27, + SYS_MKDIR = 83, + SYS_MKDIRAT = 258, + SYS_MKNOD = 133, + SYS_MKNODAT = 259, + SYS_MLOCK = 149, + SYS_MLOCK2 = 325, + SYS_MLOCKALL = 151, + SYS_MMAP = 9, + SYS_MODIFY_LDT = 154, + SYS_MOUNT = 165, + SYS_MOUNT_SETATTR = 442, + SYS_MOVE_MOUNT = 429, + SYS_MOVE_PAGES = 279, + SYS_MPROTECT = 10, + SYS_MQ_GETSETATTR = 245, + SYS_MQ_NOTIFY = 244, + SYS_MQ_OPEN = 240, + SYS_MQ_TIMEDRECEIVE = 243, + SYS_MQ_TIMEDSEND = 242, + SYS_MQ_UNLINK = 241, + SYS_MREMAP = 25, + SYS_MSGCTL = 71, + SYS_MSGGET = 68, + SYS_MSGRCV = 70, + SYS_MSGSND = 69, + SYS_MSYNC = 26, + SYS_MUNLOCK = 150, + SYS_MUNLOCKALL = 152, + SYS_MUNMAP = 11, + SYS_NAME_TO_HANDLE_AT = 303, + SYS_NANOSLEEP = 35, + SYS_NEWFSTATAT = 262, + SYS_NFSSERVCTL = 180, + SYS_OPEN = 2, + SYS_OPEN_BY_HANDLE_AT = 304, + SYS_OPEN_TREE = 428, + SYS_OPENAT = 257, + SYS_OPENAT2 = 437, + SYS_PAUSE = 34, + SYS_PERF_EVENT_OPEN = 298, + SYS_PERSONALITY = 135, + SYS_PIDFD_GETFD = 438, + SYS_PIDFD_OPEN = 434, + SYS_PIDFD_SEND_SIGNAL = 424, + SYS_PIPE = 22, + SYS_PIPE2 = 293, + SYS_PIVOT_ROOT = 155, + SYS_PKEY_ALLOC = 330, + SYS_PKEY_FREE = 331, + SYS_PKEY_MPROTECT = 329, + SYS_POLL = 7, + SYS_PPOLL = 271, + SYS_PRCTL = 157, + SYS_PREAD64 = 17, + SYS_PREADV = 295, + SYS_PREADV2 = 327, + SYS_PRLIMIT64 = 302, + SYS_PROCESS_MADVISE = 440, + SYS_PROCESS_VM_READV = 310, + SYS_PROCESS_VM_WRITEV = 311, + SYS_PSELECT6 = 270, + SYS_PTRACE = 101, + SYS_PUTPMSG = 182, + SYS_PWRITE64 = 18, + SYS_PWRITEV = 296, + SYS_PWRITEV2 = 328, + SYS_QUERY_MODULE = 178, + SYS_QUOTACTL = 179, + SYS_READ = 0, + SYS_READAHEAD = 187, + SYS_READLINK = 89, + SYS_READLINKAT = 267, + SYS_READV = 19, + SYS_REBOOT = 169, + SYS_RECVFROM = 45, + SYS_RECVMMSG = 299, + SYS_RECVMSG = 47, + SYS_REMAP_FILE_PAGES = 216, + SYS_REMOVEXATTR = 197, + SYS_RENAME = 82, + SYS_RENAMEAT = 264, + SYS_RENAMEAT2 = 316, + SYS_REQUEST_KEY = 249, + SYS_RESTART_SYSCALL = 219, + SYS_RMDIR = 84, + SYS_RSEQ = 334, + SYS_RT_SIGACTION = 13, + SYS_RT_SIGPENDING = 127, + SYS_RT_SIGPROCMASK = 14, + SYS_RT_SIGQUEUEINFO = 129, + SYS_RT_SIGRETURN = 15, + SYS_RT_SIGSUSPEND = 130, + SYS_RT_SIGTIMEDWAIT = 128, + SYS_RT_TGSIGQUEUEINFO = 297, + SYS_SCHED_GET_PRIORITY_MAX = 146, + SYS_SCHED_GET_PRIORITY_MIN = 147, + SYS_SCHED_GETAFFINITY = 204, + SYS_SCHED_GETATTR = 315, + SYS_SCHED_GETPARAM = 143, + SYS_SCHED_GETSCHEDULER = 145, + SYS_SCHED_RR_GET_INTERVAL = 148, + SYS_SCHED_SETAFFINITY = 203, + SYS_SCHED_SETATTR = 314, + SYS_SCHED_SETPARAM = 142, + SYS_SCHED_SETSCHEDULER = 144, + SYS_SCHED_YIELD = 24, + SYS_SECCOMP = 317, + SYS_SECURITY = 185, + SYS_SELECT = 23, + SYS_SEMCTL = 66, + SYS_SEMGET = 64, + SYS_SEMOP = 65, + SYS_SEMTIMEDOP = 220, + SYS_SENDFILE = 40, + SYS_SENDMMSG = 307, + SYS_SENDMSG = 46, + SYS_SENDTO = 44, + SYS_SET_MEMPOLICY = 238, + SYS_SET_ROBUST_LIST = 273, + SYS_SET_THREAD_AREA = 205, + SYS_SET_TID_ADDRESS = 218, + SYS_SETDOMAINNAME = 171, + SYS_SETFSGID = 123, + SYS_SETFSUID = 122, + SYS_SETGID = 106, + SYS_SETGROUPS = 116, + SYS_SETHOSTNAME = 170, + SYS_SETITIMER = 38, + SYS_SETNS = 308, + SYS_SETPGID = 109, + SYS_SETPRIORITY = 141, + SYS_SETREGID = 114, + SYS_SETRESGID = 119, + SYS_SETRESUID = 117, + SYS_SETREUID = 113, + SYS_SETRLIMIT = 160, + SYS_SETSID = 112, + SYS_SETSOCKOPT = 54, + SYS_SETTIMEOFDAY = 164, + SYS_SETUID = 105, + SYS_SETXATTR = 188, + SYS_SHMAT = 30, + SYS_SHMCTL = 31, + SYS_SHMDT = 67, + SYS_SHMGET = 29, + SYS_SHUTDOWN = 48, + SYS_SIGALTSTACK = 131, + SYS_SIGNALFD = 282, + SYS_SIGNALFD4 = 289, + SYS_SOCKET = 41, + SYS_SOCKETPAIR = 53, + SYS_SPLICE = 275, + SYS_STAT = 4, + SYS_STATFS = 137, + SYS_STATX = 332, + SYS_SWAPOFF = 168, + SYS_SWAPON = 167, + SYS_SYMLINK = 88, + SYS_SYMLINKAT = 266, + SYS_SYNC = 162, + SYS_SYNC_FILE_RANGE = 277, + SYS_SYNCFS = 306, + SYS_SYSFS = 139, + SYS_SYSINFO = 99, + SYS_SYSLOG = 103, + SYS_TEE = 276, + SYS_TGKILL = 234, + SYS_TIME = 201, + SYS_TIMER_CREATE = 222, + SYS_TIMER_DELETE = 226, + SYS_TIMER_GETOVERRUN = 225, + SYS_TIMER_GETTIME = 224, + SYS_TIMER_SETTIME = 223, + SYS_TIMERFD_CREATE = 283, + SYS_TIMERFD_GETTIME = 287, + SYS_TIMERFD_SETTIME = 286, + SYS_TIMES = 100, + SYS_TKILL = 200, + SYS_TRUNCATE = 76, + SYS_TUXCALL = 184, + SYS_UMASK = 95, + SYS_UMOUNT2 = 166, + SYS_UNAME = 63, + SYS_UNLINK = 87, + SYS_UNLINKAT = 263, + SYS_UNSHARE = 272, + SYS_USELIB = 134, + SYS_USERFAULTFD = 323, + SYS_USTAT = 136, + SYS_UTIME = 132, + SYS_UTIMENSAT = 280, + SYS_UTIMES = 235, + SYS_VFORK = 58, + SYS_VHANGUP = 153, + SYS_VMSPLICE = 278, + SYS_VSERVER = 236, + SYS_WAIT4 = 61, + SYS_WAITID = 247, + SYS_WRITE = 1, + SYS_WRITEV = 20, +} + +impl TryFrom for SysCall { + type Error = SystemError; + + fn try_from(value: usize) -> Result { + match ::from_usize(value) { + Some(p) => Ok(p), + None => Err(SystemError::EINVAL), + } + } +} + +impl From for usize { + fn from(value: SysCall) -> Self { + ::to_usize(&value).unwrap() + } +} \ No newline at end of file diff --git a/kernel/src/driver/net/e1000e/e1000e_driver.rs b/kernel/src/driver/net/e1000e/e1000e_driver.rs index ed2a43461..1f3e758b8 100644 --- a/kernel/src/driver/net/e1000e/e1000e_driver.rs +++ b/kernel/src/driver/net/e1000e/e1000e_driver.rs @@ -96,11 +96,11 @@ pub struct InnerE1000EInterface { } impl phy::RxToken for E1000ERxToken { - fn consume(mut self, f: F) -> R + fn consume(self, f: F) -> R where - F: FnOnce(&mut [u8]) -> R, + F: FnOnce(&[u8]) -> R, { - let result = f(self.0.as_mut_slice()); + let result = f(self.0.as_slice()); self.0.free_buffer(); return result; } diff --git a/kernel/src/driver/net/loopback.rs b/kernel/src/driver/net/loopback.rs index 9bbc92d0b..5b02d54a5 100644 --- a/kernel/src/driver/net/loopback.rs +++ b/kernel/src/driver/net/loopback.rs @@ -50,11 +50,11 @@ impl phy::RxToken for LoopbackRxToken { /// /// ## 返回值 /// 返回函数 `f` 在 `self.buffer` 上的调用结果。 - fn consume(mut self, f: F) -> R + fn consume(self, f: F) -> R where - F: FnOnce(&mut [u8]) -> R, + F: FnOnce(&[u8]) -> R { - f(self.buffer.as_mut_slice()) + f(self.buffer.as_slice()) } } @@ -277,20 +277,41 @@ impl LoopbackInterface { /// 返回一个 `Arc`,即一个指向新创建的 `LoopbackInterface` 实例的智能指针。 pub fn new(mut driver: LoopbackDriver) -> Arc { let iface_id = generate_iface_id(); - let mut iface_config = smoltcp::iface::Config::new(HardwareAddress::Ethernet( - smoltcp::wire::EthernetAddress([0x00, 0x00, 0x00, 0x00, 0x00, 0x00]), - )); + + let hardware_addr = HardwareAddress::Ethernet(smoltcp::wire::EthernetAddress([ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + ])); + + let mut iface_config = smoltcp::iface::Config::new(hardware_addr); + iface_config.random_seed = rand() as u64; let mut iface = smoltcp::iface::Interface::new(iface_config, &mut driver, Instant::now().into()); + + iface.set_any_ip(true); + + let addr = IpAddress::v4(127, 0, 0, 1); + let cidr = IpCidr::new(addr, 8); + //设置网卡地址为127.0.0.1 iface.update_ip_addrs(|ip_addrs| { ip_addrs - .push(IpCidr::new(IpAddress::v4(127, 0, 0, 1), 8)) + .push(cidr) .expect("Push ipCidr failed: full"); }); + iface.routes_mut().update(|routes_map| { + routes_map + .push(smoltcp::iface::Route { + cidr, + via_router: addr, + preferred_until: None, + expires_at: None, + }) + .expect("Add default ipv4 route failed: full"); + }); + Arc::new(LoopbackInterface { driver: LoopbackDriverWapper(UnsafeCell::new(driver)), common: IfaceCommon::new(iface_id, false, iface), diff --git a/kernel/src/driver/net/mod.rs b/kernel/src/driver/net/mod.rs index 457b33f56..227be9208 100644 --- a/kernel/src/driver/net/mod.rs +++ b/kernel/src/driver/net/mod.rs @@ -209,19 +209,21 @@ impl IfaceCommon { let mut interface = self.smol_iface.lock_irqsave(); let (has_events, poll_at) = { - let mut has_events = false; - let mut poll_at; - loop { - has_events |= interface.poll(timestamp, device, &mut sockets); - poll_at = interface.poll_at(timestamp, &sockets); - let Some(instant) = poll_at else { - break; - }; - if instant > timestamp { - break; + ( + matches!( + interface.poll(timestamp, device, &mut sockets), + smoltcp::iface::PollResult::SocketStateChanged + ), + loop { + let poll_at = interface.poll_at(timestamp, &sockets); + let Some(instant) = poll_at else { + break poll_at; + }; + if instant > timestamp { + break poll_at; + } } - } - (has_events, poll_at) + ) }; // drop sockets here to avoid deadlock diff --git a/kernel/src/driver/net/virtio_net.rs b/kernel/src/driver/net/virtio_net.rs index a8b3b0586..e3ca055d8 100644 --- a/kernel/src/driver/net/virtio_net.rs +++ b/kernel/src/driver/net/virtio_net.rs @@ -585,11 +585,11 @@ impl phy::TxToken for VirtioNetToken { impl phy::RxToken for VirtioNetToken { fn consume(self, f: F) -> R where - F: FnOnce(&mut [u8]) -> R, + F: FnOnce(&[u8]) -> R, { // 为了线程安全,这里需要对VirtioNet进行加【写锁】,以保证对设备的互斥访问。 - let mut rx_buf = self.rx_buffer.unwrap(); - let result = f(rx_buf.packet_mut()); + let rx_buf = self.rx_buffer.unwrap(); + let result = f(rx_buf.packet()); self.driver .inner .lock() diff --git a/kernel/src/net/posix.rs b/kernel/src/net/posix.rs index e703a79c7..681a4c485 100644 --- a/kernel/src/net/posix.rs +++ b/kernel/src/net/posix.rs @@ -122,29 +122,29 @@ impl SockAddr { let addr_in: SockAddrIn = addr.addr_in; use smoltcp::wire; - let ip: wire::IpAddress = wire::IpAddress::from(wire::Ipv4Address::from_bytes( - &u32::from_be(addr_in.sin_addr).to_be_bytes()[..], + let ip: wire::IpAddress = wire::IpAddress::from(wire::Ipv4Address::from_bits( + u32::from_be(addr_in.sin_addr), )); let port = u16::from_be(addr_in.sin_port); return Ok(Endpoint::Ip(wire::IpEndpoint::new(ip, port))); } - AddressFamily::INet6 => { - if len < addr.len()? { - log::error!("len < addr.len()"); - return Err(SystemError::EINVAL); - } - log::debug!("INet6"); - let addr_in: SockAddrIn = addr.addr_in; + // AddressFamily::INet6 => { + // if len < addr.len()? { + // log::error!("len < addr.len()"); + // return Err(SystemError::EINVAL); + // } + // log::debug!("INet6"); + // let addr_in: SockAddrIn = addr.addr_in; - use smoltcp::wire; - let ip: wire::IpAddress = wire::IpAddress::from(wire::Ipv6Address::from_bytes( - &u32::from_be(addr_in.sin_addr).to_be_bytes()[..], - )); - let port = u16::from_be(addr_in.sin_port); + // use smoltcp::wire; + // let ip: wire::IpAddress = wire::IpAddress::from(wire::Ipv6Address::from_bits( + // u128::from_be(addr_in.sin_addr), + // )); + // let port = u16::from_be(addr_in.sin_port); - return Ok(Endpoint::Ip(wire::IpEndpoint::new(ip, port))); - } + // return Ok(Endpoint::Ip(wire::IpEndpoint::new(ip, port))); + // } AddressFamily::Unix => { let addr_un: SockAddrUn = addr.addr_un; @@ -232,12 +232,7 @@ impl SockAddr { }; return Ok(Endpoint::Unixpath((inode.metadata()?.inode_id, path))); - } - AddressFamily::Packet => { - // TODO: support packet socket - log::warn!("not support address family {:?}", addr.family); - return Err(SystemError::EINVAL); - } + }, _ => { log::warn!("not support address family {:?}", addr.family); return Err(SystemError::EINVAL); @@ -312,7 +307,7 @@ impl From for SockAddr { let addr_in = SockAddrIn { sin_family: AddressFamily::INet as u16, sin_port: ip_endpoint.port.to_be(), - sin_addr: u32::from_be_bytes(ipv4_addr.0).to_be(), + sin_addr: ipv4_addr.to_bits(), sin_zero: [0; 8], }; diff --git a/kernel/src/net/socket/inet/common/mod.rs b/kernel/src/net/socket/inet/common/mod.rs index 983b23162..58c209c89 100644 --- a/kernel/src/net/socket/inet/common/mod.rs +++ b/kernel/src/net/socket/inet/common/mod.rs @@ -41,40 +41,24 @@ impl BoundInner { T: smoltcp::socket::AnySocket<'static>, { if address.is_unspecified() { - // let inner = Vec::new(); - // for (_, iface) in *NET_DEVICES.read_irqsave() { - // let handle = iface.sockets().lock_no_preempt().add(socket); - // iface - // } // 强绑VirtualIO - // log::debug!("Not bind to any iface, bind to virtIO"); - - let ifaces: Vec> = NET_DEVICES + let iface = NET_DEVICES .read_irqsave() .iter() - .filter_map(|(_, v)| { + .find_map(|(_, v)| { if v.common().is_default_iface() { Some(v.clone()) } else { None } }) - .collect(); + .expect("No default interface"); - // let iface = NET_DEVICES - // .read_irqsave() - // .get(&0) - // .expect("??bind without virtIO, serious?") - // .clone(); - - let iface = ifaces[0].clone(); let handle = iface.sockets().lock_no_preempt().add(socket); return Ok(Self { handle, iface }); } else { let iface = get_iface_to_bind(address).ok_or(ENODEV)?; let handle = iface.sockets().lock_no_preempt().add(socket); - // log::debug!("Bind to iface: {}", iface.iface_name()); - // return Ok(Self { inner: vec![(handle, iface)] }); return Ok(Self { handle, iface }); } } diff --git a/kernel/src/net/socket/inet/stream/inner.rs b/kernel/src/net/socket/inet/stream/inner.rs index 20f7943fb..e63e2081f 100644 --- a/kernel/src/net/socket/inet/stream/inner.rs +++ b/kernel/src/net/socket/inet/stream/inner.rs @@ -31,13 +31,13 @@ where #[derive(Debug)] pub enum Init { - Unbound((Box>, bool)), + Unbound((Box>, smoltcp::wire::IpVersion)), Bound((socket::inet::BoundInner, smoltcp::wire::IpEndpoint)), } impl Init { - pub(super) fn new(v4: bool) -> Self { - Init::Unbound((Box::new(new_smoltcp_socket()), v4)) + pub(super) fn new(ver: smoltcp::wire::IpVersion) -> Self { + Init::Unbound((Box::new(new_smoltcp_socket()), ver)) } /// 传入一个已经绑定的socket @@ -75,14 +75,14 @@ impl Init { remote_endpoint: smoltcp::wire::IpEndpoint, ) -> Result<(socket::inet::BoundInner, smoltcp::wire::IpEndpoint), (Self, SystemError)> { match self { - Init::Unbound((socket, v4)) => { + Init::Unbound((socket, ver)) => { let (bound, address) = socket::inet::BoundInner::bind_ephemeral(*socket, remote_endpoint.addr) - .map_err(|err| (Self::new(v4), err))?; + .map_err(|err| (Self::new(ver), err))?; let bound_port = bound .port_manager() .bind_ephemeral_port(Types::Tcp) - .map_err(|err| (Self::new(v4), err))?; + .map_err(|err| (Self::new(ver), err))?; let endpoint = smoltcp::wire::IpEndpoint::new(address, bound_port); Ok((bound, endpoint)) } @@ -129,14 +129,16 @@ impl Init { } else { smoltcp::wire::IpListenEndpoint::from(local) }; - // log::debug!("listen at {:?}", listen_addr); + log::debug!("listen at {:?}", listen_addr); let mut inners = Vec::new(); if let Err(err) = || -> Result<(), SystemError> { for _ in 0..(backlog - 1) { // -1 because the first one is already bound let new_listen = socket::inet::BoundInner::bind( new_listen_smoltcp_socket(listen_addr), - &local.addr, + listen_addr.addr.as_ref().unwrap_or( + &smoltcp::wire::IpAddress::from(smoltcp::wire::Ipv4Address::UNSPECIFIED) + ), )?; inners.push(new_listen); } @@ -155,8 +157,19 @@ impl Init { return Ok(Listening { inners, connect: AtomicUsize::new(0), + listen_addr, }); } + + pub(super) fn close(&self) { + match self { + Init::Unbound(_) => {} + Init::Bound((inner, endpoint)) => { + inner.port_manager().unbind_port(Types::Tcp, endpoint.port); + inner.with_mut::(|socket| socket.close()); + } + } + } } #[derive(Debug, Default, Clone, Copy)] @@ -245,6 +258,7 @@ impl Connecting { pub struct Listening { inners: Vec, connect: AtomicUsize, + listen_addr: smoltcp::wire::IpListenEndpoint, } impl Listening { @@ -258,23 +272,20 @@ impl Listening { return Err(EAGAIN_OR_EWOULDBLOCK); } - let (local_endpoint, remote_endpoint) = connected + let remote_endpoint = connected .with::(|socket| { - ( - socket - .local_endpoint() - .expect("A Connected Tcp With No Local Endpoint"), - socket - .remote_endpoint() - .expect("A Connected Tcp With No Remote Endpoint"), - ) + socket + .remote_endpoint() + .expect("A Connected Tcp With No Remote Endpoint") }); // log::debug!("local at {:?}", local_endpoint); let mut new_listen = socket::inet::BoundInner::bind( - new_listen_smoltcp_socket(local_endpoint), - &local_endpoint.addr, + new_listen_smoltcp_socket(self.listen_addr), + self.listen_addr.addr.as_ref().unwrap_or( + &smoltcp::wire::IpAddress::from(smoltcp::wire::Ipv4Address::UNSPECIFIED), + ), )?; // swap the connected socket with the new_listen socket @@ -307,14 +318,21 @@ impl Listening { } pub fn get_name(&self) -> smoltcp::wire::IpEndpoint { - self.inners[0].with::(|socket| { - if let Some(name) = socket.local_endpoint() { - return name; - } else { - // TODO: IPV6 - return UNSPECIFIED_LOCAL_ENDPOINT_V4; - } - }) + smoltcp::wire::IpEndpoint::new(self.listen_addr.addr.unwrap_or( + smoltcp::wire::IpAddress::from(smoltcp::wire::Ipv4Address::UNSPECIFIED), + ), self.listen_addr.port) + } + + pub fn close(&self) { + log::debug!("Close Listening Socket"); + let port = self.get_name().port; + for inner in self.inners.iter() { + inner.with_mut::(|socket| socket.close()); + } + self.inners[0] + .iface() + .port_manager() + .unbind_port(Types::Tcp, port); } } diff --git a/kernel/src/net/socket/inet/stream/mod.rs b/kernel/src/net/socket/inet/stream/mod.rs index 5cd9e9283..c56419eaf 100644 --- a/kernel/src/net/socket/inet/stream/mod.rs +++ b/kernel/src/net/socket/inet/stream/mod.rs @@ -2,7 +2,7 @@ use alloc::sync::{Arc, Weak}; use core::sync::atomic::{AtomicBool, AtomicUsize}; use system_error::SystemError::{self, *}; -use crate::libs::rwlock::RwLock; +use crate::{arch::init, libs::rwlock::RwLock}; use crate::net::event_poll::EPollEventType; use crate::net::net_core::poll_ifaces; use crate::net::socket::*; @@ -29,9 +29,9 @@ pub struct TcpSocket { } impl TcpSocket { - pub fn new(nonblock: bool, v4: bool) -> Arc { + pub fn new(nonblock: bool, ver: smoltcp::wire::IpVersion) -> Arc { Arc::new_cyclic(|me| Self { - inner: RwLock::new(Some(Inner::Init(Init::new(v4)))), + inner: RwLock::new(Some(Inner::Init(Init::new(ver)))), shutdown: Shutdown::new(), nonblock: AtomicBool::new(nonblock), wait_queue: WaitQueue::default(), @@ -234,12 +234,11 @@ impl Socket for TcpSocket { fn get_name(&self) -> Result { match self.inner.read().as_ref().expect("Tcp Inner is None") { - Inner::Init(Init::Unbound((_, v4))) => { - if *v4 { - Ok(Endpoint::Ip(UNSPECIFIED_LOCAL_ENDPOINT_V4)) - } else { - Ok(Endpoint::Ip(UNSPECIFIED_LOCAL_ENDPOINT_V6)) - } + Inner::Init(Init::Unbound((_, ver))) => { + Ok(Endpoint::Ip( match ver { + smoltcp::wire::IpVersion::Ipv4 => UNSPECIFIED_LOCAL_ENDPOINT_V4, + smoltcp::wire::IpVersion::Ipv6 => UNSPECIFIED_LOCAL_ENDPOINT_V6, + })) } Inner::Init(Init::Bound((_, local))) => Ok(Endpoint::Ip(*local)), Inner::Connecting(connecting) => Ok(Endpoint::Ip(connecting.get_name())), @@ -324,7 +323,14 @@ impl Socket for TcpSocket { es.release(); Ok(()) } - _ => Ok(()), + Inner::Listening(ls) => { + ls.close(); + Ok(()) + } + Inner::Init(init) => { + init.close(); + Ok(()) + }, }) .unwrap_or(Ok(())) } diff --git a/kernel/src/net/socket/inet/syscall.rs b/kernel/src/net/socket/inet/syscall.rs index bb541f873..6049c990a 100644 --- a/kernel/src/net/socket/inet/syscall.rs +++ b/kernel/src/net/socket/inet/syscall.rs @@ -8,7 +8,7 @@ use inet::{TcpSocket, UdpSocket}; use crate::net::socket::*; fn create_inet_socket( - v4: bool, + version: smoltcp::wire::IpVersion, socket_type: PSOCK, protocol: smoltcp::wire::IpProtocol, ) -> Result, SystemError> { @@ -26,7 +26,7 @@ fn create_inet_socket( }, PSOCK::Stream => match protocol { HopByHop | Tcp => { - return Ok(TcpSocket::new(false, v4)); + return Ok(TcpSocket::new(false, version)); } _ => { return Err(EPROTONOSUPPORT); @@ -44,8 +44,11 @@ fn create_inet_socket( pub struct Inet; impl family::Family for Inet { fn socket(stype: PSOCK, protocol: u32) -> Result, SystemError> { - let socket = - create_inet_socket(true, stype, smoltcp::wire::IpProtocol::from(protocol as u8))?; + let socket = create_inet_socket( + smoltcp::wire::IpVersion::Ipv4, + stype, + smoltcp::wire::IpProtocol::from(protocol as u8) + )?; Ok(Inode::new(socket)) } } @@ -54,7 +57,7 @@ pub struct Inet6; impl family::Family for Inet6 { fn socket(stype: PSOCK, protocol: u32) -> Result, SystemError> { let socket = create_inet_socket( - false, + smoltcp::wire::IpVersion::Ipv6, stype, smoltcp::wire::IpProtocol::from(protocol as u8), )?;