iPXE
3c5x9.c File Reference
#include <ipxe/ethernet.h>
#include "etherboot.h"
#include "nic.h"
#include <ipxe/isa.h>
#include "3c509.h"

Go to the source code of this file.

Enumerations

enum  { none , bnc , utp }

Functions

 FILE_LICENCE (BSD2)
void t5x9_disable (struct nic *nic)
static void t509_enable (struct nic *nic)
static void t509_reset (struct nic *nic)
static void t509_transmit (struct nic *nic, const char *d, unsigned int t, unsigned int s, const char *p)
static int t509_poll (struct nic *nic, int retrieve)
static void t509_irq (struct nic *nic __unused, irq_action_t action __unused)
static int eeprom_rdy (uint16_t ioaddr)
static int get_e (uint16_t ioaddr, int offset)
int t5x9_probe (struct nic *nic, uint16_t prod_id_check, uint16_t prod_id_mask)

Variables

static enum { ... }  connector = none
static char padmap []
static struct nic_operations t509_operations

Enumeration Type Documentation

◆ anonymous enum

anonymous enum
Enumerator
none 
bnc 
utp 

Definition at line 35 of file 3c5x9.c.

35{ none, bnc, utp } connector = none; /* for 3C509 */
static enum @204357277152330206202240171322066215216352015347 connector
@ bnc
Definition 3c5x9.c:35
@ utp
Definition 3c5x9.c:35
@ none
Definition 3c5x9.c:35

Function Documentation

◆ FILE_LICENCE()

FILE_LICENCE ( BSD2 )

◆ t5x9_disable()

void t5x9_disable ( struct nic * nic)

Definition at line 40 of file 3c5x9.c.

40 {
41 /* stop card */
45 ;
48 udelay(1000);
55
56 /*
57 * wait for reset to complete
58 */
60 ;
61
63
64 /* Disable the card */
66
67 /* Configure IRQ to none */
69}
#define TX_RESET
Definition 3c509.h:218
#define SET_IRQ(i)
Definition 3c509.h:351
#define C_INTR_LATCH
Definition 3c509.h:238
#define RX_RESET
Definition 3c509.h:214
#define EP_W0_RESOURCE_CFG
Definition 3c509.h:118
#define SET_INTR_MASK
Definition 3c509.h:220
#define EP_STATUS
Definition 3c509.h:110
#define STOP_TRANSCEIVER
Definition 3c509.h:232
#define S_COMMAND_IN_PROGRESS
Definition 3c509.h:275
#define GO_WINDOW(b, x)
Definition 3c509.h:75
#define EP_W0_CONFIG_CTRL
Definition 3c509.h:120
#define SET_RX_FILTER
Definition 3c509.h:222
#define SET_RD_0_MASK
Definition 3c509.h:221
#define RX_DISCARD_TOP_PACK
Definition 3c509.h:215
#define EP_COMMAND
Definition 3c509.h:109
#define RX_DISABLE
Definition 3c509.h:212
#define TX_DISABLE
Definition 3c509.h:217
#define inw(io_addr)
Definition io.h:292
#define outw(data, io_addr)
Definition io.h:320
Definition nic.h:49
unsigned int ioaddr
Definition nic.h:55
void udelay(unsigned long usecs)
Delay for a fixed number of microseconds.
Definition timer.c:61

References C_INTR_LATCH, EP_COMMAND, EP_STATUS, EP_W0_CONFIG_CTRL, EP_W0_RESOURCE_CFG, GO_WINDOW, inw, nic::ioaddr, outw, RX_DISABLE, RX_DISCARD_TOP_PACK, RX_RESET, S_COMMAND_IN_PROGRESS, SET_INTR_MASK, SET_IRQ, SET_RD_0_MASK, SET_RX_FILTER, STOP_TRANSCEIVER, TX_DISABLE, TX_RESET, and udelay().

Referenced by el3_eisa_disable(), legacy_t509_disable(), t509_reset(), and t529_disable().

◆ t509_enable()

void t509_enable ( struct nic * nic)
static

Definition at line 71 of file 3c5x9.c.

