Changeset 565b6ff in mainline for uspace/lib/ext4/libext4_directory.c


Ignore:
Timestamp:
2012-02-05T12:35:02Z (12 years ago)
Author:
Frantisek Princ <frantisek.princ@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
50601ef
Parents:
512a7df
Message:
  • bugfix in adding directory entry (linear)
  • added skeleton for using directory index (not used yet)
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/ext4/libext4_directory.c

    r512a7df r565b6ff  
    278278}
    279279
    280 int ext4_directory_add_entry(ext4_filesystem_t *fs, ext4_inode_ref_t * inode_ref,
     280int ext4_directory_add_entry(ext4_filesystem_t *fs, ext4_inode_ref_t * parent,
    281281                const char *entry_name, ext4_inode_ref_t *child)
    282282{
    283283        int rc;
    284284
    285         // USE index if allowed
     285        EXT4FS_DBG("adding entry to directory \%u [ino = \%u, name = \%s]", parent->index, child->index, entry_name);
    286286
    287287        uint16_t name_len = strlen(entry_name);
     288
     289        // Index adding (if allowed)
     290        if (ext4_superblock_has_feature_compatible(fs->superblock, EXT4_FEATURE_COMPAT_DIR_INDEX) &&
     291                        ext4_inode_has_flag(parent->inode, EXT4_INODE_FLAG_INDEX)) {
     292
     293                EXT4FS_DBG("trying INDEX");
     294
     295                rc = ext4_directory_dx_add_entry(fs, parent, name_len, entry_name);
     296
     297                // Check if index is not corrupted
     298                if (rc != EXT4_ERR_BAD_DX_DIR) {
     299
     300                        if (rc != EOK) {
     301                                return rc;
     302                        }
     303
     304                        return EOK;
     305                }
     306
     307                // Needed to clear dir index flag
     308                ext4_inode_clear_flag(parent->inode, EXT4_INODE_FLAG_INDEX);
     309                parent->dirty = true;
     310
     311                EXT4FS_DBG("index is corrupted - doing linear algorithm, index flag cleared");
     312        }
     313
     314        // Linear algorithm
    288315        uint16_t required_len = 8 + name_len + (4 - name_len % 4);
    289316
    290317        ext4_directory_iterator_t it;
    291         rc = ext4_directory_iterator_init(&it, fs, inode_ref, 0);
     318        rc = ext4_directory_iterator_init(&it, fs, parent, 0);
    292319        if (rc != EOK) {
    293320                return rc;
    294321        }
     322
     323        uint32_t block_size = ext4_superblock_get_block_size(fs->superblock);
    295324
    296325        while (it.current != NULL) {
     
    310339                        uint16_t used_name_len = ext4_directory_entry_ll_get_name_length(
    311340                                        fs->superblock, it.current);
    312                         uint16_t free_space = rec_len - 8 - (used_name_len + (4- used_name_len % 4));
     341
     342                        uint16_t used_space = 8 + used_name_len;
     343                        if ((used_name_len % 4) != 0) {
     344                                used_space += 4 - (used_name_len % 4);
     345                        }
     346                        uint16_t free_space = rec_len - used_space;
     347
     348                        EXT4FS_DBG("rec_len = \%u, used_space = \%u, free space = \%u", rec_len, used_space, free_space);
    313349
    314350                        if (free_space >= required_len) {
     
    319355
    320356                                // SEEK manually
    321                                 it.current_offset += used_len;
    322                                 ext4_directory_entry_ll_t *new_entry = it.current_block->data + it.current_offset;
     357                                uint32_t local_offset = (it.current_offset % block_size);
     358                                local_offset += used_len;
     359                                ext4_directory_entry_ll_t *new_entry = it.current_block->data + local_offset;
    323360
    324361                                // We are sure, that both entries are in the same data block
     
    344381
    345382        // Compute next block index and allocate data block
    346         uint32_t block_size = ext4_superblock_get_block_size(fs->superblock);
    347383        uint32_t block_idx = pos / block_size;
    348384
    349385        uint32_t fblock;
    350         rc = ext4_filesystem_get_inode_data_block_index(fs, inode_ref->inode, block_idx, &fblock);
     386        rc = ext4_filesystem_get_inode_data_block_index(fs, parent->inode, block_idx, &fblock);
    351387        if (rc != EOK) {
    352388                return rc;
     
    354390
    355391        if (fblock == 0) {
    356                 rc =  ext4_balloc_alloc_block(fs, inode_ref, &fblock);
    357                 if (rc != EOK) {
    358                         return rc;
    359                 }
    360 
    361                 rc = ext4_filesystem_set_inode_data_block_index(fs, inode_ref, block_idx, fblock);
    362                 if (rc != EOK) {
    363                         ext4_balloc_free_block(fs, inode_ref, fblock);
    364                         return rc;
    365                 }
    366 
    367                 uint64_t inode_size = ext4_inode_get_size(fs->superblock, inode_ref->inode);
     392                rc =  ext4_balloc_alloc_block(fs, parent, &fblock);
     393                if (rc != EOK) {
     394                        return rc;
     395                }
     396
     397                rc = ext4_filesystem_set_inode_data_block_index(fs, parent, block_idx, fblock);
     398                if (rc != EOK) {
     399                        ext4_balloc_free_block(fs, parent, fblock);
     400                        return rc;
     401                }
     402
     403                uint64_t inode_size = ext4_inode_get_size(fs->superblock, parent->inode);
    368404                inode_size += block_size;
    369                 ext4_inode_set_size(inode_ref->inode, inode_size);
    370 
    371                 inode_ref->dirty = true;
     405                ext4_inode_set_size(parent->inode, inode_size);
     406
     407                parent->dirty = true;
    372408        }
    373409
     
    418454
    419455                EXT4FS_DBG("index is corrupted - doing linear search");
     456
     457                // TODO Needed to clear dir index flag
     458                //ext4_inode_clear_flag(parent->inode, EXT4_INODE_FLAG_INDEX);
     459                //parent->dirty = true;
     460
    420461        }
    421462
Note: See TracChangeset for help on using the changeset viewer.