1 /*-
2 * ===================================
3 * HARP | Host ATM Research Platform
4 * ===================================
5 *
6 * This Host ATM Research Platform ("HARP") file (the "Software") is
7 * made available by Network Computing Services, Inc. ("NetworkCS")
8 * "AS IS". NetworkCS does not provide maintenance, improvements or
9 * support of any kind.
10 *
11 * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
12 * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
13 * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
14 * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
15 * In no event shall NetworkCS be responsible for any damages, including
16 * but not limited to consequential damages, arising from or relating to
17 * any use of the Software or related support.
18 *
19 * Copyright 1994-1998 Network Computing Services, Inc.
20 *
21 * Copies of this Software may be made, however, the above copyright
22 * notice must be reproduced on all copies.
23 */
24
25 #include <sys/cdefs.h>
26 __FBSDID("$FreeBSD$");
27
28 /*
29 * FORE Systems 200-Series Adapter Support
30 * ---------------------------------------
31 *
32 * Device statistics routines
33 *
34 */
35
36 #include <sys/param.h>
37 #include <sys/systm.h>
38 #include <sys/socket.h>
39 #include <sys/socketvar.h>
40 #include <vm/vm.h>
41 #include <vm/pmap.h>
42 #include <net/if.h>
43 #include <netatm/port.h>
44 #include <netatm/queue.h>
45 #include <netatm/atm.h>
46 #include <netatm/atm_sys.h>
47 #include <netatm/atm_sap.h>
48 #include <netatm/atm_cm.h>
49 #include <netatm/atm_if.h>
50 #include <netatm/atm_stack.h>
51 #include <netatm/atm_pcb.h>
52 #include <netatm/atm_var.h>
53 #include <dev/pci/pcivar.h>
54 #include <dev/hfa/fore.h>
55 #include <dev/hfa/fore_aali.h>
56 #include <dev/hfa/fore_slave.h>
57 #include <dev/hfa/fore_stats.h>
58 #include <dev/hfa/fore_var.h>
59 #include <dev/hfa/fore_include.h>
60
61 #ifndef lint
62 __RCSID("@(#) $FreeBSD$");
63 #endif
64
65
66 /*
67 * Get device statistics from CP
68 *
69 * This function will issue a GET_STATS command to the CP in order to
70 * initiate the DMA transfer of the CP's statistics structure to the host.
71 * We will then sleep pending command completion. This must only be called
72 * from the ioctl system call handler.
73 *
74 * Called at splnet.
75 *
76 * Arguments:
77 * fup pointer to device unit structure
78 *
79 * Returns:
80 * 0 stats retrieval successful
81 * errno stats retrieval failed - reason indicated
82 *
83 */
84 int
85 fore_get_stats(fup)
86 Fore_unit *fup;
87 {
88 H_cmd_queue *hcp;
89 Cmd_queue *cqp;
90 int s, sst;
91
92 ATM_DEBUG1("fore_get_stats: fup=%p\n", fup);
93
94 /*
95 * Make sure device has been initialized
96 */
97 if ((fup->fu_flags & CUF_INITED) == 0) {
98 return (EIO);
99 }
100
101 /*
102 * If someone has already initiated a stats request, we'll
103 * just wait for that one to complete
104 */
105 s = splimp();
106 if (fup->fu_flags & FUF_STATCMD) {
107
108 #if (defined(BSD) && (BSD >= 199103))
109 sst = tsleep((caddr_t)&fup->fu_stats, PWAIT|PCATCH, "fore", 0);
110 #else
111 sst = sleep((caddr_t)&fup->fu_stats, PWAIT|PCATCH);
112 if (sst != 0)
113 sst = EINTR;
114 #endif
115 (void) splx(s);
116 return (sst ? sst : fup->fu_stats_ret);
117 }
118
119 /*
120 * Limit stats gathering to once a second or so
121 */
122 if (time_second == fup->fu_stats_time) {
123 (void) splx(s);
124 return (0);
125 } else
126 fup->fu_stats_time = time_second;
127
128 /*
129 * Queue command at end of command queue
130 */
131 hcp = fup->fu_cmd_tail;
132 if ((*hcp->hcq_status) & QSTAT_FREE) {
133 vm_paddr_t dma;
134
135 /*
136 * Queue entry available, so set our view of things up
137 */
138 hcp->hcq_code = CMD_GET_STATS;
139 hcp->hcq_arg = NULL;
140 fup->fu_cmd_tail = hcp->hcq_next;
141
142 /*
143 * Now set the CP-resident queue entry - the CP will grab
144 * the command when the op-code is set.
145 */
146 cqp = hcp->hcq_cpelem;
147 (*hcp->hcq_status) = QSTAT_PENDING;
148
149 dma = vtophys(fup->fu_stats);
150 if (dma == 0) {
151 fup->fu_stats->st_drv.drv_cm_nodma++;
152 (void) splx(s);
153 return (EIO);
154 }
155 fup->fu_statsd = dma;
156 cqp->cmdq_stats.stats_buffer = (CP_dma) CP_WRITE(dma);
157
158 fup->fu_flags |= FUF_STATCMD;
159 cqp->cmdq_stats.stats_cmd =
160 CP_WRITE(CMD_GET_STATS | CMD_INTR_REQ);
161
162 /*
163 * Now wait for command to finish
164 */
165 #if (defined(BSD) && (BSD >= 199103))
166 sst = tsleep((caddr_t)&fup->fu_stats, PWAIT|PCATCH, "fore", 0);
167 #else
168 sst = sleep((caddr_t)&fup->fu_stats, PWAIT|PCATCH);
169 if (sst != 0)
170 sst = EINTR;
171 #endif
172 (void) splx(s);
173 return (sst ? sst : fup->fu_stats_ret);
174
175 } else {
176 /*
177 * Command queue full
178 */
179 fup->fu_stats->st_drv.drv_cm_full++;
180 (void) splx(s);
181 return (EIO);
182 }
183 }
184
Cache object: 0ac6e583ad8518209c36e3c236b18170
|