71 {
72 int i;
73
74 /* Enable the card */
77
79
80 /* Reload the ether_addr. */
81 for (i = 0; i < ETH_ALEN; i++)
83
86
87 /* Window 1 is operating window */
89 for (i = 0; i < 31; i++)
91
92 /* get rid of stray intr's */
93 outw(ACK_INTR | 0xff, nic->ioaddr + EP_COMMAND);
94
96
98
101
102 /* configure BNC */
103 if (connector == bnc) {
105 udelay(1000);
106 }
107 /* configure UTP */
108 else if (connector == utp) {
109 GO_WINDOW(nic->ioaddr,4);
111 mdelay(2000); /* Give time for media to negotiate */
112 GO_WINDOW(nic->ioaddr,1);
113 }
114
115 /* start transceiver and receiver */
118
119 /* set early threshold for minimal packet length */
122}
#define ENABLE_UTP
Definition 3c509.h:344
#define FIL_BRDCST
Definition 3c509.h:225
#define SET_TX_START_THRESH
Definition 3c509.h:229
#define EP_W2_ADDR_0
Definition 3c509.h:148
#define ENABLE_DRQ_IRQ
Definition 3c509.h:337
#define RX_ENABLE
Definition 3c509.h:213
#define S_5_INTS
Definition 3c509.h:273
#define EP_W1_TX_STATUS
Definition 3c509.h:133
#define ACK_INTR
Definition 3c509.h:237
#define SET_RX_EARLY_THRESH
Definition 3c509.h:227
#define FIL_INDIVIDUAL
Definition 3c509.h:223
#define EP_W4_MEDIA_TYPE
Definition 3c509.h:161
#define FIL_GROUP
Definition 3c509.h:224
#define START_TRANSCEIVER
Definition 3c509.h:211
#define TX_ENABLE
Definition 3c509.h:216
#define ETH_ZLEN
Definition if_ether.h:11
#define ETH_ALEN
Definition if_ether.h:9
#define outb(data, io_addr)
Definition io.h:310
#define inb(io_addr)
Definition io.h:283
unsigned char * node_addr
Definition nic.h:52
void mdelay(unsigned long msecs)
Delay for a fixed number of milliseconds.
Definition timer.c:79

References ACK_INTR, bnc, connector, ENABLE_DRQ_IRQ, ENABLE_UTP, EP_COMMAND, EP_W0_CONFIG_CTRL, EP_W1_TX_STATUS, EP_W2_ADDR_0, EP_W4_MEDIA_TYPE, ETH_ALEN, ETH_ZLEN, FIL_BRDCST, FIL_GROUP, FIL_INDIVIDUAL, GO_WINDOW, inb, nic::ioaddr, mdelay(), nic::node_addr, outb, outw, RX_ENABLE, RX_RESET, S_5_INTS, SET_INTR_MASK, SET_RD_0_MASK, SET_RX_EARLY_THRESH, SET_RX_FILTER, SET_TX_START_THRESH, START_TRANSCEIVER, TX_ENABLE, TX_RESET, udelay(), and utp.

Referenced by t509_reset().

◆ t509_reset()

void t509_reset ( struct nic * nic)
static

Definition at line 124 of file 3c5x9.c.

124 {
125 t5x9_disable ( nic );
126 t509_enable ( nic );
127}
static void t509_enable(struct nic *nic)
Definition 3c5x9.c:71
void t5x9_disable(struct nic *nic)
Definition 3c5x9.c:40

References t509_enable(), and t5x9_disable().

Referenced by t5x9_probe().

◆ t509_transmit()

void t509_transmit ( struct nic * nic,
const char * d,
unsigned int t,
unsigned int s,
const char * p )
static

Definition at line 135 of file 3c5x9.c.

