aboutsummaryrefslogtreecommitdiff
path: root/src/networking.rs
diff options
context:
space:
mode:
authorMatthew Collins <[email protected]>2018-05-07 01:02:44 +0100
committerMatthew Collins <[email protected]>2018-05-07 01:02:44 +0100
commit63f96e3eb579cd53b4a7bee84ef173add5f888e8 (patch)
tree8badd7acdc85a70f141f3750bbf047c586cffd44 /src/networking.rs
parentFix building with older steam sdks (diff)
downloadsteamworks-rs-63f96e3eb579cd53b4a7bee84ef173add5f888e8.tar.xz
steamworks-rs-63f96e3eb579cd53b4a7bee84ef173add5f888e8.zip
Steam networking support + other improvements
Diffstat (limited to 'src/networking.rs')
-rw-r--r--src/networking.rs109
1 files changed, 109 insertions, 0 deletions
diff --git a/src/networking.rs b/src/networking.rs
new file mode 100644
index 0000000..258abda
--- /dev/null
+++ b/src/networking.rs
@@ -0,0 +1,109 @@
+use super::*;
+
+/// Access to the steam networking interface
+pub struct Networking<Manager> {
+ pub(crate) net: *mut sys::ISteamNetworking,
+ pub(crate) _inner: Arc<Inner<Manager>>,
+}
+
+/// The method used to send a packet
+#[derive(Debug)]
+pub enum SendType {
+ /// Send the packet directly over udp.
+ ///
+ /// Can't be larger than 1200 bytes
+ Unreliable,
+ /// Like `Unreliable` but doesn't buffer packets
+ /// sent before the connection has started.
+ UnreliableNoDelay,
+ /// Reliable packet sending.
+ ///
+ /// Can't be larger than 1 megabyte.
+ Reliable,
+ /// Like `Reliable` but applies the nagle
+ /// algorithm to packets being sent
+ ReliableWithBuffering,
+}
+
+impl <Manager> Networking<Manager> {
+ /// Accepts incoming packets from the given user
+ ///
+ /// Should only be called in response to a `P2PSessionRequest`.
+ pub fn accept_p2p_session(&self, user: SteamId) {
+ unsafe {
+ sys::SteamAPI_ISteamNetworking_AcceptP2PSessionWithUser(self.net, user.0);
+ }
+ }
+
+ /// Closes the p2p connection between the given user
+ pub fn close_p2p_session(&self, user: SteamId) {
+ unsafe {
+ sys::SteamAPI_ISteamNetworking_CloseP2PSessionWithUser(self.net, user.0);
+ }
+ }
+
+ /// Sends a packet to the start user starting the
+ /// connection if it isn't started already
+ pub fn send_p2p_packet(&self, remote: SteamId, send_type: SendType, data: &[u8]) -> bool {
+ unsafe {
+ let send_type = match send_type {
+ SendType::Unreliable => sys::EP2PSend_k_EP2PSendUnreliable,
+ SendType::UnreliableNoDelay => sys::EP2PSend_k_EP2PSendUnreliableNoDelay,
+ SendType::Reliable => sys::EP2PSend_k_EP2PSendReliable,
+ SendType::ReliableWithBuffering => sys::EP2PSend_k_EP2PSendReliableWithBuffering,
+ };
+ sys::SteamAPI_ISteamNetworking_SendP2PPacket(self.net, remote.0, data.as_ptr() as *const _, data.len() as u32, send_type, 0) != 0
+ }
+ }
+
+ /// Returns whether there is a packet queued that can be read.
+ ///
+ /// Returns the size of the queued packet if any.
+ pub fn is_p2p_packet_available(&self) -> Option<usize> {
+ unsafe {
+ let mut size = 0;
+ if sys::SteamAPI_ISteamNetworking_IsP2PPacketAvailable(self.net, &mut size, 0) != 0 {
+ Some(size as usize)
+ } else {
+ None
+ }
+ }
+ }
+
+ /// Attempts to read a queued packet into the buffer
+ /// if there are any.
+ ///
+ /// Returns the steam id of the sender and the size of the
+ /// packet.
+ pub fn read_p2p_packet(&self, buf: &mut [u8]) -> Option<(SteamId, usize)> {
+ unsafe {
+ let mut size = 0;
+ let mut remote = 0;
+ if sys::SteamAPI_ISteamNetworking_ReadP2PPacket(self.net, buf.as_mut_ptr() as *mut _, buf.len() as _, &mut size, &mut remote, 0) != 0 {
+ Some((SteamId(remote), size as usize))
+ } else {
+ None
+ }
+ }
+ }
+}
+
+/// Called when a user wants to communicate via p2p
+#[derive(Debug)]
+pub struct P2PSessionRequest {
+ /// The steam ID of the user requesting a p2p
+ /// session
+ pub remote: SteamId,
+}
+
+unsafe impl Callback for P2PSessionRequest {
+ const ID: i32 = sys::P2PSessionRequest_t_k_iCallback as i32;
+ const SIZE: i32 = ::std::mem::size_of::<sys::P2PSessionRequest_t>() as i32;
+
+ unsafe fn from_raw(raw: *mut libc::c_void) -> Self {
+ let val = &mut *(raw as *mut sys::P2PSessionRequest_t);
+ P2PSessionRequest {
+ remote: SteamId(val.get_m_steamIDRemote()),
+ }
+ }
+}