@@ -16,6 +16,7 @@ use std::sync::{Arc, RwLock};
1616use super :: limits:: { FsLimits , FsUsage } ;
1717use super :: traits:: { DirEntry , FileSystem , FileType , Metadata } ;
1818use crate :: error:: Result ;
19+ use std:: io:: ErrorKind ;
1920
2021/// Filesystem with Unix-style mount points.
2122///
@@ -295,6 +296,15 @@ impl MountableFs {
295296 result
296297 }
297298
299+ /// THREAT[TM-DOS-046]: Validate path using root filesystem limits before delegation.
300+ fn validate_path ( & self , path : & Path ) -> Result < ( ) > {
301+ self . root
302+ . limits ( )
303+ . validate_path ( path)
304+ . map_err ( |e| IoError :: new ( ErrorKind :: InvalidInput , e. to_string ( ) ) ) ?;
305+ Ok ( ( ) )
306+ }
307+
298308 /// Resolve a path to the appropriate filesystem and relative path.
299309 ///
300310 /// Returns (filesystem, path_within_mount).
@@ -353,21 +363,26 @@ impl FileSystem for MountableFs {
353363 }
354364
355365 async fn write_file ( & self , path : & Path , content : & [ u8 ] ) -> Result < ( ) > {
366+ // THREAT[TM-DOS-046]: Validate path before delegation
367+ self . validate_path ( path) ?;
356368 let ( fs, resolved) = self . resolve ( path) ;
357369 fs. write_file ( & resolved, content) . await
358370 }
359371
360372 async fn append_file ( & self , path : & Path , content : & [ u8 ] ) -> Result < ( ) > {
373+ self . validate_path ( path) ?;
361374 let ( fs, resolved) = self . resolve ( path) ;
362375 fs. append_file ( & resolved, content) . await
363376 }
364377
365378 async fn mkdir ( & self , path : & Path , recursive : bool ) -> Result < ( ) > {
379+ self . validate_path ( path) ?;
366380 let ( fs, resolved) = self . resolve ( path) ;
367381 fs. mkdir ( & resolved, recursive) . await
368382 }
369383
370384 async fn remove ( & self , path : & Path , recursive : bool ) -> Result < ( ) > {
385+ self . validate_path ( path) ?;
371386 let ( fs, resolved) = self . resolve ( path) ;
372387 fs. remove ( & resolved, recursive) . await
373388 }
@@ -425,6 +440,8 @@ impl FileSystem for MountableFs {
425440 }
426441
427442 async fn rename ( & self , from : & Path , to : & Path ) -> Result < ( ) > {
443+ self . validate_path ( from) ?;
444+ self . validate_path ( to) ?;
428445 let ( from_fs, from_resolved) = self . resolve ( from) ;
429446 let ( to_fs, to_resolved) = self . resolve ( to) ;
430447
@@ -442,6 +459,8 @@ impl FileSystem for MountableFs {
442459 }
443460
444461 async fn copy ( & self , from : & Path , to : & Path ) -> Result < ( ) > {
462+ self . validate_path ( from) ?;
463+ self . validate_path ( to) ?;
445464 let ( from_fs, from_resolved) = self . resolve ( from) ;
446465 let ( to_fs, to_resolved) = self . resolve ( to) ;
447466
@@ -455,6 +474,7 @@ impl FileSystem for MountableFs {
455474 }
456475
457476 async fn symlink ( & self , target : & Path , link : & Path ) -> Result < ( ) > {
477+ self . validate_path ( link) ?;
458478 let ( fs, resolved) = self . resolve ( link) ;
459479 fs. symlink ( target, & resolved) . await
460480 }
@@ -465,6 +485,7 @@ impl FileSystem for MountableFs {
465485 }
466486
467487 async fn chmod ( & self , path : & Path , mode : u32 ) -> Result < ( ) > {
488+ self . validate_path ( path) ?;
468489 let ( fs, resolved) = self . resolve ( path) ;
469490 fs. chmod ( & resolved, mode) . await
470491 }
0 commit comments