Move fs-filo to filo-fs
Signed-off-by: Thomas Heijligen <src@posteo.de>
diff --git a/src/filo-fs-ext2.adb b/src/filo-fs-ext2.adb
new file mode 100644
index 0000000..7bd2c15
--- /dev/null
+++ b/src/filo-fs-ext2.adb
@@ -0,0 +1,201 @@
+-- Derived from GRUB -- GRand Unified Bootloader
+-- Copyright (C) 1999, 2001, 2003 Free Software Foundation, Inc.
+-- Copyright (C) 2023 secunet Security Networks AG
+--
+-- This program is free software; you can redistribute it and/or modify
+-- it under the terms of the GNU General Public License as published by
+-- the Free Software Foundation; either version 2 of the License, or
+-- (at your option) any later version.
+
+with System;
+with Interfaces;
+with Interfaces.C;
+with Interfaces.C.Strings;
+
+with FILO.Blockdev;
+with FILO.FS.VFS;
+
+use Interfaces.C;
+
+package body FILO.FS.Ext2 is
+
+ function Is_Mounted (State : T) return Boolean is (State.S >= Mounted);
+ function Is_Open (State : T) return Boolean is (State.S = File_Opened);
+
+ --------------------------------------------------------------------------
+
+ SUPERBLOCK_SIZE : constant := 1024;
+ SUPERBLOCK_BLOCKS : constant := SUPERBLOCK_SIZE / BLOCK_SIZE;
+
+ SUPERBLOCK_MAGIC : constant := 16#ef53#;
+ OLD_REV : constant := 0;
+ DYNAMIC_REV : constant := 1;
+ FEATURE_INCOMPAT_EXTENTS : constant := 16#0040#;
+ FEATURE_INCOMPAT_64BIT : constant := 16#0080#;
+
+ procedure Mount
+ (State : in out T;
+ Part_Len : in Partition_Length;
+ Success : out Boolean)
+ is
+ Super_Block : Buffer_Type (0 .. SUPERBLOCK_SIZE - 1) := (others => 0);
+ begin
+ if Part_Len < 2 * SUPERBLOCK_SIZE then
+ Success := False;
+ return;
+ end if;
+
+ Blockdev.Read (Super_Block, 1 * SUPERBLOCK_SIZE, Success);
+ if not Success then
+ return;
+ end if;
+
+ if Read_LE16 (Super_Block, 14 * 4) /= 16#ef53# then
+ Success := False;
+ return;
+ end if;
+
+ State.Part_Len := Part_Len;
+ State.First_Data_Block := Block_Offset (Read_LE32 (Super_Block, 5 * 4));
+
+ declare
+ S_Log_Block_Size : constant Unsigned_32 := Read_LE32 (Super_Block, 6 * 4);
+ begin
+ if S_Log_Block_Size <= Unsigned_32 (Log_Block_Size'Last - 10) then
+ State.Block_Size_Bits := Log_Block_Size (S_Log_Block_Size + 10);
+ else
+ Success := False;
+ return;
+ end if;
+ end;
+
+ declare
+ S_Inodes_Per_Group : constant Unsigned_32 := Read_LE32 (Super_Block, 10 * 4);
+ begin
+ if S_Inodes_Per_Group in 1 .. Unsigned_32 (Positive'Last) then
+ State.Inodes_Per_Group := Positive (S_Inodes_Per_Group);
+ else
+ Success := False;
+ return;
+ end if;
+ end;
+
+ declare
+ S_Rev_Level : constant Unsigned_32 := Read_LE32 (Super_Block, 19 * 4);
+ begin
+ if S_Rev_Level >= DYNAMIC_REV then
+ declare
+ S_Inode_Size : constant Unsigned_16 := Read_LE16 (Super_Block, 22 * 4);
+ begin
+ if S_Inode_Size in
+ Unsigned_16 (Inode_Size'First) .. Unsigned_16 (Inode_Size'Last)
+ then
+ State.Inode_Size := Inode_Size (S_Inode_Size);
+ else
+ Success := False;
+ return;
+ end if;
+ end;
+ else
+ State.Inode_Size := Inode_Size'First;
+ end if;
+ end;
+
+ declare
+ S_Feature_Incompat : constant Unsigned_32 := Read_LE32 (Super_Block, 24 * 4);
+ begin
+ State.Feature_Extents := (S_Feature_Incompat and FEATURE_INCOMPAT_EXTENTS) /= 0;
+ State.Feature_64Bit := (S_Feature_Incompat and FEATURE_INCOMPAT_64BIT) /= 0;
+ if State.Feature_64Bit then
+ declare
+ S_Desc_Size : constant Unsigned_16 := Read_LE16 (Super_Block, 63 * 4 + 2);
+ begin
+ if S_Desc_Size in
+ Unsigned_16 (Desc_Size'First) .. Unsigned_16 (Desc_Size'Last)
+ then
+ State.Desc_Size := Desc_Size (S_Desc_Size);
+ else
+ Success := False;
+ return;
+ end if;
+ end;
+ else
+ State.Desc_Size := Desc_Size'First;
+ end if;
+ end;
+
+ State.S := Mounted;
+ end Mount;
+
+ procedure Open
+ (State : in out T;
+ File_Len : out File_Length;
+ File_Path : in String;
+ Success : out Boolean)
+ is
+ begin
+ File_Len := 0;
+ Success := False;
+ end Open;
+
+ procedure Close (State : in out T) is
+ begin
+ State.S := Mounted;
+ end Close;
+
+ procedure Read
+ (State : in out T;
+ File_Len : in File_Length;
+ File_Pos : in out File_Offset;
+ Buf : out Buffer_Type;
+ Len : out Natural)
+ is
+ begin
+ Buf := (others => 0);
+ Len := 0;
+ end Read;
+
+ --------------------------------------------------------------------------
+
+ package C is new VFS (T => T, Initial => (S => Unmounted, others => <>));
+
+ function C_Mount return int
+ with
+ Export,
+ Convention => C,
+ External_Name => "ext2fs_mount";
+ function C_Mount return int
+ with
+ SPARK_Mode => Off
+ is
+ begin
+ return C.C_Mount;
+ end C_Mount;
+
+ function C_Open (File_Path : Strings.chars_ptr) return int
+ with
+ Export,
+ Convention => C,
+ External_Name => "ext2fs_dir";
+ function C_Open (File_Path : Strings.chars_ptr) return int
+ with
+ SPARK_Mode => Off
+ is
+ begin
+ return C.C_Open (File_Path);
+ end C_Open;
+
+ function C_Read (Buf : System.Address; Len : int) return int
+ with
+ Export,
+ Convention => C,
+ External_Name => "ext2fs_read";
+ function C_Read (Buf : System.Address; Len : int) return int
+ with
+ SPARK_Mode => Off
+ is
+ begin
+ return C.C_Read (Buf, Len);
+ end C_Read;
+
+end FILO.FS.Ext2;