141{
142 register unsigned int len;
143 int pad;
144 int status;
145
146#ifdef EDEBUG
147 printf("{l=%d,t=%hX}",s+ETH_HLEN,t);
148#endif
149
150 /* swap bytes of type */
151 t= htons(t);
152
153 len=s+ETH_HLEN; /* actual length of packet */
154 pad = padmap[len & 3];
155
156 /*
157 * The 3c509 automatically pads short packets to minimum ethernet length,
158 * but we drop packets that are too large. Perhaps we should truncate
159 * them instead?
160 */
161 if (len + pad > ETH_FRAME_LEN) {
162 return;
163 }
164
165 /* drop acknowledgements */
170 }
172 }
173
174 while (inw(nic->ioaddr + EP_W1_FREE_TX) < (unsigned short)len + pad + 4)
175 ; /* no room in FIFO */
176
178 outw(0x0, nic->ioaddr + EP_W1_TX_PIO_WR_1); /* Second dword meaningless */
179
180 /* write packet */
184 outsw(nic->ioaddr + EP_W1_TX_PIO_WR_1, p, s / 2);
185 if (s & 1)
186 outb(*(p+s - 1), nic->ioaddr + EP_W1_TX_PIO_WR_1);
187
188 while (pad--)
189 outb(0, nic->ioaddr + EP_W1_TX_PIO_WR_1); /* Padding */
190
191 /* wait for Tx complete */
192 while((inw(nic->ioaddr + EP_STATUS) & S_COMMAND_IN_PROGRESS) != 0)
193 ;
194}
#define EP_W1_FREE_TX
Definition 3c509.h:132
#define TXS_STATUS_OVERFLOW
Definition 3c509.h:326
#define EP_W1_TX_PIO_WR_1
Definition 3c509.h:130
#define TXS_UNDERRUN
Definition 3c509.h:324
#define TXS_MAX_COLLISION
Definition 3c509.h:325
#define TXS_COMPLETE
Definition 3c509.h:321
static char padmap[]
Definition 3c515.c:498
u32 pad[9]
Padding.
Definition ar9003_mac.h:23
ring len
Length.
Definition dwmac.h:226
uint8_t status
Status.
Definition ena.h:5
#define ETH_FRAME_LEN
Definition if_ether.h:12
#define ETH_HLEN
Definition if_ether.h:10
#define htons(value)
Definition byteswap.h:136
#define outsw(io_addr, data, count)
Definition io.h:447
int printf(const char *fmt,...)
Write a formatted string to the console.
Definition vsprintf.c:465

References EP_COMMAND, EP_STATUS, EP_W1_FREE_TX, EP_W1_TX_PIO_WR_1, EP_W1_TX_STATUS, ETH_ALEN, ETH_FRAME_LEN, ETH_HLEN, htons, inb, inw, nic::ioaddr, len, nic::node_addr, outb, outsw, outw, pad, padmap, printf(), S_COMMAND_IN_PROGRESS, status, TX_ENABLE, TX_RESET, TXS_COMPLETE, TXS_MAX_COLLISION, TXS_STATUS_OVERFLOW, and TXS_UNDERRUN.

◆ t509_poll()

int t509_poll ( struct nic * nic,
int retrieve )
static

Definition at line 199 of file 3c5x9.c.

200{
201 /* common variables */
202 /* variables for 3C509 */
203 short status, cst;
204 register short rx_fifo;
205
206 cst=inw(nic->ioaddr + EP_STATUS);
207
208#ifdef EDEBUG
209 if(cst & 0x1FFF)
210 printf("-%hX-",cst);
211#endif
212
213 if( (cst & S_RX_COMPLETE)==0 ) {
214 /* acknowledge everything */
217
218 return 0;
219 }
220
222#ifdef EDEBUG
223 printf("*%hX*",status);
224#endif
225
226 if (status & ERR_RX) {
228 return 0;
229 }
230
231 rx_fifo = status & RX_BYTES_MASK;
232 if (rx_fifo==0)
233 return 0;
234
235 if ( ! retrieve ) return 1;
236
237 /* read packet */
238#ifdef EDEBUG
239 printf("[l=%d",rx_fifo);
240#endif
241 insw(nic->ioaddr + EP_W1_RX_PIO_RD_1, nic->packet, rx_fifo / 2);
242 if(rx_fifo & 1)
243 nic->packet[rx_fifo-1]=inb(nic->ioaddr + EP_W1_RX_PIO_RD_1);
244 nic->packetlen=rx_fifo;
245
246 while(1) {
248#ifdef EDEBUG
249 printf("*%hX*",status);
250#endif
251 rx_fifo = status & RX_BYTES_MASK;
252 if(rx_fifo>0) {
254 if(rx_fifo & 1)
256 nic->packetlen+=rx_fifo;
257#ifdef EDEBUG
258 printf("+%d",rx_fifo);
259#endif
260 }
261 if(( status & RX_INCOMPLETE )==0) {
262#ifdef EDEBUG
263 printf("=%d",nic->packetlen);
264#endif
265 break;
266 }
267 udelay(1000); /* if incomplete wait 1 ms */
268 }
269 /* acknowledge reception of packet */
272 ;
273#ifdef EDEBUG
274{
275 unsigned short type = 0; /* used by EDEBUG */
276 type = (nic->packet[12]<<8) | nic->packet[13];
277 if(nic->packet[0]+nic->packet[1]+nic->packet[2]+nic->packet[3]+nic->packet[4]+
278 nic->packet[5] == 0xFF*ETH_ALEN)
279 printf(",t=%hX,b]",type);
280 else
281 printf(",t=%hX]",type);
282}
283#endif
284 return (1);
285}
#define S_RX_COMPLETE
Definition 3c509.h:269
#define RX_BYTES_MASK
Definition 3c509.h:357
#define RX_INCOMPLETE
Definition 3c509.h:359
#define EP_W1_RX_STATUS
Definition 3c509.h:135
#define EP_W1_RX_PIO_RD_1
Definition 3c509.h:137
#define ERR_RX
Definition 3c509.h:295
uint32_t type
Operating system type.
Definition ena.h:1
#define insw(io_addr, data, count)
Definition io.h:412
unsigned char * packet
Definition nic.h:53
unsigned int packetlen
Definition nic.h:54

