/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
* vim:expandtab:shiftwidth=8:tabstop=8:
*
- * Copyright 2008 Sun Microsystems, Inc. All rights reserved
+ * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
*
* This file is part of Portals
* http://sourceforge.net/projects/sandiaportals/
#if defined(__KERNEL__) && defined(LNET_ROUTER)
-/* this is really lnet_proc.c */
+/* This is really lnet_proc.c. You might need to update sanity test 215
+ * if any file format is changed. */
static cfs_sysctl_table_header_t *lnet_table_header = NULL;
#define PSDEV_LNET_NIS CTL_UNNUMBERED
#endif
+/*
+ * NB: we don't use the highest bit of *ppos because it's signed;
+ * next 9 bits is used to stash idx (assuming that
+ * LNET_PEER_HASHSIZE < 512)
+ */
+#define LNET_LOFFT_BITS (sizeof(loff_t) * 8)
+#define LNET_VERSION_BITS MAX(((MIN(LNET_LOFFT_BITS, 64)) / 4), 8)
+#define LNET_PHASH_IDX_BITS 9
+#define LNET_PHASH_NUM_BITS (LNET_LOFFT_BITS - 1 -\
+ LNET_VERSION_BITS - LNET_PHASH_IDX_BITS)
+#define LNET_PHASH_BITS (LNET_PHASH_IDX_BITS + LNET_PHASH_NUM_BITS)
+
+#define LNET_VERSION_BITMASK ((1ULL << LNET_VERSION_BITS) - 1)
+#define LNET_PHASH_IDX_BITMASK ((1ULL << LNET_PHASH_IDX_BITS) - 1)
+#define LNET_PHASH_NUM_BITMASK ((1ULL << LNET_PHASH_NUM_BITS) - 1)
+
+#define LNET_VERSION_MASK (LNET_VERSION_BITMASK << LNET_PHASH_BITS)
+#define LNET_PHASH_IDX_MASK (LNET_PHASH_IDX_BITMASK << LNET_PHASH_NUM_BITS)
+#define LNET_PHASH_NUM_MASK (LNET_PHASH_NUM_BITMASK)
+
+#define LNET_VERSION_GET(pos) (int)(((pos) & LNET_VERSION_MASK) >> \
+ LNET_PHASH_BITS)
+#define LNET_PHASH_IDX_GET(pos) (int)(((pos) & LNET_PHASH_IDX_MASK) >> \
+ LNET_PHASH_NUM_BITS)
+#define LNET_PHASH_NUM_GET(pos) (int)((pos) & LNET_PHASH_NUM_MASK)
+#define LNET_VERSION_VALID_MASK(ver) \
+ (unsigned int)((ver) & \
+ LNET_VERSION_BITMASK)
+#define LNET_PHASH_POS_MAKE(ver, idx, num) \
+ (((((loff_t)(ver)) & LNET_VERSION_BITMASK) << \
+ LNET_PHASH_BITS) | \
+ ((((loff_t)(idx)) & LNET_PHASH_IDX_BITMASK) <<\
+ LNET_PHASH_NUM_BITS) | \
+ ((num) & LNET_PHASH_NUM_BITMASK))
+
static int __proc_lnet_stats(void *data, int write,
loff_t pos, void *buffer, int nob)
{
if (pos >= min_t(int, len, strlen(tmpstr)))
rc = 0;
else
- rc = trace_copyout_string(buffer, nob,
- tmpstr + pos, "\n");
+ rc = cfs_trace_copyout_string(buffer, nob,
+ tmpstr + pos, "\n");
LIBCFS_FREE(tmpstr, tmpsiz);
LIBCFS_FREE(ctrs, sizeof(*ctrs));
char *s;
const int tmpsiz = 256;
int len;
- int *ver_p = (unsigned int *)(&filp->private_data);
+ int ver;
+ int num;
DECLARE_LL_PROC_PPOS_DECL;
+ num = LNET_PHASH_NUM_GET(*ppos);
+ ver = LNET_VERSION_GET(*ppos);
+
LASSERT (!write);
if (*lenp == 0)
LASSERT (tmpstr + tmpsiz - s > 0);
LNET_LOCK();
- *ver_p = (unsigned int)the_lnet.ln_remote_nets_version;
+ ver = (unsigned int)the_lnet.ln_remote_nets_version;
LNET_UNLOCK();
+ *ppos = LNET_PHASH_POS_MAKE(ver, 0, num);
} else {
- struct list_head *n;
- struct list_head *r;
+ cfs_list_t *n;
+ cfs_list_t *r;
lnet_route_t *route = NULL;
lnet_remotenet_t *rnet = NULL;
- int skip = *ppos - 1;
+ int skip = num - 1;
LNET_LOCK();
- if (*ver_p != (unsigned int)the_lnet.ln_remote_nets_version) {
+ if (ver != LNET_VERSION_VALID_MASK(the_lnet.ln_remote_nets_version)) {
LNET_UNLOCK();
LIBCFS_FREE(tmpstr, tmpsiz);
return -ESTALE;
n = the_lnet.ln_remote_nets.next;
while (n != &the_lnet.ln_remote_nets && route == NULL) {
- rnet = list_entry(n, lnet_remotenet_t, lrn_list);
+ rnet = cfs_list_entry(n, lnet_remotenet_t, lrn_list);
r = rnet->lrn_routes.next;
while (r != &rnet->lrn_routes) {
- lnet_route_t *re = list_entry(r, lnet_route_t,
- lr_list);
+ lnet_route_t *re =
+ cfs_list_entry(r, lnet_route_t,
+ lr_list);
if (skip == 0) {
route = re;
break;
if (len > *lenp) { /* linux-supplied buffer is too small */
rc = -EINVAL;
} else if (len > 0) { /* wrote something */
- if (copy_to_user(buffer, tmpstr, len))
+ if (cfs_copy_to_user(buffer, tmpstr, len))
rc = -EFAULT;
- else
- *ppos += 1;
+ else {
+ num += 1;
+ *ppos = LNET_PHASH_POS_MAKE(ver, 0, num);
+ }
}
LIBCFS_FREE(tmpstr, tmpsiz);
char *s;
const int tmpsiz = 256;
int len;
- int *ver_p = (unsigned int *)(&filp->private_data);
+ int ver;
+ int num;
DECLARE_LL_PROC_PPOS_DECL;
+ num = LNET_PHASH_NUM_GET(*ppos);
+ ver = LNET_VERSION_GET(*ppos);
+
LASSERT (!write);
if (*lenp == 0)
LASSERT (tmpstr + tmpsiz - s > 0);
LNET_LOCK();
- *ver_p = (unsigned int)the_lnet.ln_routers_version;
+ ver = (unsigned int)the_lnet.ln_routers_version;
LNET_UNLOCK();
+ *ppos = LNET_PHASH_POS_MAKE(ver, 0, num);
} else {
- struct list_head *r;
+ cfs_list_t *r;
lnet_peer_t *peer = NULL;
- int skip = *ppos - 1;
+ int skip = num - 1;
LNET_LOCK();
- if (*ver_p != (unsigned int)the_lnet.ln_routers_version) {
+ if (ver != LNET_VERSION_VALID_MASK(the_lnet.ln_routers_version)) {
LNET_UNLOCK();
LIBCFS_FREE(tmpstr, tmpsiz);
return -ESTALE;
r = the_lnet.ln_routers.next;
while (r != &the_lnet.ln_routers) {
- lnet_peer_t *lp = list_entry(r, lnet_peer_t,
- lp_rtr_list);
+ lnet_peer_t *lp = cfs_list_entry(r, lnet_peer_t,
+ lp_rtr_list);
if (skip == 0) {
peer = lp;
if (len > *lenp) { /* linux-supplied buffer is too small */
rc = -EINVAL;
} else if (len > 0) { /* wrote something */
- if (copy_to_user(buffer, tmpstr, len))
+ if (cfs_copy_to_user(buffer, tmpstr, len))
rc = -EFAULT;
- else
- *ppos += 1;
+ else {
+ num += 1;
+ *ppos = LNET_PHASH_POS_MAKE(ver, 0, num);
+ }
}
LIBCFS_FREE(tmpstr, tmpsiz);
return rc;
}
-/*
- * NB: we don't use the highest bit of *ppos because it's signed;
- * next 9 bits is used to stash idx (assuming that
- * LNET_PEER_HASHSIZE < 512)
- */
-#define LNET_LOFFT_BITS (sizeof(loff_t) * 8)
-#define LNET_PHASH_BITS 9
-#define LNET_PHASH_IDX_MASK (((1ULL << LNET_PHASH_BITS) - 1) << \
- (LNET_LOFFT_BITS - LNET_PHASH_BITS - 1))
-#define LNET_PHASH_NUM_MASK ((1ULL << \
- (LNET_LOFFT_BITS - LNET_PHASH_BITS -1)) - 1)
-#define LNET_PHASH_IDX_GET(pos) (int)(((pos) & LNET_PHASH_IDX_MASK) >> \
- (LNET_LOFFT_BITS - LNET_PHASH_BITS -1))
-#define LNET_PHASH_NUM_GET(pos) (int)((pos) & LNET_PHASH_NUM_MASK)
-#define LNET_PHASH_POS_MAKE(idx, num) ((((loff_t)idx) << (LNET_LOFFT_BITS - \
- LNET_PHASH_BITS -1)) | (num))
-
int LL_PROC_PROTO(proc_lnet_peers)
{
int rc = 0;
char *s;
const int tmpsiz = 256;
int len;
- int *ver_p = (unsigned int *)(&filp->private_data);
+ int ver;
int idx;
int num;
idx = LNET_PHASH_IDX_GET(*ppos);
num = LNET_PHASH_NUM_GET(*ppos);
+ ver = LNET_VERSION_GET(*ppos);
- CLASSERT ((1 << LNET_PHASH_BITS) > LNET_PEER_HASHSIZE);
+ CLASSERT ((1ULL << LNET_PHASH_BITS) > LNET_PEER_HASHSIZE);
LASSERT (!write);
if (*ppos == 0) {
s += snprintf(s, tmpstr + tmpsiz - s,
- "%-24s %4s %5s %5s %5s %5s %5s %5s %s\n",
- "nid", "refs", "state", "max",
+ "%-24s %4s %5s %5s %5s %5s %5s %5s %5s %s\n",
+ "nid", "refs", "state", "last", "max",
"rtr", "min", "tx", "min", "queue");
LASSERT (tmpstr + tmpsiz - s > 0);
LNET_LOCK();
- *ver_p = (unsigned int)the_lnet.ln_peertable_version;
+ ver = (unsigned int)the_lnet.ln_peertable_version;
LNET_UNLOCK();
+ *ppos = LNET_PHASH_POS_MAKE(ver, idx, num);
num++;
} else {
- struct list_head *p = NULL;
+ cfs_list_t *p = NULL;
lnet_peer_t *peer = NULL;
int skip = num - 1;
LNET_LOCK();
- if (*ver_p != (unsigned int)the_lnet.ln_peertable_version) {
+ if (ver != LNET_VERSION_VALID_MASK(the_lnet.ln_peertable_version)) {
LNET_UNLOCK();
LIBCFS_FREE(tmpstr, tmpsiz);
return -ESTALE;
p = the_lnet.ln_peer_hash[idx].next;
while (p != &the_lnet.ln_peer_hash[idx]) {
- lnet_peer_t *lp = list_entry(p, lnet_peer_t,
- lp_hashlist);
+ lnet_peer_t *lp = cfs_list_entry(p, lnet_peer_t,
+ lp_hashlist);
if (skip == 0) {
peer = lp;
- /* minor optimiztion: start from idx+1
+ /* minor optimization: start from idx+1
* on next iteration if we've just
* drained lp_hashlist */
if (lp->lp_hashlist.next ==
if (peer != NULL) {
lnet_nid_t nid = peer->lp_nid;
int nrefs = peer->lp_refcount;
+ int lastalive = -1;
char *aliveness = "NA";
int maxcr = peer->lp_ni->ni_peertxcredits;
int txcr = peer->lp_txcredits;
int txqnob = peer->lp_txqnob;
if (lnet_isrouter(peer) ||
- peer->lp_ni->ni_peertimeout > 0)
+ lnet_peer_aliveness_enabled(peer))
aliveness = peer->lp_alive ? "up" : "down";
+ if (lnet_peer_aliveness_enabled(peer)) {
+ cfs_time_t now = cfs_time_current();
+ cfs_duration_t delta;
+
+ delta = cfs_time_sub(now, peer->lp_last_alive);
+ lastalive = cfs_duration_sec(delta);
+
+ /* No need to mess up peers contents with
+ * arbitrarily long integers - it suffices to
+ * know that lastalive is more than 10000s old
+ */
+ if (lastalive >= 10000)
+ lastalive = 9999;
+ }
+
s += snprintf(s, tmpstr + tmpsiz - s,
- "%-24s %4d %5s %5d %5d %5d %5d %5d %d\n",
+ "%-24s %4d %5s %5d %5d %5d %5d %5d %5d %d\n",
libcfs_nid2str(nid), nrefs, aliveness,
- maxcr, rtrcr, minrtrcr, txcr,
+ lastalive, maxcr, rtrcr, minrtrcr, txcr,
mintxcr, txqnob);
LASSERT (tmpstr + tmpsiz - s > 0);
}
if (len > *lenp) { /* linux-supplied buffer is too small */
rc = -EINVAL;
} else if (len > 0) { /* wrote something */
- if (copy_to_user(buffer, tmpstr, len))
+ if (cfs_copy_to_user(buffer, tmpstr, len))
rc = -EFAULT;
else
- *ppos = LNET_PHASH_POS_MAKE(idx, num);
+ *ppos = LNET_PHASH_POS_MAKE(ver, idx, num);
}
LIBCFS_FREE(tmpstr, tmpsiz);
if (pos >= min_t(int, len, strlen(tmpstr)))
rc = 0;
else
- rc = trace_copyout_string(buffer, nob,
- tmpstr + pos, NULL);
+ rc = cfs_trace_copyout_string(buffer, nob,
+ tmpstr + pos, NULL);
LIBCFS_FREE(tmpstr, tmpsiz);
return rc;
"rtr", "max", "tx", "min");
LASSERT (tmpstr + tmpsiz - s > 0);
} else {
- struct list_head *n;
+ cfs_list_t *n;
lnet_ni_t *ni = NULL;
int skip = *ppos - 1;
n = the_lnet.ln_nis.next;
while (n != &the_lnet.ln_nis) {
- lnet_ni_t *a_ni = list_entry(n, lnet_ni_t, ni_list);
+ lnet_ni_t *a_ni = cfs_list_entry(n, lnet_ni_t, ni_list);
if (skip == 0) {
ni = a_ni;
if (len > *lenp) { /* linux-supplied buffer is too small */
rc = -EINVAL;
} else if (len > 0) { /* wrote something */
- if (copy_to_user(buffer, tmpstr, len))
+ if (cfs_copy_to_user(buffer, tmpstr, len))
rc = -EFAULT;
else
*ppos += 1;
* to go via /proc for portability.
*/
{
- .ctl_name = PSDEV_LNET_STATS,
+ INIT_CTL_NAME(PSDEV_LNET_STATS)
.procname = "stats",
.mode = 0644,
.proc_handler = &proc_lnet_stats,
},
{
- .ctl_name = PSDEV_LNET_ROUTES,
+ INIT_CTL_NAME(PSDEV_LNET_ROUTES)
.procname = "routes",
.mode = 0444,
.proc_handler = &proc_lnet_routes,
},
{
- .ctl_name = PSDEV_LNET_ROUTERS,
+ INIT_CTL_NAME(PSDEV_LNET_ROUTERS)
.procname = "routers",
.mode = 0444,
.proc_handler = &proc_lnet_routers,
},
{
- .ctl_name = PSDEV_LNET_PEERS,
+ INIT_CTL_NAME(PSDEV_LNET_PEERS)
.procname = "peers",
.mode = 0444,
.proc_handler = &proc_lnet_peers,
},
{
- .ctl_name = PSDEV_LNET_PEERS,
+ INIT_CTL_NAME(PSDEV_LNET_PEERS)
.procname = "buffers",
.mode = 0444,
.proc_handler = &proc_lnet_buffers,
},
{
- .ctl_name = PSDEV_LNET_NIS,
+ INIT_CTL_NAME(PSDEV_LNET_NIS)
.procname = "nis",
.mode = 0444,
.proc_handler = &proc_lnet_nis,
},
- {0}
+ {
+ INIT_CTL_NAME(0)
+ }
};
static cfs_sysctl_table_t top_table[] = {
{
- .ctl_name = CTL_LNET,
+ INIT_CTL_NAME(CTL_LNET)
.procname = "lnet",
.mode = 0555,
.data = NULL,
.child = lnet_table,
},
{
- .ctl_name = 0
+ INIT_CTL_NAME(0)
}
};