import struct CHUNK = 128 * 512 LV_START = 5120000 * 512 BSIZE = 4096 IPG = 8192 INODE_SIZE = 256 def read_virt(virt_offset, length): result = bytearray(length) pos = virt_offset remaining = length with open('/dev/nbd0', 'rb') as f: while remaining > 0: f.seek(pos) chunk = f.read(min(remaining, 65536)) if not chunk: break dst = pos - virt_offset result[dst:dst+len(chunk)] = chunk pos += len(chunk) remaining -= len(chunk) return bytes(result) def get_inode_table_block(group): # Use backup GDT at group 1 gdt_start = (1 * 32768 + 1) * BSIZE entry = read_virt(gdt_start + group * 64, 64) it_lo = struct.unpack_from(' 0 and name_len > 0: name = data[off+8:off+8+name_len].decode('utf-8',errors='replace') grp = (ino-1)//IPG entries.append((name, ino, ftype, grp)) off += rec_len type_names = {1:'file',2:'dir',7:'symlink'} print(f'Directory entries ({len(entries)}):') for name, ino, ftype, grp in sorted(entries): status = 'INTACT' if grp >= 13 else 'LOST' tname = type_names.get(ftype, str(ftype)) print(f' [{status}] {tname:6s} inode={ino:10d} group={grp:6d} {name!r}') # Read the volumes directory list_dir(1585918)