fix tun device on mac (#58)

This commit is contained in:
Sijie.Sun
2024-04-26 21:19:47 +08:00
committed by GitHub
parent 57c9f11371
commit 096af6aa45
3 changed files with 37 additions and 22 deletions

View File

@@ -225,7 +225,7 @@ impl Instance {
); );
let ret = sink.send(packet).await; let ret = sink.send(packet).await;
if ret.is_err() { if ret.is_err() {
panic!("do_forward_tunnel_to_nic"); tracing::error!(?ret, "do_forward_tunnel_to_nic sink error");
} }
} }
}); });

View File

@@ -12,13 +12,14 @@ use crate::{
ifcfg::{IfConfiger, IfConfiguerTrait}, ifcfg::{IfConfiger, IfConfiguerTrait},
}, },
tunnel::{ tunnel::{
common::{FramedWriter, TunnelWrapper, ZCPacketToBytes}, common::{reserve_buf, FramedWriter, TunnelWrapper, ZCPacketToBytes},
packet_def::ZCPacket, packet_def::{ZCPacket, ZCPacketType},
StreamItem, Tunnel, TunnelError, StreamItem, Tunnel, TunnelError,
}, },
}; };
use byteorder::WriteBytesExt as _; use byteorder::WriteBytesExt as _;
use bytes::BytesMut;
use futures::{lock::BiLock, ready, Stream}; use futures::{lock::BiLock, ready, Stream};
use pin_project_lite::pin_project; use pin_project_lite::pin_project;
use tokio::io::AsyncWrite; use tokio::io::AsyncWrite;
@@ -30,15 +31,23 @@ pin_project! {
pub struct TunStream { pub struct TunStream {
#[pin] #[pin]
l: BiLock<AsyncDevice>, l: BiLock<AsyncDevice>,
cur_packet: Option<ZCPacket>, cur_buf: BytesMut,
has_packet_info: bool,
payload_offset: usize,
} }
} }
impl TunStream { impl TunStream {
pub fn new(l: BiLock<AsyncDevice>) -> Self { pub fn new(l: BiLock<AsyncDevice>, has_packet_info: bool) -> Self {
let mut payload_offset = ZCPacketType::NIC.get_packet_offsets().payload_offset;
if has_packet_info {
payload_offset -= 4;
}
Self { Self {
l, l,
cur_packet: None, cur_buf: BytesMut::new(),
has_packet_info,
payload_offset,
} }
} }
} }
@@ -47,19 +56,20 @@ impl Stream for TunStream {
type Item = StreamItem; type Item = StreamItem;
fn poll_next(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Option<StreamItem>> { fn poll_next(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Option<StreamItem>> {
let self_mut = self.project(); let mut self_mut = self.project();
let mut g = ready!(self_mut.l.poll_lock(cx)); let mut g = ready!(self_mut.l.poll_lock(cx));
if self_mut.cur_packet.is_none() { reserve_buf(&mut self_mut.cur_buf, 2500, 128 * 1024);
*self_mut.cur_packet = Some(ZCPacket::new_with_reserved_payload(2048)); if self_mut.cur_buf.len() == 0 {
unsafe {
self_mut.cur_buf.set_len(*self_mut.payload_offset);
}
} }
let cur_packet = self_mut.cur_packet.as_mut().unwrap(); match ready!(poll_read_buf(g.as_pin_mut(), cx, &mut self_mut.cur_buf)) {
match ready!(poll_read_buf(
g.as_pin_mut(),
cx,
&mut cur_packet.mut_inner()
)) {
Ok(0) => Poll::Ready(None), Ok(0) => Poll::Ready(None),
Ok(_n) => Poll::Ready(Some(Ok(self_mut.cur_packet.take().unwrap()))), Ok(_n) => Poll::Ready(Some(Ok(ZCPacket::new_from_buf(
self_mut.cur_buf.split(),
ZCPacketType::NIC,
)))),
Err(err) => { Err(err) => {
println!("tun stream error: {:?}", err); println!("tun stream error: {:?}", err);
Poll::Ready(None) Poll::Ready(None)
@@ -128,11 +138,15 @@ impl TunZCPacketToBytes {
Self { has_packet_info } Self { has_packet_info }
} }
pub fn fill_packet_info(&self, mut buf: &mut [u8]) -> Result<(), io::Error> { pub fn fill_packet_info(
&self,
mut buf: &mut [u8],
proto: PacketProtocol,
) -> Result<(), io::Error> {
// flags is always 0 // flags is always 0
buf.write_u16::<NativeEndian>(0)?; buf.write_u16::<NativeEndian>(0)?;
// write the protocol as network byte order // write the protocol as network byte order
buf.write_u16::<NetworkEndian>(infer_proto(&buf).into_pi_field()?)?; buf.write_u16::<NetworkEndian>(proto.into_pi_field()?)?;
Ok(()) Ok(())
} }
} }
@@ -146,7 +160,8 @@ impl ZCPacketToBytes for TunZCPacketToBytes {
let ret = if self.has_packet_info { let ret = if self.has_packet_info {
let mut inner = inner.split_off(payload_offset - 4); let mut inner = inner.split_off(payload_offset - 4);
self.fill_packet_info(&mut inner[0..4])?; let proto = infer_proto(&inner[4..]);
self.fill_packet_info(&mut inner[0..4], proto)?;
inner inner
} else { } else {
inner.split_off(payload_offset) inner.split_off(payload_offset)
@@ -264,7 +279,7 @@ impl VirtualNic {
let (a, b) = BiLock::new(dev); let (a, b) = BiLock::new(dev);
let ft = TunnelWrapper::new( let ft = TunnelWrapper::new(
TunStream::new(a), TunStream::new(a, has_packet_info),
FramedWriter::new_with_converter( FramedWriter::new_with_converter(
TunAsyncWrite { l: b }, TunAsyncWrite { l: b },
TunZCPacketToBytes::new(has_packet_info), TunZCPacketToBytes::new(has_packet_info),

View File

@@ -161,10 +161,10 @@ impl ZCPacket {
ret ret
} }
pub fn new_with_reserved_payload(cap: usize) -> Self { pub fn new_for_tun(cap: usize, packet_info_len: usize) -> Self {
let mut ret = Self::new_nic_packet(); let mut ret = Self::new_nic_packet();
ret.inner.reserve(cap); ret.inner.reserve(cap);
let total_len = ret.packet_type.get_packet_offsets().payload_offset; let total_len = ret.packet_type.get_packet_offsets().payload_offset - packet_info_len;
ret.inner.resize(total_len, 0); ret.inner.resize(total_len, 0);
ret ret
} }