1919
2020from __future__ import annotations
2121import os
22+ from pathlib import PurePath
2223import time
2324from typing import TYPE_CHECKING
2425from ubireader .ubifs .decrypt import decrypt_symlink_target
3233 from ubireader .ubifs import ubifs as Ubifs , nodes
3334 from ubireader .ubifs .walk import Inode
3435
35- def list_files (ubifs : Ubifs , list_path : str ) -> None :
36- pathnames = list_path .split ("/" )
37- pnames : list [str ] = []
38- for i in pathnames :
39- if len (i ) > 0 :
40- pnames .append (i )
36+ def list_files (ubifs : Ubifs , list_path : PurePath | str , * , recursive : bool = False ) -> None :
37+ list_path = PurePath (list_path )
38+ pnames = [part for part in list_path .parts if part != '/' ]
4139 try :
4240 inodes : dict [int , Inode ] = {}
4341 bad_blocks : list [int ] = []
@@ -56,8 +54,11 @@ def list_files(ubifs: Ubifs, list_path: str) -> None:
5654 return
5755
5856 for dent in inodes [inum ]['dent' ]:
59- print_dent (ubifs , inodes , dent , longts = False )
60-
57+ if recursive :
58+ print_dent_recursive (ubifs , inodes , dent , longts = False , dent_path = list_path / dent .name )
59+ else :
60+ print_dent (ubifs , inodes , dent , longts = False )
61+
6162 if len (bad_blocks ):
6263 error (list_files , 'Warn' , 'Data may be missing or corrupted, bad blocks, LEB [%s]' % ',' .join (map (str , bad_blocks )))
6364
@@ -113,9 +114,11 @@ def find_dir(inodes: Mapping[int, Inode], inum: int, names: list[str], idx: int)
113114 return find_dir (inodes , dent .inum , names , idx + 1 )
114115 return None
115116
116-
117- def print_dent (ubifs : Ubifs , inodes : Mapping [int , Inode ], dent_node : nodes .dent_node , long : bool = True , longts : bool = False ) -> None :
117+ def print_dent (ubifs : Ubifs , inodes : Mapping [int , Inode ], dent_node : nodes .dent_node , long : bool = True , longts : bool = False , * , dent_path : PurePath | None = None ) -> None :
118118 inode = inodes [dent_node .inum ]
119+ # Display the full path if path is set, otherwise just the name.
120+ display_path = str (dent_path ) if dent_path is not None else dent_node .name
121+
119122 if long :
120123 fl = file_leng (ubifs , inode )
121124
@@ -128,9 +131,21 @@ def print_dent(ubifs: Ubifs, inodes: Mapping[int, Inode], dent_node: nodes.dent_
128131 else :
129132 mtime = time .strftime ("%b %d %H:%M" , time .gmtime (inode ['ino' ].mtime_sec ))
130133
131- print ('%6o %2d %s %s %7d %s %s%s' % (inode ['ino' ].mode , inode ['ino' ].nlink , inode ['ino' ].uid , inode ['ino' ].gid , fl , mtime , dent_node . name , lnk ))
134+ print ('%6o %2d %s %s %7d %s %s%s' % (inode ['ino' ].mode , inode ['ino' ].nlink , inode ['ino' ].uid , inode ['ino' ].gid , fl , mtime , display_path , lnk ))
132135 else :
133- print (dent_node .name )
136+ print (display_path )
137+
138+
139+ def print_dent_recursive (ubifs : Ubifs , inodes : Mapping [int , Inode ], dent_node : nodes .dent_node , long : bool , longts : bool , * , dent_path : PurePath ) -> None :
140+ inode = inodes [dent_node .inum ]
141+
142+ print_dent (ubifs , inodes , dent_node , long = long , longts = longts , dent_path = dent_path )
143+
144+ if dent_node .type != UBIFS_ITYPE_DIR :
145+ return
146+
147+ for dnode in inode .get ('dent' , []):
148+ print_dent_recursive (ubifs , inodes , dnode , long = long , longts = longts , dent_path = dent_path / dnode .name )
134149
135150
136151def file_leng (ubifs : Ubifs , inode : Inode ) -> int :
0 commit comments