iso9660: Implement proper file-name matching
Check for special cases `00' (current dir) and `01' (parent dir),
and ignore file version and potential trailing dots.
diff --git a/src/filo-fs-iso9660.adb b/src/filo-fs-iso9660.adb
index f232c86..110201f 100644
--- a/src/filo-fs-iso9660.adb
+++ b/src/filo-fs-iso9660.adb
@@ -226,7 +226,6 @@
Dir_Rec_Name : Buffer_Type (0 .. File_Name_Max - 1);
Record_Dir_Pos : File_Offset := Dir_Pos;
Dir_Rec_Length : File_Length;
- Inode : Inode_Index;
Len : Natural;
begin
Read
@@ -238,25 +237,45 @@
return;
end if;
- -- FIXME: need to strip trailing . and file version
- if File_Name'Length = Natural (Dir_Rec (32)) then
+ if File_Name'Length <= Natural (Dir_Rec (32)) and
+ Natural (Dir_Rec (32)) <= File_Name'Length + 3
+ then
pragma Warnings
(GNATprove, Off, """Record_Dir_Pos"" is set*but not used",
Reason => "We only care about intermedidate values.");
Read
(State => State,
File_Pos => Record_Dir_Pos,
- Buf => Dir_Rec_Name,
+ Buf => Dir_Rec_Name (0 .. Natural (Dir_Rec (32) - 1)),
Len => Len);
pragma Warnings (GNATprove, On, """Record_Dir_Pos"" is set*but not used");
- if Len < File_Name'Length then
- return;
- end if;
- Success := Str_Buf_Equal (File_Name, Dir_Rec_Name);
+ if (Len = 1 and Dir_Rec_Name (0) = 16#00# and File_Name = ".") or
+ (Len = 1 and Dir_Rec_Name (0) = 16#01# and File_Name = "..")
+ then
+ Success := True;
+ else
+ -- Remove file version
+ if Len >= File_Name'Length + 2 and
+ Dir_Rec_Name (Len - 2) = Character'Pos (';') and
+ Dir_Rec_Name (Len - 1) = Character'Pos ('1')
+ then
+ Len := Len - 2;
+ end if;
+
+ -- Remove trailing .
+ if Len >= File_Name'Length + 1 and
+ Dir_Rec_Name (Len - 1) = Character'Pos ('.')
+ then
+ Len := Len - 1;
+ end if;
+
+ Success := Len = File_Name'Length and then
+ Str_Buf_Equal (File_Name, Dir_Rec_Name);
+ end if;
if Success then
Found_Inode :=
- (Block => FSBlock (Dir_Pos / FSBlock_Size),
+ (Block => FSBlock (Dir_Pos / FSBlock_Size) + State.Inode.Extents (0).Start,
Offset => FSBlock_Index (Dir_Pos mod FSBlock_Size));
exit;
end if;