feat(local-tun): disable receive checksum, improving performance

- ref #1923

Checksum running on receiving packets are the most significant cost of
CPU time in local-tun.
This commit is contained in:
zonyitoo
2025-03-26 00:36:35 +08:00
parent d0f83d7366
commit aac36757d4
3 changed files with 11 additions and 4 deletions
+1
View File
@@ -185,6 +185,7 @@ smoltcp = { version = "0.12", optional = true, default-features = false, feature
"log",
"medium-ip",
"proto-ipv4",
"proto-ipv4-fragmentation",
"proto-ipv6",
"socket-icmp",
"socket-udp",
@@ -18,7 +18,7 @@ use log::{debug, error, trace};
use shadowsocks::{net::TcpSocketOpts, relay::socks5::Address};
use smoltcp::{
iface::{Config as InterfaceConfig, Interface, PollResult, SocketHandle, SocketSet},
phy::{DeviceCapabilities, Medium},
phy::{Checksum, DeviceCapabilities, Medium},
socket::tcp::{CongestionControl, Socket as TcpSocket, SocketBuffer as TcpSocketBuffer, State as TcpState},
storage::RingBuffer,
time::{Duration as SmolDuration, Instant as SmolInstant},
@@ -42,9 +42,9 @@ use crate::{
use super::virt_device::VirtTunDevice;
// NOTE: Default buffer could contain 20 AEAD packets
const DEFAULT_TCP_SEND_BUFFER_SIZE: u32 = 0x3FFF * 20;
const DEFAULT_TCP_RECV_BUFFER_SIZE: u32 = 0x3FFF * 20;
// NOTE: Default buffer could contain 5 AEAD packets
const DEFAULT_TCP_SEND_BUFFER_SIZE: u32 = (0x3FFFu32 * 5).next_power_of_two();
const DEFAULT_TCP_RECV_BUFFER_SIZE: u32 = (0x3FFFu32 * 5).next_power_of_two();
#[derive(Debug, Clone, Copy, Eq, PartialEq)]
enum TcpSocketState {
@@ -261,6 +261,11 @@ impl TcpTun {
let mut capabilities = DeviceCapabilities::default();
capabilities.medium = Medium::Ip;
capabilities.max_transmission_unit = mtu as usize;
capabilities.checksum.ipv4 = Checksum::Tx;
capabilities.checksum.tcp = Checksum::Tx;
capabilities.checksum.udp = Checksum::Tx;
capabilities.checksum.icmpv4 = Checksum::Tx;
capabilities.checksum.icmpv6 = Checksum::Tx;
let (mut device, iface_rx, iface_tx, iface_tx_avail) = VirtTunDevice::new(capabilities);
@@ -64,6 +64,7 @@ impl Device for VirtTunDevice {
buffer,
phantom_device: PhantomData,
};
self.in_buf_avail.store(true, Ordering::Release);
let tx = VirtTxToken(self);
return Some((rx, tx));
}