Whamcloud - gitweb
b=16098
[fs/lustre-release.git] / lustre / llite / lproc_llite.c
index 9ed89be..5a362a3 100644 (file)
@@ -1,23 +1,37 @@
 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
  * vim:expandtab:shiftwidth=8:tabstop=8:
  *
- *  Copyright (C) 2002 Cluster File Systems, Inc.
+ * GPL HEADER START
  *
- *   This file is part of Lustre, http://www.lustre.org.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
- *   Lustre is free software; you can redistribute it and/or
- *   modify it under the terms of version 2 of the GNU General Public
- *   License as published by the Free Software Foundation.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 only,
+ * as published by the Free Software Foundation.
  *
- *   Lustre is distributed in the hope that it will be useful,
- *   but WITHOUT ANY WARRANTY; without even the implied warranty of
- *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *   GNU General Public License for more details.
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License version 2 for more details (a copy is included
+ * in the LICENSE file that accompanied this code).
  *
- *   You should have received a copy of the GNU General Public License
- *   along with Lustre; if not, write to the Free Software
- *   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * You should have received a copy of the GNU General Public License
+ * version 2 along with this program; If not, see [sun.com URL with a
+ * copy of GPLv2].
  *
+ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+ * CA 95054 USA or visit www.sun.com if you need additional information or
+ * have any questions.
+ *
+ * GPL HEADER END
+ */
+/*
+ * Copyright  2008 Sun Microsystems, Inc. All rights reserved
+ * Use is subject to license terms.
+ */
+/*
+ * This file is part of Lustre, http://www.lustre.org/
+ * Lustre is a trademark of Sun Microsystems, Inc.
  */
 #define DEBUG_SUBSYSTEM S_LLITE
 
