static int remove_block(ospfs_inode_t *oi) { // current number of blocks in file uint32_t n = ospfs_size2nblocks(oi->oi_size); uint32_t block_no = 0; uint32_t *ptr; // keep track of allocations to free in case of -ENOSPC uint32_t allocated[2] = { 0, 0 }; /* EXERCISE: Your code here */ if (0 < n && n <= OSPFS_NDIRECT) { oi->oi_direct[n - 1] = 0; free_block(n - 1); goto out; } // The block to be allocated has to be in indirect or indirect2 n -= OSPFS_NDIRECT; if (0 < n && n <= OSPFS_NINDIRECT) { if (oi->oi_indirect) { ptr = ospfs_block(oi->oi_indirect); free_block(ptr[n - 1]); ptr[n - 1] = 0; if ((n - 1) == 0) { free_block(oi->oi_indirect); oi->oi_indirect = 0; } } goto out; } // next block must lie in indirect2 n -= OSPFS_NINDIRECT; if (0 < n && n <= (OSPFS_NINDIRECT * OSPFS_NINDIRECT)) { uint32_t *ptrl1, *ptrl2; uint32_t level1 = (n - 1) / OSPFS_NINDIRECT; uint32_t level2 = (n - 1) % OSPFS_NINDIRECT; ptrl1 = ospfs_block(oi->oi_indirect2); ptrl2 = ospfs_block(ptrl1[level1]); if (ptrl2[level2]) { free_block(ptrl2[level2]); ptrl2[level2] = 0; } if (level2 == 0) { free_block(ptrl1[level1]); ptrl1[level1] = 0; if (level1 == 0) { free_block(oi->oi_indirect2); oi->oi_indirect2 = 0; } } } out: return 0; }
static int remove_block(ospfs_inode_t *oi) { // current number of blocks in file uint32_t n = ospfs_size2nblocks(oi->oi_size); //the nth block is the one to remove if (n < 0 || n > OSPFS_MAXFILEBLKS) return -EIO; if (n == 0) return 0; n--; //just remove n and free the block if (n < OSPFS_NDIRECT) { free_block(oi->oi_direct[n]); oi->oi_direct[n] = 0; } // we have single indirection else if (n < OSPFS_NDIRECT + OSPFS_NINDIRECT) { // actual indirect block in memory uint32_t* indirect_block = (uint32_t *) ospfs_block(oi->oi_indirect); // free the direct block, data block is simply unbound after freeing the direct block free_block(indirect_block[direct_index(n)]); // set the block number of n in the indirect block to 0 indirect_block[direct_index(n)] = 0; // if we freed the last block indirected to, we free the indirect block and variable as well if (!direct_index(n)) { free_block(oi->oi_indirect); oi->oi_indirect = 0; } } // ugh, double indirection else { uint32_t* indirect2_block = (uint32_t *) ospfs_block(oi->oi_indirect2); uint32_t* indirect_block = (uint32_t *) ospfs_block(indirect2_block[indir_index(n)]); // free the direct block free_block(indirect_block[direct_index(n)]); indirect_block[direct_index(n)] = 0; if (direct_index(n) == 0) { free_block(indirect2_block[indir_index(n)]); indirect2_block[indir_index(n)] = 0; } if (indir_index(n) == 0) { free_block(oi->oi_indirect2); oi->oi_indirect2 = 0; } } oi->oi_size = oi->oi_size - OSPFS_BLKSIZE; return 0; }
static uint32_t allocate_block(void) { /* EXERCISE: Your code here */ uint32_t i; for(i = 1; i < ospfs_super->os_nblocks; i++){ if(bitvector_test(ospfs_block(OSPFS_FREEMAP_BLK),i)){ bitvector_clear(ospfs_block(OSPFS_FREEMAP_BLK),i); return i; } } return 0; }
static void free_block(uint32_t blockno) { /* EXERCISE: Your code here */ if(blockno > ospfs_super->os_firstinob + ospfs_super->os_ninodes/OSPFS_BLKINODES && blockno < ospfs_super->os_nblocks) bitvector_set(ospfs_block(OSPFS_FREEMAP_BLK),blockno); }
static inline uint32_t ospfs_inode_blockno(ospfs_inode_t *oi, uint32_t offset) { uint32_t blockno = offset / OSPFS_BLKSIZE; if (offset >= oi->oi_size || oi->oi_ftype == OSPFS_FTYPE_SYMLINK) return 0; else if (blockno >= OSPFS_NDIRECT + OSPFS_NINDIRECT) { uint32_t blockoff = blockno - (OSPFS_NDIRECT + OSPFS_NINDIRECT); uint32_t *indirect2_block = ospfs_block(oi->oi_indirect2); uint32_t *indirect_block = ospfs_block(indirect2_block[blockoff / OSPFS_NINDIRECT]); return indirect_block[blockoff % OSPFS_NINDIRECT]; } else if (blockno >= OSPFS_NDIRECT) { uint32_t *indirect_block = ospfs_block(oi->oi_indirect); return indirect_block[blockno - OSPFS_NDIRECT]; } else return oi->oi_direct[blockno]; }
int mark_inode_bitmap(ospfs_inode_t *oi, uint8_t *bitmap) { int i, j; uint32_t *ptrl1, *ptrl2; int next_block = ospfs_size2nblocks(oi->oi_size); if (next_block == 0) { return 0; } for (i = 0; (i < OSPFS_NDIRECT) && oi->oi_direct[i]; i++) { bitvector_clear(bitmap, oi->oi_direct[i]); } if (i < OSPFS_NDIRECT || !oi->oi_indirect) { return 0; } next_block -= OSPFS_NDIRECT; bitvector_clear(bitmap, oi->oi_indirect); ptrl1 = ospfs_block(oi->oi_indirect); for (i = 0; i < OSPFS_NINDIRECT && ptrl1[i]; i++) { bitvector_clear(bitmap, ptrl1[i]); } if (i < OSPFS_NINDIRECT || !oi->oi_indirect2) { return 0; } next_block -= OSPFS_NINDIRECT; bitvector_clear(bitmap, oi->oi_indirect2); ptrl1 = ospfs_block(oi->oi_indirect); for (i = 0; i < OSPFS_NINDIRECT && ptrl1[i]; i++) { ptrl2 = ospfs_block(ptrl1[i]); bitvector_clear(bitmap, ptrl1[i]); for (j = 0; j < OSPFS_NINDIRECT && ptrl2[j]; j++) { bitvector_clear(bitmap, ptrl2[j]); } if (j < OSPFS_NINDIRECT) { break; } } return 0; }
static void zero_block(uint32_t block){ char *ptr = (char*)ospfs_block(block); int i; for(i = 0; i < OSPFS_BLKSIZE; i++){ ptr[i] = 0; } }
static ssize_t ospfs_read(struct file *filp, char __user *buffer, size_t count, loff_t *f_pos) { ospfs_inode_t *oi = ospfs_inode(filp->f_dentry->d_inode->i_ino); int retval = 0; size_t amount = 0; // Make sure we don't read past the end of the file! // Change 'count' so we never read past the end of the file. if(*f_pos > oi->oi_size) return 0; //we do not read past the end of the file if(*f_pos + count > oi->oi_size) count = oi->oi_size - *f_pos; /* EXERCISE: Your code here */ // Copy the data to user block by block while (amount < count && retval >= 0) { uint32_t blockno = ospfs_inode_blockno(oi, *f_pos); uint32_t n; char *data; //eprintk("reading!!"); // ospfs_inode_blockno returns 0 on error if (blockno == 0) { retval = -EIO; goto done; } data = ospfs_block(blockno); int offs = *f_pos % OSPFS_BLKSIZE; n = OSPFS_BLKSIZE - offs; int left = count - amount; n = (n > left) ? left : n; if(copy_to_user (buffer, data, n)) //if copy success return 0; { retval = -EFAULT; goto done; } //to: Destination address, in user space. //from: Source address, in kernel space. //n: Number of bytes to copy. // Figure out how much data is left in this block to read. // Copy data into user space. Return -EFAULT if unable to write // into user space. // Use variable 'n' to track number of bytes moved. /* EXERCISE: Your code here */ //retval = -EIO; // Replace these lines //goto done; buffer += n; amount += n; *f_pos += n; } done: return (retval >= 0 ? amount : retval); }
static inline ospfs_inode_t * ospfs_inode(ino_t ino) { ospfs_inode_t *oi; if (ino >= ospfs_super->os_ninodes) return 0; oi = ospfs_block(ospfs_super->os_firstinob); return &oi[ino]; }
static void free_block(uint32_t blockno) { void *bitmap = ospfs_block(OSPFS_FREEMAP_BLK); // TODO: check validity of block bitvector_set(bitmap, blockno); // mark as free (set i bit to 1) }
static void free_block(uint32_t blockno) { /* EXERCISE: Your code here */ if(blockno < ospfs_super->os_firstinob) return; bitvector_set(ospfs_block(blockno / OSPFS_BLKBITSIZE + OSPFS_FREEMAP_BLK), blockno % OSPFS_BLKBITSIZE); }
static int ospfs_symlink(struct inode *dir, struct dentry *dentry, const char *symname) { //eprintk("simlink"); ospfs_inode_t *dir_oi = ospfs_inode(dir->i_ino); uint32_t entry_ino = 0; //EXERCISE: Your code here. if (dentry->d_name.len > OSPFS_MAXNAMELEN) return -ENAMETOOLONG; if (find_direntry(dir_oi, dentry->d_name.name, dentry->d_name.len)) return -EEXIST; //create a new symlink inode ospfs_inode_t *free_inode = ospfs_block(ospfs_super->os_firstinob); uint32_t count = 1; while(count<ospfs_super->os_ninodes) { if (free_inode[count].oi_nlink == 0) break; count++; } //no free inode if (count == ospfs_super->os_ninodes) { count = 0; return -ENOSPC; } else entry_ino = count; //create new inode and entry; ospfs_symlink_inode_t* symlink_oi = ospfs_inode(entry_ino); ospfs_direntry_t * sym_dentry = create_blank_direntry(dir_oi); if (IS_ERR(sym_dentry)) return PTR_ERR(sym_dentry); //init symlink inode: if (strlen(symname)>OSPFS_MAXSYMLINKLEN) return -ENAMETOOLONG; symlink_oi->oi_size = strlen(symname); symlink_oi->oi_ftype = OSPFS_FTYPE_SYMLINK; symlink_oi->oi_nlink = 1; memcpy (symlink_oi->oi_symlink, symname, strlen(symname)); symlink_oi->oi_symlink[strlen(symname)] = '\0'; memcpy (sym_dentry->od_name, dentry->d_name.name, dentry->d_name.len); sym_dentry->od_name[dentry->d_name.len] = '\0'; sym_dentry->od_ino = entry_ino; //Execute this code after your function has successfully created the //file. Set entry_ino to the created file's inode number before //getting here. { struct inode *i = ospfs_mk_linux_inode(dir->i_sb, entry_ino); if (!i) return -ENOMEM; d_instantiate(dentry, i); return 0; } }
static int remove_block(ospfs_inode_t *oi) { // current number of blocks in file uint32_t n = ospfs_size2nblocks(oi->oi_size); /* EXERCISE: Your code here */ uint32_t blockno = n - 1; if (blockno >= OSPFS_NDIRECT + OSPFS_NINDIRECT) { uint32_t blockoff = blockno - (OSPFS_NDIRECT + OSPFS_NINDIRECT); uint32_t *indirect2_block; uint32_t *indirect_block; if (oi->oi_indirect2 == 0) return -EIO; indirect2_block = ospfs_block(oi->oi_indirect2); if (indirect2_block[blockoff / OSPFS_NINDIRECT] == 0) return -EIO; indirect_block = ospfs_block(indirect2_block[blockoff / OSPFS_NINDIRECT]); free_block(indirect_block[blockoff % OSPFS_NINDIRECT]); indirect_block[blockoff % OSPFS_NINDIRECT] = 0; if (blockoff % OSPFS_NINDIRECT == 0) { free_block(indirect2_block[blockoff / OSPFS_NINDIRECT]); indirect2_block[blockoff / OSPFS_NINDIRECT] = 0; if (blockno == OSPFS_NDIRECT + OSPFS_NINDIRECT) { free_block(oi->oi_indirect2); oi->oi_indirect2 = 0; } } } else if (blockno >= OSPFS_NDIRECT) { uint32_t *indirect_block = ospfs_block(oi->oi_indirect); if (oi->oi_indirect == 0) return -EIO; free_block(indirect_block[blockno - OSPFS_NINDIRECT]); if (blockno - OSPFS_NDIRECT == 0) free_block(oi->oi_indirect); } else { free_block(oi->oi_direct[blockno]); oi->oi_direct[blockno] = 0; } oi->oi_size -= OSPFS_BLKSIZE; return 0; }
static ssize_t ospfs_read(struct file *filp, char __user *buffer, size_t count, loff_t *f_pos) { ospfs_inode_t *oi = ospfs_inode(filp->f_dentry->d_inode->i_ino); int retval = 0; size_t amount = 0; // Make sure we don't read past the end of the file! // Change 'count' so we never read past the end of the file. /* DONE: Your code here */ if (count > oi->oi_size - *f_pos) { count = oi->oi_size - *f_pos; } // Copy the data to user block by block while (amount < count && retval >= 0) { uint32_t blockno = ospfs_inode_blockno(oi, *f_pos); uint32_t n; char *data; // ospfs_inode_blockno returns 0 on error if (blockno == 0) { retval = -EIO; goto done; } data = ospfs_block(blockno); // Figure out how much data is left in this block to read. // Copy data into user space. Return -EFAULT if unable to write // into user space. // Use variable 'n' to track number of bytes moved. //goto done; long block_pos = *f_pos % OSPFS_BLKSIZE; if (count - amount > OSPFS_BLKSIZE - block_pos) { n = OSPFS_BLKSIZE - block_pos; } else { n = count - amount; } retval = copy_to_user(buffer, data + block_pos, n); if (retval != 0) { return -EFAULT; } buffer += n; amount += n; *f_pos += n; } done: return (retval >= 0 ? amount : retval); }
/* Return Newly allocated block number */ static uint32_t _add_block(int *ptr) { uint32_t block_no = allocate_block(); if (block_no) { *ptr = block_no; memset(ospfs_block(block_no), 0, OSPFS_BLKSIZE); } return block_no; }
static void free_block(uint32_t blockno) { /* DONE: Your code here */ // will not free boot, super, bitmap, or inode blocks if (blockno > ospfs_super->os_firstinob + OSPFS_BLKINODES){ void* bitvector = ospfs_block(OSPFS_FREEMAP_BLK); bitvector_set(bitvector, blockno); } return 0; }
static ssize_t ospfs_write(struct file *filp, const char __user *buffer, size_t count, loff_t *f_pos) { ospfs_inode_t *oi = ospfs_inode(filp->f_dentry->d_inode->i_ino); int retval = 0; size_t amount = 0; // Support files opened with the O_APPEND flag. To detect O_APPEND, // use struct file's f_flags field and the O_APPEND bit. /* EXERCISE: Your code here */ int append = filp->f_flags & O_APPEND; if (append) *f_pos = oi->oi_size; // If the user is writing past the end of the file, change the file's // size to accomodate the request. (Use change_size().) /* EXERCISE: Your code here */ if (count > oi->oi_size - *f_pos) { change_size(oi, count + oi->oi_size); } // Copy data block by block while (amount < count && retval >= 0) { uint32_t blockno = ospfs_inode_blockno(oi, *f_pos); uint32_t n; char *data; if (blockno == 0) { retval = -EIO; goto done; } data = ospfs_block(blockno); // Figure out how much data is left in this block to write. // Copy data from user space. Return -EFAULT if unable to read // read user space. // Keep track of the number of bytes moved in 'n'. /* EXERCISE: Your code here */ n = count - amount; //left to write! if (n > OSPFS_BLKSIZE) n = OSPFS_BLKSIZE; if (copy_from_user(data + *f_pos, buffer, n) != 0) { return -EFAULT; } buffer += n; amount += n; *f_pos += n; } done: return (retval >= 0 ? amount : retval); }
static int remove_block(ospfs_inode_t *oi) { // current number of blocks in file uint32_t n = ospfs_size2nblocks(oi->oi_size); if(indir2_index(n)==0) { uint32_t *id2_block = ospfs_block(oi->oi_indirect2); uint32_t id2_off = indir_index(n); uint32_t *id_block = ospfs_block(id2_block[id2_off]); uint32_t d_off = direct_index(n); if(d_off == 0)//d_off == 0 means the direct is null which should make id2_block[id2_off] null { id2_block[id2_off] = NULL; if(id2_off == 0) oi->oi_indirect2 = NULL; } free_block(id_block[d_off]); id_block[d_off] = NULL; } else if(indir_index(n)==0) { uint32_t *id_block = ospfs_block(oi->oi_indirect); uint32_t d_off = direct_index(n); if(d_off == 0)//d_off == 0 means the direct is null which should make id2_block[id2_off] null { oi->oi_indirect = NULL; } free_block(id_block[d_off]); id_block[d_off] = NULL; } else { uint32_t d_off = direct_index(n); free_block(oi->oi_direct[d_off]); oi->oi_direct[d_off] = NULL; } /* EXERCISE: Your code here */ oi->oi_size = (n-1)*OSPFS_BLKSIZE; return 0; // Replace this line }
static void free_block(uint32_t blockno) { /* EXERCISE: Your code here */ void* input_bitmap = ospfs_block(OSPFS_FREEMAP_BLK); int upperlimit = ospfs_super->os_nblocks; //make sure our blocknumber is within the bounds, then call set on that blocknumber if (blockno > OSPFS_FREEMAP_BLK && blockno < upperlimit) { bitvector_set(input_bitmap, blockno); } else printk("Error! Invalid block number to be freed\n"); }
static void free_block(uint32_t blockno) { /* EXERCISE: Your code here */ //might want to add in functionality so that it skips all inode blocks int min_blocks = ospfs_super->os_firstinob; void *bitmap = ospfs_block(OSPFS_FREEMAP_BLK); if(blockno > min_blocks && blockno < OSPFS_MAXFILEBLKS){ if(bitvector_test(bitmap, blockno) == 0){ bitvector_set(bitmap, blockno); } } }
static int remove_block(ospfs_inode_t *oi) { // current number of blocks in file uint32_t n = ospfs_size2nblocks(oi->oi_size); /* EXERCISE: Your code here */ if(n < 0) return -EIO; else if(n == 0) return 0; int index = n-1; if(index < OSPFS_NDIRECT){ free_block(oi->oi_direct[index]); oi->oi_direct[index] = 0; } else if(index < OSPFS_NDIRECT + OSPFS_NINDIRECT && index > OSPFS_NDIRECT){ uint32_t* indirect_block = (uint32_t *)ospfs_block(oi->oi_indirect); free_block(indirect_block[direct_index(index)]); indirect_block[direct_index(index)] = 0; free_block(oi->oi_indirect); oi->oi_indirect = 0; } else if(index < OSPFS_MAXFILEBLKS){ uint32_t * indirect2_block = (uint32_t *) ospfs_block(oi->oi_indirect2); uint32_t * indirect_block = (uint32_t *) ospfs_block(indirect2_block[indir_index(index)]); free_block(indirect_block[direct_index(index)]); indirect_block[direct_index(index)] = 0; free_block(indirect2_block[indir_index(index)]); indirect2_block[indir_index(index)] = 0; free_block(oi->oi_indirect2); oi->oi_indirect2 = 0; } else return -EIO; oi->oi_size -= OSPFS_BLKSIZE; return 0; }
static int remove_block(ospfs_inode_t *oi) { // current number of blocks in file uint32_t n = ospfs_size2nblocks(oi->oi_size) - 1; /* EXERCISE: Your code here */ //3 cases: below OSPFS_NDIRECT, below OSPFS_NDIRECT+OSPFS_NINDIRECT, below OSPFS_NDIRECT+OSPFS_NINDRECT+OSPFS_NINDIRECT^2 uint32_t* block; if(n <= OSPFS_NDIRECT) free_block(oi->oi_direct[n]); else if(n <= (OSPFS_NDIRECT + OSPFS_NINDIRECT)) { block = ospfs_block(oi->oi_indirect); free_block(block[n-OSPFS_NDIRECT]); if(n == OSPFS_NDIRECT+1) free_block(oi->oi_indirect); } else if(n <= (OSPFS_NINDIRECT + OSPFS_NDIRECT + (OSPFS_NINDIRECT*OSPFS_NINDIRECT))) { block = ospfs_block(oi->oi_indirect2); //edge cases: if ((n-OSPFS_NDIRECT-OSPFS_NINDIRECT)%OSPFS_NINDIRECT == 0) free_block(block[(n-OSPFS_NDIRECT-OSPFS_NINDIRECT)%OSPFS_NINDIRECT]); if ((n-OSPFS_NDIRECT-OSPFS_NINDIRECT)/OSPFS_NINDIRECT == 0) free_block(block[(n-OSPFS_NDIRECT-OSPFS_NINDIRECT)/OSPFS_NINDIRECT]); //otherwise: free_block(oi->oi_indirect2); } else return -EIO; oi->oi_size = n * OSPFS_BLKSIZE; return 0; }
static ssize_t ospfs_write(struct file *filp, const char __user *buffer, size_t count, loff_t *f_pos) { ospfs_inode_t *oi = ospfs_inode(filp->f_dentry->d_inode->i_ino); int retval = 0; size_t amount = 0; // Support files opened with the O_APPEND flag. To detect O_APPEND, // use struct file's f_flags field and the O_APPEND bit. /* EXERCISE: Your code here */ // If the user is writing past the end of the file, change the file's // size to accomodate the request. (Use change_size().) /* EXERCISE: Your code here */ // Copy data block by block while (amount < count && retval >= 0) { uint32_t blockno = ospfs_inode_blockno(oi, *f_pos); uint32_t n; char *data; if (blockno == 0) { retval = -EIO; goto done; } data = ospfs_block(blockno); //unsigned long copy_from_user ( (void *) ,(const void __user *) buffer, unsigned long count); // Returns: a pointer to that block's data //to Destination address, in kernel space. //from: Source address, in user space. //n: Number of bytes to copy. // Figure out how much data is left in this block to write. // Copy data from user space. Return -EFAULT if unable to read // read user space. // Keep track of the number of bytes moved in 'n'. /* EXERCISE: Your code here */ retval = -EIO; // Replace these lines goto done; buffer += n; amount += n; *f_pos += n; } done: return (retval >= 0 ? amount : retval); }
static uint32_t allocate_block(void) { void *bitmap = ospfs_block(OSPFS_FREEMAP_BLK); int i; // iterate through bitmap vector and return first free block for (i = 0; i < ospfs_super->os_nblocks; i++) { if (bitvector_test(bitmap, i)) { bitvector_clear(bitmap, i); // mark as used (set i bit to 0) return i; } } return 0; }
static void free_block(uint32_t blockno) { /* EXERCISE: Your code here */ /* EXERCISE: Your code here */ if(blockno < ospfs_super->os_firstinob || blockno >= ospfs_super->os_nblocks) return; void *bitmap = ospfs_block(OSPFS_FREEMAP_BLK); /// bitvector_set -- Set 'i'th bit of 'vector' to 1. bitvector_set(bitmap, blockno); }
static uint32_t allocate_block(void) { /* DONE: Your code here */ int bits_in_bitmap = ospfs_super->os_nblocks; // also is the number of blocks in our entire FS int x; void* bitvector = ospfs_block(OSPFS_FREEMAP_BLK); for (x = 0; x < bits_in_bitmap; x++) { if (bitvector_test(bitvector, x)) { bitvector_clear(bitvector, x); return x; } } return 0; }
static ssize_t ospfs_read(struct file *filp, char __user *buffer, size_t count, loff_t *f_pos) { ospfs_inode_t *oi = ospfs_inode(filp->f_dentry->d_inode->i_ino); int retval = 0; size_t amount = 0; /* EXERCISE: Your code here */ //Never let count request more data than the file size if(count > oi->oi_size - *f_pos) count = oi->oi_size - *f_pos; // Copy the data to user block by block while (amount < count && retval >= 0) { uint32_t blockno = ospfs_inode_blockno(oi, *f_pos); uint32_t n; char *data; // ospfs_inode_blockno returns 0 on error if (blockno == 0) { retval = -EIO; goto done; } data = ospfs_block(blockno); /* EXERCISE: Your code here */ //Calulate amount of block left needed to copy n = count-amount; //Calculate offset of f_pos from a multiple of blocksize uint32_t offset = *f_pos % OSPFS_BLKSIZE; if(count-amount > OSPFS_BLKSIZE - offset){ n = OSPFS_BLKSIZE - offset; } if(copy_to_user(buffer, data + offset, n) != 0){ //eprintk("Unable to write into user space.\n"); retval = -EFAULT; goto done; } buffer += n; amount += n; *f_pos += n; } done: return (retval >= 0 ? amount : retval); }
static uint32_t allocate_block(void) { int i; /* EXERCISE: Your code here */ void *free_map = ospfs_block(OSPFS_FREEMAP_BLK); for (i = OSPFS_FREEMAP_BLK; i < ospfs_super->os_nblocks; i++) { if (bitvector_test(free_map, i)) { bitvector_clear(free_map, i); break; } } return (i == ospfs_super->os_nblocks) ? 0 : i; }
static uint32_t allocate_block(void) { /* EXERCISE: Your code here */ int i; for (i = OSPFS_FREEMAP_BLK; i < ospfs_super->os_firstinob; i++) { char *bitvector = ospfs_block(i); int j = 0; for (j = 0; j < OSPFS_BLKBITSIZE; j++) { if (bitvector_test(bitvector, j)) { bitvector_clear(bitvector, j); return (i - OSPFS_FREEMAP_BLK) * OSPFS_BLKBITSIZE + j; } } } return 0; }
static uint32_t allocate_block(void) { /* EXERCISE: Your code here */ void *bitmap = ospfs_block(OSPFS_FREEMAP_BLK); //check for free blocks. 0-2 blocks are always reserved so start at 3. int i; for(i = OSPFS_FREEMAP_BLK+1; i < ospfs_super->os_nblocks; i++){ if(bitvector_test(bitmap, i) == 1){ bitvector_clear(bitmap, i); return i; } } return 0; }