⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 llite_lib.c

📁 lustre 1.6.5 source code
💻 C
📖 第 1 页 / 共 5 页
字号:
        err = mdc_getstatus(sbi->ll_mdc_exp, &rootfid);        if (err) {                CERROR("cannot mds_connect: rc = %d\n", err);                GOTO(out_lock_cn_cb, err);        }        CDEBUG(D_SUPER, "rootfid "LPU64"\n", rootfid.id);        sbi->ll_rootino = rootfid.id;        sb->s_op = &lustre_super_operations;#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))        sb->s_export_op = &lustre_export_operations;#endif        /* make root inode         * XXX: move this to after cbd setup? */        err = mdc_getattr(sbi->ll_mdc_exp, &rootfid,                          OBD_MD_FLGETATTR | OBD_MD_FLBLOCKS |                          (sbi->ll_flags & LL_SBI_ACL ? OBD_MD_FLACL : 0),                          0, &request);        if (err) {                CERROR("mdc_getattr failed for root: rc = %d\n", err);                GOTO(out_lock_cn_cb, err);        }        err = mdc_req2lustre_md(request, REPLY_REC_OFF, sbi->ll_osc_exp, &md);        if (err) {                CERROR("failed to understand root inode md: rc = %d\n",err);                ptlrpc_req_finished (request);                GOTO(out_lock_cn_cb, err);        }        LASSERT(sbi->ll_rootino != 0);        root = ll_iget(sb, sbi->ll_rootino, &md);        ptlrpc_req_finished(request);        if (root == NULL || is_bad_inode(root)) {                mdc_free_lustre_md(sbi->ll_osc_exp, &md);                CERROR("lustre_lite: bad iget4 for root\n");                GOTO(out_root, err = -EBADF);        }        err = ll_close_thread_start(&sbi->ll_lcq);        if (err) {                CERROR("cannot start close thread: rc %d\n", err);                GOTO(out_root, err);        }        checksum = sbi->ll_flags & LL_SBI_DATA_CHECKSUM;        err = obd_set_info_async(sbi->ll_osc_exp, strlen("checksum"),                                 "checksum", sizeof(checksum),                                 &checksum, NULL);        /* making vm readahead 0 for 2.4.x. In the case of 2.6.x,           backing dev info assigned to inode mapping is used for           determining maximal readahead. */#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0)) && \    !defined(KERNEL_HAS_AS_MAX_READAHEAD)        /* bug 2805 - set VM readahead to zero */        vm_max_readahead = vm_min_readahead = 0;#endif        sb->s_root = d_alloc_root(root);        if (data != NULL)                OBD_FREE(data, sizeof(*data));        sb->s_root->d_op = &ll_d_root_ops;        RETURN(err);out_root:        if (root)                iput(root);out_lock_cn_cb:        obd_unregister_lock_cancel_cb(sbi->ll_osc_exp,                                      ll_extent_lock_cancel_cb);out_page_rm_cb:        obd_unregister_page_removal_cb(sbi->ll_osc_exp,                                       ll_page_removal_cb);out_osc:        obd_disconnect(sbi->ll_osc_exp);        sbi->ll_osc_exp = NULL;out_mdc:        obd_disconnect(sbi->ll_mdc_exp);        sbi->ll_mdc_exp = NULL;out:        if (data != NULL)                OBD_FREE(data, sizeof(*data));        lprocfs_unregister_mountpoint(sbi);        RETURN(err);}int ll_get_max_mdsize(struct ll_sb_info *sbi, int *lmmsize){        int size, rc;        *lmmsize = obd_size_diskmd(sbi->ll_osc_exp, NULL);        size = sizeof(int);        rc = obd_get_info(sbi->ll_mdc_exp, strlen("max_easize"), "max_easize",                          &size, lmmsize);        if (rc)                CERROR("Get max mdsize error rc %d \n", rc);        RETURN(rc);}void ll_dump_inode(struct inode *inode){        struct list_head *tmp;        int dentry_count = 0;        LASSERT(inode != NULL);        list_for_each(tmp, &inode->i_dentry)                dentry_count++;        CERROR("inode %p dump: dev=%s ino=%lu mode=%o count=%u, %d dentries\n",               inode, ll_i2mdcexp(inode)->exp_obd->obd_name, inode->i_ino,               inode->i_mode, atomic_read(&inode->i_count), dentry_count);}void lustre_dump_dentry(struct dentry *dentry, int recur){        struct list_head *tmp;        int subdirs = 0;        LASSERT(dentry != NULL);        list_for_each(tmp, &dentry->d_subdirs)                subdirs++;        CERROR("dentry %p dump: name=%.*s parent=%.*s (%p), inode=%p, count=%u,"               " flags=0x%x, fsdata=%p, %d subdirs\n", dentry,               dentry->d_name.len, dentry->d_name.name,               dentry->d_parent->d_name.len, dentry->d_parent->d_name.name,               dentry->d_parent, dentry->d_inode, atomic_read(&dentry->d_count),               dentry->d_flags, dentry->d_fsdata, subdirs);        if (dentry->d_inode != NULL)                ll_dump_inode(dentry->d_inode);        if (recur == 0)                return;        list_for_each(tmp, &dentry->d_subdirs) {                struct dentry *d = list_entry(tmp, struct dentry, d_child);                lustre_dump_dentry(d, recur - 1);        }}#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0))void lustre_throw_orphan_dentries(struct super_block *sb){        struct dentry *dentry, *next;        struct ll_sb_info *sbi = ll_s2sbi(sb);        /* Do this to get rid of orphaned dentries. That is not really trw. */        list_for_each_entry_safe(dentry, next, &sbi->ll_orphan_dentry_list,                                 d_hash) {                CWARN("found orphan dentry %.*s (%p->%p) at unmount, dumping "                      "before and after shrink_dcache_parent\n",                      dentry->d_name.len, dentry->d_name.name, dentry, next);                lustre_dump_dentry(dentry, 1);                shrink_dcache_parent(dentry);                lustre_dump_dentry(dentry, 1);        }}#else#define lustre_throw_orphan_dentries(sb)#endif#ifdef HAVE_EXPORT___IGETstatic void prune_dir_dentries(struct inode *inode){        struct dentry *dentry, *prev = NULL;        /* due to lustre specific logic, a directory         * can have few dentries - a bug from VFS POV */restart:        spin_lock(&dcache_lock);        if (!list_empty(&inode->i_dentry)) {                dentry = list_entry(inode->i_dentry.prev,                                    struct dentry, d_alias);                /* in order to prevent infinite loops we                 * break if previous dentry is busy */                if (dentry != prev) {                        prev = dentry;                        dget_locked(dentry);                        spin_unlock(&dcache_lock);                        /* try to kill all child dentries */                        shrink_dcache_parent(dentry);                        dput(dentry);                        /* now try to get rid of current dentry */                        d_prune_aliases(inode);                        goto restart;                }        }        spin_unlock(&dcache_lock);}static void prune_deathrow_one(struct ll_inode_info *lli){        struct inode *inode = ll_info2i(lli);        /* first, try to drop any dentries - they hold a ref on the inode */        if (S_ISDIR(inode->i_mode))                prune_dir_dentries(inode);        else                d_prune_aliases(inode);        /* if somebody still uses it, leave it */        LASSERT(atomic_read(&inode->i_count) > 0);        if (atomic_read(&inode->i_count) > 1)                goto out;        CDEBUG(D_INODE, "inode %lu/%u(%d) looks a good candidate for prune\n",               inode->i_ino,inode->i_generation, atomic_read(&inode->i_count));        /* seems nobody uses it anymore */        inode->i_nlink = 0;out:        iput(inode);        return;}static void prune_deathrow(struct ll_sb_info *sbi, int try){        struct ll_inode_info *lli;        int empty;        do {                if (need_resched() && try)                        break;                if (try) {                        if (!spin_trylock(&sbi->ll_deathrow_lock))                                break;                } else {                        spin_lock(&sbi->ll_deathrow_lock);                }                empty = 1;                lli = NULL;                if (!list_empty(&sbi->ll_deathrow)) {                        lli = list_entry(sbi->ll_deathrow.next,                                         struct ll_inode_info,                                         lli_dead_list);                        list_del_init(&lli->lli_dead_list);                        if (!list_empty(&sbi->ll_deathrow))                                empty = 0;                }                spin_unlock(&sbi->ll_deathrow_lock);                if (lli)                        prune_deathrow_one(lli);        } while (empty == 0);}#else /* !HAVE_EXPORT___IGET */#define prune_deathrow(sbi, try) do {} while (0)#endif /* HAVE_EXPORT___IGET */void client_common_put_super(struct super_block *sb){        struct ll_sb_info *sbi = ll_s2sbi(sb);        ENTRY;        ll_close_thread_shutdown(sbi->ll_lcq);        lprocfs_unregister_mountpoint(sbi);        /* destroy inodes in deathrow */        prune_deathrow(sbi, 0);        list_del(&sbi->ll_conn_chain);        /* callbacks is cleared after disconnect each target */        obd_disconnect(sbi->ll_osc_exp);        sbi->ll_osc_exp = NULL;        obd_disconnect(sbi->ll_mdc_exp);        sbi->ll_mdc_exp = NULL;        lustre_throw_orphan_dentries(sb);        EXIT;}void ll_kill_super(struct super_block *sb){        struct ll_sb_info *sbi;        ENTRY;        /* not init sb ?*/        if (!(sb->s_flags & MS_ACTIVE))                return;        sbi = ll_s2sbi(sb);        /* we need restore s_dev from changed for clustred NFS before put_super         * because new kernels have cached s_dev and change sb->s_dev in          * put_super not affected real removing devices */        if (sbi)                sb->s_dev = sbi->ll_sdev_orig;        EXIT;}char *ll_read_opt(const char *opt, char *data){        char *value;        char *retval;        ENTRY;        CDEBUG(D_SUPER, "option: %s, data %s\n", opt, data);        if (strncmp(opt, data, strlen(opt)))                RETURN(NULL);        if ((value = strchr(data, '=')) == NULL)                RETURN(NULL);        value++;        OBD_ALLOC(retval, strlen(value) + 1);        if (!retval) {                CERROR("out of memory!\n");                RETURN(NULL);        }        memcpy(retval, value, strlen(value)+1);        CDEBUG(D_SUPER, "Assigned option: %s, value %s\n", opt, retval);        RETURN(retval);}static inline int ll_set_opt(const char *opt, char *data, int fl){        if (strncmp(opt, data, strlen(opt)) != 0)                return(0);        else                return(fl);}/* non-client-specific mount options are parsed in lmd_parse */static int ll_options(char *options, int *flags){        int tmp;        char *s1 = options, *s2;        ENTRY;        if (!options)                RETURN(0);        CDEBUG(D_CONFIG, "Parsing opts %s\n", options);        while (*s1) {                CDEBUG(D_SUPER, "next opt=%s\n", s1);                tmp = ll_set_opt("nolock", s1, LL_SBI_NOLCK);                if (tmp) {                        *flags |= tmp;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -