sonic.c 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616
  1. /*
  2. * sonic.c
  3. *
  4. * (C) 1996,1998 by Thomas Bogendoerfer (tsbogend@alpha.franken.de)
  5. *
  6. * This driver is based on work from Andreas Busse, but most of
  7. * the code is rewritten.
  8. *
  9. * (C) 1995 by Andreas Busse (andy@waldorf-gmbh.de)
  10. *
  11. * Core code included by system sonic drivers
  12. */
  13. /*
  14. * Sources: Olivetti M700-10 Risc Personal Computer hardware handbook,
  15. * National Semiconductors data sheet for the DP83932B Sonic Ethernet
  16. * controller, and the files "8390.c" and "skeleton.c" in this directory.
  17. */
  18. /*
  19. * Open/initialize the SONIC controller.
  20. *
  21. * This routine should set everything up anew at each open, even
  22. * registers that "should" only need to be set once at boot, so that
  23. * there is non-reboot way to recover if something goes wrong.
  24. */
  25. static int sonic_open(struct net_device *dev)
  26. {
  27. if (sonic_debug > 2)
  28. printk("sonic_open: initializing sonic driver.\n");
  29. /*
  30. * We don't need to deal with auto-irq stuff since we
  31. * hardwire the sonic interrupt.
  32. */
  33. /*
  34. * XXX Horrible work around: We install sonic_interrupt as fast interrupt.
  35. * This means that during execution of the handler interrupt are disabled
  36. * covering another bug otherwise corrupting data. This doesn't mean
  37. * this glue works ok under all situations.
  38. */
  39. // if (sonic_request_irq(dev->irq, &sonic_interrupt, 0, "sonic", dev)) {
  40. if (sonic_request_irq(dev->irq, &sonic_interrupt, SA_INTERRUPT,
  41. "sonic", dev)) {
  42. printk("\n%s: unable to get IRQ %d .\n", dev->name, dev->irq);
  43. return -EAGAIN;
  44. }
  45. /*
  46. * Initialize the SONIC
  47. */
  48. sonic_init(dev);
  49. netif_start_queue(dev);
  50. if (sonic_debug > 2)
  51. printk("sonic_open: Initialization done.\n");
  52. return 0;
  53. }
  54. /*
  55. * Close the SONIC device
  56. */
  57. static int sonic_close(struct net_device *dev)
  58. {
  59. unsigned int base_addr = dev->base_addr;
  60. if (sonic_debug > 2)
  61. printk("sonic_close\n");
  62. netif_stop_queue(dev);
  63. /*
  64. * stop the SONIC, disable interrupts
  65. */
  66. SONIC_WRITE(SONIC_ISR, 0x7fff);
  67. SONIC_WRITE(SONIC_IMR, 0);
  68. SONIC_WRITE(SONIC_CMD, SONIC_CR_RST);
  69. sonic_free_irq(dev->irq, dev); /* release the IRQ */
  70. return 0;
  71. }
  72. static void sonic_tx_timeout(struct net_device *dev)
  73. {
  74. struct sonic_local *lp = (struct sonic_local *) dev->priv;
  75. printk("%s: transmit timed out.\n", dev->name);
  76. /* Try to restart the adaptor. */
  77. sonic_init(dev);
  78. lp->stats.tx_errors++;
  79. dev->trans_start = jiffies;
  80. netif_wake_queue(dev);
  81. }
  82. /*
  83. * transmit packet
  84. */
  85. static int sonic_send_packet(struct sk_buff *skb, struct net_device *dev)
  86. {
  87. struct sonic_local *lp = (struct sonic_local *) dev->priv;
  88. unsigned int base_addr = dev->base_addr;
  89. unsigned int laddr;
  90. int entry, length;
  91. netif_stop_queue(dev);
  92. if (sonic_debug > 2)
  93. printk("sonic_send_packet: skb=%p, dev=%p\n", skb, dev);
  94. /*
  95. * Map the packet data into the logical DMA address space
  96. */
  97. if ((laddr = vdma_alloc(CPHYSADDR(skb->data), skb->len)) == ~0UL) {
  98. printk("%s: no VDMA entry for transmit available.\n",
  99. dev->name);
  100. dev_kfree_skb(skb);
  101. netif_start_queue(dev);
  102. return 1;
  103. }
  104. entry = lp->cur_tx & SONIC_TDS_MASK;
  105. lp->tx_laddr[entry] = laddr;
  106. lp->tx_skb[entry] = skb;
  107. length = (skb->len < ETH_ZLEN) ? ETH_ZLEN : skb->len;
  108. flush_cache_all();
  109. /*
  110. * Setup the transmit descriptor and issue the transmit command.
  111. */
  112. lp->tda[entry].tx_status = 0; /* clear status */
  113. lp->tda[entry].tx_frag_count = 1; /* single fragment */
  114. lp->tda[entry].tx_pktsize = length; /* length of packet */
  115. lp->tda[entry].tx_frag_ptr_l = laddr & 0xffff;
  116. lp->tda[entry].tx_frag_ptr_h = laddr >> 16;
  117. lp->tda[entry].tx_frag_size = length;
  118. lp->cur_tx++;
  119. lp->stats.tx_bytes += length;
  120. if (sonic_debug > 2)
  121. printk("sonic_send_packet: issueing Tx command\n");
  122. SONIC_WRITE(SONIC_CMD, SONIC_CR_TXP);
  123. dev->trans_start = jiffies;
  124. if (lp->cur_tx < lp->dirty_tx + SONIC_NUM_TDS)
  125. netif_start_queue(dev);
  126. else
  127. lp->tx_full = 1;
  128. return 0;
  129. }
  130. /*
  131. * The typical workload of the driver:
  132. * Handle the network interface interrupts.
  133. */
  134. static irqreturn_t sonic_interrupt(int irq, void *dev_id, struct pt_regs *regs)
  135. {
  136. struct net_device *dev = (struct net_device *) dev_id;
  137. unsigned int base_addr = dev->base_addr;
  138. struct sonic_local *lp;
  139. int status;
  140. if (dev == NULL) {
  141. printk("sonic_interrupt: irq %d for unknown device.\n", irq);
  142. return IRQ_NONE;
  143. }
  144. lp = (struct sonic_local *) dev->priv;
  145. status = SONIC_READ(SONIC_ISR);
  146. SONIC_WRITE(SONIC_ISR, 0x7fff); /* clear all bits */
  147. if (sonic_debug > 2)
  148. printk("sonic_interrupt: ISR=%x\n", status);
  149. if (status & SONIC_INT_PKTRX) {
  150. sonic_rx(dev); /* got packet(s) */
  151. }
  152. if (status & SONIC_INT_TXDN) {
  153. int dirty_tx = lp->dirty_tx;
  154. while (dirty_tx < lp->cur_tx) {
  155. int entry = dirty_tx & SONIC_TDS_MASK;
  156. int status = lp->tda[entry].tx_status;
  157. if (sonic_debug > 3)
  158. printk
  159. ("sonic_interrupt: status %d, cur_tx %d, dirty_tx %d\n",
  160. status, lp->cur_tx, lp->dirty_tx);
  161. if (status == 0) {
  162. /* It still hasn't been Txed, kick the sonic again */
  163. SONIC_WRITE(SONIC_CMD, SONIC_CR_TXP);
  164. break;
  165. }
  166. /* put back EOL and free descriptor */
  167. lp->tda[entry].tx_frag_count = 0;
  168. lp->tda[entry].tx_status = 0;
  169. if (status & 0x0001)
  170. lp->stats.tx_packets++;
  171. else {
  172. lp->stats.tx_errors++;
  173. if (status & 0x0642)
  174. lp->stats.tx_aborted_errors++;
  175. if (status & 0x0180)
  176. lp->stats.tx_carrier_errors++;
  177. if (status & 0x0020)
  178. lp->stats.tx_window_errors++;
  179. if (status & 0x0004)
  180. lp->stats.tx_fifo_errors++;
  181. }
  182. /* We must free the original skb */
  183. if (lp->tx_skb[entry]) {
  184. dev_kfree_skb_irq(lp->tx_skb[entry]);
  185. lp->tx_skb[entry] = 0;
  186. }
  187. /* and the VDMA address */
  188. vdma_free(lp->tx_laddr[entry]);
  189. dirty_tx++;
  190. }
  191. if (lp->tx_full
  192. && dirty_tx + SONIC_NUM_TDS > lp->cur_tx + 2) {
  193. /* The ring is no longer full, clear tbusy. */
  194. lp->tx_full = 0;
  195. netif_wake_queue(dev);
  196. }
  197. lp->dirty_tx = dirty_tx;
  198. }
  199. /*
  200. * check error conditions
  201. */
  202. if (status & SONIC_INT_RFO) {
  203. printk("%s: receive fifo underrun\n", dev->name);
  204. lp->stats.rx_fifo_errors++;
  205. }
  206. if (status & SONIC_INT_RDE) {
  207. printk("%s: receive descriptors exhausted\n", dev->name);
  208. lp->stats.rx_dropped++;
  209. }
  210. if (status & SONIC_INT_RBE) {
  211. printk("%s: receive buffer exhausted\n", dev->name);
  212. lp->stats.rx_dropped++;
  213. }
  214. if (status & SONIC_INT_RBAE) {
  215. printk("%s: receive buffer area exhausted\n", dev->name);
  216. lp->stats.rx_dropped++;
  217. }
  218. /* counter overruns; all counters are 16bit wide */
  219. if (status & SONIC_INT_FAE)
  220. lp->stats.rx_frame_errors += 65536;
  221. if (status & SONIC_INT_CRC)
  222. lp->stats.rx_crc_errors += 65536;
  223. if (status & SONIC_INT_MP)
  224. lp->stats.rx_missed_errors += 65536;
  225. /* transmit error */
  226. if (status & SONIC_INT_TXER)
  227. lp->stats.tx_errors++;
  228. /*
  229. * clear interrupt bits and return
  230. */
  231. SONIC_WRITE(SONIC_ISR, status);
  232. return IRQ_HANDLED;
  233. }
  234. /*
  235. * We have a good packet(s), get it/them out of the buffers.
  236. */
  237. static void sonic_rx(struct net_device *dev)
  238. {
  239. unsigned int base_addr = dev->base_addr;
  240. struct sonic_local *lp = (struct sonic_local *) dev->priv;
  241. sonic_rd_t *rd = &lp->rda[lp->cur_rx & SONIC_RDS_MASK];
  242. int status;
  243. while (rd->in_use == 0) {
  244. struct sk_buff *skb;
  245. int pkt_len;
  246. unsigned char *pkt_ptr;
  247. status = rd->rx_status;
  248. if (sonic_debug > 3)
  249. printk("status %x, cur_rx %d, cur_rra %x\n",
  250. status, lp->cur_rx, lp->cur_rra);
  251. if (status & SONIC_RCR_PRX) {
  252. pkt_len = rd->rx_pktlen;
  253. pkt_ptr =
  254. (char *)
  255. sonic_chiptomem((rd->rx_pktptr_h << 16) +
  256. rd->rx_pktptr_l);
  257. if (sonic_debug > 3)
  258. printk
  259. ("pktptr %p (rba %p) h:%x l:%x, bsize h:%x l:%x\n",
  260. pkt_ptr, lp->rba, rd->rx_pktptr_h,
  261. rd->rx_pktptr_l,
  262. SONIC_READ(SONIC_RBWC1),
  263. SONIC_READ(SONIC_RBWC0));
  264. /* Malloc up new buffer. */
  265. skb = dev_alloc_skb(pkt_len + 2);
  266. if (skb == NULL) {
  267. printk
  268. ("%s: Memory squeeze, dropping packet.\n",
  269. dev->name);
  270. lp->stats.rx_dropped++;
  271. break;
  272. }
  273. skb->dev = dev;
  274. skb_reserve(skb, 2); /* 16 byte align */
  275. skb_put(skb, pkt_len); /* Make room */
  276. eth_copy_and_sum(skb, pkt_ptr, pkt_len, 0);
  277. skb->protocol = eth_type_trans(skb, dev);
  278. netif_rx(skb); /* pass the packet to upper layers */
  279. dev->last_rx = jiffies;
  280. lp->stats.rx_packets++;
  281. lp->stats.rx_bytes += pkt_len;
  282. } else {
  283. /* This should only happen, if we enable accepting broken packets. */
  284. lp->stats.rx_errors++;
  285. if (status & SONIC_RCR_FAER)
  286. lp->stats.rx_frame_errors++;
  287. if (status & SONIC_RCR_CRCR)
  288. lp->stats.rx_crc_errors++;
  289. }
  290. rd->in_use = 1;
  291. rd = &lp->rda[(++lp->cur_rx) & SONIC_RDS_MASK];
  292. /* now give back the buffer to the receive buffer area */
  293. if (status & SONIC_RCR_LPKT) {
  294. /*
  295. * this was the last packet out of the current receice buffer
  296. * give the buffer back to the SONIC
  297. */
  298. lp->cur_rra += sizeof(sonic_rr_t);
  299. if (lp->cur_rra >
  300. (lp->rra_laddr +
  301. (SONIC_NUM_RRS -
  302. 1) * sizeof(sonic_rr_t))) lp->cur_rra =
  303. lp->rra_laddr;
  304. SONIC_WRITE(SONIC_RWP, lp->cur_rra & 0xffff);
  305. } else
  306. printk
  307. ("%s: rx desc without RCR_LPKT. Shouldn't happen !?\n",
  308. dev->name);
  309. }
  310. /*
  311. * If any worth-while packets have been received, dev_rint()
  312. * has done a mark_bh(NET_BH) for us and will work on them
  313. * when we get to the bottom-half routine.
  314. */
  315. }
  316. /*
  317. * Get the current statistics.
  318. * This may be called with the device open or closed.
  319. */
  320. static struct net_device_stats *sonic_get_stats(struct net_device *dev)
  321. {
  322. struct sonic_local *lp = (struct sonic_local *) dev->priv;
  323. unsigned int base_addr = dev->base_addr;
  324. /* read the tally counter from the SONIC and reset them */
  325. lp->stats.rx_crc_errors += SONIC_READ(SONIC_CRCT);
  326. SONIC_WRITE(SONIC_CRCT, 0xffff);
  327. lp->stats.rx_frame_errors += SONIC_READ(SONIC_FAET);
  328. SONIC_WRITE(SONIC_FAET, 0xffff);
  329. lp->stats.rx_missed_errors += SONIC_READ(SONIC_MPT);
  330. SONIC_WRITE(SONIC_MPT, 0xffff);
  331. return &lp->stats;
  332. }
  333. /*
  334. * Set or clear the multicast filter for this adaptor.
  335. */
  336. static void sonic_multicast_list(struct net_device *dev)
  337. {
  338. struct sonic_local *lp = (struct sonic_local *) dev->priv;
  339. unsigned int base_addr = dev->base_addr;
  340. unsigned int rcr;
  341. struct dev_mc_list *dmi = dev->mc_list;
  342. unsigned char *addr;
  343. int i;
  344. rcr = SONIC_READ(SONIC_RCR) & ~(SONIC_RCR_PRO | SONIC_RCR_AMC);
  345. rcr |= SONIC_RCR_BRD; /* accept broadcast packets */
  346. if (dev->flags & IFF_PROMISC) { /* set promiscuous mode */
  347. rcr |= SONIC_RCR_PRO;
  348. } else {
  349. if ((dev->flags & IFF_ALLMULTI) || (dev->mc_count > 15)) {
  350. rcr |= SONIC_RCR_AMC;
  351. } else {
  352. if (sonic_debug > 2)
  353. printk
  354. ("sonic_multicast_list: mc_count %d\n",
  355. dev->mc_count);
  356. lp->cda.cam_enable = 1; /* always enable our own address */
  357. for (i = 1; i <= dev->mc_count; i++) {
  358. addr = dmi->dmi_addr;
  359. dmi = dmi->next;
  360. lp->cda.cam_desc[i].cam_cap0 =
  361. addr[1] << 8 | addr[0];
  362. lp->cda.cam_desc[i].cam_cap1 =
  363. addr[3] << 8 | addr[2];
  364. lp->cda.cam_desc[i].cam_cap2 =
  365. addr[5] << 8 | addr[4];
  366. lp->cda.cam_enable |= (1 << i);
  367. }
  368. SONIC_WRITE(SONIC_CDC, 16);
  369. /* issue Load CAM command */
  370. SONIC_WRITE(SONIC_CDP, lp->cda_laddr & 0xffff);
  371. SONIC_WRITE(SONIC_CMD, SONIC_CR_LCAM);
  372. }
  373. }
  374. if (sonic_debug > 2)
  375. printk("sonic_multicast_list: setting RCR=%x\n", rcr);
  376. SONIC_WRITE(SONIC_RCR, rcr);
  377. }
  378. /*
  379. * Initialize the SONIC ethernet controller.
  380. */
  381. static int sonic_init(struct net_device *dev)
  382. {
  383. unsigned int base_addr = dev->base_addr;
  384. unsigned int cmd;
  385. struct sonic_local *lp = (struct sonic_local *) dev->priv;
  386. unsigned int rra_start;
  387. unsigned int rra_end;
  388. int i;
  389. /*
  390. * put the Sonic into software-reset mode and
  391. * disable all interrupts
  392. */
  393. SONIC_WRITE(SONIC_ISR, 0x7fff);
  394. SONIC_WRITE(SONIC_IMR, 0);
  395. SONIC_WRITE(SONIC_CMD, SONIC_CR_RST);
  396. /*
  397. * clear software reset flag, disable receiver, clear and
  398. * enable interrupts, then completely initialize the SONIC
  399. */
  400. SONIC_WRITE(SONIC_CMD, 0);
  401. SONIC_WRITE(SONIC_CMD, SONIC_CR_RXDIS);
  402. /*
  403. * initialize the receive resource area
  404. */
  405. if (sonic_debug > 2)
  406. printk("sonic_init: initialize receive resource area\n");
  407. rra_start = lp->rra_laddr & 0xffff;
  408. rra_end =
  409. (rra_start + (SONIC_NUM_RRS * sizeof(sonic_rr_t))) & 0xffff;
  410. for (i = 0; i < SONIC_NUM_RRS; i++) {
  411. lp->rra[i].rx_bufadr_l =
  412. (lp->rba_laddr + i * SONIC_RBSIZE) & 0xffff;
  413. lp->rra[i].rx_bufadr_h =
  414. (lp->rba_laddr + i * SONIC_RBSIZE) >> 16;
  415. lp->rra[i].rx_bufsize_l = SONIC_RBSIZE >> 1;
  416. lp->rra[i].rx_bufsize_h = 0;
  417. }
  418. /* initialize all RRA registers */
  419. SONIC_WRITE(SONIC_RSA, rra_start);
  420. SONIC_WRITE(SONIC_REA, rra_end);
  421. SONIC_WRITE(SONIC_RRP, rra_start);
  422. SONIC_WRITE(SONIC_RWP, rra_end);
  423. SONIC_WRITE(SONIC_URRA, lp->rra_laddr >> 16);
  424. SONIC_WRITE(SONIC_EOBC, (SONIC_RBSIZE - 2) >> 1);
  425. lp->cur_rra =
  426. lp->rra_laddr + (SONIC_NUM_RRS - 1) * sizeof(sonic_rr_t);
  427. /* load the resource pointers */
  428. if (sonic_debug > 3)
  429. printk("sonic_init: issueing RRRA command\n");
  430. SONIC_WRITE(SONIC_CMD, SONIC_CR_RRRA);
  431. i = 0;
  432. while (i++ < 100) {
  433. if (SONIC_READ(SONIC_CMD) & SONIC_CR_RRRA)
  434. break;
  435. }
  436. if (sonic_debug > 2)
  437. printk("sonic_init: status=%x\n", SONIC_READ(SONIC_CMD));
  438. /*
  439. * Initialize the receive descriptors so that they
  440. * become a circular linked list, ie. let the last
  441. * descriptor point to the first again.
  442. */
  443. if (sonic_debug > 2)
  444. printk("sonic_init: initialize receive descriptors\n");
  445. for (i = 0; i < SONIC_NUM_RDS; i++) {
  446. lp->rda[i].rx_status = 0;
  447. lp->rda[i].rx_pktlen = 0;
  448. lp->rda[i].rx_pktptr_l = 0;
  449. lp->rda[i].rx_pktptr_h = 0;
  450. lp->rda[i].rx_seqno = 0;
  451. lp->rda[i].in_use = 1;
  452. lp->rda[i].link =
  453. lp->rda_laddr + (i + 1) * sizeof(sonic_rd_t);
  454. }
  455. /* fix last descriptor */
  456. lp->rda[SONIC_NUM_RDS - 1].link = lp->rda_laddr;
  457. lp->cur_rx = 0;
  458. SONIC_WRITE(SONIC_URDA, lp->rda_laddr >> 16);
  459. SONIC_WRITE(SONIC_CRDA, lp->rda_laddr & 0xffff);
  460. /*
  461. * initialize transmit descriptors
  462. */
  463. if (sonic_debug > 2)
  464. printk("sonic_init: initialize transmit descriptors\n");
  465. for (i = 0; i < SONIC_NUM_TDS; i++) {
  466. lp->tda[i].tx_status = 0;
  467. lp->tda[i].tx_config = 0;
  468. lp->tda[i].tx_pktsize = 0;
  469. lp->tda[i].tx_frag_count = 0;
  470. lp->tda[i].link =
  471. (lp->tda_laddr +
  472. (i + 1) * sizeof(sonic_td_t)) | SONIC_END_OF_LINKS;
  473. }
  474. lp->tda[SONIC_NUM_TDS - 1].link =
  475. (lp->tda_laddr & 0xffff) | SONIC_END_OF_LINKS;
  476. SONIC_WRITE(SONIC_UTDA, lp->tda_laddr >> 16);
  477. SONIC_WRITE(SONIC_CTDA, lp->tda_laddr & 0xffff);
  478. lp->cur_tx = lp->dirty_tx = 0;
  479. /*
  480. * put our own address to CAM desc[0]
  481. */
  482. lp->cda.cam_desc[0].cam_cap0 =
  483. dev->dev_addr[1] << 8 | dev->dev_addr[0];
  484. lp->cda.cam_desc[0].cam_cap1 =
  485. dev->dev_addr[3] << 8 | dev->dev_addr[2];
  486. lp->cda.cam_desc[0].cam_cap2 =
  487. dev->dev_addr[5] << 8 | dev->dev_addr[4];
  488. lp->cda.cam_enable = 1;
  489. for (i = 0; i < 16; i++)
  490. lp->cda.cam_desc[i].cam_entry_pointer = i;
  491. /*
  492. * initialize CAM registers
  493. */
  494. SONIC_WRITE(SONIC_CDP, lp->cda_laddr & 0xffff);
  495. SONIC_WRITE(SONIC_CDC, 16);
  496. /*
  497. * load the CAM
  498. */
  499. SONIC_WRITE(SONIC_CMD, SONIC_CR_LCAM);
  500. i = 0;
  501. while (i++ < 100) {
  502. if (SONIC_READ(SONIC_ISR) & SONIC_INT_LCD)
  503. break;
  504. }
  505. if (sonic_debug > 2) {
  506. printk("sonic_init: CMD=%x, ISR=%x\n",
  507. SONIC_READ(SONIC_CMD), SONIC_READ(SONIC_ISR));
  508. }
  509. /*
  510. * enable receiver, disable loopback
  511. * and enable all interrupts
  512. */
  513. SONIC_WRITE(SONIC_CMD, SONIC_CR_RXEN | SONIC_CR_STP);
  514. SONIC_WRITE(SONIC_RCR, SONIC_RCR_DEFAULT);
  515. SONIC_WRITE(SONIC_TCR, SONIC_TCR_DEFAULT);
  516. SONIC_WRITE(SONIC_ISR, 0x7fff);
  517. SONIC_WRITE(SONIC_IMR, SONIC_IMR_DEFAULT);
  518. cmd = SONIC_READ(SONIC_CMD);
  519. if ((cmd & SONIC_CR_RXEN) == 0 || (cmd & SONIC_CR_STP) == 0)
  520. printk("sonic_init: failed, status=%x\n", cmd);
  521. if (sonic_debug > 2)
  522. printk("sonic_init: new status=%x\n",
  523. SONIC_READ(SONIC_CMD));
  524. return 0;
  525. }
  526. MODULE_LICENSE("GPL");