struct block_device *bdget(dev_t dev)

struct bdev_inode {
    struct block_device bdev;
    struct inode vfs_inode;
};

struct block_device *bdget(dev_t dev)

{

    struct block_device *bdev;
    struct inode *inode;

    inode = iget5_locked(blockdev_superblock, hash(dev),bdev_test, bdev_set, &dev);    //bdev_test, bdev_set函数不允许睡眠

    if (!inode)
        return NULL;

    bdev = &BDEV_I(inode)->bdev;

    if (inode->i_state & I_NEW) {
        bdev->bd_contains = NULL;
        bdev->bd_inode = inode;
        bdev->bd_block_size = (1 << inode->i_blkbits);
        bdev->bd_part_count = 0;
        bdev->bd_invalidated = 0;
        inode->i_mode = S_IFBLK;
        inode->i_rdev = dev;
        inode->i_bdev = bdev;
        inode->i_data.a_ops = &def_blk_aops;
        mapping_set_gfp_mask(&inode->i_data, GFP_USER);
        inode->i_data.backing_dev_info = &default_backing_dev_info;
        spin_lock(&bdev_lock);
        list_add(&bdev->bd_list, &all_bdevs);
        spin_unlock(&bdev_lock);
        unlock_new_inode(inode);
    }
    return bdev;

}

给定dev_t dev,可通过该函数查找或创建请求的块设备。

struct inode *iget5_locked(struct super_block *sb, unsigned long hashval,
        int (*test)(struct inode *, void *),
        int (*set)(struct inode *, void *), void *data)
{
    struct hlist_head *head = inode_hashtable + hash(sb, hashval);
    struct inode *inode;

    inode = ifind(sb, head, test, data, 1);
    if (inode)
        return inode;
    /*
     * get_new_inode() will do the right thing, re-trying the search
     * in case it had to block at any point.
     */
    return get_new_inode(sb, head, test, set, data);
}

iget5_locked(...)使用ifind()函数查找由hashval和data指定的inode或创建新的inode.

该inode经过container_of获取bdev_inode类型指针

然后由获得的bdev_inode指针对 struct block_device bdev进行操作。如果是新创建的,则初始化;否则直接返回以创建的bdev.


你可能感兴趣的:(struct,list,user,null,search)