Whamcloud - gitweb
Branch HEAD
authorbobijam <bobijam>
Tue, 16 Sep 2008 03:16:05 +0000 (03:16 +0000)
committerbobijam <bobijam>
Tue, 16 Sep 2008 03:16:05 +0000 (03:16 +0000)
b=16788
i=adilger
i=nathan.rutman

add per-nid statistics on HEAD.

lustre/include/lprocfs_status.h
lustre/include/lustre_export.h
lustre/ldlm/ldlm_lockd.c
lustre/mdt/mdt_handler.c
lustre/mgs/lproc_mgs.c
lustre/mgs/mgs_fs.c
lustre/mgs/mgs_handler.c
lustre/mgs/mgs_internal.h
lustre/obdclass/lprocfs_status.c
lustre/obdfilter/filter.c

index 9696a7b..355ece4 100644 (file)
@@ -390,8 +390,11 @@ extern void lprocfs_clear_stats(struct lprocfs_stats *stats);
 extern void lprocfs_free_stats(struct lprocfs_stats **stats);
 extern void lprocfs_init_ops_stats(int num_private_stats,
                                    struct lprocfs_stats *stats);
+extern void lprocfs_init_ldlm_stats(struct lprocfs_stats *ldlm_stats);
 extern int lprocfs_alloc_obd_stats(struct obd_device *obddev,
                                    unsigned int num_private_stats);
+extern int lprocfs_alloc_md_stats(struct obd_device *obddev,
+                                  unsigned int num_private_stats);
 extern void lprocfs_counter_init(struct lprocfs_stats *stats, int index,
                                  unsigned conf, const char *name,
                                  const char *units);
