Back to home page

OSCL-LXR

 
 

    


0001 /*
0002  * Kernel CAPI 2.0 Module - /proc/capi handling
0003  *
0004  * Copyright 1999 by Carsten Paeth <calle@calle.de>
0005  * Copyright 2002 by Kai Germaschewski <kai@germaschewski.name>
0006  *
0007  * This software may be used and distributed according to the terms
0008  * of the GNU General Public License, incorporated herein by reference.
0009  *
0010  */
0011 
0012 
0013 #include "kcapi.h"
0014 #include <linux/proc_fs.h>
0015 #include <linux/seq_file.h>
0016 #include <linux/init.h>
0017 #include <linux/export.h>
0018 
0019 static char *state2str(unsigned short state)
0020 {
0021     switch (state) {
0022     case CAPI_CTR_DETECTED: return "detected";
0023     case CAPI_CTR_LOADING:  return "loading";
0024     case CAPI_CTR_RUNNING:  return "running";
0025     default:            return "???";
0026     }
0027 }
0028 
0029 // /proc/capi
0030 // ===========================================================================
0031 
0032 // /proc/capi/controller:
0033 //      cnr driver cardstate name driverinfo
0034 // /proc/capi/contrstats:
0035 //      cnr nrecvctlpkt nrecvdatapkt nsentctlpkt nsentdatapkt
0036 // ---------------------------------------------------------------------------
0037 
0038 static void *controller_start(struct seq_file *seq, loff_t *pos)
0039     __acquires(capi_controller_lock)
0040 {
0041     mutex_lock(&capi_controller_lock);
0042 
0043     if (*pos < CAPI_MAXCONTR)
0044         return &capi_controller[*pos];
0045 
0046     return NULL;
0047 }
0048 
0049 static void *controller_next(struct seq_file *seq, void *v, loff_t *pos)
0050 {
0051     ++*pos;
0052     if (*pos < CAPI_MAXCONTR)
0053         return &capi_controller[*pos];
0054 
0055     return NULL;
0056 }
0057 
0058 static void controller_stop(struct seq_file *seq, void *v)
0059     __releases(capi_controller_lock)
0060 {
0061     mutex_unlock(&capi_controller_lock);
0062 }
0063 
0064 static int controller_show(struct seq_file *seq, void *v)
0065 {
0066     struct capi_ctr *ctr = *(struct capi_ctr **) v;
0067 
0068     if (!ctr)
0069         return 0;
0070 
0071     seq_printf(seq, "%d %-10s %-8s %-16s %s\n",
0072            ctr->cnr, ctr->driver_name,
0073            state2str(ctr->state),
0074            ctr->name,
0075            ctr->procinfo ?  ctr->procinfo(ctr) : "");
0076 
0077     return 0;
0078 }
0079 
0080 static int contrstats_show(struct seq_file *seq, void *v)
0081 {
0082     struct capi_ctr *ctr = *(struct capi_ctr **) v;
0083 
0084     if (!ctr)
0085         return 0;
0086 
0087     seq_printf(seq, "%d %lu %lu %lu %lu\n",
0088            ctr->cnr,
0089            ctr->nrecvctlpkt,
0090            ctr->nrecvdatapkt,
0091            ctr->nsentctlpkt,
0092            ctr->nsentdatapkt);
0093 
0094     return 0;
0095 }
0096 
0097 static const struct seq_operations seq_controller_ops = {
0098     .start  = controller_start,
0099     .next   = controller_next,
0100     .stop   = controller_stop,
0101     .show   = controller_show,
0102 };
0103 
0104 static const struct seq_operations seq_contrstats_ops = {
0105     .start  = controller_start,
0106     .next   = controller_next,
0107     .stop   = controller_stop,
0108     .show   = contrstats_show,
0109 };
0110 
0111 // /proc/capi/applications:
0112 //      applid l3cnt dblkcnt dblklen #ncci recvqueuelen
0113 // /proc/capi/applstats:
0114 //      applid nrecvctlpkt nrecvdatapkt nsentctlpkt nsentdatapkt
0115 // ---------------------------------------------------------------------------
0116 
0117 static void *applications_start(struct seq_file *seq, loff_t *pos)
0118     __acquires(capi_controller_lock)
0119 {
0120     mutex_lock(&capi_controller_lock);
0121 
0122     if (*pos < CAPI_MAXAPPL)
0123         return &capi_applications[*pos];
0124 
0125     return NULL;
0126 }
0127 
0128 static void *
0129 applications_next(struct seq_file *seq, void *v, loff_t *pos)
0130 {
0131     ++*pos;
0132     if (*pos < CAPI_MAXAPPL)
0133         return &capi_applications[*pos];
0134 
0135     return NULL;
0136 }
0137 
0138 static void applications_stop(struct seq_file *seq, void *v)
0139     __releases(capi_controller_lock)
0140 {
0141     mutex_unlock(&capi_controller_lock);
0142 }
0143 
0144 static int
0145 applications_show(struct seq_file *seq, void *v)
0146 {
0147     struct capi20_appl *ap = *(struct capi20_appl **) v;
0148 
0149     if (!ap)
0150         return 0;
0151 
0152     seq_printf(seq, "%u %d %d %d\n",
0153            ap->applid,
0154            ap->rparam.level3cnt,
0155            ap->rparam.datablkcnt,
0156            ap->rparam.datablklen);
0157 
0158     return 0;
0159 }
0160 
0161 static int
0162 applstats_show(struct seq_file *seq, void *v)
0163 {
0164     struct capi20_appl *ap = *(struct capi20_appl **) v;
0165 
0166     if (!ap)
0167         return 0;
0168 
0169     seq_printf(seq, "%u %lu %lu %lu %lu\n",
0170            ap->applid,
0171            ap->nrecvctlpkt,
0172            ap->nrecvdatapkt,
0173            ap->nsentctlpkt,
0174            ap->nsentdatapkt);
0175 
0176     return 0;
0177 }
0178 
0179 static const struct seq_operations seq_applications_ops = {
0180     .start  = applications_start,
0181     .next   = applications_next,
0182     .stop   = applications_stop,
0183     .show   = applications_show,
0184 };
0185 
0186 static const struct seq_operations seq_applstats_ops = {
0187     .start  = applications_start,
0188     .next   = applications_next,
0189     .stop   = applications_stop,
0190     .show   = applstats_show,
0191 };
0192 
0193 // ---------------------------------------------------------------------------
0194 
0195 /* /proc/capi/drivers is always empty */
0196 static ssize_t empty_read(struct file *file, char __user *buf,
0197               size_t size, loff_t *off)
0198 {
0199     return 0;
0200 }
0201 
0202 static const struct proc_ops empty_proc_ops = {
0203     .proc_read  = empty_read,
0204     .proc_lseek = default_llseek,
0205 };
0206 
0207 // ---------------------------------------------------------------------------
0208 
0209 void __init
0210 kcapi_proc_init(void)
0211 {
0212     proc_mkdir("capi",             NULL);
0213     proc_mkdir("capi/controllers", NULL);
0214     proc_create_seq("capi/controller",   0, NULL, &seq_controller_ops);
0215     proc_create_seq("capi/contrstats",   0, NULL, &seq_contrstats_ops);
0216     proc_create_seq("capi/applications", 0, NULL, &seq_applications_ops);
0217     proc_create_seq("capi/applstats",    0, NULL, &seq_applstats_ops);
0218     proc_create("capi/driver",           0, NULL, &empty_proc_ops);
0219 }
0220 
0221 void
0222 kcapi_proc_exit(void)
0223 {
0224     remove_proc_entry("capi/driver",       NULL);
0225     remove_proc_entry("capi/controller",   NULL);
0226     remove_proc_entry("capi/contrstats",   NULL);
0227     remove_proc_entry("capi/applications", NULL);
0228     remove_proc_entry("capi/applstats",    NULL);
0229     remove_proc_entry("capi/controllers",  NULL);
0230     remove_proc_entry("capi",              NULL);
0231 }