xref: /DragonOS/kernel/src/net/net_core.rs (revision 4dd4856f933be0b4624c7f7ffa9e3d0c8c218873)
1 use alloc::{boxed::Box, collections::BTreeMap, sync::Arc};
2 use log::{debug, info, warn};
3 use smoltcp::{socket::dhcpv4, wire};
4 use system_error::SystemError;
5 
6 use crate::{
7     driver::net::{NetDevice, Operstate},
8     libs::rwlock::RwLockReadGuard,
9     net::{socket::SocketPollMethod, NET_DEVICES},
10     time::timer::{next_n_ms_timer_jiffies, Timer, TimerFunction},
11 };
12 
13 use super::{
14     event_poll::{EPollEventType, EventPoll},
15     socket::{handle::GlobalSocketHandle, inet::TcpSocket, HANDLE_MAP, SOCKET_SET},
16 };
17 
18 /// The network poll function, which will be called by timer.
19 ///
20 /// The main purpose of this function is to poll all network interfaces.
21 #[derive(Debug)]
22 #[allow(dead_code)]
23 struct NetWorkPollFunc;
24 
25 impl TimerFunction for NetWorkPollFunc {
26     fn run(&mut self) -> Result<(), SystemError> {
27         poll_ifaces_try_lock(10).ok();
28         let next_time = next_n_ms_timer_jiffies(10);
29         let timer = Timer::new(Box::new(NetWorkPollFunc), next_time);
30         timer.activate();
31         return Ok(());
32     }
33 }
34 
35 pub fn net_init() -> Result<(), SystemError> {
36     dhcp_query()?;
37     // Init poll timer function
38     // let next_time = next_n_ms_timer_jiffies(5);
39     // let timer = Timer::new(Box::new(NetWorkPollFunc), next_time);
40     // timer.activate();
41     return Ok(());
42 }
43 
44 fn dhcp_query() -> Result<(), SystemError> {
45     let binding = NET_DEVICES.write_irqsave();
46 
47     //由于现在os未实现在用户态为网卡动态分配内存,而lo网卡的id最先分配且ip固定不能被分配
48     //所以特判取用id为1的网卡(也就是virto_net)
49     let net_face = binding.get(&1).ok_or(SystemError::ENODEV)?.clone();
50 
51     drop(binding);
52 
53     // Create sockets
54     let mut dhcp_socket = dhcpv4::Socket::new();
55 
56     // Set a ridiculously short max lease time to show DHCP renews work properly.
57     // This will cause the DHCP client to start renewing after 5 seconds, and give up the
58     // lease after 10 seconds if renew hasn't succeeded.
59     // IMPORTANT: This should be removed in production.
60     dhcp_socket.set_max_lease_duration(Some(smoltcp::time::Duration::from_secs(10)));
61 
62     let dhcp_handle = SOCKET_SET.lock_irqsave().add(dhcp_socket);
63 
64     const DHCP_TRY_ROUND: u8 = 10;
65     for i in 0..DHCP_TRY_ROUND {
66         debug!("DHCP try round: {}", i);
67         net_face.poll(&mut SOCKET_SET.lock_irqsave()).ok();
68         let mut binding = SOCKET_SET.lock_irqsave();
69         let event = binding.get_mut::<dhcpv4::Socket>(dhcp_handle).poll();
70 
71         match event {
72             None => {}
73 
74             Some(dhcpv4::Event::Configured(config)) => {
75                 // debug!("Find Config!! {config:?}");
76                 // debug!("Find ip address: {}", config.address);
77                 // debug!("iface.ip_addrs={:?}", net_face.inner_iface.ip_addrs());
78 
79                 net_face
80                     .update_ip_addrs(&[wire::IpCidr::Ipv4(config.address)])
81                     .ok();
82 
83                 if let Some(router) = config.router {
84                     net_face
85                         .inner_iface()
86                         .lock()
87                         .routes_mut()
88                         .add_default_ipv4_route(router)
89                         .unwrap();
90                     let cidr = net_face.inner_iface().lock().ip_addrs().first().cloned();
91                     if let Some(cidr) = cidr {
92                         // 这里先在这里将网卡设置为up,后面等netlink实现了再修改
93                         net_face.set_operstate(Operstate::IF_OPER_UP);
94                         info!("Successfully allocated ip by Dhcpv4! Ip:{}", cidr);
95                         return Ok(());
96                     }
97                 } else {
98                     net_face
99                         .inner_iface()
100                         .lock()
101                         .routes_mut()
102                         .remove_default_ipv4_route();
103                 }
104             }
105 
106             Some(dhcpv4::Event::Deconfigured) => {
107                 debug!("Dhcp v4 deconfigured");
108                 net_face
109                     .update_ip_addrs(&[smoltcp::wire::IpCidr::Ipv4(wire::Ipv4Cidr::new(
110                         wire::Ipv4Address::UNSPECIFIED,
111                         0,
112                     ))])
113                     .ok();
114                 net_face
115                     .inner_iface()
116                     .lock()
117                     .routes_mut()
118                     .remove_default_ipv4_route();
119             }
120         }
121     }
122 
123     return Err(SystemError::ETIMEDOUT);
124 }
125 
126 pub fn poll_ifaces() {
127     let guard: RwLockReadGuard<BTreeMap<usize, Arc<dyn NetDevice>>> = NET_DEVICES.read_irqsave();
128     if guard.len() == 0 {
129         warn!("poll_ifaces: No net driver found!");
130         return;
131     }
132     let mut sockets = SOCKET_SET.lock_irqsave();
133     for (_, iface) in guard.iter() {
134         iface.poll(&mut sockets).ok();
135     }
136     let _ = send_event(&sockets);
137 }
138 
139 /// 对ifaces进行轮询,最多对SOCKET_SET尝试times次加锁。
140 ///
141 /// @return 轮询成功,返回Ok(())
142 /// @return 加锁超时,返回SystemError::EAGAIN_OR_EWOULDBLOCK
143 /// @return 没有网卡,返回SystemError::ENODEV
144 pub fn poll_ifaces_try_lock(times: u16) -> Result<(), SystemError> {
145     let mut i = 0;
146     while i < times {
147         let guard: RwLockReadGuard<BTreeMap<usize, Arc<dyn NetDevice>>> =
148             NET_DEVICES.read_irqsave();
149         if guard.len() == 0 {
150             warn!("poll_ifaces: No net driver found!");
151             // 没有网卡,返回错误
152             return Err(SystemError::ENODEV);
153         }
154         let sockets = SOCKET_SET.try_lock_irqsave();
155         // 加锁失败,继续尝试
156         if sockets.is_err() {
157             i += 1;
158             continue;
159         }
160 
161         let mut sockets = sockets.unwrap();
162         for (_, iface) in guard.iter() {
163             iface.poll(&mut sockets).ok();
164         }
165         send_event(&sockets)?;
166         return Ok(());
167     }
168     // 尝试次数用完,返回错误
169     return Err(SystemError::EAGAIN_OR_EWOULDBLOCK);
170 }
171 
172 /// 对ifaces进行轮询,最多对SOCKET_SET尝试一次加锁。
173 ///
174 /// @return 轮询成功,返回Ok(())
175 /// @return 加锁超时,返回SystemError::EAGAIN_OR_EWOULDBLOCK
176 /// @return 没有网卡,返回SystemError::ENODEV
177 pub fn poll_ifaces_try_lock_onetime() -> Result<(), SystemError> {
178     let guard: RwLockReadGuard<BTreeMap<usize, Arc<dyn NetDevice>>> = NET_DEVICES.read_irqsave();
179     if guard.len() == 0 {
180         warn!("poll_ifaces: No net driver found!");
181         // 没有网卡,返回错误
182         return Err(SystemError::ENODEV);
183     }
184     let mut sockets = SOCKET_SET.try_lock_irqsave()?;
185     for (_, iface) in guard.iter() {
186         iface.poll(&mut sockets).ok();
187     }
188     send_event(&sockets)?;
189     return Ok(());
190 }
191 
192 /// ### 处理轮询后的事件
193 fn send_event(sockets: &smoltcp::iface::SocketSet) -> Result<(), SystemError> {
194     for (handle, socket_type) in sockets.iter() {
195         let handle_guard = HANDLE_MAP.read_irqsave();
196         let global_handle = GlobalSocketHandle::new_smoltcp_handle(handle);
197         let item: Option<&super::socket::SocketHandleItem> = handle_guard.get(&global_handle);
198         if item.is_none() {
199             continue;
200         }
201 
202         let handle_item = item.unwrap();
203         let posix_item = handle_item.posix_item();
204         if posix_item.is_none() {
205             continue;
206         }
207         let posix_item = posix_item.unwrap();
208 
209         // 获取socket上的事件
210         let mut events = SocketPollMethod::poll(socket_type, handle_item).bits() as u64;
211 
212         // 分发到相应类型socket处理
213         match socket_type {
214             smoltcp::socket::Socket::Raw(_) | smoltcp::socket::Socket::Udp(_) => {
215                 posix_item.wakeup_any(events);
216             }
217             smoltcp::socket::Socket::Icmp(_) => unimplemented!("Icmp socket hasn't unimplemented"),
218             smoltcp::socket::Socket::Tcp(inner_socket) => {
219                 if inner_socket.is_active() {
220                     events |= TcpSocket::CAN_ACCPET;
221                 }
222                 if inner_socket.state() == smoltcp::socket::tcp::State::Established {
223                     events |= TcpSocket::CAN_CONNECT;
224                 }
225                 if inner_socket.state() == smoltcp::socket::tcp::State::CloseWait {
226                     events |= EPollEventType::EPOLLHUP.bits() as u64;
227                 }
228 
229                 posix_item.wakeup_any(events);
230             }
231             smoltcp::socket::Socket::Dhcpv4(_) => {}
232             smoltcp::socket::Socket::Dns(_) => unimplemented!("Dns socket hasn't unimplemented"),
233         }
234         EventPoll::wakeup_epoll(
235             &posix_item.epitems,
236             Some(EPollEventType::from_bits_truncate(events as u32)),
237         )?;
238         drop(handle_guard);
239         // crate::debug!(
240         //     "{} send_event {:?}",
241         //     handle,
242         //     EPollEventType::from_bits_truncate(events as u32)
243         // );
244     }
245     Ok(())
246 }
247