@@ -643,9 +646,14 @@ static inline int lprocfs_register_stats(cfs_proc_dir_entry_t *root,
 static inline void lprocfs_init_ops_stats(int num_private_stats,
                                           struct lprocfs_stats *stats)
 { return; }
+static inline void lprocfs_init_ldlm_stats(struct lprocfs_stats *ldlm_stats)
+{ return; }
 static inline int lprocfs_alloc_obd_stats(struct obd_device *obddev,
                                              unsigned int num_private_stats)
 { return 0; }
+static inline int lprocfs_alloc_md_stats(struct obd_device *obddev,
+                                         unsigned int num_private_stats)
+{ return 0; }
 static inline void lprocfs_free_obd_stats(struct obd_device *obddev)
 { return; }
 
index 55961d1..4851fbc 100644 (file)
@@ -96,13 +96,20 @@ struct filter_export_data {
         struct brw_stats           fed_brw_stats;
 };
 
+typedef struct nid_stat_uuid {
+        struct list_head ns_uuid_list;
+        struct obd_uuid  ns_uuid;
+} nid_stat_uuid_t;
+
 typedef struct nid_stat {
         lnet_nid_t               nid;
         struct hlist_node        nid_hash;
         struct list_head         nid_list;
+        struct list_head         nid_uuid_list;
         struct obd_device       *nid_obd;
         struct proc_dir_entry   *nid_proc;
         struct lprocfs_stats    *nid_stats;
+        struct lprocfs_stats    *nid_ldlm_stats;
         struct brw_stats        *nid_brw_stats;
         int                      nid_exp_ref_count;
 }nid_stat_t;
@@ -121,7 +128,6 @@ struct obd_export {
         struct obd_import        *exp_imp_reverse; /* to make RPCs backwards */
         struct nid_stat          *exp_nid_stats;
         struct lprocfs_stats     *exp_md_stats;
-        struct lprocfs_stats     *exp_ldlm_stats;
         struct ptlrpc_connection *exp_connection;
         __u32                     exp_conn_cnt;
         lustre_hash_t            *exp_lock_hash; /* existing lock hash */
index 870ae23..f2965fc 100644 (file)
@@ -548,16 +548,16 @@ static int ldlm_cb_interpret(struct ptlrpc_request *req, void *data, int rc)
         lock = req->rq_async_args.pointer_arg[1];
         LASSERT(lock != NULL);
         if (rc != 0) {
-                /* If client canceled the lock but the cancel has not 
+                /* If client canceled the lock but the cancel has not
                  * been recieved yet, we need to update lvbo to have the
                  * proper attributes cached. */
                 if (rc == -EINVAL && arg->type == LDLM_BL_CALLBACK)
-                        ldlm_res_lvbo_update(lock->l_resource, NULL, 
+                        ldlm_res_lvbo_update(lock->l_resource, NULL,
                                              0, 1);
-                rc = ldlm_handle_ast_error(lock, req, rc, 
+                rc = ldlm_handle_ast_error(lock, req, rc,
                                            arg->type == LDLM_BL_CALLBACK
                                            ? "blocking" : "completion");
-        }                
+        }
 
         LDLM_LOCK_PUT(lock);
 
@@ -585,7 +585,7 @@ static inline int ldlm_bl_and_cp_ast_fini(struct ptlrpc_request *req,
         } else {
                 LDLM_LOCK_GET(lock);
                 ptlrpc_set_add_req(arg->set, req);
-        }       
+        }
 
         RETURN(rc);
 }
@@ -672,8 +672,9 @@ int ldlm_server_blocking_ast(struct ldlm_lock *lock,
         if (AT_OFF)
                 req->rq_timeout = ldlm_get_rq_timeout();
 
-        if (lock->l_export && lock->l_export->exp_ldlm_stats)
-                lprocfs_counter_incr(lock->l_export->exp_ldlm_stats,
+        if (lock->l_export && lock->l_export->exp_nid_stats &&
+            lock->l_export->exp_nid_stats->nid_ldlm_stats)
+                lprocfs_counter_incr(lock->l_export->exp_nid_stats->nid_ldlm_stats,
                                      LDLM_BL_CALLBACK - LDLM_FIRST_OPC);
 
         rc = ldlm_bl_and_cp_ast_fini(req, arg, lock, instant_cancel);
@@ -777,8 +778,9 @@ int ldlm_server_completion_ast(struct ldlm_lock *lock, int flags, void *data)
         }
         unlock_res_and_lock(lock);
 
-        if (lock->l_export && lock->l_export->exp_ldlm_stats)
-                lprocfs_counter_incr(lock->l_export->exp_ldlm_stats,
+        if (lock->l_export && lock->l_export->exp_nid_stats &&
+            lock->l_export->exp_nid_stats->nid_ldlm_stats)
+                lprocfs_counter_incr(lock->l_export->exp_nid_stats->nid_ldlm_stats,
                                      LDLM_CP_CALLBACK - LDLM_FIRST_OPC);
 
         rc = ldlm_bl_and_cp_ast_fini(req, arg, lock, instant_cancel);
@@ -820,8 +822,9 @@ int ldlm_server_glimpse_ast(struct ldlm_lock *lock, void *data)
         if (AT_OFF)
                 req->rq_timeout = ldlm_get_rq_timeout();
 
-        if (lock->l_export && lock->l_export->exp_ldlm_stats)
-                lprocfs_counter_incr(lock->l_export->exp_ldlm_stats,
+        if (lock->l_export && lock->l_export->exp_nid_stats &&
+            lock->l_export->exp_nid_stats->nid_ldlm_stats)
+                lprocfs_counter_incr(lock->l_export->exp_nid_stats->nid_ldlm_stats,
                                      LDLM_GL_CALLBACK - LDLM_FIRST_OPC);
 
         rc = ptlrpc_queue_wait(req);
@@ -907,8 +910,9 @@ int ldlm_handle_enqueue0(struct ldlm_namespace *ns,
                 ldlm_svc_get_eopc(dlm_req,
                                   req->rq_rqbd->rqbd_service->srv_stats);
 
-        if (req->rq_export->exp_ldlm_stats)
-                lprocfs_counter_incr(req->rq_export->exp_ldlm_stats,
+        if (req->rq_export && req->rq_export->exp_nid_stats &&
+            req->rq_export->exp_nid_stats->nid_ldlm_stats)
+                lprocfs_counter_incr(req->rq_export->exp_nid_stats->nid_ldlm_stats,
                                      LDLM_ENQUEUE - LDLM_FIRST_OPC);
 
         if (unlikely(dlm_req->lock_desc.l_resource.lr_type < LDLM_MIN_TYPE ||
@@ -994,7 +998,7 @@ int ldlm_handle_enqueue0(struct ldlm_namespace *ns,
 
         if (lock->l_export->exp_lock_hash)
                 lustre_hash_add(lock->l_export->exp_lock_hash,
-                                &lock->l_remote_handle, 
+                                &lock->l_remote_handle,
                                 &lock->l_exp_hash);
 
 existing_lock:
@@ -1172,8 +1176,9 @@ int ldlm_handle_convert0(struct ptlrpc_request *req,
         int rc;
         ENTRY;
 
-        if (req->rq_export && req->rq_export->exp_ldlm_stats)
-                lprocfs_counter_incr(req->rq_export->exp_ldlm_stats,
+        if (req->rq_export && req->rq_export->exp_nid_stats &&
+            req->rq_export->exp_nid_stats->nid_ldlm_stats)
+                lprocfs_counter_incr(req->rq_export->exp_nid_stats->nid_ldlm_stats,
                                      LDLM_CONVERT - LDLM_FIRST_OPC);
 
         rc = req_capsule_server_pack(&req->rq_pill);
@@ -1296,8 +1301,9 @@ int ldlm_handle_cancel(struct ptlrpc_request *req)
                 RETURN(-EFAULT);
         }
 
-        if (req->rq_export && req->rq_export->exp_ldlm_stats)
-                lprocfs_counter_incr(req->rq_export->exp_ldlm_stats,
+        if (req->rq_export && req->rq_export->exp_nid_stats &&
+            req->rq_export->exp_nid_stats->nid_ldlm_stats)
+                lprocfs_counter_incr(req->rq_export->exp_nid_stats->nid_ldlm_stats,
                                      LDLM_CANCEL - LDLM_FIRST_OPC);
 
         rc = req_capsule_server_pack(&req->rq_pill);
@@ -1394,7 +1400,7 @@ static void ldlm_handle_cp_callback(struct ptlrpc_request *req,
                    &lock->l_resource->lr_name,
                    sizeof(lock->l_resource->lr_name)) != 0) {
                 unlock_res_and_lock(lock);
-                if (ldlm_lock_change_resource(ns, lock, 
+                if (ldlm_lock_change_resource(ns, lock,
                                 &dlm_req->lock_desc.l_resource.lr_name) != 0) {
                         LDLM_ERROR(lock, "Failed to allocate resource");
                         LDLM_LOCK_PUT(lock);
@@ -2024,8 +2030,8 @@ void ldlm_put_ref(void)
         EXIT;
 }
 
-/* 
- * Export handle<->lock hash operations. 
+/*
+ * Export handle<->lock hash operations.
  */
 static unsigned
 ldlm_export_lock_hash(lustre_hash_t *lh, void *key, unsigned mask)
@@ -2248,7 +2254,7 @@ static int ldlm_cleanup(void)
 #endif
         ENTRY;
 
-        if (!list_empty(ldlm_namespace_list(LDLM_NAMESPACE_SERVER)) || 
+        if (!list_empty(ldlm_namespace_list(LDLM_NAMESPACE_SERVER)) ||
             !list_empty(ldlm_namespace_list(LDLM_NAMESPACE_CLIENT))) {
                 CERROR("ldlm still has namespaces; clean these up first.\n");
                 ldlm_dump_all_namespaces(LDLM_NAMESPACE_SERVER, D_DLMTRACE);
index bc457d4..545ec84 100644 (file)
@@ -2081,8 +2081,8 @@ static int mdt_req_handle(struct mdt_thread_info *info,
         LASSERT(current->journal_info == NULL);
 
         /*
-         * Checking for various OBD_FAIL_$PREF_$OPC_NET codes. _Do_ not try 
-         * to put same checks into handlers like mdt_close(), mdt_reint(), 
+         * Checking for various OBD_FAIL_$PREF_$OPC_NET codes. _Do_ not try
+         * to put same checks into handlers like mdt_close(), mdt_reint(),
          * etc., without talking to mdt authors first. Checking same thing
          * there again is useless and returning 0 error wihtout packing reply
          * is buggy! Handlers either pack reply or return error.
@@ -2712,8 +2712,8 @@ int mdt_intent_lock_replace(struct mdt_thread_info *info,
                 RETURN(ELDLM_LOCK_REPLACED);
         }
 
-        /* 
-         * Fixup the lock to be given to the client. 
+        /*
+         * Fixup the lock to be given to the client.
          */
         lock_res_and_lock(new_lock);
         new_lock->l_readers = 0;
@@ -2726,7 +2726,7 @@ int mdt_intent_lock_replace(struct mdt_thread_info *info,
         new_lock->l_flags &= ~LDLM_FL_LOCAL;
 
         lustre_hash_add(new_lock->l_export->exp_lock_hash,
-                        &new_lock->l_remote_handle, 
+                        &new_lock->l_remote_handle,
                         &new_lock->l_exp_hash);
 
         unlock_res_and_lock(new_lock);
@@ -2912,7 +2912,7 @@ static int mdt_intent_reint(enum mdt_it_code opcode,
 
         lhc->mlh_reg_lh.cookie = 0ull;
         if (rc == -ENOTCONN || rc == -ENODEV) {
-                /* 
+                /*
                  * If it is the disconnect error (ENODEV & ENOCONN), the error
                  * will be returned by rq_status, and client at ptlrpc layer
                  * will detect this, then disconnect, reconnect the import
@@ -2920,15 +2920,15 @@ static int mdt_intent_reint(enum mdt_it_code opcode,
                  */
                 RETURN(rc);
         } else {
-                /* 
+                /*
                  * For other cases, the error will be returned by intent.
                  * and client will retrieve the result from intent.
-                 */ 
-                 /* 
+                 */
+                 /*
                   * FIXME: when open lock is finished, that should be
                   * checked here.
                   */
-                RETURN(ELDLM_LOCK_ABORTED); 
+                RETURN(ELDLM_LOCK_ABORTED);
         }
 }
 
@@ -4446,6 +4446,9 @@ static int mdt_obd_disconnect(struct obd_export *exp)
         if (mdt->mdt_namespace != NULL || exp->exp_obd->obd_namespace != NULL)
                 ldlm_cancel_locks_for_export(exp);
 
+        /* release nid stat refererence */
+        lprocfs_exp_cleanup(exp);
+
         /* complete all outstanding replies */
         spin_lock(&exp->exp_lock);
         while (!list_empty(&exp->exp_outstanding_replies)) {
index 1d84a12..d3434bf 100644 (file)
@@ -121,7 +121,7 @@ int lproc_mgs_cleanup(struct obd_device *obd)
         struct mgs_obd *mgs;
 
         if (!obd)
-                RETURN(-EINVAL);
+                return -EINVAL;
 
         mgs = &obd->u.mgs;
         if (mgs->mgs_proc_live) {
@@ -130,6 +130,7 @@ int lproc_mgs_cleanup(struct obd_device *obd)
                 lprocfs_remove(&mgs->mgs_proc_live);
                 mgs->mgs_proc_live = NULL;
         }
+        lprocfs_free_per_client_stats(obd);
         lprocfs_free_obd_stats(obd);
 
         return lprocfs_obd_cleanup(obd);
@@ -165,22 +166,22 @@ static void seq_show_srpc_rule(struct seq_file *seq, const char *tgtname,
         }
 }
 
-static int mgs_live_seq_show(struct seq_file *seq, void *v) 
+static int mgs_live_seq_show(struct seq_file *seq, void *v)
 {
         struct fs_db             *fsdb = seq->private;
         struct mgs_tgt_srpc_conf *srpc_tgt;
         int i;
-        
+
         down(&fsdb->fsdb_sem);
 
         seq_printf(seq, "fsname: %s\n", fsdb->fsdb_name);
-        seq_printf(seq, "flags: %#x     gen: %d\n", 
+        seq_printf(seq, "flags: %#x     gen: %d\n",
                    fsdb->fsdb_flags, fsdb->fsdb_gen);
         for (i = 0; i < INDEX_MAP_SIZE * 8; i++)
-                 if (test_bit(i, fsdb->fsdb_mdt_index_map)) 
+                 if (test_bit(i, fsdb->fsdb_mdt_index_map))
                          seq_printf(seq, "%s-MDT%04x\n", fsdb->fsdb_name, i);
         for (i = 0; i < INDEX_MAP_SIZE * 8; i++)
-                 if (test_bit(i, fsdb->fsdb_ost_index_map)) 
+                 if (test_bit(i, fsdb->fsdb_ost_index_map))
                          seq_printf(seq, "%s-OST%04x\n", fsdb->fsdb_name, i);
 
         seq_printf(seq, "\nSecure RPC Config Rules:\n");
@@ -206,9 +207,9 @@ int lproc_mgs_add_live(struct obd_device *obd, struct fs_db *fsdb)
         struct mgs_obd *mgs = &obd->u.mgs;
         int rc;
 
-        if (!mgs->mgs_proc_live) 
+        if (!mgs->mgs_proc_live)
                 return 0;
-        rc = lprocfs_seq_create(mgs->mgs_proc_live, fsdb->fsdb_name, 0444, 
+        rc = lprocfs_seq_create(mgs->mgs_proc_live, fsdb->fsdb_name, 0444,
                                 &mgs_live_fops, fsdb);
 
         return 0;
@@ -218,7 +219,7 @@ int lproc_mgs_del_live(struct obd_device *obd, struct fs_db *fsdb)
 {
         struct mgs_obd *mgs = &obd->u.mgs;
 
-        if (!mgs->mgs_proc_live) 
+        if (!mgs->mgs_proc_live)
                 return 0;
 
         lprocfs_remove_proc_entry(fsdb->fsdb_name, mgs->mgs_proc_live);
index 78b6675..4b87e84 100644 (file)
 #include <libcfs/list.h>
 #include "mgs_internal.h"
 
+static int mgs_export_stats_init(struct obd_device *obd, struct obd_export *exp,
+                                 void *localdata)
+{
+        lnet_nid_t *client_nid = localdata;
+        int rc, newnid;
+
+        rc = lprocfs_exp_setup(exp, client_nid, &newnid);
+        if (rc) {
+                /* Mask error for already created
+                 * /proc entries */
+                if (rc == -EALREADY)
+                        rc = 0;
+                return rc;
+        }
+
+        if (!obd->md_stats &&
+            lprocfs_alloc_md_stats(obd, LPROC_MGS_LAST))
+                        return rc;
+        if (newnid) {
+                /* Always add in ldlm_stats */
+                exp->exp_nid_stats->nid_ldlm_stats =
+                        lprocfs_alloc_stats(LDLM_LAST_OPC - LDLM_FIRST_OPC, 0);
+                if (exp->exp_nid_stats->nid_ldlm_stats == NULL)
+                        return -ENOMEM;
+                lprocfs_init_ldlm_stats(exp->exp_nid_stats->nid_ldlm_stats);
+                rc = lprocfs_register_stats(exp->exp_nid_stats->nid_proc,
+                                            "ldlm_stats",
+                                            exp->exp_nid_stats->nid_ldlm_stats);
+        }
+        return rc;
+}
+
+/**
+ * Add client export data to the MGS.  This data is currently NOT stored on
+ * disk in the last_rcvd file or anywhere else.  In the event of a MGS
+ * crash all connections are treated as new connections.
+ */
+int mgs_client_add(struct obd_device *obd, struct obd_export *exp,
+                   void *localdata)
+{
+        return mgs_export_stats_init(obd, exp, localdata);
+}
+
+/* Remove client export data from the MGS */
+int mgs_client_free(struct obd_export *exp)
+{
+        return 0;
+}
+
 /* Same as mds_fid2dentry */
 /* Look up an entry by inode number. */
 /* this function ONLY returns valid dget'd dentries with an initialized inode
@@ -75,9 +124,9 @@ static struct dentry *mgs_fid2dentry(struct mgs_obd *mgs,
 
         if (ino == 0)
                 RETURN(ERR_PTR(-ESTALE));
-        
+
         snprintf(fid_name, sizeof(fid_name), "0x%lx", (unsigned long)ino);
-        
+
         /* under ext3 this is neither supposed to return bad inodes nor NULL
            inodes. */
         result = ll_lookup_one_len(fid_name, mgs->mgs_fid_de, strlen(fid_name));
@@ -152,7 +201,7 @@ int mgs_fs_setup(struct obd_device *obd, struct vfsmount *mnt)
         dentry = simple_mkdir(current->fs->pwd, mnt, MOUNT_CONFIGS_DIR, 0777, 1);
         if (IS_ERR(dentry)) {
                 rc = PTR_ERR(dentry);
-                CERROR("cannot create %s directory: rc = %d\n", 
+                CERROR("cannot create %s directory: rc = %d\n",
                        MOUNT_CONFIGS_DIR, rc);
                 GOTO(err_pop, rc);
         }
index 1bd26d6..40e1275 100644 (file)
@@ -90,6 +90,8 @@ static int mgs_connect(const struct lu_env *env,
                 data->ocd_version = LUSTRE_VERSION_CODE;
         }
 
+        rc = mgs_client_add(obd, exp, localdata);
+
         if (rc) {
                 class_disconnect(exp);
         } else {
@@ -108,6 +110,8 @@ static int mgs_reconnect(const struct lu_env *env,
         if (exp == NULL || obd == NULL || cluuid == NULL)
                 RETURN(-EINVAL);
 
+        mgs_counter_incr(exp, LPROC_MGS_CONNECT);
+
         if (data != NULL) {
                 data->ocd_connect_flags &= MGS_CONNECT_SUPPORTED;
                 exp->exp_connect_flags = data->ocd_connect_flags;
@@ -463,7 +467,7 @@ static int mgs_handle_target_reg(struct ptlrpc_request *req)
                 }
                 mti->mti_flags |= LDD_F_UPDATE;
                 /* Erased logs means start from scratch. */
-                mti->mti_flags &= ~LDD_F_UPGRADE14; 
+                mti->mti_flags &= ~LDD_F_UPGRADE14;
         }
 
         /* COMPAT_146 */
@@ -473,7 +477,7 @@ static int mgs_handle_target_reg(struct ptlrpc_request *req)
                         CERROR("Can't upgrade from 1.4 (%d)\n", rc);
                         GOTO(out, rc);
                 }
-                
+
                 /* We're good to go */
                 mti->mti_flags |= LDD_F_UPDATE;
         }
@@ -709,6 +713,7 @@ static inline int mgs_destroy_export(struct obd_export *exp)
         ENTRY;
 
         target_destroy_export(exp);
+        mgs_client_free(exp);
         ldlm_destroy_export(exp);
 
         RETURN(0);
@@ -732,7 +737,7 @@ static int mgs_extract_fs_pool(char * arg, char *fsname, char *poolname)
         RETURN(0);
 }
 
-static int mgs_iocontrol_pool(struct obd_device *obd, 
+static int mgs_iocontrol_pool(struct obd_device *obd,
                               struct obd_ioctl_data *data)
 {
         int rc;
index d5d18bd..99e698f 100644 (file)
@@ -49,9 +49,9 @@
 
 /* mgs_llog.c */
 int class_dentry_readdir(struct obd_device *obd, struct dentry *dir,
-                         struct vfsmount *inmnt, 
+                         struct vfsmount *inmnt,
                          struct list_head *dentry_list);
+
 struct mgs_tgt_srpc_conf {
         struct mgs_tgt_srpc_conf  *mtsc_next;
         char                      *mtsc_tgt;
@@ -99,6 +99,9 @@ int mgs_pool_cmd(struct obd_device *obd, enum lcfg_command_type cmd,
                  char *poolname, char *fsname, char *ostname);
 
 /* mgs_fs.c */
+int mgs_client_add(struct obd_device *obd, struct obd_export *exp,
+                   void *localdata);
+int mgs_client_free(struct obd_export *exp);
 int mgs_fs_setup(struct obd_device *obd, struct vfsmount *mnt);
 int mgs_fs_cleanup(struct obd_device *obddev);
 
@@ -110,7 +113,7 @@ int lproc_mgs_add_live(struct obd_device *obd, struct fs_db *fsdb);
 int lproc_mgs_del_live(struct obd_device *obd, struct fs_db *fsdb);
 void lprocfs_mgs_init_vars(struct lprocfs_static_vars *lvars);
 #else
-static inline int lproc_mgs_setup(struct obd_device *dev) 
+static inline int lproc_mgs_setup(struct obd_device *dev)
 {return 0;}
 static inline int lproc_mgs_cleanup(struct obd_device *obd)
 {return 0;}
index 79eb987..82366e4 100644 (file)
@@ -838,6 +838,9 @@ static void lprocfs_free_client_stats(struct nid_stat *client_stat)
         if (client_stat->nid_brw_stats)
                 OBD_FREE(client_stat->nid_brw_stats, sizeof(struct brw_stats));
 
+        if (client_stat->nid_ldlm_stats)
+                lprocfs_free_stats(&client_stat->nid_ldlm_stats);
+
         OBD_FREE(client_stat, sizeof(*client_stat));
         return;
 
@@ -1284,7 +1287,7 @@ int lprocfs_alloc_md_stats(struct obd_device *obd,
         LASSERT(obd->obd_proc_entry != NULL);
         LASSERT(obd->md_cntr_base == 0);
 
-        num_stats = 1 + MD_COUNTER_OFFSET(get_remote_perm) +
+        num_stats = 1 + MD_COUNTER_OFFSET(revalidate_lock) +
                     num_private_stats;
         stats = lprocfs_alloc_stats(num_stats, 0);
         if (stats == NULL)
@@ -1349,6 +1352,28 @@ void lprocfs_free_md_stats(struct obd_device *obd)
         }
 }
 
+void lprocfs_init_ldlm_stats(struct lprocfs_stats *ldlm_stats)
+{
+        lprocfs_counter_init(ldlm_stats,
+                             LDLM_ENQUEUE - LDLM_FIRST_OPC,
+                             0, "ldlm_enqueue", "reqs");
+        lprocfs_counter_init(ldlm_stats,
+                             LDLM_CONVERT - LDLM_FIRST_OPC,
+                             0, "ldlm_convert", "reqs");
+        lprocfs_counter_init(ldlm_stats,
+                             LDLM_CANCEL - LDLM_FIRST_OPC,
+                             0, "ldlm_cancel", "reqs");
+        lprocfs_counter_init(ldlm_stats,
+                             LDLM_BL_CALLBACK - LDLM_FIRST_OPC,
+                             0, "ldlm_bl_callback", "reqs");
+        lprocfs_counter_init(ldlm_stats,
+                             LDLM_CP_CALLBACK - LDLM_FIRST_OPC,
+                             0, "ldlm_cp_callback", "reqs");
+        lprocfs_counter_init(ldlm_stats,
+                             LDLM_GL_CALLBACK - LDLM_FIRST_OPC,
+                             0, "ldlm_gl_callback", "reqs");
+}
+
 int lprocfs_exp_rd_nid(char *page, char **start, off_t off, int count,
                          int *eof,  void *data)
 {
@@ -1450,17 +1475,16 @@ void lprocfs_nid_stats_clear_write_cb(void *obj, void *data)
 {
         struct nid_stat *stat = obj;
         int i;
-
+        ENTRY;
         /* object has only hash + iterate_all references.
          * add/delete blocked by hash bucket lock */
         CDEBUG(D_INFO,"refcnt %d\n", stat->nid_exp_ref_count);
-        if(stat->nid_exp_ref_count == 2) {
+        if (stat->nid_exp_ref_count == 2) {
                 hlist_del_init(&stat->nid_hash);
                 stat->nid_exp_ref_count--;
                 spin_lock(&stat->nid_obd->obd_nid_lock);
-                list_del_init(&stat->nid_list);
+                list_move(&stat->nid_list, data);
                 spin_unlock(&stat->nid_obd->obd_nid_lock);
-                list_add(&stat->nid_list, data);
                 EXIT;
                 return;
         }
@@ -1498,10 +1522,11 @@ EXPORT_SYMBOL(lprocfs_nid_stats_clear_write);
 
 int lprocfs_exp_setup(struct obd_export *exp, lnet_nid_t *nid, int *newnid)
 {
-        int rc = 0;
-        struct nid_stat *tmp = NULL, *tmp1;
+        struct nid_stat *new_stat, *old_stat;
+        struct nid_stat_uuid *new_ns_uuid;
         struct obd_device *obd = NULL;
         cfs_proc_dir_entry_t *entry;
+        int rc = 0;
         ENTRY;
 
         *newnid = 0;
@@ -1511,8 +1536,8 @@ int lprocfs_exp_setup(struct obd_export *exp, lnet_nid_t *nid, int *newnid)
                 RETURN(-EINVAL);
 
        /* not test against zero because eric say:
-        * You may only test nid against another nid, or LNET_NID_ANY.  Anything else is
-        * nonsense.*/
+        * You may only test nid against another nid, or LNET_NID_ANY.
+         * Anything else is nonsense.*/
         if (!nid || *nid == LNET_NID_ANY)
                 RETURN(0);
 
@@ -1520,75 +1545,139 @@ int lprocfs_exp_setup(struct obd_export *exp, lnet_nid_t *nid, int *newnid)
 
         CDEBUG(D_CONFIG, "using hash %p\n", obd->obd_nid_stats_hash);
 
-        OBD_ALLOC(tmp, sizeof(struct nid_stat));
-        if (tmp == NULL)
+        OBD_ALLOC(new_stat, sizeof(struct nid_stat));
+        if (new_stat == NULL)
+                RETURN(-ENOMEM);
+
+        OBD_ALLOC(new_ns_uuid, sizeof(struct nid_stat_uuid));
+        if (new_ns_uuid == NULL) {
+                OBD_FREE(new_stat, sizeof(struct nid_stat));
                 RETURN(-ENOMEM);
+        }
+        CFS_INIT_LIST_HEAD(&new_ns_uuid->ns_uuid_list);
+        strncpy(new_ns_uuid->ns_uuid.uuid, exp->exp_client_uuid.uuid,
+                sizeof(struct obd_uuid));
 
-        tmp->nid = *nid;
-        tmp->nid_obd = exp->exp_obd;
-        tmp->nid_exp_ref_count = 1; /* need live in hash after destroy export */
+        CFS_INIT_LIST_HEAD(&new_stat->nid_uuid_list);
+        new_stat->nid               = *nid;
+        new_stat->nid_obd           = exp->exp_obd;
+        new_stat->nid_exp_ref_count = 1; /* live in hash after destroy export */
 
        /* protect competitive add to list, not need locking on destroy */
         spin_lock(&obd->obd_nid_lock);
-        list_add(&tmp->nid_list, &obd->obd_nid_stats);
+        list_add(&new_stat->nid_list, &obd->obd_nid_stats);
         spin_unlock(&obd->obd_nid_lock);
 
-        tmp1 = lustre_hash_findadd_unique(obd->obd_nid_stats_hash,
-                                          nid, &tmp->nid_hash);
+        old_stat = lustre_hash_findadd_unique(obd->obd_nid_stats_hash,
+                                              nid, &new_stat->nid_hash);
         CDEBUG(D_INFO, "Found stats %p for nid %s - ref %d\n",
-               tmp1, libcfs_nid2str(*nid), tmp->nid_exp_ref_count);
+               old_stat, libcfs_nid2str(*nid), new_stat->nid_exp_ref_count);
+
+        /* Return -EALREADY here so that we know that the /proc
+         * entry already has been created */
+        if (old_stat != new_stat) {
+                struct nid_stat_uuid *tmp_uuid;
+                int found = 0;
+
+                exp->exp_nid_stats = old_stat;
+                /* We need to decrement the refcount if the uuid was
+                 * already in our list */
+                spin_lock(&obd->obd_nid_lock);
+                list_for_each_entry(tmp_uuid, &old_stat->nid_uuid_list,
+                                    ns_uuid_list) {
+                        if (tmp_uuid && obd_uuid_equals(&tmp_uuid->ns_uuid,
+                                                        &exp->exp_client_uuid)){
+                                found = 1;
+                                --old_stat->nid_exp_ref_count;
+                                break;
+                        }
+                }
+
+                if (!found)
+                        list_add(&new_ns_uuid->ns_uuid_list,
+                                 &old_stat->nid_uuid_list);
+                else
+                        OBD_FREE(new_ns_uuid, sizeof(struct nid_stat));
 
-        if (tmp1 != tmp) {
-                exp->exp_nid_stats = tmp1;
-                GOTO(destroy_new, rc = 0);
+                spin_unlock(&obd->obd_nid_lock);
+
+                GOTO(destroy_new, rc = -EALREADY);
         }
         /* not found - create */
-        tmp->nid_proc = lprocfs_register(libcfs_nid2str(*nid),
-                                         obd->obd_proc_exports_entry, NULL, NULL);
-        if (!tmp->nid_proc) {
-                CERROR("Error making export directory for"
-                       " nid %s\n", libcfs_nid2str(*nid));
-                lustre_hash_del(obd->obd_nid_stats_hash, nid, &tmp->nid_hash);
+        new_stat->nid_proc = lprocfs_register(libcfs_nid2str(*nid),
+                                              obd->obd_proc_exports_entry,
+                                              NULL, NULL);
+        if (new_stat->nid_proc == NULL) {
+                CERROR("Error making export directory for nid %s\n",
+                       libcfs_nid2str(*nid));
+                lustre_hash_del(obd->obd_nid_stats_hash, nid,
+                                &new_stat->nid_hash);
                 GOTO(destroy_new, rc = -ENOMEM);
         }
 
-        entry = lprocfs_add_simple(tmp->nid_proc, "uuid",
-                                   lprocfs_exp_rd_uuid, NULL, tmp, NULL);
+        /* Add in uuid to our nid_stats list */
+        spin_lock(&obd->obd_nid_lock);
+        list_add(&new_ns_uuid->ns_uuid_list, &new_stat->nid_uuid_list);
+        spin_unlock(&obd->obd_nid_lock);
+
+        entry = lprocfs_add_simple(new_stat->nid_proc, "uuid",
+                                   lprocfs_exp_rd_uuid, NULL, new_stat, NULL);
         if (IS_ERR(entry)) {
-                CWARN("Error adding the uuid file\n");
+                CWARN("Error adding the NID stats file\n");
                 rc = PTR_ERR(entry);
         }
 
-        entry = lprocfs_add_simple(tmp->nid_proc, "hash",
-                                lprocfs_exp_rd_hash, NULL, tmp, NULL);
+        entry = lprocfs_add_simple(new_stat->nid_proc, "hash",
+                                   lprocfs_exp_rd_hash, NULL, new_stat, NULL);
         if (IS_ERR(entry)) {
                 CWARN("Error adding the hash file\n");
                 rc = PTR_ERR(entry);
         }
 
-        exp->exp_nid_stats = tmp;
+        exp->exp_nid_stats = new_stat;
         *newnid = 1;
         RETURN(rc);
 
 destroy_new:
         spin_lock(&obd->obd_nid_lock);
-        list_del(&tmp->nid_list);
+        list_del(&new_stat->nid_list);
         spin_unlock(&obd->obd_nid_lock);
-        OBD_FREE(tmp, sizeof(struct nid_stat));
+        OBD_FREE(new_stat, sizeof(struct nid_stat));
         RETURN(rc);
 }
 
 int lprocfs_exp_cleanup(struct obd_export *exp)
 {
         struct nid_stat *stat = exp->exp_nid_stats;
+        struct nid_stat_uuid *cursor, *tmp;
+        int found = 0;
 
-        if(!stat)
+        if(!stat || !exp->exp_obd)
                 RETURN(0);
 
+        spin_lock(&exp->exp_obd->obd_nid_lock);
+        list_for_each_entry_safe(cursor, tmp,
+                                 &stat->nid_uuid_list,
+                                 ns_uuid_list) {
+                if (cursor && obd_uuid_equals(&cursor->ns_uuid,
+                                              &exp->exp_client_uuid)) {
+                        found = 1;
+                        list_del(&cursor->ns_uuid_list);
+                        OBD_FREE(cursor, sizeof(struct nid_stat_uuid));
+                        break;
+                }
+        }
+        spin_unlock(&exp->exp_obd->obd_nid_lock);
+        if (!found)
+                CERROR("obd_export's client uuid %s are not found in its "
+                       "nid_stats list\n", exp->exp_client_uuid.uuid);
+
         stat->nid_exp_ref_count--;
         CDEBUG(D_INFO, "Put stat %p - %d\n", stat, stat->nid_exp_ref_count);
 
         exp->exp_nid_stats = NULL;
+        lprocfs_free_md_stats(exp->exp_obd);
+
         return 0;
 }
 
@@ -1986,7 +2075,9 @@ EXPORT_SYMBOL(lprocfs_free_stats);
 EXPORT_SYMBOL(lprocfs_clear_stats);
 EXPORT_SYMBOL(lprocfs_register_stats);
 EXPORT_SYMBOL(lprocfs_init_ops_stats);
+EXPORT_SYMBOL(lprocfs_init_ldlm_stats);
 EXPORT_SYMBOL(lprocfs_alloc_obd_stats);
+EXPORT_SYMBOL(lprocfs_alloc_md_stats);
 EXPORT_SYMBOL(lprocfs_free_obd_stats);
 EXPORT_SYMBOL(lprocfs_exp_setup);
 EXPORT_SYMBOL(lprocfs_exp_cleanup);
index 3c7c88f..34518f3 100644 (file)
@@ -135,7 +135,7 @@ int filter_finish_transno(struct obd_export *exp, struct obd_trans_info *oti,
                 err = -EINVAL;
         } else {
                 if (!force_sync)
-                        force_sync = fsfilt_add_journal_cb(exp->exp_obd, 
+                        force_sync = fsfilt_add_journal_cb(exp->exp_obd,
                                                            last_rcvd,
                                                            oti->oti_handle,
                                                            filter_commit_cb,
@@ -255,7 +255,7 @@ static int filter_client_add(struct obd_device *obd, struct obd_export *exp,
         struct filter_export_data *fed = &exp->exp_filter_data;
         unsigned long *bitmap = filter->fo_last_rcvd_slots;
         int new_client = (cl_idx == -1);
+
         ENTRY;
 
         LASSERT(bitmap != NULL);
@@ -987,7 +987,7 @@ static int filter_read_group_internal(struct obd_device *obd, int group,
                         RETURN(PTR_ERR(dentry));
                 }
         } else {
-                dentry = simple_mkdir(filter->fo_dentry_O, filter->fo_vfsmnt, 
+                dentry = simple_mkdir(filter->fo_dentry_O, filter->fo_vfsmnt,
                                       name, 0700, 1);
                 if (IS_ERR(dentry)) {
                         CERROR("cannot lookup/create O/%s: rc = %ld\n", name,
@@ -1022,7 +1022,7 @@ static int filter_read_group_internal(struct obd_device *obd, int group,
                         char dir[20];
                         snprintf(dir, sizeof(dir), "d%u", i);
 
-                        tmp_subdirs->dentry[i] = simple_mkdir(dentry, 
+                        tmp_subdirs->dentry[i] = simple_mkdir(dentry,
                                                               filter->fo_vfsmnt,
                                                               dir, 0700, 1);
                         if (IS_ERR(tmp_subdirs->dentry[i])) {
@@ -1150,7 +1150,7 @@ static int filter_prep_groups(struct obd_device *obd)
         loff_t off = 0;
         ENTRY;
 
-        O_dentry = simple_mkdir(current->fs->pwd, filter->fo_vfsmnt, 
+        O_dentry = simple_mkdir(current->fs->pwd, filter->fo_vfsmnt,
                                 "O", 0700, 1);
         CDEBUG(D_INODE, "got/created O: %p\n", O_dentry);
         if (IS_ERR(O_dentry)) {
@@ -1764,7 +1764,7 @@ static int filter_intent_policy(struct ldlm_namespace *ns,
                 if (tree->lit_mode == LCK_PR)
                         continue;
 
-                interval_iterate_reverse(tree->lit_root, 
+                interval_iterate_reverse(tree->lit_root,
                                          filter_intent_cb, &arg);
         }
         unlock_res(res);
@@ -2195,7 +2195,7 @@ static int filter_olg_fini(struct obd_llog_group *olg)
         RETURN(rc);
 }
 
-static int 
+static int
 filter_olg_init(struct obd_device *obd, struct obd_llog_group *olg,
                 struct obd_device *tgt)
 {
@@ -2221,7 +2221,7 @@ cleanup:
 /**
  * Init the default olg, which is embeded in the obd_device, for filter.
  */
-static int 
+static int
 filter_default_olg_init(struct obd_device *obd, struct obd_llog_group *olg,
                         struct obd_device *tgt)
 {
@@ -2245,7 +2245,7 @@ filter_default_olg_init(struct obd_device *obd, struct obd_llog_group *olg,
 
         ctxt = llog_group_get_ctxt(olg, LLOG_MDS_OST_REPL_CTXT);
         if (!ctxt) {
-                CERROR("Can't get ctxt for %p:%x\n", olg, 
+                CERROR("Can't get ctxt for %p:%x\n", olg,
                        LLOG_MDS_OST_REPL_CTXT);
                 GOTO(cleanup_olg, rc = -ENODEV);
         }
@@ -2261,8 +2261,8 @@ cleanup_lcm:
         filter->fo_lcm = NULL;
         return rc;
 }
-                     
-static int 
+
+static int
 filter_llog_init(struct obd_device *obd, struct obd_llog_group *olg,
                  struct obd_device *tgt, int count, struct llog_catid *catid,
                  struct obd_uuid *uuid)
@@ -2282,7 +2282,7 @@ filter_llog_init(struct obd_device *obd, struct obd_llog_group *olg,
                 RETURN(rc);
         ctxt = llog_group_get_ctxt(olg, LLOG_MDS_OST_REPL_CTXT);
         if (!ctxt) {
-                CERROR("Can't get ctxt for %p:%x\n", olg, 
+                CERROR("Can't get ctxt for %p:%x\n", olg,
                        LLOG_MDS_OST_REPL_CTXT);
                 filter_olg_fini(olg);
                 RETURN(-ENODEV);
@@ -2298,7 +2298,7 @@ static int filter_llog_finish(struct obd_device *obd, int count)
         struct filter_obd *filter = &obd->u.filter;
         struct llog_ctxt *ctxt;
         ENTRY;
-        
+
         ctxt = llog_group_get_ctxt(&obd->obd_olg, LLOG_MDS_OST_REPL_CTXT);
         LASSERT(ctxt != NULL);
         mutex_down(&ctxt->loc_sem);
@@ -2354,11 +2354,11 @@ struct obd_llog_group *filter_find_olg(struct obd_device *obd, int group)
         olg = filter_find_olg_internal(filter, group);
         spin_unlock(&filter->fo_llog_list_lock);
 
-        RETURN(olg); 
+        RETURN(olg);
 }
 /**
  * Find the llog_group of the filter according to the group. If it can not
- * find, create the llog_group, which only happens when mds is being synced 
+ * find, create the llog_group, which only happens when mds is being synced
  * with OST.
  */
 struct obd_llog_group *filter_find_create_olg(struct obd_device *obd, int group)
@@ -2428,7 +2428,7 @@ static int filter_llog_connect(struct obd_export *exp,
         olg = filter_find_olg(obd, body->lgdc_logid.lgl_ogr);
         if (!olg) {
                 CERROR(" %s: can not find olg of group %d\n",
-                       obd->obd_name, (int)body->lgdc_logid.lgl_ogr); 
+                       obd->obd_name, (int)body->lgdc_logid.lgl_ogr);
                 RETURN(-ENOENT);
         }
         llog_group_set_export(olg, exp);
@@ -2469,8 +2469,8 @@ static int filter_llog_preclean(struct obd_device *obd)
                 list_add(&olg->olg_list, &remove_list);
         }
         spin_unlock(&filter->fo_llog_list_lock);
-        
-        list_for_each_entry_safe(olg, tmp, &remove_list, olg_list) {  
+
+        list_for_each_entry_safe(olg, tmp, &remove_list, olg_list) {
                 list_del_init(&olg->olg_list);
                 rc = filter_olg_fini(olg);
                 if (rc)
@@ -2943,7 +2943,7 @@ static void filter_sync_llogs(struct obd_device *obd, struct obd_export *dexp)
                         llog_ctxt_put(ctxt);
                         if (err)
                                 CERROR("error flushing logs to MDS: rc %d\n",
-                                       err);                        
+                                       err);
                 }
         } while (olg_min != NULL);
 }
@@ -3259,7 +3259,7 @@ int filter_setattr(struct obd_export *exp, struct obd_info *oinfo,
 
         /* This would be very bad - accidentally truncating a file when
          * changing the time or similar - bug 12203. */
-        if (oinfo->oi_oa->o_valid & OBD_MD_FLSIZE && 
+        if (oinfo->oi_oa->o_valid & OBD_MD_FLSIZE &&
             oinfo->oi_policy.l_extent.end != OBD_OBJECT_EOF) {
                 static char mdsinum[48];
 
@@ -3407,7 +3407,7 @@ static int filter_destroy_precreated(struct obd_export *exp, struct obdo *oa,
 
         CWARN("%s: deleting orphan objects from "LPU64" to "LPU64"\n",
                exp->exp_obd->obd_name, oa->o_id + 1, last);
-               
+
         for (id = last; id > oa->o_id; id--) {
                 doa.o_id = id;
                 rc = filter_destroy(exp, &doa, NULL, NULL, NULL);
@@ -3634,7 +3634,7 @@ static int filter_precreate(struct obd_device *obd, struct obdo *oa,
                         rc = -EAGAIN;
                         break;
                 }
-                
+
                 if (recreate_obj) {
                         __u64 last_id;
                         next_id = oa->o_id;
@@ -3947,13 +3947,13 @@ cleanup:
                                                      filter_cancel_cookies_cb,
                                                      fcc);
                 /* If add_journal_cb failed, then filter_finish_transno
-                 * will commit the handle and we will do a sync 
-                 * on commit. then we call callback directly to free 
-                 * the fcc. 
+                 * will commit the handle and we will do a sync
+                 * on commit. then we call callback directly to free
+                 * the fcc.
                  */
                 rc = filter_finish_transno(exp, oti, rc, sync);
                 if (sync) {
-                        filter_cancel_cookies_cb(obd, 0, fcc, rc); 
+                        filter_cancel_cookies_cb(obd, 0, fcc, rc);
                         fcc = NULL;
                 }
                 rc2 = fsfilt_commit(obd, dparent->d_inode, handle, 0);
@@ -4202,7 +4202,7 @@ static int filter_set_info_async(struct obd_export *exp, __u32 keylen,
                 RETURN(PTR_ERR(olg));
 
         llog_group_set_export(olg, exp);
-        
+
         ctxt = llog_group_get_ctxt(olg, LLOG_MDS_OST_REPL_CTXT);
         LASSERTF(ctxt != NULL, "ctxt is null\n"),