The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/port/devmntstats.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 #include        "u.h"
    2 #include        "../port/lib.h"
    3 #include        "mem.h"
    4 #include        "dat.h"
    5 #include        "fns.h"
    6 #include        "../port/error.h"
    7 
    8 void (*mntstats)(int, Chan*, uvlong, ulong);
    9 
   10 enum
   11 {
   12         Qmntstat = 1<<12,
   13 
   14         Nhash=  31,
   15         Nms=    256,
   16         Nrpc=   (Tmax-Tnop)/2,
   17 };
   18 
   19 typedef struct Mntstats Mntstats;
   20 struct Mntstats
   21 {
   22         Mntstats *next;
   23         int     inuse;
   24         Chan    c;
   25         uvlong  hi[Nrpc];               /* high water time spent */
   26         uvlong  tot[Nrpc];              /* cumulative time spent */
   27         uvlong  bytes[Nrpc];            /* cumulative bytes xfered */
   28         ulong   n[Nrpc];                /* number of messages/msg type */
   29         uvlong  bigtot[Nrpc];           /* cumulative time spent in big messages */
   30         uvlong  bigbytes[Nrpc];         /* cumulative bytes xfered in big messages */
   31         ulong   bign[Nrpc];             /* number of big messages */
   32 };
   33 
   34 static struct
   35 {
   36         Lock;
   37         Mntstats        *hash[Nhash];
   38         Mntstats        all[Nms];
   39         int             n;
   40 } msalloc;
   41 
   42 static void
   43 _mntstats(int type, Chan *c, uvlong start, ulong bytes)
   44 {
   45         uint h;
   46         Mntstats **l, *m;
   47         uvlong elapsed;
   48 
   49         elapsed = fastticks(nil) - start;
   50         type -= Tnop;
   51         type >>= 1;
   52 
   53         h = (c->dev<<4)+(c->type<<2)+c->qid.path;
   54         h %= Nhash;
   55         for(l = &msalloc.hash[h]; *l; l = &(*l)->next)
   56                 if(eqchan(&(*l)->c, c, 0))
   57                         break;
   58         m = *l;
   59 
   60         if(m == nil){
   61                 lock(&msalloc);
   62                 for(m = msalloc.all; m < &msalloc.all[Nms]; m++)
   63                         if(m->inuse && eqchan(&m->c, c, 0))
   64                                 break;
   65                 if(m == &msalloc.all[Nms])
   66                         for(m = msalloc.all; m < &msalloc.all[Nms]; m++){
   67                                 if(m->inuse == 0){
   68                                         m->inuse = 1;
   69                                         m->c = *c;
   70                                         *l = m;
   71                                         msalloc.n++;
   72                                         break;
   73                                 }
   74                         }
   75                 unlock(&msalloc);
   76                 if(m >= &msalloc.all[Nms])
   77                         return;
   78         }
   79 
   80         if(m->hi[type] < elapsed)
   81                 m->hi[type] = elapsed;
   82         m->tot[type] += elapsed;
   83         m->n[type]++;
   84         m->bytes[type] += bytes;
   85 
   86         if(bytes >= 8*1024){
   87                 m->bigtot[type] += elapsed;
   88                 m->bign[type]++;
   89                 m->bigbytes[type] += bytes;
   90         }
   91 }
   92 
   93 static int
   94 mntstatsgen(Chan *c, Dirtab*, int, int i, Dir *dp)
   95 {
   96         Qid q;
   97         Mntstats *m;
   98 
   99         if(i == DEVDOTDOT){
  100                 devdir(c, (Qid){CHDIR,0}, "#z", 0, eve, 0555, dp);
  101                 return 1;
  102         }
  103 
  104         m = &msalloc.all[i];
  105         if(i > Nms || m->inuse == 0)
  106                 return -1;
  107 
  108         q = (Qid){Qmntstat+i, 0};
  109         snprint(up->genbuf, sizeof up->genbuf, "%C%lud.%lux", devtab[m->c.type]->dc, m->c.dev, m->c.qid.path);
  110         devdir(c, q, up->genbuf, 0, eve, 0666, dp);
  111 
  112         return 1;
  113 }
  114 
  115 static void
  116 mntstatsinit(void)
  117 {
  118         mntstats = _mntstats;
  119 }
  120 
  121 static Chan*
  122 mntstatsattach(char *spec)
  123 {
  124         return devattach('z', spec);
  125 }
  126 
  127 static int
  128 mntstatswalk(Chan *c, char *name)
  129 {
  130         return devwalk(c, name, 0, msalloc.n, mntstatsgen);
  131 }
  132 
  133 static void
  134 mntstatsstat(Chan *c, char *dp)
  135 {
  136         devstat(c, dp, 0, msalloc.n, mntstatsgen);
  137 }
  138 
  139 static Chan*
  140 mntstatsopen(Chan *c, int omode)
  141 {
  142         return devopen(c, omode, 0, msalloc.n, mntstatsgen);
  143 }
  144 
  145 static void
  146 mntstatsclose(Chan*)
  147 {
  148 }
  149 
  150 enum
  151 {
  152         Nline=  136,
  153 };
  154 
  155 char *rpcname[Nrpc] =
  156 {
  157         "nop",
  158         "osession",
  159         "error",
  160         "flush",
  161         "oattach",
  162         "clone",
  163         "walk",
  164         "open",
  165         "create",
  166         "read",
  167         "write",
  168         "clunk",
  169         "remove",
  170         "stat",
  171         "wstat",
  172         "clwalk",
  173         "auth",
  174         "session",
  175         "attach",
  176 };
  177 
  178 static long
  179 mntstatsread(Chan *c, void *buf, long n, vlong off)
  180 {
  181         char *a, *start;
  182         ulong o;
  183         char xbuf[Nline+1];
  184         Mntstats *m;
  185 
  186         start = a = buf;
  187 
  188         if(n <= 0)
  189                 return n;
  190 
  191         if(c->qid.path & CHDIR)
  192                 return devdirread(c, buf, n, 0, msalloc.n, mntstatsgen);
  193 
  194         m = &msalloc.all[c->qid.path - Qmntstat];
  195         o = off;
  196         if((o % Nline) != 0)
  197                 error(Ebadarg);
  198         n = n/Nline;
  199         o = o/Nline;
  200         while(n > 0 && o < Nrpc){
  201                 snprint(xbuf, sizeof(xbuf), "%-8.8s\t%20.0llud\n\t%20.0llud %20.0llud %9.0lud\n\t%20.0llud %20.0llud %9.0lud\n",
  202                         rpcname[o], m->hi[o],
  203                         m->tot[o], m->bytes[o], m->n[o],
  204                         m->bigtot[o], m->bigbytes[o], m->bign[o]);
  205                 memmove(a, xbuf, Nline);
  206                 a += Nline;
  207                 o++;
  208                 n--;
  209         }
  210         return a - start;
  211 }
  212 
  213 static long
  214 mntstatswrite(Chan*, void*, long, vlong)
  215 {
  216         lock(&msalloc);
  217         memset(msalloc.all, 0, sizeof(msalloc.all));
  218         msalloc.n = 0;
  219         unlock(&msalloc);
  220         return 0;
  221 }
  222 
  223 Dev mntstatsdevtab = {
  224         'z',
  225         "mntstats",
  226 
  227         devreset,
  228         mntstatsinit,
  229         mntstatsattach,
  230         devclone,
  231         mntstatswalk,
  232         mntstatsstat,
  233         mntstatsopen,
  234         devcreate,
  235         mntstatsclose,
  236         mntstatsread,
  237         devbread,
  238         mntstatswrite,
  239         devbwrite,
  240         devremove,
  241         devwstat,
  242 };

Cache object: 489e5a2be4595a3a56ea3717260612f6


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.