diff --git a/repos/dde_rump/run/rump_ext2.run b/repos/dde_rump/run/rump_ext2.run
index 8800307..9bd0809 100644
--- a/repos/dde_rump/run/rump_ext2.run
+++ b/repos/dde_rump/run/rump_ext2.run
@@ -24,8 +24,8 @@ build $build_components
#
# Build EXT2-file-system image
#
-catch { exec $dd if=/dev/zero of=bin/ext2.raw bs=1M count=16 }
-catch { exec $mke2fs -F bin/ext2.raw }
+#catch { exec $dd if=/dev/zero of=bin/ext2.raw bs=1M count=16 }
+#catch { exec $mke2fs -F bin/ext2.raw }
create_boot_directory
@@ -60,7 +60,7 @@ append config {
-
+
@@ -96,4 +96,4 @@ append qemu_args " -m 256 -nographic"
run_genode_until {.*child "test-libc_vfs" exited with exit value 0.*} 60
-exec rm -f bin/ext2.raw
+#exec rm -f bin/ext2.raw
diff --git a/repos/dde_rump/src/server/rump_fs/Ext2Filesystem.cc b/repos/dde_rump/src/server/rump_fs/Ext2Filesystem.cc
new file mode 100644
index 0000000..18db68d
--- /dev/null
+++ b/repos/dde_rump/src/server/rump_fs/Ext2Filesystem.cc
@@ -0,0 +1,625 @@
+#include "Ext2Filesystem.h"
+#include "Ext2Directory.h"
+#include "Ext2File.h"
+
+Ext2Filesystem::Ext2Filesystem(Genode::Allocator &md_alloc) :
+ m_alloc(md_alloc),m_pSuperblock(0), m_pGroupDescriptors(), m_BlockSize(0), m_InodeSize(0),
+ m_nGroupDescriptors(0){
+}
+
+Ext2Filesystem::~Ext2Filesystem()
+{
+ if(m_pRoot)
+ m_alloc.free((void*)m_pRoot,sizeof(File*));
+}
+
+bool Ext2Filesystem::initialise()
+{
+ m_pSuperblock=new (&m_alloc)Superblock;
+File_system::readb(2,2,buff);
+
+
+ Genode::memcpy((void*)m_pSuperblock,(void*)buff,1024);
+
+PERR("Ext2 Magic Number :: %x\n",m_pSuperblock->s_magic);
+PERR(" Ext2 rev level :: %lu\n",m_pSuperblock->s_rev_level);
+ // Read correctly?
+ if (m_pSuperblock->s_magic != 0xef53)
+ {
+ PERR("Ext2: Superblock not found on device : device 0 " );
+
+ }
+
+ // Clean?
+ if (m_pSuperblock->s_state != 1)
+ {
+ PDBG("Ext2: filesystem on device dev :: 0 is not clean.");
+ }
+
+ m_InodeSize = sizeof(Inode);
+
+PERR("Ext2 :: block size %d :: First data block %lu \n",1024<s_log_block_size,m_pSuperblock->s_first_data_block);
+ // Calculate the block size.
+ m_BlockSize = 1024 << m_pSuperblock->s_log_block_size;
+
+
+
+ // Where is the group descriptor table?
+ uint32_t gdBlock = m_pSuperblock->s_first_data_block + 1;
+
+ // How many group descriptors do we have? Round up the result.
+ uint32_t inodeCount = m_pSuperblock->s_inodes_count;
+PERR("Ext2 Free Inodes Count :: %lu\n", m_pSuperblock->s_free_inodes_count);
+ uint32_t inodesPerGroup = m_pSuperblock->s_inodes_per_group;
+ m_nGroupDescriptors = (inodeCount / inodesPerGroup) + (inodeCount % inodesPerGroup);
+
+
+ // Add an entry to the group descriptor tree for each GD.
+ PERR("\nExt2 Inodes per group:: %lu Inode Count %lu :: Inode size %lu \n",inodesPerGroup,inodeCount,m_InodeSize);
+
+ m_pGroupDescriptors = new (&m_alloc)GroupDesc*[m_nGroupDescriptors];
+ for (size_t i = 0; i < m_nGroupDescriptors; i++)
+ {
+ uintptr_t idx = (i * sizeof(GroupDesc)) / m_BlockSize;
+ uintptr_t off = (i * sizeof(GroupDesc)) % m_BlockSize;
+
+ //uintptr_t block = readBlock(gdBlock+idx);
+ //m_pGroupDescriptors[i] = reinterpret_cast(block+off);
+m_pGroupDescriptors[i]=new (&m_alloc)GroupDesc;
+//char temp[1024];
+File_system::readb(2,2*(gdBlock+idx),buff);
+//PERR("\n%lu %d\n",gdBlock, idx);
+Genode::memcpy((void*)m_pGroupDescriptors[i],(void*)(buff+off),sizeof(GroupDesc));
+//m_pGroupDescriptors[i]=reinterpret_cast(temp+off);
+//PERR("\n\n::%d\n\n",i);
+}
+//PERR("\n\n Desc :: %u %lu %lu %lu \n\n",m_nGroupDescriptors,m_pGroupDescriptors[0]->bg_block_bitmap,m_pGroupDescriptors[0]->bg_inode_bitmap,m_pGroupDescriptors[0]->bg_inode_table);
+
+//PERR("\n\n Desc :: %u %d %d %d \n\n",m_nGroupDescriptors,m_pGroupDescriptors[1]->bg_block_bitmap,m_pGroupDescriptors[1]->bg_inode_bitmap,m_pGroupDescriptors[1]->bg_inode_table);
+
+
+ // Create our bitmap arrays and tables.
+
+ m_pInodeTables = new (&m_alloc)char*[m_nGroupDescriptors];
+ m_pInodeBitmaps = new (&m_alloc)char*[m_nGroupDescriptors];
+ m_pBlockBitmaps = new (&m_alloc)char*[m_nGroupDescriptors];
+
+for(size_t i=0;i< m_nGroupDescriptors;i++){
+m_pBlockBitmaps[i]=new (&m_alloc)char[sizeof(m_BlockSize)];
+ m_pInodeBitmaps[i]=new (&m_alloc)char[sizeof(m_BlockSize)];
+}
+
+ //uint32_t inodesPerGroup = m_pSuperblock->s_inodes_per_group;
+ size_t nBlocks = (inodesPerGroup * m_InodeSize) / m_BlockSize;
+ if ((inodesPerGroup * m_InodeSize) / m_BlockSize)
+ nBlocks ++;
+for(size_t i=0;i(newInode), 0, m_InodeSize);
+ newInode->i_mode = mask | type;
+ //PDBG(" start 1 \n");
+ // If we have a value to store, and it's small enough, use the block indices.
+
+ Ext2Directory *pE2Parent = reinterpret_cast(parent);
+//PDBG("start 2\n");
+ // Create the new File object.
+ File *pFile = 0;
+ switch (type)
+ {
+ case EXT2_S_IFREG:
+ pFile = new (&m_alloc)Ext2File(filename, inode_num, newInode, this, parent);
+ break;
+ case EXT2_S_IFDIR:
+ {
+
+ Ext2Directory *pE2Dir = new (&m_alloc)Ext2Directory(filename, inode_num, newInode, this, parent);
+ pFile = pE2Dir;
+
+ Inode *parentInode = getInode(pE2Parent->getInodeNumber());
+
+ // Create dot and dotdot entries.
+char current[2]={'.','\0'};
+char previous[3]={'.','.','\0'};
+ Ext2Directory *pDot = new (&m_alloc)Ext2Directory(current, inode_num, newInode, this, pE2Dir);
+ Ext2Directory *pDotDot = new (&m_alloc)Ext2Directory(previous,pE2Parent->getInodeNumber(), parentInode, this, pE2Dir);
+
+ // Add created dot/dotdot entries to the new directory.
+ pE2Dir->addEntry(current, pDot, EXT2_S_IFDIR);
+ pE2Dir->addEntry(previous, pDotDot, EXT2_S_IFDIR);
+ break;
+ }
+ default:
+ PERR("EXT2: Unrecognised file type: %x ",type);
+ break;
+ }
+
+ // Else case from earlier.
+ if (Genode::strlen(value) && Genode::strlen(value) >= 4*15)
+ {
+ const char *pStr = value;
+ pFile->write(0ULL, Genode::strlen(value), reinterpret_cast(pStr));
+ }
+
+ // Add to the parent directory.
+ if (!pE2Parent->addEntry(filename, pFile, type))
+ {
+
+ PERR("EXT2: Internal error adding directory entry.");
+
+ return false;
+ }
+
+
+
+ // Write updated inodes.
+ writeInode(inode_num);
+PERR("Writing Inode back :: number %lu :: Filename %s\n", inode_num, filename);
+ writeInode(pE2Parent->getInodeNumber());
+PERR("Parent Inode Number :: %lu \n", pE2Parent->getInodeNumber());
+pE2Parent->listEntries();
+
+ return true;
+}
+
+bool Ext2Filesystem::createFile(File *parent, char* filename, uint32_t mask)
+{
+return true;
+ // return createNode(parent, filename, mask, String(""), EXT2_S_IFREG);
+}
+
+
+bool Ext2Filesystem::createDirectory(File* parent, char* filename)
+{
+
+char *temp=new (&m_alloc)char[1];
+temp='\0';
+ if (!createNode(parent, filename, 0755,temp , EXT2_S_IFDIR))
+ return false;
+ return true;
+}
+
+
+bool Ext2Filesystem::remove(File* parent, File* file)
+{
+
+
+
+ if (!parent->isDirectory())
+ {
+
+PERR("I0 Error in remove :: Ext2Filesystem.cc");
+ return false;
+ }
+
+ Ext2Node *pNode = 0;
+ char* filename=new (&m_alloc)char[256];
+ if (file->isDirectory())
+ {
+ Ext2Directory *pDirectory = static_cast(file);
+ pNode = pDirectory;
+Genode::memcpy(filename,pDirectory->getName(),sizeof(char)*256);
+ }
+ else
+ {
+ Ext2File *pFile = static_cast(file);
+ pNode = pFile;
+ Genode::memcpy(filename,pFile->getName(),sizeof(char)*256);
+
+ }
+
+ Ext2Directory *pE2Parent = reinterpret_cast(parent);
+
+ return pE2Parent->removeEntry(filename, pNode);
+
+
+}
+
+
+
+char* Ext2Filesystem::readBlock(uint32_t block)
+{
+
+ File_system::readb(2,2*block,(char*)buff);
+ return buff;
+}
+
+
+void Ext2Filesystem::writeBlock(uint32_t block, char *tem)
+{
+ if (block != 0)
+ File_system::writeb(2,2*block,(char*)tem);
+}
+
+uint32_t Ext2Filesystem::findFreeBlock(uint32_t inode)
+{
+ inode--; // Inode zero is undefined, so it's not used.
+
+ uint32_t group = inode / m_pSuperblock->s_inodes_per_group;
+
+ for (; group < m_nGroupDescriptors; group++)
+ {
+ // Any free blocks here?
+ GroupDesc *pDesc = m_pGroupDescriptors[group];
+ if (!pDesc->bg_free_blocks_count)
+ {
+ // No blocks free in this group.
+ continue;
+ }
+
+ ensureFreeBlockBitmapLoaded(group);
+
+ // 8 blocks per byte - i == bitmap offset in bytes.
+ //Vector &list = m_pBlockBitmaps[group];
+ for (size_t i = 0;
+ i < (m_pSuperblock->s_blocks_per_group) / 8;
+ i += sizeof(uint8_t))
+ {
+ // Calculate block index into the bitmap.
+ //size_t idx = i / (m_BlockSize * 8);
+ size_t off = i % (m_BlockSize * 8);
+
+ // Grab the specific block for the bitmap.
+ /// \todo Endianness - to ensure correct operation, must ptr be
+ /// little endian?
+ //size_t block = &m_pBlockBitmaps[group][off];
+ uint32_t *ptr = reinterpret_cast (&m_pBlockBitmaps[group][off] );
+ uint8_t tmp = *ptr;
+
+ // Bitmap full of bits? Skip it.
+ if (tmp == ~0U)
+ continue;
+
+ // Check each bit in this field.
+ for (size_t j = 0; j < 8; j++, tmp >>= 1)
+ {
+ // Free?
+ if ((tmp & 1) == 0)
+ {
+ // This block is free! Mark used.
+ *ptr |= (1 << j);
+ pDesc->bg_free_blocks_count--;
+
+ //File_system::writeb(2,2,(char*)m_pSuperblock);
+ //since bit maps are cached not writing back these are written back only once while closing filesystem
+
+ // File_system::writeb(2,2*(m_pGroupDescriptors[group]->bg_block_bitmap),(char*)&m_pBlockBitmaps[group]);
+
+ // First block of this group...
+ uint32_t block = group * m_pSuperblock->s_blocks_per_group;
+ // Blocks skipped so far (i == offset in bytes)...
+ block += i * 8;
+ // Blocks skipped so far (j == bits ie blocks)...
+ block += j;
+ // Return block.
+ return block;
+ }
+ }
+
+ // Shouldn't get here - if there were no available blocks here it should
+ // have hit the "continue" above!
+
+ }
+ }
+
+ return 0;
+}
+
+uint32_t Ext2Filesystem::findFreeInode()
+{
+ for (uint32_t group = 0; group < m_nGroupDescriptors; group++)
+ {
+ // Any free inodes here?
+ GroupDesc *pDesc = m_pGroupDescriptors[group];
+ if (!pDesc->bg_free_inodes_count)
+ {
+ // No inodes free in this group.
+ continue;
+ }
+
+ // Make sure this block group's inode bitmap has been loaded.
+ ensureFreeInodeBitmapLoaded(group);
+
+ // 8 inodes per byte - i == bitmap offset in bytes.
+
+ for (size_t i = 0;
+ i < m_pSuperblock->s_inodes_per_group / 8;
+ i += sizeof(char))
+ {
+ // Calculate block index into the bitmap.
+ // size_t idx = i / (m_BlockSize * 8);
+ size_t off = i % (m_BlockSize * 8);
+
+ // Grab the specific block for the bitmap.
+
+
+
+ //size_t block = &m_pInodeBitmaps[group][off];
+ uint32_t *ptr = reinterpret_cast (&m_pInodeBitmaps[group][off] );
+ uint8_t tmp = *ptr;
+PDBG("FREE INODE BITMAP 8 BITS IN HEX %x \n",tmp);
+ // If all bits set, avoid searching the bitmap.
+ if (tmp == ~0U)
+ continue;
+
+ // Check each bit for free inode.
+ for (size_t j = 0; j < 8; j++, tmp >>= 1)
+ {
+ // Free?
+ if ((tmp & 1) == 0)
+ {
+ // This inode is free! Mark used.
+ *ptr |= (1 << j);
+ pDesc->bg_free_inodes_count--;
+
+ // Update superblock.
+PERR("Free inodes count before ::%lu \n", m_pSuperblock->s_free_inodes_count);
+ m_pSuperblock->s_free_inodes_count--;
+PERR(" Free Inode Count after using Inode :: %lu\n", m_pSuperblock->s_free_inodes_count);
+
+File_system::writeb(2,2,(char*)m_pSuperblock);
+File_system::readb(2,2,buff);
+
+
+PERR("Free inodes count again after writing to block :: %lu GEN CHECKING READ AND WRITE TO BLOCK DEVICES\n", ((Superblock*)(buff))->s_free_inodes_count);
+
+ //since bit maps are cached not writing back these are written back only once while closing filesystem
+
+//File_system::writeb(2,2*(m_pGroupDescriptors[group]->bg_inode_bitmap),(char*)&m_pInodeBitmaps[group]);
+
+
+
+
+
+ // First inode of this group...
+ uint32_t inode = group * m_pSuperblock->s_inodes_per_group;
+ // Inodes skipped so far (i == offset in bytes)...
+ inode += i * 8;
+ // Inodes skipped so far (j == bits ie inodes)...
+ // Note: inodes start counting at one, not zero.
+ inode += j + 1;
+ // Return inode.
+ return inode;
+ }
+ }
+
+
+ }
+ }
+
+ return 0;
+}
+
+
+
+void Ext2Filesystem::releaseBlock(uint32_t block)
+{
+ uint32_t blocksPerGroup = m_pSuperblock->s_blocks_per_group;
+ uint32_t group = block / blocksPerGroup;
+ uint32_t index = block % blocksPerGroup;
+
+ ensureFreeBlockBitmapLoaded(group);
+
+ // Free block.
+ GroupDesc *pDesc = m_pGroupDescriptors[group];
+ pDesc->bg_free_blocks_count++;
+ m_pSuperblock->s_free_blocks_count++;
+
+ // Index = block offset from the start of this block.
+ // size_t bitmapField = (index / 8) / m_BlockSize;
+ size_t bitmapOffset = (index / 8) % m_BlockSize;
+
+
+ size_t diskBlock = m_pBlockBitmaps[group][bitmapOffset];
+ uint8_t *ptr = reinterpret_cast (diskBlock );
+ *ptr &= ~(1 << (index % 8));
+
+
+ //since bit maps are cached not writing back these are written back only once while closing filesystem
+
+//File_system::writeb(2,2,(char*)m_pSuperblock);
+//File_system::writeb(2,2*(m_pGroupDescriptors[group]->bg_block_bitmap),(char*)&m_pBlockBitmaps[group]);
+
+
+
+}
+
+
+
+bool Ext2Filesystem::releaseInode(uint32_t inode)
+{
+ //Inode *pInode = getInode(inode);
+ --inode; // Inode zero is undefined, so it's not used.
+
+ uint32_t inodesPerGroup = m_pSuperblock->s_inodes_per_group;
+ uint32_t group = inode / inodesPerGroup;
+ uint32_t index = inode % inodesPerGroup;
+
+ bool bRemove = decreaseInodeRefcount(inode + 1);
+
+ // Do we need to free this inode?
+ if (bRemove)
+ {
+ ensureFreeInodeBitmapLoaded(group);
+ // Free inode.
+ GroupDesc *pDesc = m_pGroupDescriptors[group];
+ pDesc->bg_free_inodes_count++;
+ m_pSuperblock->s_free_inodes_count++;
+
+ // Index = inode offset from the start of this block.
+ // size_t bitmapField = (index / 8) / m_BlockSize;
+ size_t bitmapOffset = (index / 8) % m_BlockSize;
+
+ // size_t block = &m_pInodeBitmaps[group][bitmapOffset];
+ uint8_t *ptr = reinterpret_cast (&m_pInodeBitmaps[group][bitmapOffset] );
+ *ptr &= ~(1 << (index % 8));
+
+ //since bit maps are cached not writing back these are written back only once while closing filesystem
+
+ // File_system::writeb(2,2,(char*)m_pSuperblock);
+//File_system::writeb(2,2*(m_pGroupDescriptors[group]->bg_inode_bitmap),(char*)&m_pInodeBitmaps[group]);
+ }
+
+ writeInode(inode);
+ return bRemove;
+}
+
+Inode *Ext2Filesystem::getInode(uint32_t inode)
+{
+ inode--; // Inode zero is undefined, so it's not used.
+ uint32_t inodesPerGroup = m_pSuperblock->s_inodes_per_group;
+ uint32_t group = inode / inodesPerGroup;
+ uint32_t index = inode % inodesPerGroup;
+PERR("loading Inode \n");
+ ensureInodeTableLoaded(group);
+ //Vector &list = m_pInodeTables[group];
+
+ size_t blockNum = (index * m_InodeSize) / m_BlockSize;
+ size_t blockOff = (index * m_InodeSize) % m_BlockSize;
+
+ //size_t block = &m_pInodeTables[group][blockNum*m_BlockSize];
+
+ Inode *pInode = reinterpret_cast (&m_pInodeTables[group][blockNum*m_BlockSize+blockOff]);
+
+ return pInode;
+}
+
+void Ext2Filesystem::writeInode(uint32_t inode)
+{
+ inode--; // Inode zero is undefined, so it's not used.
+
+ uint32_t inodesPerGroup = (m_pSuperblock->s_inodes_per_group);
+ uint32_t group = inode / inodesPerGroup;
+ uint32_t index = inode % inodesPerGroup;
+
+ //ensureInodeTableLoaded(group);
+
+ size_t blockNum = (index * m_InodeSize) / m_BlockSize;
+ //since bit maps are cached not writing back these are written back only once while closing filesystem
+
+File_system::writeb(2,2*((m_pGroupDescriptors[group]->bg_inode_table) + blockNum), (char*)&m_pInodeTables[group][blockNum*m_BlockSize]);
+
+
+}
+
+
+void Ext2Filesystem::ensureFreeBlockBitmapLoaded(size_t group)
+{
+
+ if(Bbitmap[group]=='Y') return;
+Bbitmap[group]='Y';
+
+File_system::readb(2,2*(m_pGroupDescriptors[group]->bg_block_bitmap),m_pBlockBitmaps[group]);
+}
+
+void Ext2Filesystem::ensureFreeInodeBitmapLoaded(size_t group)
+{
+
+if(Ibitmap[group]=='Y') return;
+Ibitmap[group]='Y';
+
+// m_pInodeBitmaps[group]=new (&m_alloc)char[sizeof(m_BlockSize)];
+
+ File_system::readb(2,2*(m_pGroupDescriptors[group]->bg_inode_bitmap) ,m_pInodeBitmaps[group]);
+
+}
+
+void Ext2Filesystem::ensureInodeTableLoaded(size_t group)
+{
+
+
+ if(Itable[group]=='Y') return;
+Itable[group]='Y';
+
+ // Determine how many blocks to load to bring in the full inode table.
+ uint32_t inodesPerGroup = m_pSuperblock->s_inodes_per_group;
+ size_t nBlocks = (inodesPerGroup * m_InodeSize) / m_BlockSize;
+ if ((inodesPerGroup * m_InodeSize) / m_BlockSize)
+ nBlocks ++;
+ //m_pInodeTables[group]=new (&m_alloc)char[nBlocks*m_BlockSize];
+ // Load each block in the inode table.
+ PERR("loading Inode tables\n");
+ File_system::readb(nBlocks*2,2*(m_pGroupDescriptors[group]->bg_inode_table),m_pInodeTables[group]);
+
+}
+
+void Ext2Filesystem::increaseInodeRefcount(uint32_t inode)
+{
+ Inode *pInode = getInode(inode);
+ if (!pInode)
+ return;
+
+ uint32_t current_count = pInode->i_links_count;
+ pInode->i_links_count = current_count + 1;
+
+ writeInode(inode);
+}
+
+bool Ext2Filesystem::decreaseInodeRefcount(uint32_t inode)
+{
+ Inode *pInode = getInode(inode);
+ if (!pInode)
+ return true; // No inode found - but didn't decrement to zero.
+
+ uint32_t current_count = pInode->i_links_count;
+ bool bRemove = current_count <= 1;
+ if (current_count)
+ pInode->i_links_count = current_count - 1;
+
+ writeInode(inode);
+ return bRemove;
+}
+
+
+
diff --git a/repos/dde_rump/src/server/rump_fs/Ext2Filesystem.h b/repos/dde_rump/src/server/rump_fs/Ext2Filesystem.h
new file mode 100644
index 0000000..1cb04ac
--- /dev/null
+++ b/repos/dde_rump/src/server/rump_fs/Ext2Filesystem.h
@@ -0,0 +1,133 @@
+#ifndef EXT2FILESYSTEM_H
+#define EXT2FILESYSTEM_H
+#include
+#include
+#include
+#include
+extern "C" {
+#include
+#include
+}
+#include
+#include
+
+#include "file_system.h"
+#include "Filesystem.h"
+
+
+
+
+#include "ext2.h"
+//#include
+
+/** This class provides an implementation of the second extended filesystem. */
+class Ext2Filesystem : public Filesystem
+{
+
+
+ // friend class Ext2File;
+ friend class Ext2Node;
+ friend class Ext2Directory;
+
+
+
+public:
+ Ext2Filesystem(Genode::Allocator &md_alloc);
+
+ virtual ~Ext2Filesystem();
+
+ //
+ // Filesystem interface.
+ //
+ virtual bool initialise();
+ //static Filesystem *probe(Disk *pDisk);
+ //static Filesystem *probe(Genode::Allocator &md_alloc);
+Genode::Allocator &m_alloc;
+
+char *ext2allocateMemory(size_t size);
+void ext2releaseMemory(char *temp,size_t size);
+
+
+ virtual File* getRoot();
+
+ //virtual String getVolumeLabel();
+/** Size of a block. */
+ uint32_t m_BlockSize;
+protected:
+ virtual bool createFile(File* parent, char* filename, uint32_t mask);
+ virtual bool createDirectory(File* parent, char* filename);
+ //virtual bool createSymlink(File* parent, char* filename, char* value);
+ virtual bool remove(File* parent, File* file);
+
+private:
+ virtual bool createNode(File* parent, char* filename, uint32_t mask, char* value, size_t type);
+
+ /** Inaccessible copy constructor and operator= */
+ Ext2Filesystem(const Ext2Filesystem&);
+ void operator =(const Ext2Filesystem&);
+
+ /** Reads a block of data from the disk. */
+ char* readBlock(uint32_t block);
+ /** Writes a block of data to the disk. */
+ void writeBlock(uint32_t block,char* buff);
+
+ uint32_t findFreeBlock(uint32_t inode);
+ uint32_t findFreeInode();
+
+ void releaseBlock(uint32_t block);
+ /** Releases the given inode, returns true if the inode had no more links. */
+ bool releaseInode(uint32_t inode);
+
+ Inode *getInode(uint32_t num);
+ void writeInode(uint32_t num);
+
+ void ensureFreeBlockBitmapLoaded(size_t group);
+ void ensureFreeInodeBitmapLoaded(size_t group);
+ void ensureInodeTableLoaded(size_t group);
+
+ bool checkOptionalFeature(size_t feature);
+ bool checkRequiredFeature(size_t feature);
+ bool checkReadOnlyFeature(size_t feature);
+
+ void increaseInodeRefcount(uint32_t inode);
+ bool decreaseInodeRefcount(uint32_t inode);
+
+ /** Our superblock. */
+ Superblock *m_pSuperblock;
+
+ /** Group descriptors, in a tree because each GroupDesc* may be in a different block. */
+ GroupDesc **m_pGroupDescriptors;
+
+ /** Inode tables, indexed by group descriptor. */
+ // vector *m_pInodeTables;
+char **m_pInodeTables;
+char **m_pInodeBitmaps;
+char **m_pBlockBitmaps;
+ /** Free inode bitmaps, indexed by group descriptor. */
+ //vector *m_pInodeBitmaps;
+ /** Free block bitmaps, indexed by group descriptor. */
+ //vector *m_pBlockBitmaps;
+
+
+
+ /** Size of an Inode. */
+ uint32_t m_InodeSize;
+
+ /** Number of group descriptors. */
+ size_t m_nGroupDescriptors;
+
+//In testing only two groups so size of 2 later can be expaned
+char Ibitmap[2];
+char Bbitmap[2];
+char Itable[2];
+ /** Write lock - we're finding some inodes and updating the superblock and block group structures. */
+ // Mutex m_WriteLock;
+
+ /** The root filesystem node. */
+ File *m_pRoot;
+
+};
+
+
+
+#endif
diff --git a/repos/dde_rump/src/server/rump_fs/directory.h b/repos/dde_rump/src/server/rump_fs/directory.h
index c03d095..44194c0 100644
--- a/repos/dde_rump/src/server/rump_fs/directory.h
+++ b/repos/dde_rump/src/server/rump_fs/directory.h
@@ -31,7 +31,7 @@ namespace File_system {
class File_system::Directory : public Node
{
- private:
+ public:
enum { BUFFER_SIZE = 4096 };
@@ -43,26 +43,12 @@ class File_system::Directory : public Node
unsigned long _inode(char const *path, bool create)
{
- int ret;
-
- if (create) {
- mode_t ugo = S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH;
- ret = rump_sys_mkdir(path, ugo);
- if (ret == -1)
- throw No_space();
- }
-
- struct stat s;
-
- ret = rump_sys_lstat(path, &s);
- if (ret == -1)
- throw Lookup_failed();
- return s.st_ino;
+ return 5;
}
int _open(char const *path)
{
- struct stat s;
+ /*struct stat s;
int ret = rump_sys_lstat(path, &s);
if (ret == -1 || !S_ISDIR(s.st_mode))
throw Lookup_failed();
@@ -71,7 +57,8 @@ class File_system::Directory : public Node
if (fd == -1)
throw Lookup_failed();
- return fd;
+ return fd;*/
+ return 23;
}
static char *_buffer()
@@ -90,17 +77,20 @@ class File_system::Directory : public Node
_path(path, "./"),
_alloc(alloc)
{
+//PERR("dir start\n");
Node::name(basename(path));
+//PERR("dir conss\n");
}
virtual ~Directory()
{
- rump_sys_close(_fd);
+
}
File * file(char const *name, Mode mode, bool create)
{
- return new (&_alloc) File(_fd, name, mode, create);
+//PERR("READ3\n");
+ return new (&_alloc) File(_fd, name, mode, create);
}
Symlink * symlink(char const *name, bool create)
@@ -110,144 +100,54 @@ class File_system::Directory : public Node
Directory * subdir(char const *path, bool create)
{
+//PERR("i am in \n");
Path dir_path(path, _path.base());
+//PERR("subdir start\n");
Directory *dir = new (&_alloc) Directory(_alloc, dir_path.base(), create);
+//PERR("done\n");
return dir;
}
Node * node(char const *path)
{
- Path node_path(path, _path.base());
+
+ Path node_path(path, _path.base());
- struct stat s;
- int ret = rump_sys_lstat(node_path.base(), &s);
- if (ret == -1)
- throw Lookup_failed();
+ // struct stat s;
Node *node = 0;
- if (S_ISDIR(s.st_mode))
+
node = new (&_alloc) Directory(_alloc, node_path.base(), false);
- else if (S_ISREG(s.st_mode))
- node = new (&_alloc) File(node_path.base(), STAT_ONLY);
- else if (S_ISLNK(s.st_mode))
- node = new (&_alloc)Symlink(node_path.base());
- else
- throw Lookup_failed();
+
+
return node;
}
size_t read(char *dst, size_t len, seek_off_t seek_offset)
{
- if (len < sizeof(Directory_entry)) {
- PERR("read buffer too small for directory entry");
- return 0;
- }
-
- if (seek_offset % sizeof(Directory_entry)) {
- PERR("seek offset not aligned to sizeof(Directory_entry)");
- return 0;
- }
-
- seek_off_t index = seek_offset / sizeof(Directory_entry);
-
- int bytes;
- rump_sys_lseek(_fd, 0, SEEK_SET);
-
- struct dirent *dent = 0;
- seek_off_t i = 0;
- char *buf = _buffer();
- do {
- bytes = rump_sys_getdents(_fd, buf, BUFFER_SIZE);
- void *current, *end;
- for (current = buf, end = &buf[bytes];
- current < end;
- current = _DIRENT_NEXT((dirent *)current), i++)
- if (i == index) {
- dent = (dirent *)current;
- break;
- }
- } while(bytes && !dent);
-
- if (!dent)
- return 0;
-
- /*
- * Build absolute path, this becomes necessary as our 'Path' class strips
- * trailing dots, which will not work for '.' and '..' directories.
- */
- size_t base_len = strlen(_path.base());
- char path[dent->d_namlen + base_len + 2];
-
- memcpy(path, _path.base(), base_len);
- path[base_len] = '/';
- strncpy(path + base_len + 1, dent->d_name, dent->d_namlen + 1);
-
- /*
- * We cannot use 'd_type' member of 'dirent' here since the EXT2
- * implementation sets the type to unkown. Hence we use stat.
- */
- struct stat s;
- rump_sys_lstat(path, &s);
-
- Directory_entry *e = (Directory_entry *)(dst);
- if (S_ISDIR(s.st_mode))
- e->type = Directory_entry::TYPE_DIRECTORY;
- else if (S_ISREG(s.st_mode))
- e->type = Directory_entry::TYPE_FILE;
- else if (S_ISLNK(s.st_mode))
- e->type = Directory_entry::TYPE_SYMLINK;
- else
- return 0;
-
- strncpy(e->name, dent->d_name, dent->d_namlen + 1);
- return sizeof(Directory_entry);
+//PERR("READ\n");
+return 0;
}
size_t write(char const *src, size_t len, seek_off_t seek_offset)
{
/* writing to directory nodes is not supported */
+//PERR("READ2\n");
return 0;
- }
+
+}
size_t num_entries() const
{
- int bytes = 0;
- int count = 0;
-
- rump_sys_lseek(_fd, 0, SEEK_SET);
-
- char *buf = _buffer();
- do {
- bytes = rump_sys_getdents(_fd, buf, BUFFER_SIZE);
- void *current, *end;
- for (current = buf, end = &buf[bytes];
- current < end;
- current = _DIRENT_NEXT((dirent *)current), count++) { }
- } while(bytes);
-
- return count;
+ return 0;
}
void unlink(char const *path)
{
- Path node_path(path, _path.base());
-
- struct stat s;
- int ret = rump_sys_lstat(node_path.base(), &s);
- if (ret == -1)
- throw Lookup_failed();
-
- if (S_ISDIR(s.st_mode))
- ret = rump_sys_rmdir(node_path.base());
- else if (S_ISREG(s.st_mode) || S_ISLNK(s.st_mode))
- ret = rump_sys_unlink(node_path.base());
- else
- throw Lookup_failed();
-
- if (ret == -1)
- PERR("Error during unlink of %s", node_path.base());
+
+ //PERR("Error during unlink of %s", node_path.base());
}
};
diff --git a/repos/dde_rump/src/server/rump_fs/ext2.h b/repos/dde_rump/src/server/rump_fs/ext2.h
new file mode 100644
index 0000000..ac18c35
--- /dev/null
+++ b/repos/dde_rump/src/server/rump_fs/ext2.h
@@ -0,0 +1,145 @@
+#ifndef EXT2_H
+#define EXT2_H
+extern "C" {
+#include
+#include
+}
+
+#define EXT2_UNKNOWN 0x0
+#define EXT2_FILE 0x1
+#define EXT2_DIRECTORY 0x2
+#define EXT2_CHAR_DEV 0x3
+#define EXT2_BLOCK_DEV 0x4
+#define EXT2_FIFO 0x5
+#define EXT2_SOCKET 0x6
+#define EXT2_SYMLINK 0x7
+#define EXT2_MAX 0x8
+
+#define EXT2_STATE_CLEAN 1
+#define EXT2_STATE_UNCLEAN 2
+
+#define EXT2_S_IFSOCK 0xC000
+#define EXT2_S_IFLNK 0xA000
+#define EXT2_S_IFREG 0x8000
+#define EXT2_S_IFBLK 0x6000
+#define EXT2_S_IFDIR 0x4000
+#define EXT2_S_IFCHR 0x2000
+#define EXT2_S_IFIFO 0x1000
+
+#define EXT2_S_IRUSR 0x0100
+#define EXT2_S_IWUSR 0x0080
+#define EXT2_S_IXUSR 0x0040
+#define EXT2_S_IRGRP 0x0020
+#define EXT2_S_IWGRP 0x0010
+#define EXT2_S_IXGRP 0x0008
+#define EXT2_S_IROTH 0x0004
+#define EXT2_S_IWOTH 0x0002
+#define EXT2_S_IXOTH 0x0001
+
+#define EXT2_BAD_INO 0x01 // Bad blocks inode
+#define EXT2_ROOT_INO 0x02 // root directory inode
+#define EXT2_ACL_IDX_INO 0x03 // ACL index inode (deprecated?)
+#define EXT2_ACL_DATA_INO 0x04 // ACL data inode (deprecated?)
+#define EXT2_BOOT_LOADER_INO 0x05 // boot loader inode
+#define EXT2_UNDEL_DIR_INO 0x06
+
+
+
+/** The Ext2 superblock structure. */
+struct Superblock
+{
+ uint32_t s_inodes_count;
+ uint32_t s_blocks_count;
+ uint32_t s_r_blocks_count;
+ uint32_t s_free_blocks_count;
+ uint32_t s_free_inodes_count;
+ uint32_t s_first_data_block;
+ uint32_t s_log_block_size;
+ uint32_t s_log_frag_size;
+ uint32_t s_blocks_per_group;
+ uint32_t s_frags_per_group;
+ uint32_t s_inodes_per_group;
+ uint32_t s_mtime;
+ uint32_t s_wtime;
+ uint16_t s_mnt_count;
+ uint16_t s_max_mnt_count;
+ uint16_t s_magic;
+ uint16_t s_state;
+ uint16_t s_errors;
+ uint16_t s_minor_rev_level;
+ uint32_t s_lastcheck;
+ uint32_t s_checkinterval;
+ uint32_t s_creator_os;
+ uint32_t s_rev_level;
+ uint16_t s_def_resuid;
+ uint16_t s_def_resgid;
+// -- EXT2_DYNAMIC_REV Specific --
+ uint32_t s_first_ino;
+ uint16_t s_inode_size;
+ uint16_t s_block_group_nr;
+ uint32_t s_feature_compat;
+ uint32_t s_feature_incompat;
+ uint32_t s_feature_ro_compat;
+ char s_uuid[16];
+
+ char s_volume_name[16];
+ char s_last_mounted[64];
+ uint32_t s_algo_bitmap;
+// -- Performance Hints --
+ uint8_t s_prealloc_blocks;
+ uint8_t s_prealloc_dir_blocks;
+ uint16_t alignment;
+// -- Journaling Support --
+ char s_journal_uuid[16];
+ uint32_t s_journal_inum;
+ uint32_t s_journal_dev;
+ uint32_t s_last_orphan;
+} __attribute__((packed));
+
+/** The ext2 block group descriptor structure */
+struct GroupDesc
+{
+ uint32_t bg_block_bitmap;
+ uint32_t bg_inode_bitmap;
+ uint32_t bg_inode_table;
+ uint16_t bg_free_blocks_count;
+ uint16_t bg_free_inodes_count;
+ uint16_t bg_used_dirs_count;
+ uint16_t bg_pad;
+ uint8_t bg_reserved[12];
+} __attribute__((packed));
+
+/** An ext2 Inode. */
+struct Inode
+{
+ uint16_t i_mode;
+ uint16_t i_uid;
+ uint32_t i_size;
+ uint32_t i_atime;
+ uint32_t i_ctime;
+ uint32_t i_mtime;
+ uint32_t i_dtime;
+ uint16_t i_gid;
+ uint16_t i_links_count;
+ uint32_t i_blocks;
+ uint32_t i_flags;
+ uint32_t i_osd1;
+ uint32_t i_block[15];
+ uint32_t i_generation;
+ uint32_t i_file_acl;
+ uint32_t i_dir_acl; // Top 32-bits of file size.
+ uint32_t i_faddr;
+ uint8_t i_osd2[12];
+} __attribute__((packed));
+
+/** An ext2 directory entry. */
+struct Dir
+{
+ uint32_t d_inode;
+ uint16_t d_reclen;
+ uint8_t d_namelen;
+ uint8_t d_file_type;
+ char d_name[256];
+} __attribute__((packed));
+
+#endif
diff --git a/repos/dde_rump/src/server/rump_fs/file.h b/repos/dde_rump/src/server/rump_fs/file.h
index 38a4923..a29aa6f 100644
--- a/repos/dde_rump/src/server/rump_fs/file.h
+++ b/repos/dde_rump/src/server/rump_fs/file.h
@@ -42,52 +42,25 @@ class File_system::File : public Node
unsigned long _inode(int dir, char const *name, bool create)
{
- int ret;
+
- if (create) {
- mode_t ugo = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH;
- ret = rump_sys_mknodat(dir, name, S_IFREG | ugo, 0);
- if (ret == -1 && errno != EEXIST)
- throw No_space();
- }
-
- struct stat s;
-
- ret = rump_sys_fstatat(dir, name, &s, 0);
- if (ret == -1)
- throw Lookup_failed();
-
- return s.st_ino;
+ return 4;
}
unsigned long _inode_path(char const *path)
{
- int ret;
- struct stat s;
-
- ret = rump_sys_stat(path, &s);
- if (ret == -1)
- throw Lookup_failed();
-
- return s.st_ino;
- }
+ return 4;}
int _open(int dir, char const *name, Mode mode)
{
- int fd = rump_sys_openat(dir, name, _access_mode(mode));
- if (fd == -1)
- throw Lookup_failed();
-
- return fd;
+
+ return 4;
}
int _open_path(char const *path, Mode mode)
{
- int fd = rump_sys_open(path, _access_mode(mode));
- if (fd == -1)
- throw Lookup_failed();
-
- return fd;
+
+ return 4;
}
public:
@@ -110,44 +83,28 @@ class File_system::File : public Node
Node::name(basename(path));
}
- virtual ~File() { rump_sys_close(_fd); }
+ virtual ~File() { }
size_t read(char *dst, size_t len, seek_off_t seek_offset)
{
- ssize_t ret = rump_sys_pread(_fd, dst, len, seek_offset);
+ ssize_t ret = 0;
return ret == -1 ? 0 : ret;
}
size_t write(char const *src, size_t len, seek_off_t seek_offset)
{
- /* should we append? */
- if (seek_offset == ~0ULL) {
- off_t off = rump_sys_lseek(_fd, 0, SEEK_END);
- if (off == -1)
- return 0;
- seek_offset = off;
- }
-
- ssize_t ret = rump_sys_pwrite(_fd, src, len, seek_offset);
- return ret == -1 ? 0 : ret;
+ return 0;
}
file_size_t length() const
{
- struct stat s;
-
- if(rump_sys_fstat(_fd, &s) < 0)
- return 0;
-
- return s.st_size;
+ return 0;
}
void truncate(file_size_t size)
{
- rump_sys_ftruncate(_fd, size);
-
- mark_as_updated();
+
}
};
diff --git a/repos/dde_rump/src/server/rump_fs/file_system.cc b/repos/dde_rump/src/server/rump_fs/file_system.cc
index 98436ed..51e1109 100644
--- a/repos/dde_rump/src/server/rump_fs/file_system.cc
+++ b/repos/dde_rump/src/server/rump_fs/file_system.cc
@@ -15,141 +15,163 @@
#include
#include
-#include
+
#include
#include
#include
+#include
+#include
+#include
-/**
- * We define our own fs arg structure to fit all sizes, we assume that 'fspec'
- * is the only valid argument and all other fields are unused.
- */
-struct fs_args
-{
- char *fspec;
- char pad[150];
-
- fs_args() { Genode::memset(pad, 0, sizeof(pad)); }
-};
+//===========================/
+#include "ext2.h"
-namespace File_system {
- class Sync;
-};
+char buff[1025];
-static char const *fs_types[] = { RUMP_MOUNT_CD9660, RUMP_MOUNT_EXT2FS,
- RUMP_MOUNT_FFS, RUMP_MOUNT_MSDOS,
- RUMP_MOUNT_NTFS, RUMP_MOUNT_UDF, 0 };
-static char _fs_type[10];
static bool _supports_symlinks;
+using namespace Genode;
+//=================================
+
+Superblock sb_ext2_main;
+
+Superblock sb_ext2_main2;
+
+static bool const verbose = false;
+
+static Genode::Allocator_avl _block_alloc(Genode::env()->heap());
+static size_t _blk_size = 0;
+static Block::sector_t _blk_cnt = 0;
+static Block::Session::Tx::Source *_source;
+static Block::Connection *_block_connection;
-static bool _check_type(char const *type)
-{
- for (int i = 0; fs_types[i]; i++)
- if (!Genode::strcmp(type, fs_types[i]))
- return true;
- return false;
-}
-static void _print_types()
-{
- PERR("fs types:");
- for (int i = 0; fs_types[i]; i++)
- PERR("\t%s", fs_types[i]);
-}
static bool check_symlinks()
{
- if (!Genode::strcmp(_fs_type, RUMP_MOUNT_EXT2FS))
- return true;
-
- if (!Genode::strcmp(_fs_type, RUMP_MOUNT_FFS))
- return true;
+
return false;
}
-static bool check_read_only()
+/*static bool check_read_only()
{
- if (!Genode::strcmp(_fs_type, RUMP_MOUNT_CD9660))
- return true;
+ //if (!Genode::strcmp(_fs_type, RUMP_MOUNT_CD9660))
+ //return true;
return false;
}
+*/
-class File_system::Sync : public Genode::Thread<1024 * sizeof(Genode::addr_t)>
-{
- private:
-
- Timer::Connection _timer;
- Genode::Signal_rpc_member _sync_dispatcher;
-
- void _process_sync(unsigned)
- {
- /* sync through front-end */
- rump_sys_sync();
- /* sync Genode back-end */
- rump_io_backend_sync();
- }
-
- protected:
-
- void entry()
- {
- while (1) {
- _timer.msleep(1000);
- /* send sync request, this goes to server entry point thread */
- Genode::Signal_transmitter(_sync_dispatcher).submit();
- }
- }
-
- public:
-
- Sync(Server::Entrypoint &ep)
- :
- Thread("rump_fs_sync"),
- _sync_dispatcher(ep, *this, &Sync::_process_sync)
- {
- start();
- }
-};
void File_system::init(Server::Entrypoint &ep)
{
- if (!Genode::config()->xml_node().attribute("fs").value(_fs_type, 10) ||
- !_check_type(_fs_type)) {
- PERR("Invalid or no file system given (use \'\"/>)");
- _print_types();
- throw Genode::Exception();
- }
- PINF("Using %s as file system", _fs_type);
- /* start rump kernel */
- rump_init();
- /* register block device */
- rump_pub_etfs_register(GENODE_DEVICE, GENODE_BLOCK_SESSION, RUMP_ETFS_BLK);
- /* mount into extra-terrestrial-file system */
- struct fs_args args;
- int opts = check_read_only() ? RUMP_MNT_RDONLY : 0;
+ PDBG("disk_initialize(drv=%u) called.", 0);
+
+_block_connection = new (Genode::env()->heap()) Block::Connection(&_block_alloc);
+ // Block::Connection _block_connection(&_block_alloc);
+
+ _source = _block_connection->tx();
- args.fspec = (char *)GENODE_DEVICE;
- if (rump_sys_mount(_fs_type, "/", opts, &args, sizeof(args)) == -1) {
- PERR("Mounting '%s' file system failed (errno %u)", _fs_type, errno);
- throw Genode::Exception();
+ Block::Session::Operations ops;
+ _block_connection->info(&_blk_cnt, &_blk_size, &ops);
+
+ /* check for read- and write-capability */
+ if (!ops.supported(Block::Packet_descriptor::READ)) {
+ PERR("Block device not readable!");
+ //destroy(env()->heap(), _block_connection);
+ }
+ if (!ops.supported(Block::Packet_descriptor::WRITE)) {
+ PINF("Block device not writeable!");
}
+ PDBG("We have %llu blocks with a size of %zu bytes",
+ _blk_cnt, _blk_size);
+
+
+
+
+
/* check support for symlinks */
_supports_symlinks = check_symlinks();
- new (Genode::env()->heap()) Sync(ep);
+ //new (Genode::env()->heap()) Sync(ep);
+}
+
+void File_system::readb(int count,int sector, char *buff){
+//PERR(" i came here e");
+int drv = 0;
+
+//int sector = 2; //TODO: block count implement
+
+ PDBG("disk_read(drv=%u, buff=%p, sector=%u, count=%u) called.",
+ drv, buff, (unsigned int)sector, count);
+for(int i=0;ialloc_packet( 2*_blk_size),
+ Block::Packet_descriptor::READ, sector+i, 2);
+//PERR("dd\n");
+ _source->submit_packet(p);
+//PERR("dd1\n");
+ p = _source->get_acked_packet();
+//PERR("yo\n");
+ /* check for success of operation */
+ if (!p.succeeded()) {
+ PERR("Could not read block(s)");
+ _source->release_packet(p);
+ return ;
+ }
+
+
+//PERR("takkuva \n");
+ memcpy((void*)(buff+512*i), _source->packet_content(p), 1024);
+
+
+//PDBG("%x\n",sb_ext2_main.s_mnt_count);
+
+ //PDBG("read() successful, contents of buff = \n");
+
+ //for (unsigned int i = 0; i < count * _blk_size; i++)
+ //PDBG("%8x: %2x %c", i, buff[i], buff[i] >= 32 ? buff[i] : '-');
+//PERR("tret\n");
+ _source->release_packet(p);
+
+//PERR("pettu\n");
}
+PDBG("Block Read successful\n");
+}
+void File_system::writeb(int count,int sector, char *buff){
+
+
+//int drv = 0;
+
+//int sector = 2; //TODO: block count implement
+
+
+PERR("writing back data to block device\n");
+/* allocate packet-descriptor for writing */
+ Block::Packet_descriptor p(_source->alloc_packet(count * _blk_size),
+ Block::Packet_descriptor::WRITE, sector, count);
+ memcpy(_source->packet_content(p), (void*)buff, count * _blk_size);
+
+ _source->submit_packet(p);
+ p = _source->get_acked_packet();
+if (!p.succeeded()) {
+ PERR("Could not read block(s)");
+ }
+
+ _source->release_packet(p);
+
+}
bool File_system::supports_symlinks() { return _supports_symlinks; }
diff --git a/repos/dde_rump/src/server/rump_fs/file_system.h b/repos/dde_rump/src/server/rump_fs/file_system.h
index 7484baa..1148fad 100644
--- a/repos/dde_rump/src/server/rump_fs/file_system.h
+++ b/repos/dde_rump/src/server/rump_fs/file_system.h
@@ -21,18 +21,19 @@ extern "C" {
#include
#include
#include
-#include
-#include
}
#include
#include
-
+#include "ext2.h"
namespace File_system {
void init(Server::Entrypoint &ep);
bool supports_symlinks();
+void readb(int,int, char*);
+void writeb(int,int, char*);
}
extern int errno;
-
+extern Superblock sb_ext2_main;
+extern char buff[1025];
#endif /* _FILE_SYSTEM_H_ */
diff --git a/repos/dde_rump/src/server/rump_fs/main.cc b/repos/dde_rump/src/server/rump_fs/main.cc
index 98370f2..678b129 100644
--- a/repos/dde_rump/src/server/rump_fs/main.cc
+++ b/repos/dde_rump/src/server/rump_fs/main.cc
@@ -20,6 +20,10 @@
#include
#include
#include "file_system.h"
+#include "Ext2Filesystem.h"
+#include "Ext2Directory.h"
+#include "Ext2Node.h"
+#include "RadixTree.h"
#include "directory.h"
#include "node_handle_registry.h"
@@ -30,9 +34,13 @@ namespace File_system {
struct Session_component;
}
+
+
+Filesystem *pFs;
+
class File_system::Session_component : public Session_rpc_object
{
- private:
+ public:
Allocator &_md_alloc;
Directory &_root;
@@ -53,6 +61,7 @@ class File_system::Session_component : public Session_rpc_object
*/
void _process_packet_op(Packet_descriptor &packet, Node &node)
{
+//PERR("1\n");
void * const content = tx_sink()->packet_content(packet);
size_t const length = packet.length();
seek_off_t const offset = packet.position();
@@ -78,10 +87,12 @@ class File_system::Session_component : public Session_rpc_object
packet.length(res_length);
packet.succeeded(res_length > 0);
+//PERR("1end\n");
}
void _process_packet()
{
+//PERR("2start\n");
Packet_descriptor packet = tx_sink()->get_packet();
/* assume failure by default */
@@ -100,7 +111,8 @@ class File_system::Session_component : public Session_rpc_object
* checked for 'ready_to_ack' in '_process_packets'.
*/
tx_sink()->acknowledge_packet(packet);
- }
+//PERR("2end\n");
+}
/**
* Called by signal dispatcher, executed in the context of the main
@@ -108,7 +120,8 @@ class File_system::Session_component : public Session_rpc_object
*/
void _process_packets(unsigned)
{
- while (tx_sink()->packet_avail()) {
+//PERR("3s\n");
+ while (tx_sink()->packet_avail()) {
/*
* Make sure that the '_process_packet' function does not
@@ -127,18 +140,22 @@ class File_system::Session_component : public Session_rpc_object
_process_packet();
}
- }
+
+//PERR("3end\n");
+}
/**
* Check if string represents a valid path (must start with '/')
*/
static void _assert_valid_path(char const *path)
{
- if (!path || path[0] != '/') {
+//PERR("4s\n");
+ if (!path || path[0] != '/') {
PWRN("malformed path '%s'", path);
throw Lookup_failed();
}
- }
+//PERR("4end\n");
+ }
public:
@@ -161,9 +178,11 @@ class File_system::Session_component : public Session_rpc_object
* Register '_process_packets' dispatch function as signal
* handler for packet-avail and ready-to-ack signals.
*/
- _tx.sigh_packet_avail(_process_packet_dispatcher);
+//PERR("5s %s\n", root_dir);
+ _tx.sigh_packet_avail(_process_packet_dispatcher);
_tx.sigh_ready_to_ack(_process_packet_dispatcher);
- }
+//PERR("5e\n");
+ }
/**
* Destructor
@@ -181,7 +200,9 @@ class File_system::Session_component : public Session_rpc_object
File_handle file(Dir_handle dir_handle, Name const &name, Mode mode, bool create)
{
- if (!valid_name(name.string()))
+
+//PERR("6s\n");
+if (!valid_name(name.string()))
throw Invalid_name();
Directory *dir = _handle_registry.lookup(dir_handle);
@@ -192,7 +213,8 @@ class File_system::Session_component : public Session_rpc_object
File *file = dir->file(name.string(), mode, create);
return _handle_registry.alloc(file);
- }
+//PERR("FILE\n");
+}
Symlink_handle symlink(Dir_handle dir_handle, Name const &name, bool create)
{
@@ -208,13 +230,24 @@ class File_system::Session_component : public Session_rpc_object
throw Permission_denied();
Symlink *link = dir->symlink(name.string(), create);
+//PERR("SYMLINK\n");
return _handle_registry.alloc(link);
}
Dir_handle dir(Path const &path, bool create)
{
+//PERR("ikada");
char const *path_str = path.string();
- _assert_valid_path(path_str);
+char *temp=new (&_md_alloc)char[Genode::strlen(path_str)+1];
+Genode::memcpy(temp,path_str,Genode::strlen(path_str)+1);
+PDBG(" Creating Directory \n");
+PERR("\n %s \n",temp);
+pFs->Filesystem::createDirectory(temp);
+//PERR("\n Removing Directory :: \n");
+//PDBG("\n %s \n",path_str);
+//pFs->Filesystem::remove(temp);
+
+_assert_valid_path(path_str);
/* skip leading '/' */
path_str++;
@@ -224,15 +257,16 @@ class File_system::Session_component : public Session_rpc_object
if (!path.is_valid_string())
throw Name_too_long();
-
+//PERR("%s - 1\n", path);
Directory *dir = _root.subdir(path_str, create);
+//PERR("DIR\n");
return _handle_registry.alloc(dir);
}
Node_handle node(Path const &path)
{
char const *path_str = path.string();
-
+//PERR("NODE\n");
_assert_valid_path(path_str);
Node *node = _root.node(path_str + 1);
Node_handle h = _handle_registry.alloc(node);
@@ -251,6 +285,7 @@ class File_system::Session_component : public Session_rpc_object
/* destruct node */
if (node)
destroy(&_md_alloc, node);
+//PERR("CLOSE");
}
Status status(Node_handle node_handle)
@@ -283,12 +318,14 @@ class File_system::Session_component : public Session_rpc_object
return s;
}
+//PERR("STATUS\n");
return Status();
+
}
void control(Node_handle, Control)
{
- PERR("%s not implemented", __func__);
+ //PERR("%s not implemented", __func__);
}
void unlink(Dir_handle dir_handle, Name const &name)
@@ -301,6 +338,7 @@ class File_system::Session_component : public Session_rpc_object
Directory *dir = _handle_registry.lookup(dir_handle);
dir->unlink(name.string());
+//PERR("unlink \n");
}
void truncate(File_handle file_handle, file_size_t size)
@@ -310,6 +348,7 @@ class File_system::Session_component : public Session_rpc_object
File *file = _handle_registry.lookup(file_handle);
file->truncate(size);
+//PERR("truncate funcs\n");
}
void move(Dir_handle, Name const &, Dir_handle, Name const &)
@@ -322,7 +361,7 @@ class File_system::Session_component : public Session_rpc_object
_handle_registry.sigh(node_handle, sigh);
}
- void sync() { rump_sys_sync(); }
+ void sync() { }
};
class File_system::Root : public Root_component
@@ -397,6 +436,8 @@ class File_system::Root : public Root_component
* and communication buffer.
*/
size_t session_size = sizeof(Session_component) + tx_buf_size;
+PERR("insufficient 'ram_quota', got %zd, need %zd",
+ ram_quota, session_size);
if (max((size_t)4096, session_size) > ram_quota) {
PERR("insufficient 'ram_quota', got %zd, need %zd",
ram_quota, session_size);
@@ -445,9 +486,16 @@ struct File_system::Main
ep(ep),
resource_dispatcher(ep, *this, &Main::resource_handler)
{
- File_system::init(ep);
+
env()->parent()->announce(ep.manage(fs_root));
env()->parent()->resource_avail_sigh(resource_dispatcher);
+ File_system::init(ep);
+pFs=new (&sliced_heap)Ext2Filesystem((sliced_heap));
+ pFs->initialise();
+ RadixTree::m_alloc = &sliced_heap;
+ Ext2Directory::m_alloc=&sliced_heap;
+Ext2Node::m_alloc=&sliced_heap;
+Filesystem::m_alloc=&sliced_heap;
}
};
@@ -455,8 +503,11 @@ struct File_system::Main
/**********************
** Server framework **
**********************/
-
+Genode::Allocator *RadixTree::m_alloc;
+Genode::Allocator *Ext2Node::m_alloc;
+Genode::Allocator *Ext2Directory::m_alloc;
+Genode::Allocator *Filesystem::m_alloc;
char const * Server::name() { return "rump_fs_ep"; }
Genode::size_t Server::stack_size() { return 4 * 1024 * sizeof(long); }
-void Server::construct(Server::Entrypoint &ep) { static File_system::Main inst(ep); }
+void Server::construct(Server::Entrypoint &ep) {PERR("creating server\n"); static File_system::Main inst(ep); PERR("created server\n");}
diff --git a/repos/dde_rump/src/server/rump_fs/symlink.h b/repos/dde_rump/src/server/rump_fs/symlink.h
index b4dcf55..7696407 100644
--- a/repos/dde_rump/src/server/rump_fs/symlink.h
+++ b/repos/dde_rump/src/server/rump_fs/symlink.h
@@ -48,17 +48,12 @@ class File_system::Symlink : public Node
size_t write(char const *src, size_t len, seek_off_t seek_offset)
{
- if (!_create)
- return 0;
-
- int ret = rump_sys_symlink(src, _path.base());
- return ret == -1 ? 0 : ret;
+ return 0;
}
size_t read(char *dst, size_t len, seek_off_t seek_offset)
{
- int ret = rump_sys_readlink(_path.base(), dst, len);
- return ret == -1 ? 0 : ret;
+ return 0;
}
file_size_t length()
diff --git a/repos/dde_rump/src/server/rump_fs/target.mk b/repos/dde_rump/src/server/rump_fs/target.mk
index 56fd8f4..13d8072 100644
--- a/repos/dde_rump/src/server/rump_fs/target.mk
+++ b/repos/dde_rump/src/server/rump_fs/target.mk
@@ -1,5 +1,5 @@
TARGET = rump_fs
-SRC_CC = main.cc file_system.cc random.cc
+SRC_CC = main.cc file_system.cc random.cc Ext2Filesystem.cc RadixTree.cc Ext2Directory.cc Ext2File.cc Ext2Node.cc Directory.cc File.cc Filesystem.cc
LIBS = rump rump_fs server startup
diff --git a/repos/libports/src/test/libc_ffat/main.cc b/repos/libports/src/test/libc_ffat/main.cc
index 36ddb8f..8576e49 100644
--- a/repos/libports/src/test/libc_ffat/main.cc
+++ b/repos/libports/src/test/libc_ffat/main.cc
@@ -27,12 +27,12 @@
#define CALL_AND_CHECK(ret, operation, condition, info_string, ...) \
- printf("calling " #operation " " info_string "\n", ##__VA_ARGS__); \
+ PERR("calling " #operation " " info_string "\n", ##__VA_ARGS__); \
ret = operation; \
if (condition) { \
- printf(#operation " succeeded\n"); \
+ PERR(#operation " succeeded\n"); \
} else { \
- printf(#operation " failed, " #ret "=%ld, errno=%d\n", (long)ret, errno); \
+ PERR(#operation " failed, " #ret "=%ld, errno=%d\n", (long)ret, errno); \
return -1; \
}
@@ -41,7 +41,7 @@ int main(int argc, char *argv[])
{
int ret, fd;
ssize_t count;
-
+PERR("hai\n");
char const *dir_name = "testdir";
char const *dir_name2 = "testdir2";
char const *file_name = "test.tst";
@@ -58,6 +58,7 @@ int main(int argc, char *argv[])
Genode::config()->xml_node().sub_node("iterations").attribute("value").value(&iterations);
} catch(...) { }
+PERR("Entering VFS\n");
for (unsigned int i = 0; i < iterations; i++) {
/* create directory (short name) */