Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/ext2/libext2_directory.c

    r4e36219 r911ee54  
    8686 * @param fs pointer to filesystem structure
    8787 * @param inode pointer to inode reference structure
    88  * @param pos position within inode to start at, 0 is the first entry
    8988 * @return EOK on success or negative error code on failure
    9089 */
    9190int ext2_directory_iterator_init(ext2_directory_iterator_t *it,
    92     ext2_filesystem_t *fs, ext2_inode_ref_t *inode_ref, aoff64_t pos)
    93 {       
     91    ext2_filesystem_t *fs, ext2_inode_ref_t *inode_ref)
     92{
     93        int rc;
     94        uint32_t block_id;
     95        uint32_t block_size;
     96       
    9497        it->inode_ref = inode_ref;
    9598        it->fs = fs;
    96         it->current = NULL;
    97         it->current_offset = 0;
    98         it->current_block = NULL;
    99        
    100         return ext2_directory_iterator_seek(it, pos);
     99       
     100        /* Get the first data block, so we can get the first entry */
     101        rc = ext2_filesystem_get_inode_data_block_index(fs, inode_ref->inode, 0,
     102            &block_id);
     103        if (rc != EOK) {
     104                return rc;
     105        }
     106       
     107        rc = block_get(&it->current_block, fs->device, block_id, 0);
     108        if (rc != EOK) {
     109                return rc;
     110        }
     111       
     112        block_size = ext2_superblock_get_block_size(fs->superblock);
     113       
     114        it->current_offset = 0;
     115        return ext2_directory_iterator_set(it, block_size);
    101116}
    102117
     
    109124int ext2_directory_iterator_next(ext2_directory_iterator_t *it)
    110125{
     126        int rc;
    111127        uint16_t skip;
    112        
    113         assert(it->current != NULL);
    114        
    115         skip = ext2_directory_entry_ll_get_entry_length(it->current);
    116        
    117         return ext2_directory_iterator_seek(it, it->current_offset + skip);
    118 }
    119 
    120 /**
    121  * Seek the directory iterator to the given byte offset within the inode.
    122  *
    123  * @param it pointer to iterator to initialize
    124  * @return EOK on success or negative error code on failure
    125  */
    126 int ext2_directory_iterator_seek(ext2_directory_iterator_t *it, aoff64_t pos)
    127 {
    128         int rc;
    129        
    130128        uint64_t size;
    131129        aoff64_t current_block_idx;
     
    134132        uint32_t block_size;
    135133       
     134        assert(it->current != NULL);
     135       
     136        skip = ext2_directory_entry_ll_get_entry_length(it->current);
    136137        size = ext2_inode_get_size(it->fs->superblock, it->inode_ref->inode);
    137138       
    138         /* The iterator is not valid until we seek to the desired position */
    139         it->current = NULL;
    140        
    141139        /* Are we at the end? */
    142         if (pos >= size) {             
    143                 if (it->current_block) {
    144                         rc = block_put(it->current_block);
    145                         it->current_block = NULL;
    146                         if (rc != EOK) {
    147                                 return rc;
    148                         }
     140        if (it->current_offset + skip >= size) {
     141                rc = block_put(it->current_block);
     142                it->current_block = NULL;
     143                it->current = NULL;
     144                if (rc != EOK) {
     145                        return rc;
    149146                }
    150147               
    151                 it->current_offset = pos;
     148                it->current_offset += skip;
    152149                return EOK;
    153150        }
     
    155152        block_size = ext2_superblock_get_block_size(it->fs->superblock);
    156153        current_block_idx = it->current_offset / block_size;
    157         next_block_idx = pos / block_size;
    158        
    159         /* If we don't have a block or are moving accross block boundary,
     154        next_block_idx = (it->current_offset + skip) / block_size;
     155       
     156        /* If we are moving accross block boundary,
    160157         * we need to get another block
    161158         */
    162         if (it->current_block == NULL || current_block_idx != next_block_idx) {         
    163                 if (it->current_block) {
    164                         rc = block_put(it->current_block);
    165                         it->current_block = NULL;
    166                         if (rc != EOK) {
    167                                 return rc;
    168                         }
     159        if (current_block_idx != next_block_idx) {
     160                rc = block_put(it->current_block);
     161                it->current_block = NULL;
     162                it->current = NULL;
     163                if (rc != EOK) {
     164                        return rc;
    169165                }
    170166               
     
    183179        }
    184180       
    185         it->current_offset = pos;
     181        it->current_offset += skip;
    186182        return ext2_directory_iterator_set(it, block_size);
    187183}
    188184
    189 /** Setup the entry at the current iterator offset.
    190  *
    191  * This function checks the validity of the directory entry,
    192  * before setting the data pointer.
    193  *
    194  * @return EOK on success or error code on failure
    195  */
    196185static int ext2_directory_iterator_set(ext2_directory_iterator_t *it,
    197186    uint32_t block_size)
Note: See TracChangeset for help on using the changeset viewer.