summaryrefslogtreecommitdiff
path: root/src/util/path_list.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/util/path_list.rs')
-rw-r--r--src/util/path_list.rs52
1 files changed, 52 insertions, 0 deletions
diff --git a/src/util/path_list.rs b/src/util/path_list.rs
new file mode 100644
index 0000000..88f43b9
--- /dev/null
+++ b/src/util/path_list.rs
@@ -0,0 +1,52 @@
+//! Null-separated path-list parsing helpers.
+
+use std::{ffi::OsStr, os::unix::ffi::OsStrExt, path::Path};
+
+/// Parses a NUL-separated path list into borrowed paths.
+///
+/// Empty segments are ignored. Returned paths borrow from `bytes`.
+pub fn paths_from_null_separated_bytes(bytes: &[u8]) -> Vec<&Path> {
+ bytes
+ .split(|byte| *byte == 0)
+ .filter(|segment| !segment.is_empty())
+ .map(|segment| Path::new(OsStr::from_bytes(segment)))
+ .collect()
+}
+
+#[cfg(test)]
+mod tests {
+ use std::path::Path;
+
+ use super::paths_from_null_separated_bytes;
+
+ #[test]
+ fn paths_from_null_separated_bytes_returns_empty_list_for_empty_input() {
+ let paths = paths_from_null_separated_bytes(b"");
+
+ assert!(paths.is_empty());
+ }
+
+ #[test]
+ fn paths_from_null_separated_bytes_ignores_empty_segments() {
+ let paths = paths_from_null_separated_bytes(b"\0a.rs\0\0b.rs\0");
+
+ assert_eq!(paths, vec![Path::new("a.rs"), Path::new("b.rs")]);
+ }
+
+ #[test]
+ fn paths_from_null_separated_bytes_accepts_final_path_without_trailing_nul() {
+ let paths = paths_from_null_separated_bytes(b"a.rs\0b.rs");
+
+ assert_eq!(paths, vec![Path::new("a.rs"), Path::new("b.rs")]);
+ }
+
+ #[test]
+ fn paths_from_null_separated_bytes_preserves_order() {
+ let paths = paths_from_null_separated_bytes(b"b.rs\0a.rs\0c.rs\0");
+
+ assert_eq!(
+ paths,
+ vec![Path::new("b.rs"), Path::new("a.rs"), Path::new("c.rs")]
+ );
+ }
+}