Fixed binary search: no more infinite loops when vendor is unknown.
[tangerine.git] / workbench / devs / networks / emac / mal.c
blobc340788c91f60d9c808a49850ff210ae567e3808
1 #define DEBUG 1
3 #include <asm/amcc440.h>
4 #include <inttypes.h>
6 #include <aros/debug.h>
7 #include <exec/types.h>
8 #include <exec/resident.h>
9 #include <exec/io.h>
10 #include <exec/errors.h>
11 #include <exec/lists.h>
13 #include <aros/libcall.h>
14 #include <aros/symbolsets.h>
16 #include <oop/oop.h>
18 #include <devices/sana2.h>
19 #include <devices/sana2specialstats.h>
21 #include <proto/exec.h>
22 #include <proto/kernel.h>
24 #include "emac.h"
25 #include "mal.h"
26 #include LC_LIBDEFS_FILE
28 void rx_int(struct EMACUnit *unit, struct ExecBase *SysBase);
30 static void MALMRE(struct EMACBase *EMACBase, struct EMACUnit *unit)
32 //Cause(&unit->eu_RXInt);
33 rx_int(unit, SysBase);
36 static void MALIRQHandler(struct EMACBase *EMACBase, uint8_t inttype)
38 uint32_t temp;
40 switch (inttype)
42 case INTR_MTE:
43 /* get the information about channel causing the interrupt */
44 temp = rddcr(MAL0_TXEOBISR);
45 /* Clear the interrupt flag */
46 wrdcr(MAL0_TXEOBISR, temp);
47 break;
49 case INTR_MRE:
50 /* get the information about channel causing the interrupt */
51 temp = rddcr(MAL0_RXEOBISR);
52 /* Clear the interrupt flag */
53 wrdcr(MAL0_RXEOBISR, temp);
54 if (temp & 0x80000000)
55 MALMRE(EMACBase, EMACBase->emb_Units[0]);
56 if (temp & 0x40000000)
57 MALMRE(EMACBase, EMACBase->emb_Units[0]);
58 break;
60 case INTR_MTDE:
61 D(bug("[EMAC ] MAL TXDE\n"));
62 break;
64 case INTR_MRDE:
65 D(bug("[EMAC ] MAL RXDE\n"));
66 break;
68 case INTR_MS:
69 D(bug("[EMAC ] MAL SERR\n"));
70 break;
75 void EMAC_MAL_Init(struct EMACBase *EMACBase)
77 int i;
78 void *stack;
79 void *KernelBase;
81 D(bug("[EMAC ] Memory Access Layer (MAL) Init\n"));
84 * Add all interrupt handlers required. Oh boy, MAL serves us FIVE different
85 * interrupt vectors!
88 KernelBase = OpenResource("kernel.resource");
90 EMACBase->emb_MALHandlers[0] = KrnAddIRQHandler(INTR_MTE, MALIRQHandler, EMACBase, INTR_MTE);
91 EMACBase->emb_MALHandlers[1] = KrnAddIRQHandler(INTR_MRE, MALIRQHandler, EMACBase, INTR_MRE);
92 EMACBase->emb_MALHandlers[2] = KrnAddIRQHandler(INTR_MTDE, MALIRQHandler, EMACBase, INTR_MTDE);
93 EMACBase->emb_MALHandlers[3] = KrnAddIRQHandler(INTR_MRDE, MALIRQHandler, EMACBase, INTR_MRDE);
94 EMACBase->emb_MALHandlers[4] = KrnAddIRQHandler(INTR_MS, MALIRQHandler, EMACBase, INTR_MS);
96 intptr_t buffers = (intptr_t)AllocPooled(EMACBase->emb_Pool,
97 32 + 4 * (RX_RING_SIZE + TX_RING_SIZE) * ((RXTX_ALLOC_BUFSIZE+31)& ~31));
99 D(bug("[EMAC ] Allocating %d bytes @ %p for buffers\n",
100 32 + 4 * (RX_RING_SIZE + TX_RING_SIZE) * ((RXTX_ALLOC_BUFSIZE+31)& ~31), buffers));
102 buffers = (buffers + 31) & ~31;
104 /* Allocate memory for 2 RX channels */
105 for (i=0; i < 2; i++)
107 int j;
109 EMACBase->emb_MALRXChannels[i] = (void*)((intptr_t)AllocVecPooled(EMACBase->emb_Pool, 32 + RX_RING_SIZE * sizeof(mal_descriptor_t)) & ~31);
111 for (j = 0; j < RX_RING_SIZE; j++)
113 EMACBase->emb_MALRXChannels[i][j].md_buffer = (char*)buffers;
114 EMACBase->emb_MALRXChannels[i][j].md_length = RXTX_ALLOC_BUFSIZE;
115 EMACBase->emb_MALRXChannels[i][j].md_ctrl = MAL_CTRL_RX_E | MAL_CTRL_RX_I;
117 buffers += (RXTX_ALLOC_BUFSIZE+31) & ~31;
120 EMACBase->emb_MALRXChannels[i][RX_RING_SIZE-1].md_ctrl |= MAL_CTRL_RX_W;
122 CacheClearE(EMACBase->emb_MALRXChannels[i], RX_RING_SIZE * sizeof(mal_descriptor_t), CACRF_ClearD);
124 D(bug("[EMAC ] MAL RX Channel %d @ %p\n", i, EMACBase->emb_MALRXChannels[i]));
127 /* Allocate memory for 2 TX channels */
128 for (i=0; i < 2; i++)
130 int j;
132 EMACBase->emb_MALTXChannels[i] = (void*)((intptr_t)AllocVecPooled(EMACBase->emb_Pool, 32 + TX_RING_SIZE * sizeof(mal_descriptor_t)) & ~31);
134 for (j = 0; j < TX_RING_SIZE; j++)
136 EMACBase->emb_MALTXChannels[i][j].md_buffer = (char*)buffers;
137 EMACBase->emb_MALTXChannels[i][j].md_length = RXTX_ALLOC_BUFSIZE;
138 EMACBase->emb_MALTXChannels[i][j].md_ctrl = 0;
140 buffers += (RXTX_ALLOC_BUFSIZE+31) & ~31;
143 EMACBase->emb_MALTXChannels[i][TX_RING_SIZE - 1].md_ctrl |= MAL_CTRL_TX_W;
145 CacheClearE(EMACBase->emb_MALTXChannels[i], RX_RING_SIZE * sizeof(mal_descriptor_t), CACRF_ClearD);
147 D(bug("[EMAC ] MAL TX Channel %d @ %p\n", i, EMACBase->emb_MALTXChannels[i]));
151 /* Writing to DCR registers requires supervisor rights. */
152 stack = SuperState();
154 /* Set the MAL dcr's containing pointers to the transfer descriptors */
155 // wrdcr(MAL0_TXCTP0R, (intptr_t)EMACBase->emb_MALTXChannels[0]);
156 // wrdcr(MAL0_TXCTP1R, (intptr_t)EMACBase->emb_MALTXChannels[1]);
157 // wrdcr(MAL0_TXCTP2R, (intptr_t)EMACBase->emb_MALTXChannels[2]);
158 // wrdcr(MAL0_TXCTP3R, (intptr_t)EMACBase->emb_MALTXChannels[3]);
159 wrdcr(MAL0_TXCTP0R, (intptr_t)EMACBase->emb_MALTXChannels[0]);
160 wrdcr(MAL0_TXCTP2R, (intptr_t)EMACBase->emb_MALTXChannels[1]);
161 wrdcr(MAL0_RXCTP0R, (intptr_t)EMACBase->emb_MALRXChannels[0]);
162 wrdcr(MAL0_RXCTP1R, (intptr_t)EMACBase->emb_MALRXChannels[1]);
164 /* Length of receive buffers */
165 wrdcr(MAL0_RCBS0, (RXTX_ALLOC_BUFSIZE + 15) >> 4);
166 wrdcr(MAL0_RCBS1, (RXTX_ALLOC_BUFSIZE + 15) >> 4);
168 /* Enable MAL */
169 wrdcr(MAL0_CFG, MAL_CR_PLBB | MAL_CR_OPBBL | MAL_CR_LEA | MAL_CR_PLBLT_DEFAULT);
171 UserState(stack);