Skip to content

Commit 0b58f29

Browse files
committed
Replace the IoVec type with IoSlice and IoSliceMut
1 parent c59a8c8 commit 0b58f29

File tree

9 files changed

+292
-248
lines changed

9 files changed

+292
-248
lines changed

CHANGELOG.md

+2
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,8 @@ This project adheres to [Semantic Versioning](https://semver.org/).
8585
ignoring failures from libc. And getters on the `UtsName` struct now return
8686
an `&OsStr` instead of `&str`.
8787
(#[1672](https://github.com/nix-rust/nix/pull/1672))
88+
- Replaced `IoVec` with `IoSlice` and `IoSliceMut`, and replaced `IoVec::from_slice` with
89+
`IoSlice::new`. (#[1643](https://github.com/nix-rust/nix/pull/1643))
8890

8991
### Fixed
9092

src/fcntl.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -629,7 +629,7 @@ pub fn tee(fd_in: RawFd, fd_out: RawFd, len: usize, flags: SpliceFFlags) -> Resu
629629
#[cfg(any(target_os = "linux", target_os = "android"))]
630630
pub fn vmsplice(
631631
fd: RawFd,
632-
iov: &[crate::sys::uio::IoVec<&[u8]>],
632+
iov: &[std::io::IoSlice<'_>],
633633
flags: SpliceFFlags
634634
) -> Result<usize>
635635
{

src/mount/bsd.rs

+56-55
Original file line numberDiff line numberDiff line change
@@ -3,15 +3,14 @@ use crate::{
33
Errno,
44
NixPath,
55
Result,
6-
sys::uio::IoVec
76
};
87
use libc::{c_char, c_int, c_uint, c_void};
98
use std::{
109
borrow::Cow,
1110
ffi::{CString, CStr},
1211
fmt,
1312
io,
14-
ptr
13+
marker::PhantomData,
1514
};
1615

1716

@@ -198,13 +197,45 @@ pub type NmountResult = std::result::Result<(), NmountError>;
198197
#[cfg_attr(docsrs, doc(cfg(all())))]
199198
#[derive(Debug, Default)]
200199
pub struct Nmount<'a>{
201-
iov: Vec<IoVec<&'a [u8]>>,
200+
// n.b. notgull: In reality, this is a list that contains
201+
// both mutable and immutable pointers.
202+
// Be careful using this.
203+
iov: Vec<libc::iovec>,
202204
is_owned: Vec<bool>,
205+
marker: PhantomData<&'a ()>,
203206
}
204207

205208
#[cfg(target_os = "freebsd")]
206209
#[cfg_attr(docsrs, doc(cfg(all())))]
207210
impl<'a> Nmount<'a> {
211+
/// Helper function to push a slice onto the `iov` array.
212+
fn push_slice(&mut self, val: &'a [u8], is_owned: bool) {
213+
self.iov.push(libc::iovec {
214+
iov_base: val.as_ptr() as *mut _,
215+
iov_len: val.len(),
216+
});
217+
self.is_owned.push(is_owned);
218+
}
219+
220+
/// Helper function to push a pointer and its length onto the `iov` array.
221+
fn push_pointer_and_length(&mut self, val: *const u8, len: usize, is_owned: bool) {
222+
self.iov.push(libc::iovec {
223+
iov_base: val as *mut _,
224+
iov_len: len,
225+
});
226+
self.is_owned.push(is_owned);
227+
}
228+
229+
/// Helper function to push a `nix` path as owned.
230+
fn push_nix_path<P: ?Sized + NixPath>(&mut self, val: &P) {
231+
val.with_nix_path(|s| {
232+
let len = s.to_bytes_with_nul().len();
233+
let ptr = s.to_owned().into_raw() as *const u8;
234+
235+
self.push_pointer_and_length(ptr, len, true);
236+
}).unwrap();
237+
}
238+
208239
/// Add an opaque mount option.
209240
///
210241
/// Some file systems take binary-valued mount options. They can be set
@@ -239,10 +270,8 @@ impl<'a> Nmount<'a> {
239270
len: usize
240271
) -> &mut Self
241272
{
242-
self.iov.push(IoVec::from_slice(name.to_bytes_with_nul()));
243-
self.is_owned.push(false);
244-
self.iov.push(IoVec::from_raw_parts(val, len));
245-
self.is_owned.push(false);
273+
self.push_slice(name.to_bytes_with_nul(), false);
274+
self.push_pointer_and_length(val.cast(), len, false);
246275
self
247276
}
248277

@@ -258,10 +287,8 @@ impl<'a> Nmount<'a> {
258287
/// .null_opt(&read_only);
259288
/// ```
260289
pub fn null_opt(&mut self, name: &'a CStr) -> &mut Self {
261-
self.iov.push(IoVec::from_slice(name.to_bytes_with_nul()));
262-
self.is_owned.push(false);
263-
self.iov.push(IoVec::from_raw_parts(ptr::null_mut(), 0));
264-
self.is_owned.push(false);
290+
self.push_slice(name.to_bytes_with_nul(), false);
291+
self.push_slice(&[], false);
265292
self
266293
}
267294

@@ -283,17 +310,8 @@ impl<'a> Nmount<'a> {
283310
/// ```
284311
pub fn null_opt_owned<P: ?Sized + NixPath>(&mut self, name: &P) -> &mut Self
285312
{
286-
name.with_nix_path(|s| {
287-
let len = s.to_bytes_with_nul().len();
288-
self.iov.push(IoVec::from_raw_parts(
289-
// Must free it later
290-
s.to_owned().into_raw() as *mut c_void,
291-
len
292-
));
293-
self.is_owned.push(true);
294-
}).unwrap();
295-
self.iov.push(IoVec::from_raw_parts(ptr::null_mut(), 0));
296-
self.is_owned.push(false);
313+
self.push_nix_path(name);
314+
self.push_slice(&[], false);
297315
self
298316
}
299317

@@ -315,10 +333,8 @@ impl<'a> Nmount<'a> {
315333
val: &'a CStr
316334
) -> &mut Self
317335
{
318-
self.iov.push(IoVec::from_slice(name.to_bytes_with_nul()));
319-
self.is_owned.push(false);
320-
self.iov.push(IoVec::from_slice(val.to_bytes_with_nul()));
321-
self.is_owned.push(false);
336+
self.push_slice(name.to_bytes_with_nul(), false);
337+
self.push_slice(val.to_bytes_with_nul(), false);
322338
self
323339
}
324340

@@ -341,24 +357,8 @@ impl<'a> Nmount<'a> {
341357
where P1: ?Sized + NixPath,
342358
P2: ?Sized + NixPath
343359
{
344-
name.with_nix_path(|s| {
345-
let len = s.to_bytes_with_nul().len();
346-
self.iov.push(IoVec::from_raw_parts(
347-
// Must free it later
348-
s.to_owned().into_raw() as *mut c_void,
349-
len
350-
));
351-
self.is_owned.push(true);
352-
}).unwrap();
353-
val.with_nix_path(|s| {
354-
let len = s.to_bytes_with_nul().len();
355-
self.iov.push(IoVec::from_raw_parts(
356-
// Must free it later
357-
s.to_owned().into_raw() as *mut c_void,
358-
len
359-
));
360-
self.is_owned.push(true);
361-
}).unwrap();
360+
self.push_nix_path(name);
361+
self.push_nix_path(val);
362362
self
363363
}
364364

@@ -369,18 +369,19 @@ impl<'a> Nmount<'a> {
369369

370370
/// Actually mount the file system.
371371
pub fn nmount(&mut self, flags: MntFlags) -> NmountResult {
372-
// nmount can return extra error information via a "errmsg" return
373-
// argument.
374372
const ERRMSG_NAME: &[u8] = b"errmsg\0";
375373
let mut errmsg = vec![0u8; 255];
376-
self.iov.push(IoVec::from_raw_parts(
377-
ERRMSG_NAME.as_ptr() as *mut c_void,
378-
ERRMSG_NAME.len()
379-
));
380-
self.iov.push(IoVec::from_raw_parts(
381-
errmsg.as_mut_ptr() as *mut c_void,
382-
errmsg.len()
383-
));
374+
375+
// nmount can return extra error information via a "errmsg" return
376+
// argument.
377+
self.push_slice(ERRMSG_NAME, false);
378+
379+
// SAFETY: we are pushing a mutable iovec here, so we can't use
380+
// the above method
381+
self.iov.push(libc::iovec {
382+
iov_base: errmsg.as_mut_ptr() as *mut c_void,
383+
iov_len: errmsg.len(),
384+
});
384385

385386
let niov = self.iov.len() as c_uint;
386387
let iovp = self.iov.as_mut_ptr() as *mut libc::iovec;
@@ -412,7 +413,7 @@ impl<'a> Drop for Nmount<'a> {
412413
// Free the owned string. Safe because we recorded ownership,
413414
// and Nmount does not implement Clone.
414415
unsafe {
415-
drop(CString::from_raw(iov.0.iov_base as *mut c_char));
416+
drop(CString::from_raw(iov.iov_base as *mut c_char));
416417
}
417418
}
418419
}

src/sys/sendfile.rs

+8-8
Original file line numberDiff line numberDiff line change
@@ -68,24 +68,24 @@ cfg_if! {
6868
target_os = "freebsd",
6969
target_os = "ios",
7070
target_os = "macos"))] {
71-
use crate::sys::uio::IoVec;
71+
use std::io::IoSlice;
7272

73-
#[derive(Clone, Debug, Eq, Hash, PartialEq)]
73+
#[derive(Clone, Debug)]
7474
struct SendfileHeaderTrailer<'a>(
7575
libc::sf_hdtr,
76-
Option<Vec<IoVec<&'a [u8]>>>,
77-
Option<Vec<IoVec<&'a [u8]>>>,
76+
Option<Vec<IoSlice<'a>>>,
77+
Option<Vec<IoSlice<'a>>>,
7878
);
7979

8080
impl<'a> SendfileHeaderTrailer<'a> {
8181
fn new(
8282
headers: Option<&'a [&'a [u8]]>,
8383
trailers: Option<&'a [&'a [u8]]>
8484
) -> SendfileHeaderTrailer<'a> {
85-
let header_iovecs: Option<Vec<IoVec<&[u8]>>> =
86-
headers.map(|s| s.iter().map(|b| IoVec::from_slice(b)).collect());
87-
let trailer_iovecs: Option<Vec<IoVec<&[u8]>>> =
88-
trailers.map(|s| s.iter().map(|b| IoVec::from_slice(b)).collect());
85+
let header_iovecs: Option<Vec<IoSlice<'_>>> =
86+
headers.map(|s| s.iter().map(|b| IoSlice::new(b)).collect());
87+
let trailer_iovecs: Option<Vec<IoSlice<'_>>> =
88+
trailers.map(|s| s.iter().map(|b| IoSlice::new(b)).collect());
8989
SendfileHeaderTrailer(
9090
libc::sf_hdtr {
9191
headers: {

0 commit comments

Comments
 (0)