References ACK_INTR, C_INTR_LATCH, EP_COMMAND, EP_STATUS, EP_W1_RX_PIO_RD_1, EP_W1_RX_STATUS, ERR_RX, ETH_ALEN, inb, insw, inw, nic::ioaddr, outw, nic::packet, nic::packetlen, printf(), RX_BYTES_MASK, RX_DISCARD_TOP_PACK, RX_INCOMPLETE, S_5_INTS, S_COMMAND_IN_PROGRESS, S_RX_COMPLETE, status, type, and udelay().

◆ t509_irq()

void t509_irq ( struct nic *nic __unused,
irq_action_t action __unused )
static

Definition at line 290 of file 3c5x9.c.

291{
292 switch ( action ) {
293 case DISABLE :
294 break;
295 case ENABLE :
296 break;
297 case FORCE :
298 break;
299 }
300}
@ FORCE
Definition nic.h:37
@ ENABLE
Definition nic.h:36
@ DISABLE
Definition nic.h:35

References __unused, DISABLE, ENABLE, and FORCE.

◆ eeprom_rdy()

int eeprom_rdy ( uint16_t ioaddr)
static

Definition at line 306 of file 3c5x9.c.

306 {
307 int i;
308
309 for (i = 0; is_eeprom_busy(ioaddr) && i < MAX_EEPROMBUSY; i++);
310 if (i >= MAX_EEPROMBUSY) {
311 /* printf("3c509: eeprom failed to come ready.\n"); */
312 /* memory in EPROM is tight */
313 /* printf("3c509: eeprom busy.\n"); */
314 return (0);
315 }
316 return (1);
317}
#define MAX_EEPROMBUSY
Definition 3c509.h:53
#define is_eeprom_busy(b)
Definition 3c509.h:74
static unsigned long ioaddr
Definition davicom.c:129

References ioaddr, is_eeprom_busy, and MAX_EEPROMBUSY.

◆ get_e()

int get_e ( uint16_t ioaddr,
int offset )
static

Definition at line 322 of file 3c5x9.c.

322 {
323 GO_WINDOW(ioaddr,0);
324 if (!eeprom_rdy(ioaddr))
325 return (0xffff);
327 if (!eeprom_rdy(ioaddr))
328 return (0xffff);
329 return (inw(ioaddr + EP_W0_EEPROM_DATA));
330}
#define EP_W0_EEPROM_DATA
Definition 3c509.h:116
#define EP_W0_EEPROM_COMMAND
Definition 3c509.h:117
#define EEPROM_CMD_RD
Definition 3c509.h:63
static int eeprom_rdy()
Definition 3c595.c:326
uint16_t offset
Offset to command line.
Definition bzimage.h:3

References EEPROM_CMD_RD, eeprom_rdy(), EP_W0_EEPROM_COMMAND, EP_W0_EEPROM_DATA, GO_WINDOW, inw, ioaddr, offset, and outw.

Referenced by t5x9_probe().

◆ t5x9_probe()

int t5x9_probe ( struct nic * nic,
uint16_t prod_id_check,
uint16_t prod_id_mask )

Definition at line 342 of file 3c5x9.c.

