xref: /netbsd-src/sys/arch/luna68k/stand/boot/if_le.c (revision 3dd15d69a9fe59a5a1616670bdd96da1f4872008)
1 /* $NetBSD: if_le.c,v 1.7 2019/06/30 05:04:49 tsutsui Exp $ */
2 
3 /*
4  * Copyright (c) 2013 Izumi Tsutsui.  All rights reserved.
5  * Copyright (c) 2003 Tetsuya Isaki. All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
21  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
23  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26  * SUCH DAMAGE.
27  */
28 /*
29  * Copyright (c) 1982, 1990, 1993
30  *      The Regents of the University of California.  All rights reserved.
31  *
32  * Redistribution and use in source and binary forms, with or without
33  * modification, are permitted provided that the following conditions
34  * are met:
35  * 1. Redistributions of source code must retain the above copyright
36  *    notice, this list of conditions and the following disclaimer.
37  * 2. Redistributions in binary form must reproduce the above copyright
38  *    notice, this list of conditions and the following disclaimer in the
39  *    documentation and/or other materials provided with the distribution.
40  * 3. Neither the name of the University nor the names of its contributors
41  *    may be used to endorse or promote products derived from this software
42  *    without specific prior written permission.
43  *
44  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
45  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
46  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
47  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
48  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
49  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
50  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
51  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
52  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
53  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
54  * SUCH DAMAGE.
55  *
56  * from: hp300/dev/if_le.c      7.16 (Berkeley) 3/11/93
57  *
58  *      @(#)if_le.c     8.1 (Berkeley) 6/10/93
59  */
60 
61 #include <sys/param.h>
62 
63 #include <machine/board.h>
64 #include <machine/cpu.h>
65 
66 #include <net/if.h>
67 #include <net/if_ether.h>
68 #include <netinet/in.h>
69 #include <netinet/in_systm.h>
70 
71 #include <lib/libsa/stand.h>
72 #include <lib/libsa/net.h>
73 #include <lib/libsa/netif.h>
74 
75 #include <luna68k/stand/boot/samachdep.h>
76 
77 #define TRI_PORT_RAM_LANCE_OFFSET	0x10000
78 
79 /* libsa netif_driver glue functions */
80 static int  le_match(struct netif *, void *);
81 static int  le_probe(struct netif *, void *);
82 static void le_init(struct iodesc *, void *);
83 static int  le_get(struct iodesc *, void *, size_t, saseconds_t);
84 static int  le_put(struct iodesc *, void *, size_t);
85 static void le_end(struct netif *);
86 
87 static void myetheraddr(uint8_t *);
88 
89 /* libsa netif glue stuff */
90 struct netif_stats le_stats;
91 struct netif_dif le_ifs[] = {
92 	{ 0, 1, &le_stats, 0, 0, },
93 };
94 
95 struct netif_driver le_netif_driver = {
96 	"le",
97 	le_match,
98 	le_probe,
99 	le_init,
100 	le_get,
101 	le_put,
102 	le_end,
103 	le_ifs,
104 	__arraycount(le_ifs),
105 };
106 
107 #ifdef DEBUG
108 int debug;
109 #endif
110 
111 int
leinit(int unit,void * addr)112 leinit(int unit, void *addr)
113 {
114 	void *cookie;
115 	void *reg, *mem;
116 	uint8_t eaddr[6];
117 
118 	reg = addr;
119 	mem = (void *)(TRI_PORT_RAM + TRI_PORT_RAM_LANCE_OFFSET);
120 
121 	myetheraddr(eaddr);
122 
123 	cookie = lance_attach(unit, reg, mem, eaddr);
124 	if (cookie == NULL)
125 		return 0;
126 
127 	printf("le%d: Am7990 LANCE Ethernet, mem at 0x%x\n",
128 	    unit, (uint32_t)mem);
129 	printf("le%d: Ethernet address = %s\n",
130 	    unit, ether_sprintf(eaddr));
131 
132 	return 1;
133 }
134 
135 static int
le_match(struct netif * nif,void * machdep_hint)136 le_match(struct netif *nif, void *machdep_hint)
137 {
138 	void *cookie;
139 	uint8_t *eaddr;
140 
141 	/* XXX should check nif_unit and unit number in machdep_hint path */
142 
143 	cookie = lance_cookie(nif->nif_unit);
144 	if (cookie == NULL)
145 		return 0;
146 
147 	eaddr = lance_eaddr(cookie);
148 	if (eaddr == NULL)
149 		return 0;
150 
151 	return 1;
152 }
153 
154 static int
le_probe(struct netif * nif,void * machdep_hint)155 le_probe(struct netif *nif, void *machdep_hint)
156 {
157 
158 	/* XXX what should be checked? */
159 
160 	return 0;
161 }
162 
163 static void
le_init(struct iodesc * desc,void * machdep_hint)164 le_init(struct iodesc *desc, void *machdep_hint)
165 {
166 	struct netif *nif = desc->io_netif;
167 	struct netif_dif *dif = &nif->nif_driver->netif_ifs[nif->nif_unit];
168 	void *cookie;
169 	uint8_t *eaddr;
170 
171 #ifdef DEBUG
172 	printf("%s\n", __func__);
173 #endif
174 
175 	cookie = lance_cookie(nif->nif_unit);
176 	eaddr = lance_eaddr(cookie);
177 
178 	lance_init(cookie);
179 
180 	/* fill glue stuff */
181 	dif->dif_private = cookie;
182 	memcpy(desc->myea, eaddr, 6);
183 }
184 
185 static int
le_get(struct iodesc * desc,void * pkt,size_t maxlen,saseconds_t timeout)186 le_get(struct iodesc *desc, void *pkt, size_t maxlen, saseconds_t timeout)
187 {
188 	struct netif *nif = desc->io_netif;
189 	struct netif_dif *dif = &nif->nif_driver->netif_ifs[nif->nif_unit];
190 	void *cookie = dif->dif_private;
191 	int len = -1;
192 	saseconds_t t;
193 
194 	t = getsecs() + timeout;
195 	while (getsecs() < t) {
196 		len = lance_get(cookie, pkt, len);
197 		if (len > 0)
198 			break;
199 	}
200 
201 	return len;
202 }
203 
204 static int
le_put(struct iodesc * desc,void * pkt,size_t len)205 le_put(struct iodesc *desc, void *pkt, size_t len)
206 {
207 	struct netif *nif = desc->io_netif;
208 	struct netif_dif *dif = &nif->nif_driver->netif_ifs[nif->nif_unit];
209 	void *cookie = dif->dif_private;
210 #ifdef DEBUG
211 	struct ether_header *eh;
212 
213 	eh = pkt;
214 	printf("dst:  %s\n", ether_sprintf(eh->ether_dhost));
215 	printf("src:  %s\n", ether_sprintf(eh->ether_shost));
216 	printf("type: 0x%x\n", eh->ether_type & 0xffff);
217 #endif
218 
219 	return lance_put(cookie, pkt, len) ? len : -1;
220 }
221 
222 static void
le_end(struct netif * nif)223 le_end(struct netif *nif)
224 {
225 	struct netif_dif *dif = &nif->nif_driver->netif_ifs[nif->nif_unit];
226 	void *cookie = dif->dif_private;
227 
228 #ifdef DEBUG
229 	printf("%s\n", __func__);
230 #endif
231 	lance_end(cookie);
232 }
233 
234 static void
myetheraddr(uint8_t * ether)235 myetheraddr(uint8_t *ether)
236 {
237 	unsigned int i, loc;
238 	uint8_t *ea;
239 	volatile struct { uint32_t ctl; } *ds1220;
240 
241 	switch (machtype) {
242 	case LUNA_I:
243 		ea = (uint8_t *)0x4101FFE0;
244 		for (i = 0; i < ETHER_ADDR_LEN; i++) {
245 			int u, l;
246 
247 			u = ea[0];
248 			u = (u < 'A') ? u & 0xf : u - 'A' + 10;
249 			l = ea[1];
250 			l = (l < 'A') ? l & 0xf : l - 'A' + 10;
251 
252 			ether[i] = l | (u << 4);
253 			ea += 2;
254 		}
255 		break;
256 	case LUNA_II:
257 		ds1220 = (void *)0xF1000004;
258 		loc = 12;
259 		for (i = 0; i < ETHER_ADDR_LEN; i++) {
260 			unsigned int u, l, hex;
261 
262 			ds1220->ctl = (loc) << 16;
263 			u = 0xf0 & (ds1220->ctl >> 12);
264 			ds1220->ctl = (loc + 1) << 16;
265 			l = 0x0f & (ds1220->ctl >> 16);
266 			hex = (u < '9') ? l : l + 9;
267 
268 			ds1220->ctl = (loc + 2) << 16;
269 			u = 0xf0 & (ds1220->ctl >> 12);
270 			ds1220->ctl = (loc + 3) << 16;
271 			l = 0x0f & (ds1220->ctl >> 16);
272 
273 			ether[i] = ((u < '9') ? l : l + 9) | (hex << 4);
274 			loc += 4;
275 		}
276 		break;
277 	default:
278 		ether[0] = 0x00; ether[1] = 0x00; ether[2] = 0x0a;
279 		ether[3] = 0xDE; ether[4] = 0xAD; ether[5] = 0x00;
280 		break;
281 	}
282 }
283