1use crate::env;
2use crate::ffi::OsStr;
3use crate::io;
4use crate::path::{Path, PathBuf, Prefix};
5
6#[inline]
7pub fn is_sep_byte(b: u8) -> bool {
8 b == b'/'
9}
10
11#[inline]
12pub fn is_verbatim_sep(b: u8) -> bool {
13 b == b'/'
14}
15
16#[inline]
17pub fn parse_prefix(_: &OsStr) -> Option<Prefix<'_>> {
18 None
19}
20
21pub const MAIN_SEP_STR: &str = "/";
22pub const MAIN_SEP: char = '/';
23
24/// Make a POSIX path absolute without changing its semantics.
25pub(crate) fn absolute(path: &Path) -> io::Result<PathBuf> {
26 // This is mostly a wrapper around collecting `Path::components`, with
27 // exceptions made where this conflicts with the POSIX specification.
28 // See 4.13 Pathname Resolution, IEEE Std 1003.1-2017
29 // https://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap04.html#tag_04_13
30
31 // Get the components, skipping the redundant leading "." component if it exists.
32 let mut components = path.strip_prefix(".").unwrap_or(path).components();
33 let path_os = path.as_os_str().as_encoded_bytes();
34
35 let mut normalized = if path.is_absolute() {
36 // "If a pathname begins with two successive <slash> characters, the
37 // first component following the leading <slash> characters may be
38 // interpreted in an implementation-defined manner, although more than
39 // two leading <slash> characters shall be treated as a single <slash>
40 // character."
41 if path_os.starts_with(b"//") && !path_os.starts_with(b"///") {
42 components.next();
43 PathBuf::from("//")
44 } else {
45 PathBuf::new()
46 }
47 } else {
48 env::current_dir()?
49 };
50 normalized.extend(components);
51
52 // "Interfaces using pathname resolution may specify additional constraints
53 // when a pathname that does not name an existing directory contains at
54 // least one non- <slash> character and contains one or more trailing
55 // <slash> characters".
56 // A trailing <slash> is also meaningful if "a symbolic link is
57 // encountered during pathname resolution".
58 if path_os.ends_with(b"/") {
59 normalized.push("");
60 }
61
62 Ok(normalized)
63}
64