Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/srv/fs/mfs/mfs_ops.c

    r36cb22f r4c3ad56  
    4343
    4444static bool check_magic_number(uint16_t magic, bool *native,
    45                                mfs_version_t *version, bool *longfilenames);
     45    mfs_version_t *version, bool *longfilenames);
    4646static int mfs_node_core_get(fs_node_t **rfn, struct mfs_instance *inst,
    47                              fs_index_t index);
    48 
     47    fs_index_t index);
    4948static int mfs_node_put(fs_node_t *fsnode);
    5049static int mfs_node_open(fs_node_t *fsnode);
     
    6463static hash_index_t open_nodes_hash(unsigned long key[]);
    6564static int open_nodes_compare(unsigned long key[], hash_count_t keys,
    66                 link_t *item);
     65    link_t *item);
    6766static void open_nodes_remove_cb(link_t *link);
    68 
    6967static int mfs_node_get(fs_node_t **rfn, service_id_t service_id,
    70                         fs_index_t index);
    71 static int
    72 mfs_instance_get(service_id_t service_id, struct mfs_instance **instance);
    73 
     68    fs_index_t index);
     69static int mfs_instance_get(service_id_t service_id,
     70    struct mfs_instance **instance);
     71static int mfs_check_sanity(struct mfs_sb_info *sbi);
     72static bool is_power_of_two(uint32_t n);
    7473
    7574static hash_table_t open_nodes;
     
    9695
    9796/* Hash table interface for open nodes hash table */
    98 static hash_index_t open_nodes_hash(unsigned long key[])
     97static hash_index_t
     98open_nodes_hash(unsigned long key[])
    9999{
    100100        /* TODO: This is very simple and probably can be improved */
     
    102102}
    103103
    104 static int open_nodes_compare(unsigned long key[], hash_count_t keys,
    105                 link_t *item)
     104static int
     105open_nodes_compare(unsigned long key[], hash_count_t keys,
     106    link_t *item)
    106107{
    107108        struct mfs_node *mnode = hash_table_get_instance(item, struct mfs_node, link);
     
    118119}
    119120
    120 static void open_nodes_remove_cb(link_t *link)
     121static void
     122open_nodes_remove_cb(link_t *link)
    121123{
    122124        /* We don't use remove callback for this hash table */
     
    129131};
    130132
    131 int mfs_global_init(void)
     133int
     134mfs_global_init(void)
    132135{
    133136        if (!hash_table_create(&open_nodes, OPEN_NODES_BUCKETS,
    134                         OPEN_NODES_KEYS, &open_nodes_ops)) {
     137            OPEN_NODES_KEYS, &open_nodes_ops)) {
    135138                return ENOMEM;
    136139        }
     
    140143static int
    141144mfs_mounted(service_id_t service_id, const char *opts, fs_index_t *index,
    142                 aoff64_t *size, unsigned *linkcnt)
     145    aoff64_t *size, unsigned *linkcnt)
    143146{
    144147        enum cache_mode cmode;
     
    163166                return rc;
    164167
    165         /*Allocate space for generic MFS superblock*/
     168        /* Allocate space for generic MFS superblock */
    166169        sbi = malloc(sizeof(*sbi));
    167170        if (!sbi) {
     
    170173        }
    171174
    172         /*Allocate space for filesystem instance*/
     175        /* Allocate space for filesystem instance */
    173176        instance = malloc(sizeof(*instance));
    174177        if (!instance) {
     
    191194
    192195        if (check_magic_number(sb->s_magic, &native, &version, &longnames)) {
    193                 /*This is a V1 or V2 Minix filesystem*/
     196                /* This is a V1 or V2 Minix filesystem */
    194197                magic = sb->s_magic;
    195198        } else if (check_magic_number(sb3->s_magic, &native, &version, &longnames)) {
    196                 /*This is a V3 Minix filesystem*/
     199                /* This is a V3 Minix filesystem */
    197200                magic = sb3->s_magic;
    198201        } else {
    199                 /*Not recognized*/
     202                /* Not recognized */
    200203                mfsdebug("magic number not recognized\n");
    201204                rc = ENOTSUP;
     
    205208        mfsdebug("magic number recognized = %04x\n", magic);
    206209
    207         /*Fill superblock info structure*/
     210        /* Fill superblock info structure */
    208211
    209212        sbi->fs_version = version;
     
    243246                sbi->dirsize = longnames ? MFSL_DIRSIZE : MFS_DIRSIZE;
    244247                sbi->max_name_len = longnames ? MFS_L_MAX_NAME_LEN :
    245                                     MFS_MAX_NAME_LEN;
     248                    MFS_MAX_NAME_LEN;
    246249        }
    247250
     
    259262
    260263        sbi->itable_off = 2 + sbi->ibmap_blocks + sbi->zbmap_blocks;
     264        if ((rc = mfs_check_sanity(sbi)) != EOK) {
     265                fprintf(stderr, "Filesystem corrupted, invalid superblock");
     266                goto out_error;
     267        }
    261268
    262269        rc = block_cache_init(service_id, sbi->block_size, 0, cmode);
     
    267274        }
    268275
    269         /*Initialize the instance structure and remember it*/
     276        /* Initialize the instance structure and remember it */
    270277        instance->service_id = service_id;
    271278        instance->sbi = sbi;
     
    273280        rc = fs_instance_create(service_id, instance);
    274281        if (rc != EOK) {
    275                 free(instance);
    276                 free(sbi);
    277282                block_cache_fini(service_id);
    278                 block_fini(service_id);
    279283                mfsdebug("fs instance creation failed\n");
    280                 return rc;
     284                goto out_error;
    281285        }
    282286
     
    331335}
    332336
    333 service_id_t mfs_service_get(fs_node_t *fsnode)
     337service_id_t
     338mfs_service_get(fs_node_t *fsnode)
    334339{
    335340        struct mfs_node *node = fsnode->data;
     
    337342}
    338343
    339 static int mfs_create_node(fs_node_t **rfn, service_id_t service_id, int flags)
     344static int
     345mfs_create_node(fs_node_t **rfn, service_id_t service_id, int flags)
    340346{
    341347        int r;
     
    351357                return r;
    352358
    353         /*Alloc a new inode*/
     359        /* Alloc a new inode */
    354360        r = mfs_alloc_inode(inst, &inum);
    355361        if (r != EOK)
     
    378384        if (flags & L_DIRECTORY) {
    379385                ino_i->i_mode = S_IFDIR;
    380                 ino_i->i_nlinks = 2; /*This accounts for the '.' dentry*/
    381         } else {
     386                ino_i->i_nlinks = 1; /* This accounts for the '.' dentry */
     387        } else
    382388                ino_i->i_mode = S_IFREG;
    383                 ino_i->i_nlinks = 1;
    384         }
    385389
    386390        ino_i->i_uid = 0;
     
    431435}
    432436
    433 static int mfs_match(fs_node_t **rfn, fs_node_t *pfn, const char *component)
     437static int
     438mfs_match(fs_node_t **rfn, fs_node_t *pfn, const char *component)
    434439{
    435440        struct mfs_node *mnode = pfn->data;
     
    453458
    454459                if (!d_info.d_inum) {
    455                         /*This entry is not used*/
     460                        /* This entry is not used */
    456461                        continue;
    457462                }
     
    460465
    461466                if (comp_size == dentry_name_size &&
    462                         !bcmp(component, d_info.d_name, dentry_name_size)) {
    463                         /*Hit!*/
     467                    !bcmp(component, d_info.d_name, dentry_name_size)) {
     468                        /* Hit! */
    464469                        mfs_node_core_get(rfn, mnode->instance,
    465                                           d_info.d_inum);
     470                            d_info.d_inum);
    466471                        goto found;
    467472                }
     
    472477}
    473478
    474 static aoff64_t mfs_size_get(fs_node_t *node)
     479static aoff64_t
     480mfs_size_get(fs_node_t *node)
    475481{
    476482        const struct mfs_node *mnode = node->data;
     
    480486static int
    481487mfs_node_get(fs_node_t **rfn, service_id_t service_id,
    482                         fs_index_t index)
     488    fs_index_t index)
    483489{
    484490        int rc;
     
    524530}
    525531
    526 static int mfs_node_open(fs_node_t *fsnode)
     532static int
     533mfs_node_open(fs_node_t *fsnode)
    527534{
    528535        /*
     
    533540}
    534541
    535 static fs_index_t mfs_index_get(fs_node_t *fsnode)
     542static fs_index_t
     543mfs_index_get(fs_node_t *fsnode)
    536544{
    537545        struct mfs_node *mnode = fsnode->data;
     
    539547}
    540548
    541 static unsigned mfs_lnkcnt_get(fs_node_t *fsnode)
     549static unsigned
     550mfs_lnkcnt_get(fs_node_t *fsnode)
    542551{
    543552        struct mfs_node *mnode = fsnode->data;
     
    554563}
    555564
    556 static int mfs_node_core_get(fs_node_t **rfn, struct mfs_instance *inst,
    557                              fs_index_t index)
     565static int
     566mfs_node_core_get(fs_node_t **rfn, struct mfs_instance *inst,
     567    fs_index_t index)
    558568{
    559569        fs_node_t *node = NULL;
     
    627637}
    628638
    629 static bool mfs_is_directory(fs_node_t *fsnode)
     639static bool
     640mfs_is_directory(fs_node_t *fsnode)
    630641{
    631642        const struct mfs_node *node = fsnode->data;
     
    633644}
    634645
    635 static bool mfs_is_file(fs_node_t *fsnode)
     646static bool
     647mfs_is_file(fs_node_t *fsnode)
    636648{
    637649        struct mfs_node *node = fsnode->data;
     
    639651}
    640652
    641 static int mfs_root_get(fs_node_t **rfn, service_id_t service_id)
     653static int
     654mfs_root_get(fs_node_t **rfn, service_id_t service_id)
    642655{
    643656        int rc = mfs_node_get(rfn, service_id, MFS_ROOT_INO);
     
    645658}
    646659
    647 static int mfs_link(fs_node_t *pfn, fs_node_t *cfn, const char *name)
     660static int
     661mfs_link(fs_node_t *pfn, fs_node_t *cfn, const char *name)
    648662{
    649663        struct mfs_node *parent = pfn->data;
     
    659673        if (r != EOK)
    660674                goto exit_error;
     675
     676        child->ino_i->i_nlinks++;
     677        child->ino_i->dirty = true;
    661678
    662679        if (S_ISDIR(child->ino_i->i_mode)) {
     
    720737}
    721738
    722 static int mfs_has_children(bool *has_children, fs_node_t *fsnode)
     739static int
     740mfs_has_children(bool *has_children, fs_node_t *fsnode)
    723741{
    724742        struct mfs_node *mnode = fsnode->data;
     
    741759
    742760                if (d_info.d_inum) {
    743                         /*A valid entry has been found*/
     761                        /* A valid entry has been found */
    744762                        *has_children = true;
    745763                        break;
     
    753771static int
    754772mfs_read(service_id_t service_id, fs_index_t index, aoff64_t pos,
    755                 size_t *rbytes)
     773    size_t *rbytes)
    756774{
    757775        int rc;
     
    783801
    784802                if (pos < 2) {
    785                         /*Skip the first two dentries ('.' and '..')*/
     803                        /* Skip the first two dentries ('.' and '..') */
    786804                        pos = 2;
    787805                }
     
    793811
    794812                        if (d_info.d_inum) {
    795                                 /*Dentry found!*/
     813                                /* Dentry found! */
    796814                                goto found;
    797815                        }
     
    809827
    810828                if (pos >= (size_t) ino_i->i_size) {
    811                         /*Trying to read beyond the end of file*/
     829                        /* Trying to read beyond the end of file */
    812830                        bytes = 0;
    813831                        (void) async_data_read_finalize(callid, NULL, 0);
     
    826844
    827845                if (zone == 0) {
    828                         /*sparse file*/
     846                        /* sparse file */
    829847                        uint8_t *buf = malloc(sbi->block_size);
    830848                        if (!buf) {
     
    834852                        memset(buf, 0, sizeof(sbi->block_size));
    835853                        async_data_read_finalize(callid,
    836                                                 buf + pos % sbi->block_size, bytes);
     854                            buf + pos % sbi->block_size, bytes);
    837855                        free(buf);
    838856                        goto out_success;
     
    844862
    845863                async_data_read_finalize(callid, b->data +
    846                                         pos % sbi->block_size, bytes);
     864                    pos % sbi->block_size, bytes);
    847865
    848866                rc = block_put(b);
     
    865883static int
    866884mfs_write(service_id_t service_id, fs_index_t index, aoff64_t pos,
    867                 size_t *wbytes, aoff64_t *nsize)
     885    size_t *wbytes, aoff64_t *nsize)
    868886{
    869887        fs_node_t *fn;
     
    900918
    901919        if (block == 0) {
    902                 /*Writing in a sparse block*/
    903920                uint32_t dummy;
    904921
     
    958975                return ENOENT;
    959976
    960         /*Destroy the inode*/
     977        /* Destroy the inode */
    961978        return mfs_destroy_node(fn);
    962979}
     
    977994        assert(!has_children);
    978995
    979         /*Free the entire inode content*/
     996        /* Free the entire inode content */
    980997        r = mfs_inode_shrink(mnode, mnode->ino_i->i_size);
    981998        if (r != EOK)
    982999                goto out;
    9831000
    984         /*Mark the inode as free in the bitmap*/
     1001        /* Mark the inode as free in the bitmap */
    9851002        r = mfs_free_inode(mnode->instance, mnode->ino_i->index);
    9861003
     
    10211038
    10221039        rc = fs_instance_get(service_id, &data);
    1023         if (rc == EOK) {
     1040        if (rc == EOK)
    10241041                *instance = (struct mfs_instance *) data;
    1025         } else {
     1042        else {
    10261043                mfsdebug("instance not found\n");
    10271044        }
     
    10301047}
    10311048
    1032 static bool check_magic_number(uint16_t magic, bool *native,
    1033                                mfs_version_t *version, bool *longfilenames)
     1049static bool
     1050check_magic_number(uint16_t magic, bool *native,
     1051                mfs_version_t *version, bool *longfilenames)
    10341052{
    10351053        bool rc = true;
     
    10591077}
    10601078
     1079/** Filesystem sanity check
     1080 *
     1081 * @param Pointer to the MFS superblock.
     1082 *
     1083 * @return EOK on success, ENOTSUP otherwise.
     1084 */
     1085static int
     1086mfs_check_sanity(struct mfs_sb_info *sbi)
     1087{
     1088        if (!is_power_of_two(sbi->block_size) ||
     1089            sbi->block_size < MFS_MIN_BLOCKSIZE ||
     1090            sbi->block_size > MFS_MAX_BLOCKSIZE)
     1091                return ENOTSUP;
     1092        else if (sbi->ibmap_blocks == 0 || sbi->zbmap_blocks == 0)
     1093                return ENOTSUP;
     1094        else if (sbi->ninodes == 0 || sbi->nzones == 0)
     1095                return ENOTSUP;
     1096        else if (sbi->firstdatazone == 0)
     1097                return ENOTSUP;
     1098
     1099        return EOK;
     1100}
     1101
    10611102static int
    10621103mfs_close(service_id_t service_id, fs_index_t index)
     
    10791120
    10801121        return mfs_node_put(fn);
     1122}
     1123
     1124/** Check if a given number is a power of two.
     1125 *
     1126 * @param n     The number to check.
     1127 *
     1128 * @return      true if it is a power of two, false otherwise.
     1129 */
     1130static bool
     1131is_power_of_two(uint32_t n)
     1132{
     1133        if (n == 0)
     1134                return false;
     1135
     1136        return (n & (n - 1)) == 0;
    10811137}
    10821138
Note: See TracChangeset for help on using the changeset viewer.