-
Notifications
You must be signed in to change notification settings - Fork 118
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
11 changed files
with
934 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,70 @@ | ||
// Copyright (c) Microsoft Corporation. | ||
// Licensed under the MIT license. | ||
|
||
//====================================================================================================================== | ||
// Imports | ||
//====================================================================================================================== | ||
|
||
use crate::catpowder::win::umemreg::UmemReg; | ||
use ::std::ops::{ | ||
Deref, | ||
DerefMut, | ||
}; | ||
|
||
//====================================================================================================================== | ||
// Structures | ||
//====================================================================================================================== | ||
|
||
pub struct XdpBuffer { | ||
b: *mut xdp_rs::XSK_BUFFER_DESCRIPTOR, | ||
umemreg: UmemReg, | ||
} | ||
|
||
//====================================================================================================================== | ||
// Implementations | ||
//====================================================================================================================== | ||
|
||
impl XdpBuffer { | ||
pub fn new(b: *mut xdp_rs::XSK_BUFFER_DESCRIPTOR, umemreg: UmemReg) -> Self { | ||
Self { b, umemreg } | ||
} | ||
|
||
pub fn len(&self) -> usize { | ||
unsafe { (*self.b).Length as usize } | ||
} | ||
|
||
pub fn set_len(&mut self, len: usize) { | ||
unsafe { | ||
(*self.b).Length = len as u32; | ||
} | ||
} | ||
|
||
unsafe fn base_address(&self) -> u64 { | ||
(*self.b).Address.__bindgen_anon_1.BaseAddress() | ||
} | ||
|
||
unsafe fn offset(&self) -> u64 { | ||
(*self.b).Address.__bindgen_anon_1.Offset() | ||
} | ||
|
||
unsafe fn addr(&self) -> *mut core::ffi::c_void { | ||
let mut ptr: *mut u8 = self.umemreg.get_address() as *mut u8; | ||
ptr = ptr.add(self.base_address() as usize); | ||
ptr = ptr.add(self.offset() as usize); | ||
ptr as *mut core::ffi::c_void | ||
} | ||
} | ||
|
||
impl Deref for XdpBuffer { | ||
type Target = [u8]; | ||
|
||
fn deref(&self) -> &[u8] { | ||
unsafe { std::slice::from_raw_parts(self.addr() as *const u8, self.len()) } | ||
} | ||
} | ||
|
||
impl DerefMut for XdpBuffer { | ||
fn deref_mut(&mut self) -> &mut [u8] { | ||
unsafe { std::slice::from_raw_parts_mut(self.addr() as *mut u8, self.len()) } | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
// Copyright (c) Microsoft Corporation. | ||
// Licensed under the MIT license. | ||
|
||
mod buffer; | ||
mod params; | ||
mod program; | ||
mod rule; | ||
pub mod runtime; | ||
mod rx_ring; | ||
mod socket; | ||
mod tx_ring; | ||
mod umemreg; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
// Copyright (c) Microsoft Corporation. | ||
// Licensed under the MIT license. | ||
|
||
//====================================================================================================================== | ||
// Imports | ||
//====================================================================================================================== | ||
|
||
use crate::catpowder::win::socket::XdpSocket; | ||
use ::std::mem; | ||
|
||
//====================================================================================================================== | ||
// Structures | ||
//====================================================================================================================== | ||
|
||
pub struct XdpRedirectParams { | ||
redirect: xdp_rs::XDP_REDIRECT_PARAMS, | ||
} | ||
|
||
//====================================================================================================================== | ||
// Implementations | ||
//====================================================================================================================== | ||
|
||
impl XdpRedirectParams { | ||
pub fn new(socket: &XdpSocket) -> Self { | ||
let redirect: xdp_rs::XDP_REDIRECT_PARAMS = { | ||
let mut redirect: xdp_rs::_XDP_REDIRECT_PARAMS = unsafe { mem::zeroed() }; | ||
redirect.TargetType = xdp_rs::_XDP_REDIRECT_TARGET_TYPE_XDP_REDIRECT_TARGET_TYPE_XSK; | ||
redirect.Target = socket.socket; | ||
redirect | ||
}; | ||
Self { redirect } | ||
} | ||
|
||
pub fn as_ptr(&self) -> &xdp_rs::XDP_REDIRECT_PARAMS { | ||
&self.redirect | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
// Copyright (c) Microsoft Corporation. | ||
// Licensed under the MIT license. | ||
|
||
//====================================================================================================================== | ||
// Imports | ||
//====================================================================================================================== | ||
|
||
use ::windows::Win32::Foundation::HANDLE; | ||
|
||
//====================================================================================================================== | ||
// Structures | ||
//====================================================================================================================== | ||
|
||
#[derive(Default)] | ||
pub struct XdpProgram { | ||
program: HANDLE, | ||
} | ||
|
||
//====================================================================================================================== | ||
// Implementations | ||
//====================================================================================================================== | ||
|
||
impl XdpProgram { | ||
pub fn as_ptr(&mut self) -> *mut HANDLE { | ||
&mut self.program as *mut HANDLE | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,46 @@ | ||
// Copyright (c) Microsoft Corporation. | ||
// Licensed under the MIT license. | ||
|
||
//====================================================================================================================== | ||
// Imports | ||
//====================================================================================================================== | ||
|
||
use crate::catpowder::win::{ | ||
params::XdpRedirectParams, | ||
socket::XdpSocket, | ||
}; | ||
use ::std::mem; | ||
|
||
//====================================================================================================================== | ||
// Structures | ||
//====================================================================================================================== | ||
|
||
pub struct XdpRule { | ||
rule: xdp_rs::XDP_RULE, | ||
} | ||
|
||
//====================================================================================================================== | ||
// Implementations | ||
//====================================================================================================================== | ||
|
||
impl XdpRule { | ||
pub fn new(socket: &XdpSocket) -> Self { | ||
let redirect: XdpRedirectParams = XdpRedirectParams::new(socket); | ||
let rule: xdp_rs::XDP_RULE = unsafe { | ||
let mut rule: xdp_rs::XDP_RULE = std::mem::zeroed(); | ||
rule.Match = xdp_rs::_XDP_MATCH_TYPE_XDP_MATCH_ALL; | ||
rule.Action = xdp_rs::_XDP_RULE_ACTION_XDP_PROGRAM_ACTION_REDIRECT; | ||
// TODO: Set pattern | ||
// Perform bitwise copy from redirect to rule. | ||
rule.__bindgen_anon_1 = | ||
mem::transmute_copy::<xdp_rs::XDP_REDIRECT_PARAMS, xdp_rs::_XDP_RULE__bindgen_ty_1>(redirect.as_ptr()); | ||
|
||
rule | ||
}; | ||
Self { rule } | ||
} | ||
|
||
pub fn as_ptr(&self) -> *const xdp_rs::XDP_RULE { | ||
&self.rule | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,156 @@ | ||
// Copyright (c) Microsoft Corporation. | ||
// Licensed under the MIT license. | ||
|
||
//====================================================================================================================== | ||
// Imports | ||
//====================================================================================================================== | ||
|
||
use crate::{ | ||
catpowder::win::{ | ||
buffer::XdpBuffer, | ||
rx_ring::RxRing, | ||
socket::XdpApi, | ||
tx_ring::TxRing, | ||
}, | ||
demikernel::config::Config, | ||
expect_ok, | ||
runtime::{ | ||
fail::Fail, | ||
memory::{ | ||
DemiBuffer, | ||
MemoryRuntime, | ||
}, | ||
network::{ | ||
consts::RECEIVE_BATCH_SIZE, | ||
NetworkRuntime, | ||
PacketBuf, | ||
}, | ||
Runtime, | ||
SharedObject, | ||
}, | ||
}; | ||
use ::arrayvec::ArrayVec; | ||
use ::std::borrow::{ | ||
Borrow, | ||
BorrowMut, | ||
}; | ||
|
||
//====================================================================================================================== | ||
// Structures | ||
//====================================================================================================================== | ||
|
||
struct CatpowderRuntimeInner { | ||
tx: TxRing, | ||
rx: RxRing, | ||
} | ||
/// Underlying network transport. | ||
#[derive(Clone)] | ||
pub struct CatpowderRuntime { | ||
api: XdpApi, | ||
inner: SharedObject<CatpowderRuntimeInner>, | ||
} | ||
|
||
/// A network transport built on top of Windows XDP. | ||
#[derive(Clone)] | ||
pub struct SharedXdpTransport(SharedObject<CatpowderRuntime>); | ||
|
||
//====================================================================================================================== | ||
// Associated Functions | ||
//====================================================================================================================== | ||
impl CatpowderRuntime {} | ||
|
||
impl NetworkRuntime for CatpowderRuntime { | ||
fn new(igconfig: &Config) -> Result<Self, Fail> { | ||
trace!("Creating XDP runtime."); | ||
let mut api: XdpApi = XdpApi::new()?; | ||
|
||
// TODO: read the following from the config file. | ||
let index: u32 = 5; | ||
let queueid: u32 = 0; | ||
|
||
let rx: RxRing = RxRing::new(&mut api, index, queueid)?; | ||
let tx: TxRing = TxRing::new(&mut api, index, queueid)?; | ||
|
||
Ok(Self { | ||
api, | ||
inner: SharedObject::new(CatpowderRuntimeInner { rx, tx }), | ||
}) | ||
} | ||
|
||
fn transmit(&mut self, pkt: Box<dyn PacketBuf>) { | ||
let header_size: usize = pkt.header_size(); | ||
let body_size: usize = pkt.body_size(); | ||
assert!(header_size + body_size < u16::MAX as usize); | ||
trace!("header_size={:?}, body_size={:?}", header_size, body_size); | ||
|
||
const COUNT: u32 = 1; | ||
let mut idx: u32 = 0; | ||
|
||
assert!(self.inner.borrow_mut().tx.producer_reserve(COUNT, &mut idx) == COUNT); | ||
|
||
let mut buf: XdpBuffer = self.inner.borrow_mut().tx.get_element(idx); | ||
buf.set_len(header_size + body_size); | ||
|
||
pkt.write_header(&mut buf[..header_size]); | ||
if let Some(body) = pkt.take_body() { | ||
buf[header_size..].copy_from_slice(&body[..]); | ||
} | ||
|
||
self.inner.borrow_mut().tx.producer_submit(COUNT); | ||
|
||
// Notify socket. | ||
let mut outflags = xdp_rs::XSK_NOTIFY_RESULT_FLAGS::default(); | ||
self.inner | ||
.borrow() | ||
.tx | ||
.notify_socket( | ||
&mut self.api, | ||
xdp_rs::_XSK_NOTIFY_FLAGS_XSK_NOTIFY_FLAG_POKE_TX | xdp_rs::_XSK_NOTIFY_FLAGS_XSK_NOTIFY_FLAG_WAIT_TX, | ||
u32::MAX, | ||
&mut outflags, | ||
) | ||
.unwrap(); | ||
|
||
if self.inner.borrow_mut().tx.consumer_reserve(COUNT, &mut idx) == COUNT { | ||
self.inner.borrow_mut().tx.consumer_release(COUNT); | ||
return; | ||
} | ||
|
||
warn!("failed to send packet"); | ||
} | ||
|
||
fn receive(&mut self) -> ArrayVec<DemiBuffer, RECEIVE_BATCH_SIZE> { | ||
let mut ret: ArrayVec<DemiBuffer, RECEIVE_BATCH_SIZE> = ArrayVec::new(); | ||
const COUNT: u32 = 1; | ||
let mut idx: u32 = 0; | ||
|
||
if self.inner.borrow_mut().rx.consumer_reserve(COUNT, &mut idx) == COUNT { | ||
let xdpbuf: XdpBuffer = self.inner.borrow().rx.get_element(idx); | ||
let mut out: Vec<u8> = Vec::with_capacity(xdpbuf.len()); | ||
|
||
xdpbuf[..].clone_into(&mut out); | ||
|
||
let dbuf: DemiBuffer = expect_ok!(DemiBuffer::from_slice(&out), "'bytes' should fit"); | ||
|
||
ret.push(dbuf); | ||
|
||
self.inner.borrow_mut().rx.consumer_release(COUNT); | ||
|
||
self.inner.borrow_mut().rx.producer_reserve(COUNT, &mut idx); | ||
|
||
self.inner.borrow_mut().rx.producer_submit(COUNT); | ||
} | ||
|
||
ret | ||
} | ||
} | ||
|
||
//====================================================================================================================== | ||
// Trait Implementations | ||
//====================================================================================================================== | ||
|
||
/// Memory runtime trait implementation for XDP Runtime. | ||
impl MemoryRuntime for CatpowderRuntime {} | ||
|
||
/// Runtime trait implementation for XDP Runtime. | ||
impl Runtime for CatpowderRuntime {} |
Oops, something went wrong.