diff --git a/include/fsactions.h b/include/fsactions.h index 58f4bd6..77cb95b 100644 --- a/include/fsactions.h +++ b/include/fsactions.h @@ -7,6 +7,7 @@ void AddFileToFS(FileSystem* fs, char* fname); void ListFS(FileSystem* fs); void _ListFS_(FileSystem* fs, ino_t inodeNumber, short unsigned numtabs); void RemoveFileFromFS(FileSystem* fs, char* fname); +int _RemoveFileFromFS_(FileSystem* fs, ino_t inodeNumber, char* fname); void ExtractFileFromFS(FileSystem* fs, char* fname); ino_t GetFreeInodeNumber(Inode inodes[]); diff --git a/src/fsactions.c b/src/fsactions.c index f988e03..bbd93a0 100644 --- a/src/fsactions.c +++ b/src/fsactions.c @@ -21,11 +21,11 @@ // TODO: Fix implementation to add starting at Inode 0 void AddFileToFS(FileSystem* fs, char* fname) { + int inputfd = open(fname, O_RDONLY); struct stat tempstat; ino_t currentInode = 0; ino_t newInode; int newDirectBlock; - int tempfbl[4]; char* tempname; stat(fname, &tempstat); // Get first directory, labelled by 0 to splitLocation-1, @@ -39,35 +39,28 @@ void AddFileToFS(FileSystem* fs, char* fname) // While there is a '/', make a new inode out of left and keep right side while (splitLocation > -1) { - // First: check if directory already exists in current inode - // if yes, then go to that inode and start with next directory - // Second: get a number for the next free direct block - // Third: get a free inode number - // Fourth: set info for direct block tempname = strndup(fname, splitLocation); newInode = FindDirectory(fs->inodes[currentInode], tempname); if (newInode == -1) { - for (int i = 0; i < 4; i++) - tempfbl[i] = (currentInode*4) + i; - newDirectBlock = GetFreeBlockNumber(tempfbl, 4); + newDirectBlock = GetFreeBlockNumber(fs->fbl.freeList + (currentInode*4), 4); newInode = GetFreeInodeNumber(fs->inodes); strcpy(fs->inodes[currentInode].blocks[newDirectBlock].name, tempname); free(tempname); SetupDirectoryBlock(&(fs->inodes[currentInode].blocks[newDirectBlock]), newInode); fs->inodes[newInode].isValid = 1; - currentInode = newInode; } + currentInode = newInode; fname = fname + splitLocation + 1; splitLocation = FindNextDirectory(fname); } - for (int i = 0; i < 4; i++) - tempfbl[i] = (currentInode*4) + i; - newDirectBlock = GetFreeBlockNumber(tempfbl, 4); + newDirectBlock = GetFreeBlockNumber(fs->fbl.freeList + (currentInode*4), 4); + newInode = currentInode*4 + newDirectBlock; fs->inodes[currentInode].blocks[newDirectBlock].isValid = 1; fs->inodes[currentInode].blocks[newDirectBlock].size = tempstat.st_size; strcpy(fs->inodes[currentInode].blocks[newDirectBlock].name, fname); - printf("%s\n", fs->inodes[0].blocks[0].name); + fs->inodes[currentInode].blocks[newDirectBlock].inode = newInode; + read(inputfd, &(fs->dataBlocks[newInode].byte), tempstat.st_size); return; } @@ -75,7 +68,7 @@ void AddFileToFS(FileSystem* fs, char* fname) void ListFS(FileSystem* fs) { printf("/\n"); - _ListFS_(fs, 0, 0); + _ListFS_(fs, 0, 1); return; } @@ -97,7 +90,28 @@ void _ListFS_(FileSystem* fs, ino_t inodeNumber, short unsigned numtabs) // TODO: Fix function so that it adds directories, then the file after void RemoveFileFromFS(FileSystem* fs, char* fname) { + _RemoveFileFromFS_(fs, 0, fname); +} +// Recursive bool call for checking before removing +// If the directory is not empty, returns false +int _RemoveFileFromFS_(FileSystem* fs, ino_t inodeNumber, char* fname) +{ + int emptyDir = 1; + for (int i = 0; i < DEFAULTINODEMAX; i++) + { + if (!(fs->inodes[inodeNumber].blocks[i].isValid)) + continue; + if (fs->inodes[inodeNumber].blocks[i].isDirectory) + emptyDir =_RemoveFileFromFS_(fs, fs->inodes[inodeNumber].blocks[i].inode, fname + FindNextDirectory(fname) + 1); + if (strcmp(fs->inodes[inodeNumber].blocks[i].name, fname) == 0) + fs->inodes[inodeNumber].blocks[i].isValid = 0; + else + emptyDir = 0; + } + if (!emptyDir) + return 0; + return 1; } // Extract a file from the filesystem @@ -165,7 +179,7 @@ int FindDirectory(Inode inode, char* directoryName) if (!(inode.blocks[i].isDirectory)) continue; if (strcmp(inode.blocks[i].name, directoryName) == 0) - return i; + return inode.blocks[i].inode; } return -1; } diff --git a/test/test.c b/test/test.c index cdc776d..9b16e4d 100644 --- a/test/test.c +++ b/test/test.c @@ -15,16 +15,14 @@ char* argv[5]; void setUp(void) { FuseStructInit(&dummyFuse); - argv[0] = "bin/fuse.out"; - argv[1] = "-l"; - argv[2] = "test/files/test1.txt"; - argv[3] = "-f"; - argv[4] = "test/fakefs.test"; + GetArguments(argc, argv, &dummyFuse); + OpenFS(&dummyFuse, argv[0]); + fakefs = SetupFS(&dummyFuse); } void tearDown(void) { - ; + TearDownFS(); } void Test_FuseGetArgs_Should_SetDummyArgs(void) @@ -53,16 +51,13 @@ void Test_FindEmptyBitPosition_Should_ReturnPosition(void) void Test_FileSystem_Should_SuccessfullyOpen(void) { - remove(argv[4]); GetArguments(argc, argv, &dummyFuse); OpenFS(&dummyFuse, argv[0]); fakefs = SetupFS(&dummyFuse); } -void Test_FileSystem_Should_AddFile(void) +void Test_FileSystem_Should_AddFirstFile(void) { - argv[1] = "-a"; - GetArguments(argc, argv, &dummyFuse); RunFuse(fakefs, &dummyFuse); TEST_ASSERT_EQUAL(1, fakefs->inodes[0].isValid); TEST_ASSERT_EQUAL_CHAR_ARRAY("test", fakefs->inodes[0].blocks[0].name, 4); @@ -70,11 +65,39 @@ void Test_FileSystem_Should_AddFile(void) TEST_ASSERT_EQUAL_CHAR_ARRAY("files", fakefs->inodes[1].blocks[0].name, 5); TEST_ASSERT_EQUAL(1, fakefs->inodes[2].isValid); TEST_ASSERT_EQUAL_CHAR_ARRAY("test1.txt", fakefs->inodes[2].blocks[0].name, 9); + ino_t inodeLocation = fakefs->inodes[2].blocks[0].inode; + TEST_ASSERT_NOT_EMPTY(fakefs->dataBlocks[inodeLocation].byte); +} + +void Test_FileSystem_Should_AddSecondFile(void) +{ + RunFuse(fakefs, &dummyFuse); + TEST_ASSERT_EQUAL(1, fakefs->inodes[0].isValid); + TEST_ASSERT_EQUAL_CHAR_ARRAY("test", fakefs->inodes[0].blocks[0].name, 4); + TEST_ASSERT_EQUAL(1, fakefs->inodes[1].isValid); + TEST_ASSERT_EQUAL_CHAR_ARRAY("files", fakefs->inodes[1].blocks[0].name, 5); + TEST_ASSERT_EQUAL(1, fakefs->inodes[2].isValid); + TEST_ASSERT_EQUAL_CHAR_ARRAY("test2.txt", fakefs->inodes[2].blocks[1].name, 9); + ino_t inodeLocation = fakefs->inodes[2].blocks[1].inode; + TEST_ASSERT_NOT_EMPTY(fakefs->dataBlocks[inodeLocation].byte); +} + +void Test_FileSystem_Should_AddThirdFile(void) +{ + RunFuse(fakefs, &dummyFuse); + TEST_ASSERT_EQUAL(1, fakefs->inodes[0].isValid); + TEST_ASSERT_EQUAL_CHAR_ARRAY("test", fakefs->inodes[0].blocks[0].name, 4); + TEST_ASSERT_EQUAL(1, fakefs->inodes[1].isValid); + TEST_ASSERT_EQUAL_CHAR_ARRAY("files", fakefs->inodes[1].blocks[0].name, 5); + TEST_ASSERT_EQUAL(1, fakefs->inodes[2].isValid); + TEST_ASSERT_EQUAL_CHAR_ARRAY("test3.txt", fakefs->inodes[2].blocks[2].name, 9); + ino_t inodeLocation = fakefs->inodes[2].blocks[2].inode; + TEST_ASSERT_NOT_EMPTY(fakefs->dataBlocks[inodeLocation].byte); } void Test_FileSystem_Should_ListContents(void) { - Fuse(argc, argv); + RunFuse(fakefs, &dummyFuse); TEST_ASSERT_EQUAL(1, fakefs->inodes[0].isValid); TEST_ASSERT_EQUAL_CHAR_ARRAY("test", fakefs->inodes[0].blocks[0].name, 4); TEST_ASSERT_EQUAL(1, fakefs->inodes[1].isValid); @@ -83,14 +106,43 @@ void Test_FileSystem_Should_ListContents(void) TEST_ASSERT_EQUAL_CHAR_ARRAY("test1.txt", fakefs->inodes[2].blocks[0].name, 9); TEST_MESSAGE("This only runs the list operation. Check info yourself."); } +void Test_FileSystem_Should_RemoveFile(void) +{ + RunFuse(fakefs, &dummyFuse); + TEST_ASSERT_EQUAL(0, fakefs->inodes[2].blocks[0].isValid); +} + +void Test_FileSystem_Should_RemoveEmptyDirectories(void) +{ + TEST_ASSERT_EQUAL(0, fakefs->inodes[2].isValid); + TEST_ASSERT_EQUAL(0, fakefs->inodes[1].blocks[0].isValid); + TEST_ASSERT_EQUAL(0, fakefs->inodes[1].isValid); + TEST_ASSERT_EQUAL(0, fakefs->inodes[0].blocks[0].isValid); +} int main(void) { + remove("test/fakefs.test"); + argv[0] = "bin/fuse.out"; + argv[1] = "-l"; + argv[2] = "test/files/test1.txt"; + argv[3] = "-f"; + argv[4] = "test/fakefs.test"; UNITY_BEGIN(); RUN_TEST(Test_FuseGetArgs_Should_SetDummyArgs); RUN_TEST(Test_FindEmptyBitPosition_Should_ReturnPosition); RUN_TEST(Test_FileSystem_Should_SuccessfullyOpen); - RUN_TEST(Test_FileSystem_Should_AddFile); + argv[1] = "-a"; + RUN_TEST(Test_FileSystem_Should_AddFirstFile); + argv[2] = "test/files/test2.txt"; + RUN_TEST(Test_FileSystem_Should_AddSecondFile); + argv[2] = "test/files/test3.txt"; + RUN_TEST(Test_FileSystem_Should_AddThirdFile); + argv[1] = "-l"; RUN_TEST(Test_FileSystem_Should_ListContents); + argv[1] = "-r"; + argv[2] = "test/files/test2.txt"; + RUN_TEST(Test_FileSystem_Should_RemoveFile); + RUN_TEST(Test_FileSystem_Should_RemoveEmptyDirectories); return UNITY_END(); }