@@ -47,7 +61,8 @@ static int ll_rd_blksize(char *page, char **start, off_t off, int count,
         int rc;
 
         LASSERT(sb != NULL);
-        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ);
+        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ,
+                                OBD_STATFS_NODELAY);
         if (!rc) {
               *eof = 1;
               rc = snprintf(page, count, "%u\n", osfs.os_bsize);
@@ -64,7 +79,8 @@ static int ll_rd_kbytestotal(char *page, char **start, off_t off, int count,
         int rc;
 
         LASSERT(sb != NULL);
-        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ);
+        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ,
+                                OBD_STATFS_NODELAY);
         if (!rc) {
                 __u32 blk_size = osfs.os_bsize >> 10;
                 __u64 result = osfs.os_blocks;
@@ -87,7 +103,8 @@ static int ll_rd_kbytesfree(char *page, char **start, off_t off, int count,
         int rc;
 
         LASSERT(sb != NULL);
-        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ);
+        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ,
+                                OBD_STATFS_NODELAY);
         if (!rc) {
                 __u32 blk_size = osfs.os_bsize >> 10;
                 __u64 result = osfs.os_bfree;
@@ -109,7 +126,8 @@ static int ll_rd_kbytesavail(char *page, char **start, off_t off, int count,
         int rc;
 
         LASSERT(sb != NULL);
-        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ);
+        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ,
+                                OBD_STATFS_NODELAY);
         if (!rc) {
                 __u32 blk_size = osfs.os_bsize >> 10;
                 __u64 result = osfs.os_bavail;
@@ -131,7 +149,8 @@ static int ll_rd_filestotal(char *page, char **start, off_t off, int count,
         int rc;
 
         LASSERT(sb != NULL);
-        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ);
+        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ,
+                                OBD_STATFS_NODELAY);
         if (!rc) {
                  *eof = 1;
                  rc = snprintf(page, count, LPU64"\n", osfs.os_files);
@@ -147,7 +166,8 @@ static int ll_rd_filesfree(char *page, char **start, off_t off, int count,
         int rc;
 
         LASSERT(sb != NULL);
-        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ);
+        rc = ll_statfs_internal(sb, &osfs, cfs_time_current_64() - HZ,
+                                OBD_STATFS_NODELAY);
         if (!rc) {
                  *eof = 1;
                  rc = snprintf(page, count, LPU64"\n", osfs.os_ffree);
@@ -355,8 +375,8 @@ static int ll_wr_checksum(struct file *file, const char *buffer,
         else
                 sbi->ll_flags &= ~LL_SBI_CHECKSUM;
 
-        rc = obd_set_info_async(sbi->ll_dt_exp, strlen("checksum"), "checksum",
-                                sizeof(val), &val, NULL);
+        rc = obd_set_info_async(sbi->ll_dt_exp, sizeof(KEY_CHECKSUM),
+                                KEY_CHECKSUM, sizeof(val), &val, NULL);
         if (rc)
                 CWARN("Failed to set OSC checksum flags: %d\n", rc);
 
@@ -454,6 +474,97 @@ static int ll_wr_track_gid(struct file *file, const char *buffer,
         return (ll_wr_track_id(buffer, count, data, STATS_TRACK_GID));
 }
 
+static int ll_rd_statahead_max(char *page, char **start, off_t off,
+                               int count, int *eof, void *data)
+{
+        struct super_block *sb = data;
+        struct ll_sb_info *sbi = ll_s2sbi(sb);
+
+        return snprintf(page, count, "%u\n", sbi->ll_sa_max);
+}
+
+static int ll_wr_statahead_max(struct file *file, const char *buffer,
+                               unsigned long count, void *data)
+{
+        struct super_block *sb = data;
+        struct ll_sb_info *sbi = ll_s2sbi(sb);
+        int val, rc;
+
+        rc = lprocfs_write_helper(buffer, count, &val);
+        if (rc)
+                return rc;
+
+        if (val >= 0 && val <= LL_SA_RPC_MAX)
+                sbi->ll_sa_max = val;
+        else
+                CERROR("Bad statahead_max value %d. Valid values are in the "
+                       "range [0, %d]\n", val, LL_SA_RPC_MAX);
+
+        return count;
+}
+
+static int ll_rd_statahead_stats(char *page, char **start, off_t off,
+                                 int count, int *eof, void *data)
+{
+        struct super_block *sb = data;
+        struct ll_sb_info *sbi = ll_s2sbi(sb);
+
+        return snprintf(page, count,
+                        "statahead wrong: %u\n"
+                        "statahead total: %u\n"
+                        "ls blocked:      %llu\n"
+                        "ls cached:       %llu\n"
+                        "hit count:       %llu\n"
+                        "miss count:      %llu\n",
+                        sbi->ll_sa_wrong,
+                        sbi->ll_sa_total,
+                        sbi->ll_sa_blocked,
+                        sbi->ll_sa_cached,
+                        sbi->ll_sa_hit,
+                        sbi->ll_sa_miss);
+}
+
+static int ll_rd_contention_time(char *page, char **start, off_t off,
+                                 int count, int *eof, void *data)
+{
+        struct super_block *sb = data;
+
+        *eof = 1;
+        return snprintf(page, count, "%u\n", ll_s2sbi(sb)->ll_contention_time);
+
+}
+
+static int ll_wr_contention_time(struct file *file, const char *buffer,
+                                 unsigned long count, void *data)
+{
+        struct super_block *sb = data;
+        struct ll_sb_info *sbi = ll_s2sbi(sb);
+
+        return lprocfs_write_helper(buffer, count,&sbi->ll_contention_time) ?:
+                count;
+}
+
+static int ll_rd_lockless_truncate(char *page, char **start, off_t off,
+                                   int count, int *eof, void *data)
+{
+        struct super_block *sb = data;
+
+        *eof = 1;
+        return snprintf(page, count, "%u\n",
+                        ll_s2sbi(sb)->ll_lockless_truncate_enable);
+}
+
+static int ll_wr_lockless_truncate(struct file *file, const char *buffer,
+                                   unsigned long count, void *data)
+{
+        struct super_block *sb = data;
+        struct ll_sb_info *sbi = ll_s2sbi(sb);
+
+        return lprocfs_write_helper(buffer, count,
+                                    &sbi->ll_lockless_truncate_enable)
+                                    ?: count;
+}
+
 static struct lprocfs_vars lprocfs_llite_obd_vars[] = {
         { "uuid",         ll_rd_sb_uuid,          0, 0 },
         //{ "mntpt_path",   ll_rd_path,             0, 0 },
@@ -476,6 +587,11 @@ static struct lprocfs_vars lprocfs_llite_obd_vars[] = {
         { "stats_track_pid",  ll_rd_track_pid, ll_wr_track_pid, 0 },
         { "stats_track_ppid", ll_rd_track_ppid, ll_wr_track_ppid, 0 },
         { "stats_track_gid",  ll_rd_track_gid, ll_wr_track_gid, 0 },
+        { "statahead_max",    ll_rd_statahead_max, ll_wr_statahead_max, 0 },
+        { "statahead_stats",  ll_rd_statahead_stats, 0, 0 },
+        { "contention_seconds", ll_rd_contention_time, ll_wr_contention_time, 0},
+        { "lockless_truncate", ll_rd_lockless_truncate,
+                               ll_wr_lockless_truncate, 0},
         { 0 }
 };
 
@@ -515,6 +631,7 @@ struct llite_file_opcode {
         /* inode operation */
         { LPROC_LL_SETATTR,        LPROCFS_TYPE_REGS, "setattr" },
         { LPROC_LL_TRUNC,          LPROCFS_TYPE_REGS, "truncate" },
+        { LPROC_LL_LOCKLESS_TRUNC, LPROCFS_TYPE_REGS, "lockless_truncate"},
         { LPROC_LL_FLOCK,          LPROCFS_TYPE_REGS, "flock" },
         { LPROC_LL_GETATTR,        LPROCFS_TYPE_REGS, "getattr" },
         /* special inode operation */
@@ -529,6 +646,10 @@ struct llite_file_opcode {
                                    "direct_read" },
         { LPROC_LL_DIRECT_WRITE,   LPROCFS_CNTR_AVGMINMAX|LPROCFS_TYPE_PAGES,
                                    "direct_write" },
+        { LPROC_LL_LOCKLESS_READ,  LPROCFS_CNTR_AVGMINMAX|LPROCFS_TYPE_BYTES,
+                                   "lockless_read_bytes" },
+        { LPROC_LL_LOCKLESS_WRITE, LPROCFS_CNTR_AVGMINMAX|LPROCFS_TYPE_BYTES,
+                                   "lockless_write_bytes" },
 
 };
 
@@ -558,8 +679,7 @@ int lprocfs_register_mountpoint(struct proc_dir_entry *parent,
         struct ll_sb_info *sbi = ll_s2sbi(sb);
         struct obd_device *obd;
         char name[MAX_STRING_SIZE + 1], *ptr;
-        int err, id, len;
-        struct proc_dir_entry *entry;
+        int err, id, len, rc;
         ENTRY;
 
         memset(lvars, 0, sizeof(lvars));
@@ -588,36 +708,31 @@ int lprocfs_register_mountpoint(struct proc_dir_entry *parent,
                 RETURN(err);
         }
 
-        entry = create_proc_entry("dump_page_cache", 0444, sbi->ll_proc_root);
-        if (entry == NULL)
-                GOTO(out, err = -ENOMEM);
-        entry->proc_fops = &llite_dump_pgcache_fops;
-        entry->data = sbi;
 
-        entry = create_proc_entry("read_ahead_stats", 0644, sbi->ll_proc_root);
-        if (entry == NULL)
-                GOTO(out, err = -ENOMEM);
-        entry->proc_fops = &ll_ra_stats_fops;
-        entry->data = sbi;
-
-        entry = create_proc_entry("extents_stats", 0644, sbi->ll_proc_root);
-        if (entry == NULL)
-                 GOTO(out, err = -ENOMEM);
-        entry->proc_fops = &ll_rw_extents_stats_fops;
-        entry->data = sbi;
-
-        entry = create_proc_entry("extents_stats_per_process", 0644,
-                                  sbi->ll_proc_root);
-        if (entry == NULL)
-                 GOTO(out, err = -ENOMEM);
-        entry->proc_fops = &ll_rw_extents_stats_pp_fops;
-        entry->data = sbi;
-
-        entry = create_proc_entry("offset_stats", 0644, sbi->ll_proc_root);
-        if (entry == NULL)
-                GOTO(out, err = -ENOMEM);
-        entry->proc_fops = &ll_rw_offset_stats_fops;
-        entry->data = sbi;
+        rc = lprocfs_seq_create(sbi->ll_proc_root, "dump_page_cache", 0444,
+                                &llite_dump_pgcache_fops, sbi);
+        if (rc)
+                CWARN("Error adding the dump_page_cache file\n");
+
+        rc = lprocfs_seq_create(sbi->ll_proc_root, "read_ahead_stats", 0644,
+                                &ll_ra_stats_fops, sbi);
+        if (rc)
+                CWARN("Error adding the read_ahead_stats file\n");
+
+        rc = lprocfs_seq_create(sbi->ll_proc_root, "extents_stats", 0644,
+                                &ll_rw_extents_stats_fops, sbi);
+        if (rc)
+                CWARN("Error adding the extent_stats file\n");
+
+        rc = lprocfs_seq_create(sbi->ll_proc_root, "extents_stats_per_process",
+                                0644, &ll_rw_extents_stats_pp_fops, sbi);
+        if (rc)
+                CWARN("Error adding the extents_stats_per_process file\n");
+
+        rc = lprocfs_seq_create(sbi->ll_proc_root, "offset_stats", 0644,
+                                &ll_rw_offset_stats_fops, sbi);
+        if (rc)
+                CWARN("Error adding the offset_stats file\n");
 
         /* File operations stats */
         sbi->ll_stats = lprocfs_alloc_stats(LPROC_LL_FILE_OPCODES,