343 {
344 uint16_t prod_id;
345 int i,j;
346 unsigned short *p;
347
348 /* Check product ID */
349 prod_id = get_e ( nic->ioaddr, EEPROM_PROD_ID );
350 if ( ( prod_id & prod_id_mask ) != prod_id_check ) {
351 printf ( "EEPROM Product ID is incorrect (%hx & %hx != %hx)\n",
352 prod_id, prod_id_mask, prod_id_check );
353 return 0;
354 }
355
356 /* test for presence of connectors */
357 GO_WINDOW(nic->ioaddr,0);
359 j = (inw(nic->ioaddr + EP_W0_ADDRESS_CFG) >> 14) & 0x3;
360
361 switch(j) {
362 case 0:
363 if (i & IS_UTP) {
364 printf("10baseT\n");
365 connector = utp;
366 } else {
367 printf("10baseT not present\n");
368 return 0;
369 }
370 break;
371 case 1:
372 if (i & IS_AUI) {
373 printf("10base5\n");
374 } else {
375 printf("10base5 not present\n");
376 return 0;
377 }
378 break;
379 case 3:
380 if (i & IS_BNC) {
381 printf("10base2\n");
382 connector = bnc;
383 } else {
384 printf("10base2 not present\n");
385 return 0;
386 }
387 break;
388 default:
389 printf("unknown connector\n");
390 return 0;
391 }
392
393 /*
394 * Read the station address from the eeprom
395 */
396 p = (unsigned short *) nic->node_addr;
397 for (i = 0; i < ETH_ALEN / 2; i++) {
398 p[i] = htons(get_e(nic->ioaddr,i));
399 GO_WINDOW(nic->ioaddr,2);
400 outw(ntohs(p[i]), nic->ioaddr + EP_W2_ADDR_0 + (i * 2));
401 }
402
403 DBG ( "Ethernet Address: %s\n", eth_ntoa ( nic->node_addr ) );
404
406
408 return 1;
409
410}
#define EEPROM_PROD_ID
Definition 3c509.h:90
#define IS_AUI
Definition 3c509.h:333
#define EP_W0_ADDRESS_CFG
Definition 3c509.h:119
#define IS_BNC
Definition 3c509.h:334
#define IS_UTP
Definition 3c509.h:335
static void t509_reset(struct nic *nic)
Definition 3c5x9.c:124
static int get_e(uint16_t ioaddr, int offset)
Definition 3c5x9.c:322
static struct nic_operations t509_operations
Definition 3c5x9.c:332
unsigned short uint16_t
Definition stdint.h:11
const char * eth_ntoa(const void *ll_addr)
Transcribe Ethernet address.
Definition ethernet.c:176
#define DBG(...)
Print a debugging message.
Definition compiler.h:498
#define ntohs(value)
Definition byteswap.h:137
struct nic_operations * nic_op
Definition nic.h:50

References bnc, connector, DBG, EEPROM_PROD_ID, EP_W0_ADDRESS_CFG, EP_W0_CONFIG_CTRL, EP_W2_ADDR_0, ETH_ALEN, eth_ntoa(), get_e(), GO_WINDOW, htons, inw, nic::ioaddr, IS_AUI, IS_BNC, IS_UTP, nic::nic_op, nic::node_addr, ntohs, outw, printf(), t509_operations, t509_reset(), and utp.

Referenced by el3_eisa_probe(), legacy_t509_probe(), and t529_probe().

Variable Documentation

◆ []

enum { ... } connector

Referenced by t509_enable(), and t5x9_probe().

◆ padmap

char padmap[]
static
Initial value:
= {
0, 3, 2, 1}

Definition at line 132 of file 3c5x9.c.

132 {
133 0, 3, 2, 1};

◆ t509_operations

struct nic_operations t509_operations
static
Initial value:
= {
.connect = dummy_connect,
.poll = t509_poll,
.transmit = t509_transmit,
.irq = t509_irq,
}
static void t509_irq(struct nic *nic __unused, irq_action_t action __unused)
Definition 3c5x9.c:290
static int t509_poll(struct nic *nic, int retrieve)
Definition 3c5x9.c:199
static void t509_transmit(struct nic *nic, const char *d, unsigned int t, unsigned int s, const char *p)
Definition 3c5x9.c:135
int dummy_connect(struct nic *nic __unused)
Definition legacy.c:175

Definition at line 332 of file 3c5x9.c.

332 {
333 .connect = dummy_connect,
334 .poll = t509_poll,
335 .transmit = t509_transmit,
336 .irq = t509_irq,
337};

Referenced by t5x9_probe().