Initial import from FreeBSD RELENG_4:
[dragonfly.git] / sys / dev / atm / hea / eni.h
1 /*
2  *
3  * ===================================
4  * HARP  |  Host ATM Research Platform
5  * ===================================
6  *
7  *
8  * This Host ATM Research Platform ("HARP") file (the "Software") is
9  * made available by Network Computing Services, Inc. ("NetworkCS")
10  * "AS IS".  NetworkCS does not provide maintenance, improvements or
11  * support of any kind.
12  *
13  * NETWORKCS MAKES NO WARRANTIES OR REPRESENTATIONS, EXPRESS OR IMPLIED,
14  * INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY
15  * AND FITNESS FOR A PARTICULAR PURPOSE, AS TO ANY ELEMENT OF THE
16  * SOFTWARE OR ANY SUPPORT PROVIDED IN CONNECTION WITH THIS SOFTWARE.
17  * In no event shall NetworkCS be responsible for any damages, including
18  * but not limited to consequential damages, arising from or relating to
19  * any use of the Software or related support.
20  *
21  * Copyright 1994-1998 Network Computing Services, Inc.
22  *
23  * Copies of this Software may be made, however, the above copyright
24  * notice must be reproduced on all copies.
25  *
26  *      @(#) $FreeBSD: src/sys/dev/hea/eni.h,v 1.2 1999/08/28 00:41:43 peter Exp $
27  *
28  */
29
30 /*
31  * Efficient ENI Adapter Support
32  *
33  * Protocol and implementation definitions
34  *
35  */
36
37 #ifndef _ENI_ENI_H
38 #define _ENI_ENI_H
39
40 #include <pci/pcireg.h>
41 #include <pci/pcivar.h>
42
43 /*
44  * Physical device name - used to configure HARP devices
45  */
46 #ifndef ENI_DEV_NAME
47 #define ENI_DEV_NAME    "hea"           /* HARP Efficient ATM */
48 #endif
49
50 #define ENI_MAX_UNITS   4
51
52 #define ENI_IFF_MTU     9188
53 #define ENI_MAX_VCI     1023            /* 0 - 1023 */
54 #define ENI_MAX_VPI     0
55
56 #define ENI_IFQ_MAXLEN  1000            /* rx/tx queue lengths */
57
58 #ifdef  BSD
59 /*
60  * Size of small and large receive buffers
61  */
62 #define ENI_SMALL_BSIZE         64
63 #define ENI_LARGE_BSIZE         MCLBYTES
64 #endif  /* BSD */
65
66 /*
67  * ENI memory map offsets IN WORDS, not bytes
68  *
69  * The Efficient Adapter implements a 4 MB address space. The lower
70  * 2 MB are used by bootprom (E)EPROM and by chipset registers such
71  * as the MIDWAY and SUNI chips. The (upto) upper 2 MB is used for
72  * RAM. Of the RAM, the lower 28 KB is used for fixed tables - the
73  * VCI table, the RX and TX DMA queues, and the Service List queue.
74  * Memory above the 28 KB range is available for RX and TX buffers.
75  *
76  * NOTE: Access to anything other then the (E)EPROM MUST be as a 32 bit
77  * access. Also note that Efficient uses both byte addresses and word
78  * addresses when describing offsets. BE CAREFUL or you'll get confused!
79  */
80 /*
81  * Size of memory space reserved for registers and expansion (e)eprom.
82  */
83 #define ENI_REG_SIZE    0x200000        /* Two megabytes */
84
85 #define SUNI_OFFSET     0x008000        /* SUNI chip registers */
86 #define MIDWAY_OFFSET   0x010000        /* MIDWAY chip registers */
87 #define RAM_OFFSET      0x080000        /* Adapter RAM */
88 #define VCITBL_OFFSET   0x080000        /* VCI Table offset */
89 #define RXQUEUE_OFFSET  0x081000        /* RX DMA Queue offset */
90 #define TXQUEUE_OFFSET  0x081400        /* TX DMA Queue offset */
91 #define SVCLIST_OFFSET  0x081800        /* SVC List Queue offset */
92
93 #define SEGBUF_BASE     0x007000        /* Base from start of RAM */
94
95 #define DMA_LIST_SIZE   512             /* 1024 words / 2 words per entry */
96 #define SVC_LIST_SIZE   1024            /* 1024 words / 1 word  per entry */
97
98 /*
99  * Values for testing size of RAM on adapter
100  *
101  * Efficient has (at least) two different memory sizes available. One
102  * is a client card which has either 128 KB or 512 KB RAM, the other
103  * is a server card which has 2 MB RAM. The driver will size and test
104  * the memory to correctly determine what's available.
105  */
106 #define MAX_ENI_MEM     0x200000        /* 2 MB - max. mem supported */
107 #define TEST_STEP       0x000400        /* Look at 1 KB steps */
108 #define TEST_PAT        0xA5A5A5A5      /* Test pattern */
109
110 /*
111  * Values for memory allocator
112  */
113 #define ENI_BUF_PGSZ    1024            /* Allocation unit of buffers */
114 #define ENI_BUF_NBIT    8               /* Number of bits to get from */
115                                         /* min buffer (1KB) to max (128KB) */
116
117 /*
118  * Values for allocating TX buffers
119  */
120 #define MAX_CLIENT_RAM  512             /* Most RAM a client card will have */
121 #define TX_SMALL_BSIZE  32              /* Small buffer - 32KB */
122 #define TX_LARGE_BSIZE  128             /* Large buffer - 128KB */
123
124 /*
125  * Values for allocating RX buffers
126  */
127 #define RX_SIG_BSIZE    4               /* Signalling buffer - 4KB */
128 #define RX_CLIENT_BSIZE 16              /* Client buffer - 16KB */
129 #define RX_SERVER_BSIZE 32              /* Server buffer - 32KB */
130
131 /*
132  * Adapter bases all addresses off of some power from 1KB. Thus, it
133  * only needs to store the most sigificant bits and can drop the lower
134  * 10 bits.
135  */
136 #define ENI_LOC_PREDIV  10              /* Bits location is shifted */
137                                         /* Location is prescaled by 1KB */
138                                         /* before use in various places */
139
140 #define MIDWAY_DELAY    10              /* Time to wait for Midway finish */
141
142 /*
143  * Define the MIDWAY register offsets and any interesting bits within
144  * the register
145  */
146 #define MIDWAY_ID               0x00            /* ID/Reset register */
147         #define MIDWAY_RESET    0               /* iWrite of any value */
148         #define ID_SHIFT        27              /* Midway ID version */
149         #define ID_MASK         0x1F            /* ID mask */
150         #define MID_SHIFT       7               /* Mother board ID */
151         #define MID_MASK        0x7             /* MID mask */
152         #define DID_SHIFT       0               /* Daughter board ID */
153         #define DID_MASK        0x1F            /* DID mask */
154         /*
155          * Efficient defines the following IDs for their adapters:
156          * 0x420/0x620 - SONET MMF, client memory size
157          * 0x430/0x630 - SONET MMF, server memory size
158          * 0x424/0x624 - UTP-5, client memory size
159          * 0x434/0x634 - UTP-5, server memory size
160          */
161         #define MEDIA_MASK      0x04            /* Mask off UTP-5/MMF media */
162
163 #define MIDWAY_ISA              0x01            /* Interrupt Status Ack. */
164                                                 /* Reading this register */
165                                                 /* also acknowledges the */
166                                                 /* posted interrupt(s) */
167
168 #define MIDWAY_IS               0x02            /* Interrupt Status */
169                                                 /* Reading this register */
170                                                 /* does NOT acknowledge the */
171                                                 /* posted interrupt(s) */
172         /* Interrupt names */
173         #define ENI_INT_STAT            0x00000001
174         #define ENI_INT_SUNI            0x00000002
175         #define ENI_INT_SERVICE         0x00000004
176         #define ENI_INT_TX_DMA          0x00000008
177         #define ENI_INT_RX_DMA          0x00000010
178         #define ENI_INT_DMA_ERR         0x00000020
179         #define ENI_INT_DMA_LERR        0x00000040
180         #define ENI_INT_IDEN            0x00000080
181         #define ENI_INT_DMA_OVFL        0x00000100
182         #define ENI_INT_TX_MASK         0x0001FE00
183
184 #define MIDWAY_IE               0x03            /* Interrupt Enable register */
185         /* Interrupt enable bits are the same as the Interrupt names */
186
187 #define MIDWAY_MASTER           0x04            /* Master Control */
188         /* Master control bits */
189         #define ENI_M_WAIT500   0x00000001      /* Disable interrupts .5 ms */
190         #define ENI_M_WAIT1     0x00000002      /* Disable interrupts 1 ms */
191         #define ENI_M_RXENABLE  0x00000004      /* Enable RX engine */
192         #define ENI_M_TXENABLE  0x00000008      /* Enable TX engine */
193         #define ENI_M_DMAENABLE 0x00000010      /* Enable DMA */
194         #define ENI_M_TXLOCK    0x00000020      /* 0: Streaming, 1: Lock */
195         #define ENI_M_INTSEL    0x000001C0      /* Int Select mask */
196         #define ENI_ISEL_SHIFT  6               /* Bits to shift ISEL value */
197
198 #define MIDWAY_STAT             0x05            /* Statistics register */
199
200 #define MIDWAY_SVCWR            0x06            /* Svc List write pointer */
201         #define SVC_SIZE_MASK   0x3FF           /* Valid bits in svc pointer */
202
203 #define MIDWAY_DMAADDR          0x07            /* Current virtual DMA addr */
204
205 #define MIDWAY_RX_WR            0x08            /* Write ptr to RX DMA queue */
206
207 #define MIDWAY_RX_RD            0x09            /* Read ptr to RX DMA queue */
208
209 #define MIDWAY_TX_WR            0x0A            /* Write ptr to TX DMA queue */
210
211 #define MIDWAY_TX_RD            0x0B            /* Read ptr to TX DMA queue */
212
213 /*
214  * Registers 0x0C - 0x0F are unused
215  */
216
217 /*
218  * MIDWAY supports 8 transmit channels. Each channel has 3 registers
219  * to control operation. Each new channel starts on N * 4 set. Thus,
220  * channel 0 uses register 0x10 - 0x13, channel 1 uses 0x14 - 0x17, etc.
221  * Register 0x13 + N * 4 is unused.
222  */
223
224 #define MIDWAY_TXPLACE          0x10            /* Channel N TX location */
225         #define TXSIZE_SHIFT    11              /* Bits to shift size by */
226         #define TX_PLACE_MASK   0x7FF           /* Valid bits in TXPLACE */
227
228 #define MIDWAY_RDPTR            0x11            /* Channel N Read ptr */
229
230 #define MIDWAY_DESCR            0x12            /* Channel N Descr ptr */
231
232 /*
233  * Register 0x30 on up are unused
234  */
235
236 /*
237  * Part of PCI configuration registers but not defined in <pci/pcireg.h>
238  */
239 #define PCI_CONTROL_REG         0x60
240 #define ENDIAN_SWAP_DMA         0x80            /* Enable endian swaps on DMA */
241
242 /*
243  * The Efficient adapter references adapter RAM through the use of
244  * location and size values. Eight sizes are defined. When allocating
245  * buffers, there size must be rounded up to the next size which will
246  * hold the requested size. Buffers are allocated on 'SIZE' boundaries.
247  * See eni_buffer.c for more info.
248  */
249
250 /*
251  * Buffer SIZE definitions - in words, so from 1 KB to 128 KB
252  */
253 #define SIZE_256        0x00
254 #define SIZE_512        0x01
255 #define SIZE_1K         0x02
256 #define SIZE_2K         0x03
257 #define SIZE_4K         0x04
258 #define SIZE_8K         0x05
259 #define SIZE_16K        0x06
260 #define SIZE_32K        0x07
261
262 /*
263  * Define values for DMA type - DMA descriptors include a type field and a
264  * count field except in the special case of JK (just-kidding). With type JK,
265  * the count field should be set to the address which will be loaded
266  * into the pointer, ie. where the pointer should next point to, since
267  * JK doesn't have a "size" associated with it. JK DMA is used to skip
268  * over descriptor words, and to strip off padding of AAL5 PDUs. The 
269  * DMA_nWORDM types will do a n word DMA burst, but the count field
270  * does not have to equal n. Any difference results in garbage filling
271  * the remaining words of the DMA. These types could be used where a
272  * particular burst size yields better DMA performance.
273  */
274 #define DMA_WORD        0x00
275 #define DMA_BYTE        0x01
276 #define DMA_HWORD       0x02
277 #define DMA_JK          0x03
278 #define DMA_4WORD       0x04
279 #define DMA_8WORD       0x05
280 #define DMA_16WORD      0x06
281 #define DMA_2WORD       0x07
282 #define DMA_4WORDM      0x0C
283 #define DMA_8WORDM      0x0D
284 #define DMA_16WORDM     0x0E
285 #define DMA_2WORDM      0x0F
286
287 /*
288  * Define the size of the local DMA list we'll build before
289  * giving up on the PDU.
290  */
291 #define TEMP_DMA_SIZE   120             /* Enough for 58/59 buffers */
292
293 #define DMA_COUNT_SHIFT 16              /* Number of bits to shift count */
294                                         /* in DMA descriptor word */
295 #define DMA_VCC_SHIFT   6               /* Number of bits to shift RX VCC or */
296                                         /* TX channel in DMA descriptor word */
297 #define DMA_END_BIT     0x20            /* Signal end of DMA list */
298
299 /*
300  * Defines for VCI table
301  *
302  * The VCI table is a 1K by 4 word table allowing up to 1024 (0-1023)
303  * VCIs. Entries into the table use the VCI number as the index.
304  */
305 struct vci_table {
306         u_long  vci_control;            /* Control word */
307         u_long  vci_descr;              /* Descr/ReadPtr */
308         u_long  vci_write;              /* WritePtr/State/Cell count */
309         u_long  vci_crc;                /* ongoing CRC calculation */
310 };
311 typedef volatile struct vci_table VCI_Table;
312
313 #define VCI_MODE_SHIFT  30              /* Shift to get MODE field */
314 #define VCI_MODE_MASK   0x3FFFFFFF      /* Bits to strip MODE off */
315 #define VCI_PTI_SHIFT   29              /* Shift to get PTI mode field */
316 #define VCI_LOC_SHIFT   18              /* Shift to get location field */
317 #define VCI_LOC_MASK    0x7FF           /* Valid bits in location field */
318 #define VCI_SIZE_SHIFT  15              /* Shift to get size field */
319 #define VCI_SIZE_MASK   7               /* Valid bits in size field */
320 #define VCI_IN_SERVICE  1               /* Mask for IN_SERVICE field */
321
322 /*
323  * Defines for VC mode
324  */
325 #define VCI_MODE_TRASH  0x00            /* Trash all cells for this VC */
326 #define VCI_MODE_AAL0   0x01            /* Reassemble as AAL_0 PDU */
327 #define VCI_MODE_AAL5   0x02            /* Reassemble as AAL_5 PDU */
328 /*
329  * Defines for handling cells with PTI(2) set to 1.
330  */
331 #define PTI_MODE_TRASH  0x00            /* Trash cell */
332 #define PTI_MODE_PRESV  0x01            /* Send cell to OAM channel */
333 /*
334  * Current state of VC
335  */
336 #define VCI_STATE_IDLE  0x00            /* VC is idle */
337 #define VCI_STATE_REASM 0x01            /* VC is reassembling PDU */
338 #define VCI_STATE_TRASH 0x03            /* VC is trashing cells */
339
340 /*
341  * RX Descriptor word values
342  */
343 #define DESCR_TRASH_BIT         0x1000  /* VCI was trashing cells */
344 #define DESCR_CRC_ERR           0x0800  /* PDU has CRC error */
345 #define DESCR_CELL_COUNT        0x07FF  /* Mask to get cell count */
346 /*
347  * TX Descriptor word values
348  */
349 #define TX_IDEN_SHIFT   28              /* Unique identifier location */
350 #define TX_MODE_SHIFT   27              /* AAL5 or AAL0 */
351 #define TX_VCI_SHIFT    4               /* Bits to shift VCI value */
352
353 /*
354  * When setting up descriptor words (at head of segmentation queues), there
355  * is a unique identifier used to help detect sync problems.
356  */
357 #define MIDWAY_UNQ_ID   0x0B
358
359 /*
360  * Defines for cell sizes
361  */
362 #define BYTES_PER_CELL  48              /* Number of data bytes per cell */
363 #define WORDS_PER_CELL  12              /* Number of data words per cell */
364
365 /*
366  * Access to Serial EEPROM [as opposed to expansion (E)PROM].
367  *
368  * This is a ATMEL AT24C01 serial EEPROM part.
369  * See http://www.atmel.com/atmel/products/prod162.htm for timimg diagrams
370  * for START/STOP/ACK/READ cycles.
371  */
372 #define SEEPROM         PCI_CONTROL_REG /* Serial EEPROM is accessed thru */
373                                         /* PCI control register           */
374 #define SEPROM_DATA     0x02            /* SEEPROM DATA line */
375 #define SEPROM_CLK      0x01            /* SEEPROM CLK line */
376 #define SEPROM_SIZE     128             /* Size of Serial EEPROM */
377 #define SEPROM_MAC_OFF  64              /* Offset to MAC address */
378 #define SEPROM_SN_OFF   112             /* Offset to serial number */
379 #define SEPROM_DELAY    10              /* Delay when strobing CLK/DATA lines */
380
381 /*
382  * Host protocol control blocks
383  *
384  */
385
386 /*
387  * Device VCC Entry
388  *
389  * Contains the common and ENI-specific information for each VCC
390  * which is opened through a ENI device.
391  */
392 struct eni_vcc {
393         struct cmn_vcc  ev_cmn;         /* Common VCC stuff */
394         caddr_t         ev_rxbuf;       /* Receive buffer */
395         u_long          ev_rxpos;       /* Adapter buffer read pointer */
396 };
397 typedef struct eni_vcc Eni_vcc;
398
399 #define ev_next         ev_cmn.cv_next
400 #define ev_toku         ev_cmn.cv_toku
401 #define ev_upper        ev_cmn.cv_upper
402 #define ev_connvc       ev_cmn.cv_connvc
403 #define ev_state        ev_cmn.cv_state
404
405 typedef volatile unsigned long *        Eni_mem;
406
407 /*
408  * Define the ID's we'll look for in the PCI config
409  * register when deciding if we'll support this device.
410  * The DEV_ID will need to be turned into an array of
411  * ID's in order to support multiple adapters with
412  * the same driver.
413  */
414 #define EFF_VENDOR_ID   0x111A
415 #define EFF_DEV_ID      0x0002
416
417 /*
418  * Memory allocator defines and buffer descriptors
419  */
420 #define MEM_FREE        0
421 #define MEM_INUSE       1
422
423 typedef struct mbd Mbd;
424 struct mbd {
425         Mbd     *prev;
426         Mbd     *next;
427         caddr_t base;                   /* Adapter base address */
428         int     size;                   /* Size of buffer */
429         int     state;                  /* INUSE or FREE */
430 };
431
432 /*
433  * We use a hack to allocate a smaller RX buffer for signalling
434  * channels as they tend to have small MTU lengths.
435  */
436 #define UNI_SIG_VCI     5
437
438 /*
439  * Device Unit Structure
440  *
441  * Contains all the information for a single device (adapter).
442  */
443 struct eni_unit {
444         Cmn_unit        eu_cmn;         /* Common unit stuff */
445         pcici_t         eu_pcitag;      /* PCI tag */
446         Eni_mem         eu_base;        /* Adapter memory base */
447         Eni_mem         eu_ram;         /* Adapter RAM */
448         u_long          eu_ramsize;
449
450         Eni_mem         eu_suni;        /* SUNI registers */
451
452         Eni_mem         eu_midway;      /* MIDWAY registers */
453
454         VCI_Table       *eu_vcitbl;     /* VCI Table */
455         Eni_mem         eu_rxdma;       /* Receive DMA queue */
456         Eni_mem         eu_txdma;       /* Transmit DMA queue */
457         Eni_mem         eu_svclist;     /* Service list */
458         u_long          eu_servread;    /* Read pointer into Service list */
459
460         caddr_t         eu_txbuf;       /* One large TX buff for everything */
461         u_long          eu_txsize;      /* Size of TX buffer */
462         u_long          eu_txpos;       /* Current word being stored in RAM */
463         u_long          eu_txfirst;     /* First word of unack'ed data */
464
465         u_long          eu_trash;
466         u_long          eu_ovfl;
467
468         struct ifqueue  eu_txqueue;
469         u_long          eu_txdmawr;
470         struct ifqueue  eu_rxqueue;
471         u_long          eu_rxdmawr;     /* DMA list write pointer */
472
473         u_char          eu_seeprom[SEPROM_SIZE]; /* Serial EEPROM contents */
474         u_int           eu_sevar;       /* Unique (per unit) seeprom var. */
475
476         Mbd             *eu_memmap;     /* Adapter RAM memory allocator map */
477         int             eu_memclicks[ENI_BUF_NBIT];/* Count of INUSE buffers */
478
479         Eni_stats       eu_stats;       /* Statistics */
480
481 };
482 typedef struct eni_unit         Eni_unit;
483
484 #define eu_pif          eu_cmn.cu_pif
485 #define eu_unit         eu_cmn.cu_unit
486 #define eu_flags        eu_cmn.cu_flags
487 #define eu_mtu          eu_cmn.cu_mtu
488 #define eu_open_vcc     eu_cmn.cu_open_vcc
489 #define eu_vcc          eu_cmn.cu_vcc
490 #define eu_vcc_pool     eu_cmn.cu_vcc_pool
491 #define eu_nif_pool     eu_cmn.cu_nif_pool
492 #define eu_ioctl        eu_cmn.cu_ioctl
493 #define eu_instvcc      eu_cmn.cu_instvcc
494 #define eu_openvcc      eu_cmn.cu_openvcc
495 #define eu_closevcc     eu_cmn.cu_closevcc
496 #define eu_output       eu_cmn.cu_output
497 #define eu_config       eu_cmn.cu_config
498
499 #endif  /* _ENI_ENI_H */