void readdir (struct intr_frame *f) { int fd = *value_stack_int(f->esp,4); char * name = *(char **)value_stack(f->esp,8); //get the fd and check if fd is a directory struct filed * filed = find_file(fd); if ( filed == NULL ) { exit_mythread(-1); } struct file * file = filed->file; if ( file == NULL ) { exit_mythread(-1); } //check if it is a directory if ( !file_direct(file) ) { f->eax = 0; return; } //now we can start struct dir * mydir = (struct dir *)filed->vaddr; bool success = dir_readdir (mydir, name); if (success) f->eax = 1; else f->eax = 0; }
/* Invokes readdir on the directory */ bool file_readdir (struct file *file, char *name) { if (file->dir == NULL) return false; bool success = dir_readdir (file->dir, name); return success; }
/* read directory */ bool sys_readdir(int fd, char *name) { bool result = false; struct file *pfile = process_get_file(fd); struct inode *inode = file_get_inode(pfile); struct dir *dir; int offset = 0; char entry[100]; if(pfile != NULL) { /* if file is not directory, return false */ if(inode_is_dir(inode) == false ) return result; dir = dir_open(inode); /* read directory and store to name */ while(dir_readdir(dir, entry) == true) { /* read directory except . and .. */ if( strcmp(entry,".") == 0 || strcmp(entry,"..") == 0 ) continue; /* copy entry to name */ strlcpy(&name[offset], entry, strlen(entry)+1); offset = strlen(entry) + 1; } result = true; } return true; }
/* Removes any entry for NAME in DIR. Returns true if successful, false on failure, which occurs only if there is no file with the given NAME. */ bool dir_remove (struct dir *dir, const char *name) { struct dir_entry e; struct inode *inode = NULL; bool success = false; off_t ofs; ASSERT (dir != NULL); ASSERT (name != NULL); //lock the directory for the rest of the lookup operation inode_lock(dir->inode); name = getfilename(name); /* Find directory entry. */ if (!lookup (dir, name, &e, &ofs)) goto done; /* Open inode. */ inode = inode_open (e.inode_sector); if (inode == NULL) goto done; //if it is still open don't allow deletion if(inode_type(inode) == FILE_DIR) { //is file in use? if(inode_opencnt(inode) > 1) goto done; char * temp = (char *)malloc(sizeof(char) * (NAME_MAX + 1) ); struct dir * dirtemp = dir_open(inode); //is dir empty? if (dir_readdir(dirtemp,temp)) { free(temp); dir_close(dirtemp); goto done; } free(temp); dir_close(dirtemp); } /* Erase directory entry. */ e.in_use = false; if (inode_write_at (dir->inode, &e, sizeof e, ofs) != sizeof e) goto done; /* Remove inode. */ inode_remove (inode); success = true; done: //unlock the directory inode_unlock(dir->inode); inode_close (inode); return success; }
static bool readdir_handler (int fd, char *dir) { struct file_struct * f = get_file(fd); if (f != NULL) { if (f->sys_dir != NULL) { return dir_readdir(f->sys_dir, dir); } } return false; }
bool filesys_readdir (int fd, char *name) { struct file *file = file_find (fd); if (file == NULL) return false; struct inode *inode = file_get_inode (file); if (!inode_is_dir (inode)) return false; struct dir *dir = dir_open (inode); dir_set_pos (dir, file_tell (file)); bool success = dir_readdir (dir, name); file_seek (file, dir_get_pos (dir)); dir_close (dir); return success; }
/*! Reads a directory entry from file descriptor fd. If successful, stores, * the null-terminated file name in name. If no entries are left in * directory, returns false. */ bool _readdir(uint32_t fd, char* name){ /* Check for the validity of the pointer. */ if (!checkva(name)) return false; /* Get the f_info struct of this fd*/ struct f_info* f = findfile(fd); /*Check that we are opening a directory. */ if (!f->isdir) return false; /* Use the defined dir_readir to finish the function. */ return dir_readdir(f->d, name); }
/* Deletes the file named NAME. Returns true if successful, false on failure. Fails if no file named NAME exists, or if an internal memory allocation fails. */ bool filesys_remove (const char *name) { bool success = false; struct inode *inode = NULL; struct dir *search_dir = get_cwd(name); struct dir *parent_dir = NULL; if (search_dir == NULL) { return false; } parent_dir = dir_reopen(search_dir); char *part = malloc(NAME_MAX + 1); if (part == NULL) { return false; } memset(part, 0, NAME_MAX + 1); int retrieved_next_part; for (retrieved_next_part = get_next_part(part, &name); retrieved_next_part > 0; retrieved_next_part = get_next_part(part, &name)) { if (dir_lookup (search_dir, part, &inode)) { dir_close(parent_dir); parent_dir = dir_reopen(search_dir); if (parent_dir == NULL) { dir_close(search_dir); free(part); return false; } if (!inode_is_dir(inode)) { break; } else { dir_close(search_dir); search_dir = dir_open(inode); if (search_dir == NULL) { dir_close(parent_dir); free(part); return false; } } } else { inode = NULL; break; } } if (inode == NULL || get_next_part(part, &name) != 0) { if (inode != NULL && !inode_is_dir(inode)) { inode_close(inode); } dir_close(parent_dir); dir_close(search_dir); free(part); return false; } if (parent_dir == NULL || search_dir == NULL) { dir_close(search_dir); dir_close(parent_dir); free(part); return false; } if (inode_is_dir(inode)) { char buffer[NAME_MAX + 1]; if (inode_is_open(inode) || dir_readdir(search_dir, buffer)) { success = false; } else { inode_close(inode); success = dir_remove (parent_dir, part); } } else { inode_close(inode); success = dir_remove(parent_dir, part); } dir_close(search_dir); dir_close(parent_dir); free(part); return success; }
/*Fetches directory entries for `dir`*/ error_t dir_entries_get (file_t dir, char **dirent_data, /*the list of directory entries as returned by dir_readdir */ size_t * dirent_data_size,/*the size of `dirent_data` */ struct dirent ***dirent_list/*the array of pointers to beginnings of dirents in dirent_data */ ) { error_t err = 0; /*The data (array of dirents(?)) returned by dir_readdir */ char *data; /*The size of `data` */ size_t data_size; /*The number of entries in `data` */ int entries_num; /*Try to read the contents of the specified directory */ err = dir_readdir (dir, &data, &data_size, 0, -1, 0, &entries_num); if (err) return err; /*Create a new list of dirents */ struct dirent **list; /*Allocate the memory for the list of dirents and for the finalizing element */ list = malloc (sizeof (struct dirent *) * (entries_num + 1)); /*If memory allocation has failed */ if (!list) { /*free the result of dir_readdir */ munmap (data, data_size); /*return the corresponding error */ return ENOMEM; } /*The current directory entry */ struct dirent *dp; int i; /*Go through every element of the list of dirents */ for (i = 0, dp = (struct dirent *) data; i < entries_num; ++i, dp = (struct dirent *) ((char *) dp + dp->d_reclen)) /*copy the current value into the list */ *(list + i) = dp; /*Nullify the last element of the list */ *(list + i) = NULL; /*Copy the required values in the parameters */ *dirent_data = data; *dirent_data_size = data_size; *dirent_list = list; /*Return success */ return err; } /*dir_entries_get */