@@ -3,12 +3,14 @@ use crate::fs_utf8::{from_utf8, to_utf8, DirBuilder, File, Metadata, ReadDir};
3
3
use async_std:: { fs, io} ;
4
4
use camino:: { Utf8Path , Utf8PathBuf } ;
5
5
use cap_primitives:: AmbientAuthority ;
6
+ use io_lifetimes:: raw:: { AsRawFilelike , FromRawFilelike } ;
6
7
use io_lifetimes:: AsFilelike ;
7
8
#[ cfg( not( windows) ) ]
8
- use io_lifetimes:: { AsFd , BorrowedFd , FromFd , IntoFd , OwnedFd } ;
9
+ use io_lifetimes:: { AsFd , BorrowedFd , OwnedFd } ;
9
10
#[ cfg( windows) ]
10
11
use io_lifetimes:: { AsHandle , BorrowedHandle , OwnedHandle } ;
11
12
use std:: fmt;
13
+ use std:: mem:: ManuallyDrop ;
12
14
#[ cfg( unix) ]
13
15
use {
14
16
crate :: os:: unix:: net:: { UnixDatagram , UnixListener , UnixStream } ,
@@ -170,8 +172,8 @@ impl Dir {
170
172
to_dir : & Self ,
171
173
to : Q ,
172
174
) -> io:: Result < u64 > {
173
- let from = from_utf8 ( from) ?;
174
- let to = from_utf8 ( to) ?;
175
+ let from = from_utf8 ( from. as_ref ( ) ) ?;
176
+ let to = from_utf8 ( to. as_ref ( ) ) ?;
175
177
self . cap_std . copy ( from, & to_dir. cap_std , to) . await
176
178
}
177
179
@@ -186,8 +188,8 @@ impl Dir {
186
188
dst_dir : & Self ,
187
189
dst : Q ,
188
190
) -> io:: Result < ( ) > {
189
- let src = from_utf8 ( src) ?;
190
- let dst = from_utf8 ( dst) ?;
191
+ let src = from_utf8 ( src. as_ref ( ) ) ?;
192
+ let dst = from_utf8 ( dst. as_ref ( ) ) ?;
191
193
self . cap_std . hard_link ( src, & dst_dir. cap_std , dst) . await
192
194
}
193
195
@@ -321,8 +323,8 @@ impl Dir {
321
323
to_dir : & Self ,
322
324
to : Q ,
323
325
) -> io:: Result < ( ) > {
324
- let from = from_utf8 ( from) ?;
325
- let to = from_utf8 ( to) ?;
326
+ let from = from_utf8 ( from. as_ref ( ) ) ?;
327
+ let to = from_utf8 ( to. as_ref ( ) ) ?;
326
328
self . cap_std . rename ( from, & to_dir. cap_std , to) . await
327
329
}
328
330
@@ -388,8 +390,8 @@ impl Dir {
388
390
original : P ,
389
391
link : Q ,
390
392
) -> io:: Result < ( ) > {
391
- let original = from_utf8 ( original) ?;
392
- let link = from_utf8 ( link) ?;
393
+ let original = from_utf8 ( original. as_ref ( ) ) ?;
394
+ let link = from_utf8 ( link. as_ref ( ) ) ?;
393
395
self . cap_std . symlink ( original, link) . await
394
396
}
395
397
@@ -416,8 +418,8 @@ impl Dir {
416
418
original : P ,
417
419
link : Q ,
418
420
) -> io:: Result < ( ) > {
419
- let original = from_utf8 ( original) ?;
420
- let link = from_utf8 ( link) ?;
421
+ let original = from_utf8 ( original. as_ref ( ) ) ?;
422
+ let link = from_utf8 ( link. as_ref ( ) ) ?;
421
423
self . cap_std . symlink_file ( original, link) . await
422
424
}
423
425
@@ -444,8 +446,8 @@ impl Dir {
444
446
original : P ,
445
447
link : Q ,
446
448
) -> io:: Result < ( ) > {
447
- let original = from_utf8 ( original) ?;
448
- let link = from_utf8 ( link) ?;
449
+ let original = from_utf8 ( original. as_ref ( ) ) ?;
450
+ let link = from_utf8 ( link. as_ref ( ) ) ?;
449
451
self . cap_std . symlink_dir ( original, link) . await
450
452
}
451
453
@@ -655,15 +657,17 @@ impl Dir {
655
657
/// This can be useful when interacting with other libraries and or C/C++
656
658
/// code which has invoked `openat(..., O_DIRECTORY)` external to this
657
659
/// crate.
658
- pub fn reopen_dir < Filelike : AsFilelike > ( dir : & Filelike ) -> io:: Result < Self > {
659
- spawn_blocking ( move || {
660
- cap_primitives:: fs:: open_dir (
661
- & dir. as_filelike_view :: < std:: fs:: File > ( ) ,
662
- std:: path:: Component :: CurDir . as_ref ( ) ,
663
- )
664
- } )
665
- . await
666
- . map ( Self :: from_std_file)
660
+ pub async fn reopen_dir < Filelike : AsFilelike > ( dir : & Filelike ) -> io:: Result < Self > {
661
+ // Our public API has a `&Filelike` here, which prevents us from doing
662
+ // a `clone` as we usually do. So instead, we use the raw fd, which we
663
+ // can clone and depend on it remaining open until we return.
664
+ let raw_filelike = dir. as_filelike_view :: < std:: fs:: File > ( ) . as_raw_filelike ( ) ;
665
+ // SAFETY: `raw_filelike` remains open for the duration of the `reopen_dir`
666
+ // call.
667
+ let file = ManuallyDrop :: new ( unsafe { std:: fs:: File :: from_raw_filelike ( raw_filelike) } ) ;
668
+ crate :: fs:: Dir :: reopen_dir ( & * file)
669
+ . await
670
+ . map ( Self :: from_cap_std)
667
671
}
668
672
}
669
673
0 commit comments