void remove_directory(ino iNode, ino parentiNode, const char *filename) { remove_file_from_directory(parentiNode, iNode, filename); decrease_link_count(parentiNode); reset_inode_link(iNode); decrease_link_count(iNode); }
int remove_file(ino iNode, const char *filePath) { int isFile = check_if_inode_is_file(iNode); if (isFile == -2) { return isFile; } char path[strlen(filePath)]; GetDirFromPath(filePath, path); int pathiNode = find_iNode(path); char file[FILENAME_SIZE]; GetFilenameFromPath(filePath, file); // We can't use the file inode directly since hardlinks have the same name // as the file they are linked against remove_file_from_directory(pathiNode, iNode, file); // Decrease link count and, if link == 0, remove file decrease_link_count(iNode); return 0; }
int bd_rename(const char *pFilename, const char *pDestFilename) { // Check if both directory are valid, if so keep them in memory char initialDirectory[BLOCK_SIZE]; char newDirectory[BLOCK_SIZE]; if (GetDirFromPath(pFilename, initialDirectory) != 1) { return -1; } if (GetDirFromPath(pDestFilename, newDirectory) != 1) { return -1; } // Find directory inodes and if there are valid int newDirectoryiNode = find_iNode(newDirectory); if (newDirectoryiNode == -1) { return -1; } int initialDirectoryiNode = find_iNode(initialDirectory); if (initialDirectoryiNode == -1) { return -1; } // Check if they have the same directory, if so, assigned the initial inode // to the newDirectory if (strcmp(initialDirectory, newDirectory) == 0) { newDirectoryiNode = initialDirectoryiNode; } // If pFilename is not a directory, we simply do an hardlink int pFilenameiNode = find_iNode(pFilename); if (check_if_inode_is_file(pFilenameiNode) == 0) { int renamingFilenameSuccess = bd_hardlink(pFilename, pDestFilename); if (renamingFilenameSuccess == 0) { int unlinkingFilenameSuccess = bd_unlink(pFilename); return unlinkingFilenameSuccess; } } else { // If pFilename is a directory char newFile[BLOCK_SIZE]; // If the new directory doesn't exists if (find_iNode(pDestFilename) == -1) { // We remove directory from it's initial parentDirectory if (GetFilenameFromPath(pFilename, newFile) == 1) { remove_file_from_directory(initialDirectoryiNode, pFilenameiNode, newFile); decrease_link_count(initialDirectoryiNode); } else { return -1; } // We add directory to it's new parentDirectory if (GetFilenameFromPath(pDestFilename, newFile) == 1) { char directoryDataBlock[BLOCK_SIZE]; ReadBlock(6 + newDirectoryiNode - 1, directoryDataBlock); DirEntry *directory = (DirEntry *)directoryDataBlock; int filesNumber = numberOfFilesInDirectory(directory); // Assign newDirectory informations strcpy(directory[filesNumber].Filename, newFile); directory[filesNumber].iNode = pFilenameiNode; // Adjuste the newDirectory and its parentDirectory size add_size_to_inode_size(sizeof(directory[filesNumber]), newDirectoryiNode); increase_link_count(newDirectoryiNode); add_parentiNode(pFilenameiNode, newDirectoryiNode); WriteBlock(6 + newDirectoryiNode - 1, directoryDataBlock); } } } return 0; }
static errcode_t remove_slots(ocfs2_filesys *fs, int num_slots) { errcode_t ret; uint16_t old_num = OCFS2_RAW_SB(fs->fs_super)->s_max_slots; uint16_t removed_slot = old_num - 1; struct tools_progress *prog = NULL; ret = remove_slot_check(fs, num_slots); if (ret) goto bail; /* We have seven steps in removing each slot */ prog = tools_progress_start("Removing slots", "rmslots", (old_num - num_slots) * 7); if (!prog) { ret = TUNEFS_ET_NO_MEMORY; goto bail; } /* This is cleared up in update_slot_count() if everything works */ ret = tunefs_set_in_progress(fs, OCFS2_TUNEFS_INPROG_REMOVE_SLOT); if (ret) goto bail; /* we will remove the slots once at a time so that fsck.ocfs2 can work * well and we can continue our work easily in case of any panic. */ while (removed_slot >= num_slots) { /* Link the specified extent alloc file to others. */ ret = relink_system_alloc(fs, removed_slot, num_slots, EXTENT_ALLOC_SYSTEM_INODE); if (ret) goto bail; tools_progress_step(prog, 1); /* Link the specified inode alloc file to others. */ ret = relink_system_alloc(fs, removed_slot, num_slots, INODE_ALLOC_SYSTEM_INODE); if (ret) goto bail; tools_progress_step(prog, 1); /* Truncate the orphan dir to release its clusters * to the global bitmap. */ ret = truncate_orphan_dir(fs, removed_slot); if (ret) goto bail; tools_progress_step(prog, 1); /* empty the content of journal and truncate its clusters. */ ret = empty_and_truncate_journal(fs, removed_slot); if (ret) goto bail; tools_progress_step(prog, 1); /* Now, we decrease the max_slots first and then remove the * slots for the reason that: * * 1. ocfs2_lock_down_clusters needs to lock all the journal * files. so if we delete the journal entry first and fail * to decrease the max_slots, the whole cluster can't be * locked any more due to the loss of journals. * * 2. Now all the resources except the inodes are freed * so it is safe to decrease the slots first, and if any * panic happens after we decrease the slots, we can ignore * them, and actually if we want to increase the slot in the * future, we can reuse these inodes. */ /* The slot number is updated in the super block.*/ OCFS2_RAW_SB(fs->fs_super)->s_max_slots--; ret = ocfs2_write_primary_super(fs); if (ret) goto bail; tools_progress_step(prog, 1); /* The extra system dir entries should be removed. */ ret = remove_slot_entry(fs, removed_slot); if (ret) goto bail; tools_progress_step(prog, 1); /* Decrease the i_links_count in system file directory * since the orphan_dir is removed. */ ret = decrease_link_count(fs, fs->fs_sysdir_blkno); if (ret) goto bail; tools_progress_step(prog, 1); removed_slot--; } bail: if (prog) tools_progress_stop(prog); return ret; }