Skip to content

Commit

Permalink
Add support for SO_TIMESTAMP
Browse files Browse the repository at this point in the history
  • Loading branch information
Wolvereness committed Jul 25, 2017
1 parent e08a430 commit 3c1811a
Show file tree
Hide file tree
Showing 3 changed files with 39 additions and 0 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,10 @@ This project adheres to [Semantic Versioning](http://semver.org/).

## [Unreleased]

### Added
- Added `nix::sys::socket::ControlMessage::ScmTimestamp`
([#663](https://github.com/nix-rust/nix/pull/663))

### Changed
- Renamed existing `ptrace` wrappers to encourage namespacing ([#692](https://github.com/nix-rust/nix/pull/692))

Expand Down
33 changes: 33 additions & 0 deletions src/sys/socket/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ use libc::{c_void, c_int, socklen_t, size_t, pid_t, uid_t, gid_t};
use std::{mem, ptr, slice};
use std::os::unix::io::RawFd;
use sys::uio::IoVec;
use sys::time::TimeVal;
use libc;

mod addr;
mod consts;
Expand Down Expand Up @@ -162,6 +164,10 @@ impl<'a> Iterator for CmsgIterator<'a> {
slice::from_raw_parts(
&cmsg.cmsg_data as *const _ as *const _, 1)))
},
(libc::SOL_SOCKET, libc::SCM_TIMESTAMP) => unsafe {
Some(ControlMessage::ScmTimestamp(
&*(&cmsg.cmsg_data as *const _ as *const _)))
},
(_, _) => unsafe {
Some(ControlMessage::Unknown(UnknownCmsg(
&cmsg,
Expand All @@ -182,6 +188,11 @@ pub enum ControlMessage<'a> {
/// "Ancillary messages" section of the
/// [unix(7) man page](http://man7.org/linux/man-pages/man7/unix.7.html).
ScmRights(&'a [RawFd]),
/// A message of type SCM_TIMESTAMP, containing the time the packet
/// was received by the kernel. See the kernel's explanation in
/// "SO_TIMESTAMP" of
/// [networking/timestamping](https://www.kernel.org/doc/Documentation/networking/timestamping.txt).
ScmTimestamp(&'a TimeVal),
#[doc(hidden)]
Unknown(UnknownCmsg<'a>),
}
Expand All @@ -207,6 +218,9 @@ impl<'a> ControlMessage<'a> {
ControlMessage::ScmRights(fds) => {
mem::size_of_val(fds)
},
ControlMessage::ScmTimestamp(t) => {
mem::size_of_val(t)
},
ControlMessage::Unknown(UnknownCmsg(_, bytes)) => {
mem::size_of_val(bytes)
}
Expand Down Expand Up @@ -237,6 +251,25 @@ impl<'a> ControlMessage<'a> {

copy_bytes(fds, buf);
},
ControlMessage::ScmTimestamp(t) => {
let cmsg = cmsghdr {
cmsg_len: self.len() as type_of_cmsg_len,
cmsg_level: libc::SOL_SOCKET,
cmsg_type: libc::SCM_TIMESTAMP,
cmsg_data: [],
};
copy_bytes(&cmsg, buf);

let padlen = cmsg_align(mem::size_of_val(&cmsg)) -
mem::size_of_val(&cmsg);

let mut tmpbuf = &mut [][..];
mem::swap(&mut tmpbuf, buf);
let (_padding, mut remainder) = tmpbuf.split_at_mut(padlen);
mem::swap(buf, &mut remainder);

copy_bytes(t, buf);
},
ControlMessage::Unknown(UnknownCmsg(orig_cmsg, bytes)) => {
copy_bytes(orig_cmsg, buf);
copy_bytes(bytes, buf);
Expand Down
2 changes: 2 additions & 0 deletions src/sys/socket/sockopt.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use super::{ffi, consts, GetSockOpt, SetSockOpt};
use libc;
use {Errno, Result};
use sys::time::TimeVal;
use libc::{c_int, uint8_t, c_void, socklen_t};
Expand Down Expand Up @@ -176,6 +177,7 @@ sockopt_impl!(GetOnly, SockType, consts::SOL_SOCKET, consts::SO_TYPE, super::Soc
sockopt_impl!(GetOnly, AcceptConn, consts::SOL_SOCKET, consts::SO_ACCEPTCONN, bool);
#[cfg(target_os = "linux")]
sockopt_impl!(GetOnly, OriginalDst, consts::SOL_IP, consts::SO_ORIGINAL_DST, sockaddr_in);
sockopt_impl!(Both, ReceiveTimestamp, libc::SOL_SOCKET, libc::SO_TIMESTAMP, bool);

/*
*
Expand Down

0 comments on commit 3c1811a

Please sign in to comment.