15b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* -*- Mode:C; c-basic-offset:4; -*- */ 25b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 35b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* 45b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Tulip and clone Etherboot Driver 55b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 65b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project By Marty Connor (mdc@thinguin.org) 75b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Copyright (C) 2001 Entity Cyber, Inc. 85b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 95b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project This software may be used and distributed according to the terms 105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project of the GNU Public License, incorporated herein by reference. 115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project As of April 2001 this driver should support most tulip cards that 135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project the Linux tulip driver supports because Donald Becker's Linux media 145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project detection code is now included. 155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Based on Ken Yap's Tulip Etherboot Driver and Donald Becker's 175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Linux Tulip Driver. Supports N-Way speed auto-configuration on 185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project MX98715, MX98715A and MX98725. Support inexpensive PCI 10/100 cards 195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project based on the Macronix MX987x5 chip, such as the SOHOware Fast 205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project model SFA110A, and the LinkSYS model LNE100TX. The NetGear 215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project model FA310X, based on the LC82C168 chip is supported. 225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project The TRENDnet TE100-PCIA NIC which uses a genuine Intel 21143-PD 235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project chipset is supported. Also, Davicom DM9102's. 245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Documentation and source code used: 265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Source for Etherboot driver at 275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project http://etherboot.sourceforge.net/ 285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project MX98715A Data Sheet and MX98715A Application Note 295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project on http://www.macronix.com/ (PDF format files) 305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Source for Linux tulip driver at 315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project http://cesdis.gsfc.nasa.gov/linux/drivers/tulip.html 325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Adapted by Ken Yap from 345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project FreeBSD netboot DEC 21143 driver 355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Author: David Sharp 365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project date: Nov/98 375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Some code fragments were taken from verious places, Ken Yap's 395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project etherboot, FreeBSD's if_de.c, and various Linux related files. 405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project DEC's manuals for the 21143 and SROM format were very helpful. 415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project The Linux de driver development page has a number of links to 425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project useful related information. Have a look at: 435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ftp://cesdis.gsfc.nasa.gov/pub/linux/drivers/tulip-devel.html 445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project*/ 455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Revision History */ 485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* 515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11 Apr 2001 mdc [patch to etherboot 4.7.24] 525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Major rewrite to include Linux tulip driver media detection 535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project code. This driver should support a lot more cards now. 545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 16 Jul 2000 mdc 0.75b11 555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Added support for ADMtek 0985 Centaur-P, a "Comet" tulip clone 565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project which is used on the LinkSYS LNE100TX v4.x cards. We already 575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project support LNE100TX v2.0 cards, which use a different controller. 585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 04 Jul 2000 jam ? 595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Added test of status after receiving a packet from the card. 605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Also uncommented the tulip_disable routine. Stray packets 615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project seemed to be causing problems. 625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 27 Apr 2000 njl ? 635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 29 Feb 2000 mdc 0.75b7 645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Increased reset delay to 3 seconds because Macronix cards seem to 655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project need more reset time before card comes back to a usable state. 665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 26 Feb 2000 mdc 0.75b6 675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Added a 1 second delay after initializing the transmitter because 685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project some cards seem to need the time or they drop the first packet 695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project transmitted. 705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 23 Feb 2000 mdc 0.75b5 715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project removed udelay code and used currticks() for more reliable delay 725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project code in reset pause and sanity timeouts. Added function prototypes 735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project and TX debugging code. 745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 21 Feb 2000 mdc patch to Etherboot 4.4.3 755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Incorporated patches from Bob Edwards and Paul Mackerras of 765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Linuxcare's OZLabs to deal with inefficiencies in tulip_transmit 775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project and udelay. We now wait for packet transmission to complete 785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (or sanity timeout). 795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 04 Feb 2000 Robert.Edwards@anu.edu.au patch to Etherboot 4.4.2 805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project patch to tulip.c that implements the automatic selection of the MII 815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project interface on cards using the Intel/DEC 21143 reference design, in 825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project particular, the TRENDnet TE100-PCIA NIC which uses a genuine Intel 835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 21143-PD chipset. 845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11 Jan 2000 mdc 0.75b4 855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Added support for NetGear FA310TX card based on the LC82C168 865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project chip. This should also support Lite-On LC82C168 boards. 875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Added simple MII support. Re-arranged code to better modularize 885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project initializations. 895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 04 Dec 1999 mdc 0.75b3 905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Added preliminary support for LNE100TX PCI cards. Should work for 915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project PNIC2 cards. No MII support, but single interface (RJ45) tulip 925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project cards seem to not care. 935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 03 Dec 1999 mdc 0.75b2 945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Renamed from mx987x5 to tulip, merged in original tulip init code 955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project from tulip.c to support other tulip compatible cards. 965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 02 Dec 1999 mdc 0.75b1 975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Released Beta MX987x5 Driver for code review and testing to netboot 985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project and thinguin mailing lists. 995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project*/ 1005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 1035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Declarations */ 1045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 1055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#include "etherboot.h" 1075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#include "nic.h" 1085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#include "pci.h" 1095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#include "cards.h" 1105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* User settable parameters */ 1125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#undef TULIP_DEBUG 1145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#undef TULIP_DEBUG_WHERE 1155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int tulip_debug = 2; /* 1 normal messages, 0 quiet .. 7 verbose. */ 1165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define TX_TIME_OUT 2*TICKS_PER_SEC 1185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projecttypedef unsigned char u8; 1205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projecttypedef signed char s8; 1215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projecttypedef unsigned short u16; 1225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projecttypedef signed short s16; 1235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projecttypedef unsigned int u32; 1245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projecttypedef signed int s32; 1255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* helpful macros if on a big_endian machine for changing byte order. 1275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project not strictly needed on Intel */ 1285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define le16_to_cpu(val) (val) 1295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define cpu_to_le32(val) (val) 1305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define get_unaligned(ptr) (*(ptr)) 1315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define put_unaligned(val, ptr) ((void)( *(ptr) = (val) )) 1325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define get_u16(ptr) (*(u16 *)(ptr)) 1335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define virt_to_bus(x) ((unsigned long)x) 1345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define virt_to_le32desc(addr) virt_to_bus(addr) 1355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define TULIP_IOTYPE PCI_USES_MASTER | PCI_USES_IO | PCI_ADDR0 1375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define TULIP_SIZE 0x80 1385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* This is a mysterious value that can be written to CSR11 in the 21040 (only) 1405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project to support a pre-NWay full-duplex signaling mechanism using short frames. 1415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project No one knows what it should be, but if left at its default value some 1425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10base2(!) packets trigger a full-duplex-request interrupt. */ 1435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define FULL_DUPLEX_MAGIC 0x6969 1445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic const int csr0 = 0x01A00000 | 0x8000; 1465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* The possible media types that can be set in options[] are: */ 1485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define MEDIA_MASK 31 1495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic const char * const medianame[32] = { 1505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "10baseT", "10base2", "AUI", "100baseTx", 1515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "10baseT-FDX", "100baseTx-FDX", "100baseT4", "100baseFx", 1525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "100baseFx-FDX", "MII 10baseT", "MII 10baseT-FDX", "MII", 1535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "10baseT(forced)", "MII 100baseTx", "MII 100baseTx-FDX", "MII 100baseT4", 1545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "MII 100baseFx-HDX", "MII 100baseFx-FDX", "Home-PNA 1Mbps", "Invalid-19", 1555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 1565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* This much match tulip_tbl[]! Note 21142 == 21143. */ 1585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectenum tulip_chips { 1595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project DC21040=0, DC21041=1, DC21140=2, DC21142=3, DC21143=3, 1605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project LC82C168, MX98713, MX98715, MX98725, AX88141, AX88140, PNIC2, COMET, 1615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project COMPEX9881, I21145, XIRCOM 1625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 1635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectenum pci_id_flags_bits { 1655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Set PCI command register bits before calling probe1(). */ 1665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project PCI_USES_IO=1, PCI_USES_MEM=2, PCI_USES_MASTER=4, 1675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Read and map the single following PCI BAR. */ 1685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project PCI_ADDR0=0<<4, PCI_ADDR1=1<<4, PCI_ADDR2=2<<4, PCI_ADDR3=3<<4, 1695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project PCI_ADDR_64BITS=0x100, PCI_NO_ACPI_WAKE=0x200, PCI_NO_MIN_LATENCY=0x400, 1705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project PCI_UNUSED_IRQ=0x800, 1715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 1725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct pci_id_info { 1745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project char *name; 1755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct match_info { 1765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 pci, pci_mask, subsystem, subsystem_mask; 1775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 revision, revision_mask; /* Only 8 bits. */ 1785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } id; 1795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project enum pci_id_flags_bits pci_flags; 1805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int io_size; /* Needed for I/O region check or ioremap(). */ 1815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int drv_flags; /* Driver use, intended as capability flags. */ 1825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 1835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 1845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic struct pci_id_info pci_id_tbl[] = { 1855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DC21040 Tulip", { 0x00021011, 0xffffffff, 0, 0, 0, 0 }, 1865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 0x80, DC21040 }, 1875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DC21041 Tulip", { 0x00141011, 0xffffffff, 0, 0, 0, 0 }, 1885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 0x80, DC21041 }, 1895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DS21140A Tulip", { 0x00091011, 0xffffffff, 0,0, 0x20,0xf0 }, 1905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 0x80, DC21140 }, 1915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DS21140 Tulip", { 0x00091011, 0xffffffff, 0, 0, 0, 0 }, 1925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 0x80, DC21140 }, 1935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DS21143 Tulip", { 0x00191011, 0xffffffff, 0,0, 65,0xff }, 1945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, TULIP_SIZE, DC21142 }, 1955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DS21142 Tulip", { 0x00191011, 0xffffffff, 0, 0, 0, 0 }, 1965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, TULIP_SIZE, DC21142 }, 1975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Kingston KNE110tx (PNIC)", { 0x000211AD, 0xffffffff, 0xf0022646, 0xffffffff, 0, 0 }, 1985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, LC82C168 }, 1995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Lite-On 82c168 PNIC", { 0x000211AD, 0xffffffff, 0, 0, 0, 0 }, 2005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, LC82C168 }, 2015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Macronix 98713 PMAC", { 0x051210d9, 0xffffffff, 0, 0, 0, 0 }, 2025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, MX98713 }, 2035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Macronix 98715 PMAC", { 0x053110d9, 0xffffffff, 0, 0, 0, 0 }, 2045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, MX98715 }, 2055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Macronix 98725 PMAC", { 0x053110d9, 0xffffffff, 0, 0, 0, 0 }, 2065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, MX98725 }, 2075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ASIX AX88141", { 0x1400125B, 0xffffffff, 0,0, 0x10, 0xf0 }, 2085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 128, AX88141 }, 2095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ASIX AX88140", { 0x1400125B, 0xffffffff, 0, 0, 0, 0 }, 2105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 128, AX88140 }, 2115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Lite-On LC82C115 PNIC-II", { 0xc11511AD, 0xffffffff, 0, 0, 0, 0 }, 2125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, PNIC2 }, 2135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ADMtek AN981 Comet", { 0x09811317, 0xffffffff, 0, 0, 0, 0 }, 2145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, COMET }, 2155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ADMtek Centaur-P", { 0x09851317, 0xffffffff, 0, 0, 0, 0 }, 2165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, COMET }, 2175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ADMtek Centaur-C", { 0x19851317, 0xffffffff, 0, 0, 0, 0 }, 2185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, COMET }, 2195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Compex RL100-TX", { 0x988111F6, 0xffffffff, 0, 0, 0, 0 }, 2205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 128, COMPEX9881 }, 2215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Intel 21145 Tulip", { 0x00398086, 0xffffffff, 0, 0, 0, 0 }, 2225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 128, I21145 }, 2235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Xircom Tulip clone", { 0x0003115d, 0xffffffff, 0, 0, 0, 0 }, 2245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 128, XIRCOM }, 2255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Davicom DM9102", { 0x91021282, 0xffffffff, 0, 0, 0, 0 }, 2265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 0x80, DC21140 }, 2275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Davicom DM9100", { 0x91001282, 0xffffffff, 0, 0, 0, 0 }, 2285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 0x80, DC21140 }, 2295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Macronix mxic-98715 (EN1217)", { 0x12171113, 0xffffffff, 0, 0, 0, 0 }, 2305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TULIP_IOTYPE, 256, MX98715 }, 2315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { 0, { 0, 0, 0, 0, 0, 0 }, 0, 0, 0 }, 2325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 2335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectenum tbl_flag { 2355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project HAS_MII=1, HAS_MEDIA_TABLE=2, CSR12_IN_SROM=4, ALWAYS_CHECK_MII=8, 2365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project HAS_PWRDWN=0x10, MC_HASH_ONLY=0x20, /* Hash-only multicast filter. */ 2375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project HAS_PNICNWAY=0x80, HAS_NWAY=0x40, /* Uses internal NWay xcvr. */ 2385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project HAS_INTR_MITIGATION=0x100, IS_ASIX=0x200, HAS_8023X=0x400, 2395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 2405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Note: this table must match enum tulip_chips above. */ 2425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic struct tulip_chip_table { 2435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project char *chip_name; 2445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int flags; 2455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} tulip_tbl[] = { 2465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DC21040 Tulip", 0}, 2475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DC21041 Tulip", HAS_MEDIA_TABLE | HAS_NWAY }, 2485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DS21140 Tulip", HAS_MII | HAS_MEDIA_TABLE | CSR12_IN_SROM }, 2495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Digital DS21143 Tulip", HAS_MII | HAS_MEDIA_TABLE | ALWAYS_CHECK_MII 2505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project | HAS_PWRDWN | HAS_NWAY | HAS_INTR_MITIGATION }, 2515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Lite-On 82c168 PNIC", HAS_MII | HAS_PNICNWAY }, 2525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Macronix 98713 PMAC", HAS_MII | HAS_MEDIA_TABLE | CSR12_IN_SROM }, 2535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Macronix 98715 PMAC", HAS_MEDIA_TABLE }, 2545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Macronix 98725 PMAC", HAS_MEDIA_TABLE }, 2555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ASIX AX88140", HAS_MII | HAS_MEDIA_TABLE | CSR12_IN_SROM 2565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project | MC_HASH_ONLY | IS_ASIX }, 2575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ASIX AX88141", HAS_MII | HAS_MEDIA_TABLE | CSR12_IN_SROM | MC_HASH_ONLY 2585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project | IS_ASIX }, 2595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Lite-On PNIC-II", HAS_MII | HAS_NWAY | HAS_8023X }, 2605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "ADMtek Comet", MC_HASH_ONLY }, 2615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Compex 9881 PMAC", HAS_MII | HAS_MEDIA_TABLE | CSR12_IN_SROM }, 2625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Intel DS21145 Tulip", HAS_MII | HAS_MEDIA_TABLE | ALWAYS_CHECK_MII 2635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project | HAS_PWRDWN | HAS_NWAY }, 2645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { "Xircom tulip work-alike", HAS_MII | HAS_MEDIA_TABLE | ALWAYS_CHECK_MII 2655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project | HAS_PWRDWN | HAS_NWAY }, 2665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project { 0, 0 }, 2675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 2685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* A full-duplex map for media types. */ 2705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectenum MediaIs { 2715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project MediaIsFD = 1, MediaAlwaysFD=2, MediaIsMII=4, MediaIsFx=8, 2725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project MediaIs100=16}; 2735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic const char media_cap[32] = 2755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{0,0,0,16, 3,19,16,24, 27,4,7,5, 0,20,23,20, 20,31,0,0, }; 2765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u8 t21040_csr13[] = {2,0x0C,8,4, 4,0,0,0, 0,0,0,0, 4,0,0,0}; 2775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* 21041 transceiver register settings: 10-T, 10-2, AUI, 10-T, 10T-FD */ 2795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u16 t21041_csr13[] = { 0xEF01, 0xEF09, 0xEF09, 0xEF01, 0xEF09, }; 2805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u16 t21041_csr14[] = { 0xFFFF, 0xF7FD, 0xF7FD, 0x7F3F, 0x7F3D, }; 2815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u16 t21041_csr15[] = { 0x0008, 0x0006, 0x000E, 0x0008, 0x0008, }; 2825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u16 t21142_csr13[] = { 0x0001, 0x0009, 0x0009, 0x0000, 0x0001, }; 2845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u16 t21142_csr14[] = { 0xFFFF, 0x0705, 0x0705, 0x0000, 0x7F3D, }; 2855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u16 t21142_csr15[] = { 0x0008, 0x0006, 0x000E, 0x0008, 0x0008, }; 2865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Offsets to the Command and Status Registers, "CSRs". All accesses 2885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project must be longword instructions and quadword aligned. */ 2895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectenum tulip_offsets { 2905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project CSR0=0, CSR1=0x08, CSR2=0x10, CSR3=0x18, CSR4=0x20, CSR5=0x28, 2915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project CSR6=0x30, CSR7=0x38, CSR8=0x40, CSR9=0x48, CSR10=0x50, CSR11=0x58, 2925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project CSR12=0x60, CSR13=0x68, CSR14=0x70, CSR15=0x78, CSR16=0x80, CSR20=0xA0 2935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 2945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 2955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* The bits in the CSR5 status registers, mostly interrupt sources. */ 2965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectenum status_bits { 2975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TimerInt=0x800, TPLnkFail=0x1000, TPLnkPass=0x10, 2985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project NormalIntr=0x10000, AbnormalIntr=0x8000, 2995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project RxJabber=0x200, RxDied=0x100, RxNoBuf=0x80, RxIntr=0x40, 3005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project TxFIFOUnderflow=0x20, TxJabber=0x08, TxNoBuf=0x04, TxDied=0x02, TxIntr=0x01, 3015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 3025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectenum desc_status_bits { 3045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project DescOwnded=0x80000000, RxDescFatalErr=0x8000, RxWholePkt=0x0300, 3055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 3065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct medialeaf { 3085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 type; 3095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 media; 3105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char *leafdata; 3115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 3125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct mediatable { 3145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 defaultmedia; 3155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 leafcount, csr12dir; /* General purpose pin directions. */ 3165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned has_mii:1, has_nonmii:1, has_reset:6; 3175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 csr15dir, csr15val; /* 21143 NWay setting. */ 3185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct medialeaf mleaf[0]; 3195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 3205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct mediainfo { 3225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct mediainfo *next; 3235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int info_type; 3245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int index; 3255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char *info; 3265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 3275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* EEPROM Address width definitions */ 3295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EEPROM_ADDRLEN 6 3305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EEPROM_SIZE 128 /* 2 << EEPROM_ADDRLEN */ 3315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* The EEPROM commands include the alway-set leading bit. */ 3335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_WRITE_CMD (5 << addr_len) 3345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_READ_CMD (6 << addr_len) 3355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_ERASE_CMD (7 << addr_len) 3365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* EEPROM_Ctrl bits. */ 3385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_SHIFT_CLK 0x02 /* EEPROM shift clock. */ 3395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_CS 0x01 /* EEPROM chip select. */ 3405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_DATA_WRITE 0x04 /* EEPROM chip data in. */ 3415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_WRITE_0 0x01 3425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_WRITE_1 0x05 3435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_DATA_READ 0x08 /* EEPROM chip data out. */ 3445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define EE_ENB (0x4800 | EE_CS) 3455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Delay between EEPROM clock transitions. Even at 33Mhz current PCI 3475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project implementations don't overrun the EEPROM clock. We add a bus 3485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project turn-around to insure that this remains true. */ 3495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define eeprom_delay() inl(ee_addr) 3505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Size of transmit and receive buffers */ 3525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define BUFLEN 1536 3535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Ring-wrap flag in length field, use for last ring entry. 3555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x01000000 means chain on buffer2 address, 3565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x02000000 means use the ring start address in CSR2/3. 3575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Note: Some work-alike chips do not function correctly in chained mode. 3585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project The ASIX chip works only in chained mode. 3595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Thus we indicate ring mode, but always write the 'next' field for 3605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project chained mode as well. */ 3615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define DESC_RING_WRAP 0x02000000 3625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* transmit and receive descriptor format */ 3645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct tulip_rx_desc { 3655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project volatile u32 status; 3665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 length; 3675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 buffer1, buffer2; 3685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 3695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct tulip_tx_desc { 3715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project volatile u32 status; 3725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 length; 3735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 buffer1, buffer2; 3745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project}; 3755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 3775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Global Storage */ 3785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 3795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic u32 ioaddr; 3815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Note: transmit and receive buffers must be longword aligned and 3835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project longword divisable */ 3845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define TX_RING_SIZE 2 3865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic struct tulip_tx_desc tx_ring[TX_RING_SIZE] __attribute__ ((aligned(4))); 3875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef USE_LOWMEM_BUFFER 3895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define txb ((char *)0x10000 - BUFLEN) 3905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#else 3915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic unsigned char txb[BUFLEN] __attribute__ ((aligned(4))); 3925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 3935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define RX_RING_SIZE 4 3955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic struct tulip_rx_desc rx_ring[RX_RING_SIZE] __attribute__ ((aligned(4))); 3965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 3975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef USE_LOWMEM_BUFFER 3985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define rxb ((char *)0x10000 - RX_RING_SIZE * BUFLEN - BUFLEN) 3995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#else 4005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic unsigned char rxb[RX_RING_SIZE * BUFLEN] __attribute__ ((aligned(4))); 4015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 4025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic struct tulip_private { 4045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int cur_rx; 4055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int chip_id; /* index into tulip_tbl[] */ 4065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int pci_id_idx; /* index into pci_id_tbl[] */ 4075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int revision; 4085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int flags; 4095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned short vendor_id; /* PCI card vendor code */ 4105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned short dev_id; /* PCI card device code */ 4115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char ehdr[ETH_HLEN]; /* buffer for ethernet header */ 4125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project const char *nic_name; 4135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int csr0, csr6; /* Current CSR0, CSR6 settings. */ 4145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int if_port; 4155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int full_duplex; /* Full-duplex operation requested. */ 4165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int full_duplex_lock; 4175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int medialock; /* Do not sense media type. */ 4185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int mediasense; /* Media sensing in progress. */ 4195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int nway, nwayset; /* 21143 internal NWay. */ 4205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int default_port; 4215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char eeprom[EEPROM_SIZE]; /* Serial EEPROM contents. */ 4225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 media_table_storage[(sizeof(struct mediatable) + 32*sizeof(struct medialeaf))]; 4235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 sym_advertise, mii_advertise; /* NWay to-advertise. */ 4245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct mediatable *mtable; 4255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 lpar; /* 21143 Link partner ability. */ 4265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 advertising[4]; /* MII advertise, from SROM table. */ 4275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project signed char phys[4], mii_cnt; /* MII device addresses. */ 4285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int cur_index; /* Current media index. */ 4295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int saved_if_port; 4305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} tpx; 4315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic struct tulip_private *tp; 4335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Known cards that have old-style EEPROMs. 4355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Writing this table is described at 4365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project http://cesdis.gsfc.nasa.gov/linux/drivers/tulip-drivers/tulip-media.html */ 4375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic struct fixups { 4385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project char *name; 4395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char addr0, addr1, addr2; 4405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 newtable[32]; /* Max length below. */ 4415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} eeprom_fixups[] = { 4425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project {"Asante", 0, 0, 0x94, {0x1e00, 0x0000, 0x0800, 0x0100, 0x018c, 4435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0000, 0x0000, 0xe078, 0x0001, 0x0050, 0x0018 }}, 4445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project {"SMC9332DST", 0, 0, 0xC0, { 0x1e00, 0x0000, 0x0800, 0x041f, 4455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0000, 0x009E, /* 10baseT */ 4465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0004, 0x009E, /* 10baseT-FD */ 4475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0903, 0x006D, /* 100baseTx */ 4485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0905, 0x006D, /* 100baseTx-FD */ }}, 4495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project {"Cogent EM100", 0, 0, 0x92, { 0x1e00, 0x0000, 0x0800, 0x063f, 4505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0107, 0x8021, /* 100baseFx */ 4515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0108, 0x8021, /* 100baseFx-FD */ 4525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0100, 0x009E, /* 10baseT */ 4535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0104, 0x009E, /* 10baseT-FD */ 4545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0103, 0x006D, /* 100baseTx */ 4555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0105, 0x006D, /* 100baseTx-FD */ }}, 4565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project {"Maxtech NX-110", 0, 0, 0xE8, { 0x1e00, 0x0000, 0x0800, 0x0513, 4575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x1001, 0x009E, /* 10base2, CSR12 0x10*/ 4585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0000, 0x009E, /* 10baseT */ 4595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0004, 0x009E, /* 10baseT-FD */ 4605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0303, 0x006D, /* 100baseTx, CSR12 0x03 */ 4615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0305, 0x006D, /* 100baseTx-FD CSR12 0x03 */}}, 4625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project {"Accton EN1207", 0, 0, 0xE8, { 0x1e00, 0x0000, 0x0800, 0x051F, 4635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x1B01, 0x0000, /* 10base2, CSR12 0x1B */ 4645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0B00, 0x009E, /* 10baseT, CSR12 0x0B */ 4655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x0B04, 0x009E, /* 10baseT-FD,CSR12 0x0B */ 4665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x1B03, 0x006D, /* 100baseTx, CSR12 0x1B */ 4675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 0x1B05, 0x006D, /* 100baseTx-FD CSR12 0x1B */ 4685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project }}, 4695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project {0, 0, 0, 0, {}}}; 4705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic const char * block_name[] = {"21140 non-MII", "21140 MII PHY", 4725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "21142 Serial PHY", "21142 MII PHY", "21143 SYM PHY", "21143 reset method"}; 4735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 4765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Function Prototypes */ 4775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 4785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int mdio_read(struct nic *nic, int phy_id, int location); 4795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void mdio_write(struct nic *nic, int phy_id, int location, int value); 4805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int read_eeprom(unsigned long ioaddr, int location, int addr_len); 4815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void parse_eeprom(struct nic *nic); 4825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct nic *tulip_probe(struct nic *nic, unsigned short *io_addrs, 4835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct pci_device *pci); 4845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_init_ring(struct nic *nic); 4855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_reset(struct nic *nic); 4865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_transmit(struct nic *nic, const char *d, unsigned int t, 4875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int s, const char *p); 4885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int tulip_poll(struct nic *nic); 4895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_disable(struct nic *nic); 4905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void nway_start(struct nic *nic); 4915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void pnic_do_nway(struct nic *nic); 4925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void select_media(struct nic *nic, int startup); 4935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void init_media(struct nic *nic); 4945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void start_link(struct nic *nic); 4955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int tulip_check_duplex(struct nic *nic); 4965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_wait(unsigned int nticks); 4985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 4995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 5005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void whereami(const char *str); 5015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 5025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 5045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_more(void); 5055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 5065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 5095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Utility Routines */ 5105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 5115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 5135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void whereami (const char *str) 5145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 5155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: %s\n", tp->nic_name, str); 5165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* sleep(2); */ 5175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 5185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 5195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 5215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_more(void) 5225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 5235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("\n\n-- more --"); 5245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (!iskey()) 5255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* wait */; 5265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project getchar(); 5275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("\n\n"); 5285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 5295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif /* TULIP_DEBUG */ 5305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_wait(unsigned int nticks) 5325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 5335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int to = currticks() + nticks; 5345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (currticks() < to) 5355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* wait */ ; 5365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 5375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 5405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Media Descriptor Code */ 5415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 5425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* MII transceiver control section. 5445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Read and write the MII registers using software-generated serial 5455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project MDIO protocol. See the MII specifications or DP83840A data sheet 5465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for details. */ 5475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* The maximum data clock rate is 2.5 Mhz. The minimum timing is usually 5495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project met by back-to-back PCI I/O cycles, but we insert a delay to avoid 5505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "overclocking" issues or future 66Mhz PCI. */ 5515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define mdio_delay() inl(mdio_addr) 5525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Read and write the MII registers using software-generated serial 5545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project MDIO protocol. It is just different enough from the EEPROM protocol 5555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project to not share code. The maxium data clock rate is 2.5 Mhz. */ 5565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define MDIO_SHIFT_CLK 0x10000 5575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define MDIO_DATA_WRITE0 0x00000 5585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define MDIO_DATA_WRITE1 0x20000 5595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define MDIO_ENB 0x00000 /* Ignore the 0x02000 databook setting. */ 5605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define MDIO_ENB_IN 0x40000 5615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#define MDIO_DATA_READ 0x80000 5625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* MII transceiver control section. 5645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Read and write the MII registers using software-generated serial 5655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project MDIO protocol. See the MII specifications or DP83840A data sheet 5665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for details. */ 5675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectint mdio_read(struct nic *nic, int phy_id, int location) 5695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 5705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 5715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int read_cmd = (0xf6 << 10) | (phy_id << 5) | location; 5725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int retval = 0; 5735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project long mdio_addr = ioaddr + CSR9; 5745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 5765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("mdio_read\n"); 5775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 5785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == LC82C168) { 5805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i = 1000; 5815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x60020000 + (phy_id<<23) + (location<<18), ioaddr + 0xA0); 5825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project inl(ioaddr + 0xA0); 5835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project inl(ioaddr + 0xA0); 5845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (--i > 0) 5855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ( ! ((retval = inl(ioaddr + 0xA0)) & 0x80000000)) 5865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return retval & 0xffff; 5875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0xffff; 5885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 5895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 5905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == COMET) { 5915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (phy_id == 1) { 5925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (location < 7) 5935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return inl(ioaddr + 0xB4 + (location<<2)); 5945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (location == 17) 5955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return inl(ioaddr + 0xD0); 5965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (location >= 29 && location <= 31) 5975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return inl(ioaddr + 0xD4 + ((location-29)<<2)); 5985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 5995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0xffff; 6005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Establish sync by sending at least 32 logic ones. */ 6035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 32; i >= 0; i--) { 6045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | MDIO_DATA_WRITE1, mdio_addr); 6055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | MDIO_DATA_WRITE1 | MDIO_SHIFT_CLK, mdio_addr); 6075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Shift the read command bits out. */ 6105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 15; i >= 0; i--) { 6115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int dataval = (read_cmd & (1 << i)) ? MDIO_DATA_WRITE1 : 0; 6125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | dataval, mdio_addr); 6145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | dataval | MDIO_SHIFT_CLK, mdio_addr); 6165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Read the two transition, 16 data, and wire-idle bits. */ 6195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 19; i > 0; i--) { 6205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB_IN, mdio_addr); 6215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project retval = (retval << 1) | ((inl(mdio_addr) & MDIO_DATA_READ) ? 1 : 0); 6235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB_IN | MDIO_SHIFT_CLK, mdio_addr); 6245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return (retval>>1) & 0xffff; 6275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 6285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectvoid mdio_write(struct nic *nic, int phy_id, int location, int value) 6305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 6315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 6325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int cmd = (0x5002 << 16) | (phy_id << 23) | (location<<18) | value; 6335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project long mdio_addr = ioaddr + CSR9; 6345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 6365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("mdio_write\n"); 6375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 6385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == LC82C168) { 6405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i = 1000; 6415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(cmd, ioaddr + 0xA0); 6425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project do 6435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ( ! (inl(ioaddr + 0xA0) & 0x80000000)) 6445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 6455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (--i > 0); 6465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return; 6475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == COMET) { 6505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (phy_id != 1) 6515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return; 6525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (location < 7) 6535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(value, ioaddr + 0xB4 + (location<<2)); 6545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (location == 17) 6555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(value, ioaddr + 0xD0); 6565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (location >= 29 && location <= 31) 6575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(value, ioaddr + 0xD4 + ((location-29)<<2)); 6585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return; 6595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Establish sync by sending 32 logic ones. */ 6625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 32; i >= 0; i--) { 6635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | MDIO_DATA_WRITE1, mdio_addr); 6645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | MDIO_DATA_WRITE1 | MDIO_SHIFT_CLK, mdio_addr); 6665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Shift the command bits out. */ 6695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 31; i >= 0; i--) { 6705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int dataval = (cmd & (1 << i)) ? MDIO_DATA_WRITE1 : 0; 6715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | dataval, mdio_addr); 6725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB | dataval | MDIO_SHIFT_CLK, mdio_addr); 6745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Clear out extra bits. */ 6775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 2; i > 0; i--) { 6785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB_IN, mdio_addr); 6795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(MDIO_ENB_IN | MDIO_SHIFT_CLK, mdio_addr); 6815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_delay(); 6825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 6835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 6845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 6865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 6875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* EEPROM Reading Code */ 6885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 6895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* EEPROM routines adapted from the Linux Tulip Code */ 6905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Reading a serial EEPROM is a "bit" grungy, but we work our way 6915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project through:->. 6925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project*/ 6935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int read_eeprom(unsigned long ioaddr, int location, int addr_len) 6945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 6955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 6965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned short retval = 0; 6975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project long ee_addr = ioaddr + CSR9; 6985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int read_cmd = location | EE_READ_CMD; 6995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 7015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("read_eeprom\n"); 7025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 7035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB & ~EE_CS, ee_addr); 7055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB, ee_addr); 7065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Shift the read command bits out. */ 7085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 4 + addr_len; i >= 0; i--) { 7095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project short dataval = (read_cmd & (1 << i)) ? EE_DATA_WRITE : 0; 7105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB | dataval, ee_addr); 7115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project eeprom_delay(); 7125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB | dataval | EE_SHIFT_CLK, ee_addr); 7135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project eeprom_delay(); 7145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB, ee_addr); 7165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 16; i > 0; i--) { 7185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB | EE_SHIFT_CLK, ee_addr); 7195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project eeprom_delay(); 7205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project retval = (retval << 1) | ((inl(ee_addr) & EE_DATA_READ) ? 1 : 0); 7215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB, ee_addr); 7225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project eeprom_delay(); 7235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Terminate the EEPROM access. */ 7265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(EE_ENB & ~EE_CS, ee_addr); 7275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return retval; 7285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 7295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 7325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* EEPROM Parsing Code */ 7335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 7345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void parse_eeprom(struct nic *nic) 7355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 7365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char *p, *ee_data = tp->eeprom; 7375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int new_advertise = 0; 7385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 7395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 7415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("parse_eeprom\n"); 7425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 7435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->mtable = 0; 7455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Detect an old-style (SA only) EEPROM layout: 7465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcmp(ee_data, ee_data+16, 8). */ 7475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < 8; i ++) 7485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (ee_data[i] != ee_data[16+i]) 7495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 7505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (i >= 8) { 7515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Do a fix-up based on the vendor half of the station address. */ 7525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; eeprom_fixups[i].name; i++) { 7535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (nic->node_addr[0] == eeprom_fixups[i].addr0 7545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project && nic->node_addr[1] == eeprom_fixups[i].addr1 7555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project && nic->node_addr[2] == eeprom_fixups[i].addr2) { 7565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (nic->node_addr[2] == 0xE8 && ee_data[0x1a] == 0x55) 7575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project i++; /* An Accton EN1207, not an outlaw Maxtech. */ 7585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcpy(ee_data + 26, eeprom_fixups[i].newtable, 7595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sizeof(eeprom_fixups[i].newtable)); 7605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 7615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Old format EEPROM on '%s' board.\n%s: Using substitute media control info.\n", 7625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, eeprom_fixups[i].name, tp->nic_name); 7635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 7645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 7655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (eeprom_fixups[i].name == NULL) { /* No fixup found. */ 7685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 7695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Old style EEPROM with no media selection information.\n", 7705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name); 7715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 7725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return; 7735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (ee_data[19] > 1) { 7775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 7785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Multiport cards (%d ports) may not work correctly.\n", 7795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, ee_data[19]); 7805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 7815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project p = (void *)ee_data + ee_data[27]; 7845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (ee_data[27] == 0) { /* No valid media table. */ 7865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 7875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) { 7885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: No Valid Media Table. ee_data[27] = %hhX\n", 7895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, ee_data[27]); 7905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 7915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 7925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (tp->chip_id == DC21041) { 7935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int media = get_u16(p); 7945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int count = p[2]; 7955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project p += 3; 7965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 7975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: 21041 Media table, default media %hX (%s).\n", 7985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, media, 7995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project media & 0x0800 ? "Autosense" : medianame[media & 15]); 8005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < count; i++) { 8015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char media_block = *p++; 8025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int media_code = media_block & MEDIA_MASK; 8035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (media_block & 0x40) 8045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project p += 6; 8055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project switch(media_code) { 8065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 0: new_advertise |= 0x0020; break; 8075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 4: new_advertise |= 0x0040; break; 8085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: 21041 media #%d, %s.\n", 8105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, media_code, medianame[media_code]); 8115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 8135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char csr12dir = 0; 8145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int count; 8155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct mediatable *mtable; 8165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 media = get_u16(p); 8175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project p += 2; 8195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->flags & CSR12_IN_SROM) 8205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr12dir = *p++; 8215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project count = *p++; 8225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->mtable = mtable = (struct mediatable *)&tp->media_table_storage[0]; 8245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->defaultmedia = media; 8265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->leafcount = count; 8275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->csr12dir = csr12dir; 8285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->has_nonmii = mtable->has_mii = mtable->has_reset = 0; 8295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->csr15dir = mtable->csr15val = 0; 8305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: EEPROM default media type %s.\n", tp->nic_name, 8325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project media & 0x0800 ? "Autosense" : medianame[media & MEDIA_MASK]); 8335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < count; i++) { 8355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct medialeaf *leaf = &mtable->mleaf[i]; 8365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((p[0] & 0x80) == 0) { /* 21140 Compact block. */ 8385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->type = 0; 8395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->media = p[0] & 0x3f; 8405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->leafdata = p; 8415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((p[2] & 0x61) == 0x01) /* Bogus, but Znyx boards do it. */ 8425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->has_mii = 1; 8435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project p += 4; 8445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 8455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project switch(leaf->type = p[1]) { 8465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 5: 8475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->has_reset = i; 8485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->media = p[2] & 0x0f; 8495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 8505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 1: case 3: 8515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->has_mii = 1; 8525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->media = 11; 8535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 8545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 2: 8555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((p[2] & 0x3f) == 0) { 8565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 base15 = (p[2] & 0x40) ? get_u16(p + 7) : 0x0008; 8575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 *p1 = (u16 *)(p + (p[2] & 0x40 ? 9 : 3)); 8585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->csr15dir = (get_unaligned(p1 + 0)<<16) + base15; 8595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->csr15val = (get_unaligned(p1 + 1)<<16) + base15; 8605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Fall through. */ 8625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 0: case 4: 8635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mtable->has_nonmii = 1; 8645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->media = p[2] & MEDIA_MASK; 8655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project switch (leaf->media) { 8665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 0: new_advertise |= 0x0020; break; 8675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 4: new_advertise |= 0x0040; break; 8685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 3: new_advertise |= 0x0080; break; 8695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 5: new_advertise |= 0x0100; break; 8705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 6: new_advertise |= 0x0200; break; 8715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 8735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project default: 8745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->media = 19; 8755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->leafdata = p + 2; 8775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project p += (p[0] & 0x3f) + 1; 8785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 8805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1 && leaf->media == 11) { 8815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char *bp = leaf->leafdata; 8825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: MII interface PHY %d, setup/reset sequences %d/%d long, capabilities %hhX %hhX.\n", 8835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, bp[0], bp[1], bp[2 + bp[1]*2], 8845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project bp[5 + bp[2 + bp[1]*2]*2], bp[4 + bp[2 + bp[1]*2]*2]); 8855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 8875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Index #%d - Media %s (#%d) described " 8885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "by a %s (%d) block.\n", 8895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, i, medianame[leaf->media], leaf->media, 8905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->type < 6 ? block_name[leaf->type] : "UNKNOWN", 8915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project leaf->type); 8925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (new_advertise) 8945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->sym_advertise = new_advertise; 8955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 8965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 8975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 8995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 9005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* tulip_init_ring - setup the tx and rx descriptors */ 9015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 9025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_init_ring(struct nic *nic) 9035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 9045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 9055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 9075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("tulip_init_ring\n"); 9085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 9095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->cur_rx = 0; 9115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < RX_RING_SIZE; i++) { 9135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[i].status = cpu_to_le32(0x80000000); 9145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[i].length = cpu_to_le32(BUFLEN); 9155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[i].buffer1 = virt_to_le32desc(&rxb[i * BUFLEN]); 9165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[i].buffer2 = virt_to_le32desc(&rx_ring[i+1]); 9175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 9185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Mark the last entry as wrapping the ring. */ 9195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[i-1].length = cpu_to_le32(DESC_RING_WRAP | BUFLEN); 9205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[i-1].buffer2 = virt_to_le32desc(&rx_ring[0]); 9215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* We only use 1 transmit buffer, but we use 2 descriptors so 9235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project transmit engines have somewhere to point to if they feel the need */ 9245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].status = 0x00000000; 9265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].buffer1 = virt_to_le32desc(&txb[0]); 9275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].buffer2 = virt_to_le32desc(&tx_ring[1]); 9285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* this descriptor should never get used, since it will never be owned 9305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project by the machine (status will always == 0) */ 9315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[1].status = 0x00000000; 9325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[1].buffer1 = virt_to_le32desc(&txb[0]); 9335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[1].buffer2 = virt_to_le32desc(&tx_ring[0]); 9345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Mark the last entry as wrapping the ring, though this should never happen */ 9365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[1].length = cpu_to_le32(DESC_RING_WRAP | BUFLEN); 9375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 9385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 9405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* eth_reset - Reset adapter */ 9415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 9425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_reset(struct nic *nic) 9435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 9445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 9455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned long to; 9465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 addr_low, addr_high; 9475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 9495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("tulip_reset\n"); 9505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 9515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Stop Tx and RX */ 9535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(inl(ioaddr + CSR6) & ~0x00002002, ioaddr + CSR6); 9545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* On some chip revs we must set the MII/SYM port before the reset!? */ 9565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mii_cnt || (tp->mtable && tp->mtable->has_mii)) { 9575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x814C0000, ioaddr + CSR6); 9585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 9595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Reset the chip, holding bit 0 set at least 50 PCI cycles. */ 9615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000001, ioaddr + CSR0); 9625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_wait(1); 9635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* turn off reset and set cache align=16lword, burst=unlimit */ 9655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->csr0, ioaddr + CSR0); 9665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Wait the specified 50 PCI cycles after a reset */ 9685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_wait(1); 9695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* set up transmit and receive descriptors */ 9715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_init_ring(nic); 9725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == PNIC2) { 9745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 addr_high = (nic->node_addr[1]<<8) + (nic->node_addr[0]<<0); 9755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* This address setting does not appear to impact chip operation?? */ 9765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl((nic->node_addr[5]<<8) + nic->node_addr[4] + 9775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (nic->node_addr[3]<<24) + (nic->node_addr[2]<<16), 9785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ioaddr + 0xB0); 9795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(addr_high + (addr_high<<16), ioaddr + 0xB8); 9805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 9815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* MC_HASH_ONLY boards don't support setup packets */ 9835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->flags & MC_HASH_ONLY) { 9845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 addr_low = cpu_to_le32(get_unaligned((u32 *)nic->node_addr)); 9855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 addr_high = cpu_to_le32(get_unaligned((u16 *)(nic->node_addr+4))); 9865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 9875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* clear multicast hash filters and setup MAC address filters */ 9885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->flags & IS_ASIX) { 9895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR13); 9905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(addr_low, ioaddr + CSR14); 9915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(1, ioaddr + CSR13); 9925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(addr_high, ioaddr + CSR14); 9935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(2, ioaddr + CSR13); 9945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR14); 9955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(3, ioaddr + CSR13); 9965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR14); 9975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (tp->chip_id == COMET) { 9985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(addr_low, ioaddr + 0xA4); 9995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(addr_high, ioaddr + 0xA8); 10005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + 0xAC); 10015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + 0xB0); 10025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 10035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 10045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* for other boards we send a setup packet to initialize 10055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project the filters */ 10065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 tx_flags = 0x08000000 | 192; 10075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* construct perfect filter frame with mac address as first match 10095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project and broadcast address for all others */ 10105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i=0; i<192; i++) 10115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[i] = 0xFF; 10125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[0] = nic->node_addr[0]; 10135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[1] = nic->node_addr[1]; 10145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[4] = nic->node_addr[2]; 10155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[5] = nic->node_addr[3]; 10165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[8] = nic->node_addr[4]; 10175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[9] = nic->node_addr[5]; 10185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].length = cpu_to_le32(tx_flags); 10205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].buffer1 = virt_to_le32desc(&txb[0]); 10215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].status = cpu_to_le32(0x80000000); 10225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 10235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Point to rx and tx descriptors */ 10255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl((unsigned long)&rx_ring[0], ioaddr + CSR3); 10265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl((unsigned long)&tx_ring[0], ioaddr + CSR4); 10275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project init_media(nic); 10295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* set the chip's operating mode (but don't turn on xmit and recv yet) */ 10315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl((tp->csr6 & ~0x00002002), ioaddr + CSR6); 10325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* send setup packet for cards that support it */ 10345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (!(tp->flags & MC_HASH_ONLY)) { 10355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* enable transmit wait for completion */ 10365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->csr6 | 0x00002000, ioaddr + CSR6); 10375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* immediate transmit demand */ 10385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR1); 10395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project to = currticks() + TX_TIME_OUT; 10415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while ((tx_ring[0].status & 0x80000000) && (currticks() < to)) 10425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* wait */ ; 10435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (currticks() >= to) { 10455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf ("%s: TX Setup Timeout.\n", tp->nic_name); 10465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 10475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 10485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == LC82C168) 10505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_check_duplex(nic); 10515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* enable transmit and receive */ 10535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->csr6 | 0x00002002, ioaddr + CSR6); 10545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 10555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 10585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* eth_transmit - Transmit a frame */ 10595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 10605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_transmit(struct nic *nic, const char *d, unsigned int t, 10615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int s, const char *p) 10625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 10635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 nstype; 10645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 to; 10655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 csr6 = inl(ioaddr + CSR6); 10665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 10685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("tulip_transmit\n"); 10695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 10705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Disable Tx */ 10725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr6 & ~0x00002000, ioaddr + CSR6); 10735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcpy(txb, d, ETH_ALEN); 10755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcpy(txb + ETH_ALEN, nic->node_addr, ETH_ALEN); 10765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nstype = htons((u16) t); 10775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcpy(txb + 2 * ETH_ALEN, (u8 *)&nstype, 2); 10785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcpy(txb + ETH_HLEN, p, s); 10795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project s += ETH_HLEN; 10815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project s &= 0x0FFF; 10825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* pad to minimum packet size */ 10845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (s < ETH_ZLEN) 10855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project txb[s++] = '\0'; 10865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 10885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 10895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: sending %d bytes ethtype %hX\n", tp->nic_name, s, t); 10905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 10915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* setup the transmit descriptor */ 10935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* 0x60000000 = no interrupt on completion */ 10945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].length = cpu_to_le32(0x60000000 | s); 10955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tx_ring[0].status = cpu_to_le32(0x80000000); 10965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 10975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Point to transmit descriptor */ 10985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl((u32)&tx_ring[0], ioaddr + CSR4); 10995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Enable Tx */ 11015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr6 | 0x00002000, ioaddr + CSR6); 11025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* immediate transmit demand */ 11035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR1); 11045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project to = currticks() + TX_TIME_OUT; 11065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while ((tx_ring[0].status & 0x80000000) && (currticks() < to)) 11075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* wait */ ; 11085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (currticks() >= to) { 11105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf ("TX Timeout!\n"); 11115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 11125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Disable Tx */ 11145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr6 & ~0x00002000, ioaddr + CSR6); 11155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 11165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 11185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* eth_poll - Wait for a frame */ 11195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 11205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int tulip_poll(struct nic *nic) 11215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 11225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 11245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("tulip_poll\n"); 11255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 11265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* no packet waiting. packet still owned by NIC */ 11285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (rx_ring[tp->cur_rx].status & 0x80000000) 11295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0; 11305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 11325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("tulip_poll got one\n"); 11335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 11345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->packetlen = (rx_ring[tp->cur_rx].status & 0x3FFF0000) >> 16; 11365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* if we get a corrupted packet. throw it away and move on */ 11385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (rx_ring[tp->cur_rx].status & 0x00008000) { 11395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* return the descriptor and buffer to receive ring */ 11405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[tp->cur_rx].status = 0x80000000; 11415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->cur_rx = (++tp->cur_rx) % RX_RING_SIZE; 11425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0; 11435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 11445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* copy packet to working buffer */ 11465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcpy(nic->packet, rxb + tp->cur_rx * BUFLEN, nic->packetlen); 11475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* return the descriptor and buffer to receive ring */ 11495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project rx_ring[tp->cur_rx].status = 0x80000000; 11505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->cur_rx = (++tp->cur_rx) % RX_RING_SIZE; 11515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 1; 11535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 11545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 11565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* eth_disable - Disable the interface */ 11575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 11585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void tulip_disable(struct nic *nic) 11595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 11605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 11625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("tulip_disable\n"); 11635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 11645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* disable interrupts */ 11665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000000, ioaddr + CSR7); 11675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Stop the chip's Tx and Rx processes. */ 11695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(inl(ioaddr + CSR6) & ~0x00002002, ioaddr + CSR6); 11705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Clear the missed-packet counter. */ 11725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (volatile unsigned long)inl(ioaddr + CSR8); 11735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 11745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 11765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* eth_probe - Look for an adapter */ 11775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/*********************************************************************/ 11785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstruct nic *tulip_probe(struct nic *nic, unsigned short *io_addrs, 11795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct pci_device *pci) 11805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 11815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 i, l1, l2; 11825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 chip_rev; 11835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 ee_data[EEPROM_SIZE]; 11845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned short sum; 11855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int chip_idx; 11865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project static unsigned char last_phys_addr[ETH_ALEN] = {0x00, 'L', 'i', 'n', 'u', 'x'}; 11875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (io_addrs == 0 || *io_addrs == 0) 11895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0; 11905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ioaddr = *io_addrs; 11925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* point to private storage */ 11945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp = &tpx; 11955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 11965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->vendor_id = pci->vendor; 11975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->dev_id = pci->dev_id; 11985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name = pci->name; 11995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 0; 12015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->default_port = 0; 12025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project adjust_pci_device(pci); 12045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* disable interrupts */ 12065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000000, ioaddr + CSR7); 12075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Stop the chip's Tx and Rx processes. */ 12095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(inl(ioaddr + CSR6) & ~0x00002002, ioaddr + CSR6); 12105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Clear the missed-packet counter. */ 12125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (volatile unsigned long)inl(ioaddr + CSR8); 12135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("\n"); /* so we start on a fresh line */ 12155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 12165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("tulip_probe\n"); 12175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 12185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 12205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 12215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf ("%s: Looking for Tulip Chip: Vendor=%hX Device=%hX\n", tp->nic_name, 12225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->vendor_id, tp->dev_id); 12235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 12245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Figure out which chip we're dealing with */ 12265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project i = 0; 12275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project chip_idx = -1; 12285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (pci_id_tbl[i].name) { 12305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ( (((u32) tp->dev_id << 16) | tp->vendor_id) == 12315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (pci_id_tbl[i].id.pci & pci_id_tbl[i].id.pci_mask) ) { 12325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project chip_idx = pci_id_tbl[i].drv_flags; 12335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 12345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 12355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project i++; 12365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 12375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (chip_idx == -1) { 12395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf ("%s: Unknown Tulip Chip: Vendor=%hX Device=%hX\n", tp->nic_name, 12405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->vendor_id, tp->dev_id); 12415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0; 12425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 12435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->pci_id_idx = i; 12455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->flags = tulip_tbl[chip_idx].flags; 12465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 12485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) { 12495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf ("%s: tp->pci_id_idx == %d, name == %s\n", tp->nic_name, 12505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->pci_id_idx, pci_id_tbl[tp->pci_id_idx].name); 12515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf ("%s: chip_idx == %d, name == %s\n", tp->nic_name, chip_idx, 12525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_tbl[chip_idx].chip_name); 12535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 12545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 12555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Bring the 21041/21143 out of sleep mode. 12575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Caution: Snooze mode does not work with some boards! */ 12585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->flags & HAS_PWRDWN) 12595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project pcibios_write_config_dword(pci->bus, pci->devfn, 0x40, 0x00000000); 12605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (inl(ioaddr + CSR5) == 0xFFFFFFFF) { 12625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: The Tulip chip at %X is not functioning.\n", 12635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, ioaddr); 12645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0; 12655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 12665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project pcibios_read_config_byte(pci->bus, pci->devfn, PCI_REVISION, &chip_rev); 12685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: [chip: %s] rev %d at %hX\n", tp->nic_name, 12705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_tbl[chip_idx].chip_name, chip_rev, ioaddr); 12715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Vendor=%hX Device=%hX", tp->nic_name, tp->vendor_id, tp->dev_id); 12725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (chip_idx == DC21041 && inl(ioaddr + CSR9) & 0x8000) { 12745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf(" 21040 compatible mode."); 12755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project chip_idx = DC21040; 12765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 12775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("\n"); 12795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 12805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* The SROM/EEPROM interface varies dramatically. */ 12815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sum = 0; 12825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (chip_idx == DC21040) { 12835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR9); /* Reset the pointer with a dummy write. */ 12845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < ETH_ALEN; i++) { 12855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int value, boguscnt = 100000; 12865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project do 12875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project value = inl(ioaddr + CSR9); 12885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (value < 0 && --boguscnt > 0); 12895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->node_addr[i] = value; 12905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sum += value & 0xff; 12915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 12925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (chip_idx == LC82C168) { 12935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < 3; i++) { 12945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int value, boguscnt = 100000; 12955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x600 | i, ioaddr + 0x98); 12965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project do 12975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project value = inl(ioaddr + CSR9); 12985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project while (value < 0 && --boguscnt > 0); 12995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project put_unaligned(le16_to_cpu(value), ((u16*)nic->node_addr) + i); 13005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sum += value & 0xffff; 13015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (chip_idx == COMET) { 13035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* No need to read the EEPROM. */ 13045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project put_unaligned(inl(ioaddr + 0xA4), (u32 *)nic->node_addr); 13055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project put_unaligned(inl(ioaddr + 0xA8), (u16 *)(nic->node_addr + 4)); 13065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < ETH_ALEN; i ++) 13075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sum += nic->node_addr[i]; 13085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 13095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* A serial EEPROM interface, we read now and sort it out later. */ 13105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int sa_offset = 0; 13115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int ee_addr_size = read_eeprom(ioaddr, 0xff, 8) & 0x40000 ? 8 : 6; 13125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < sizeof(ee_data)/2; i++) 13145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ((u16 *)ee_data)[i] = 13155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project le16_to_cpu(read_eeprom(ioaddr, i, ee_addr_size)); 13165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* DEC now has a specification (see Notes) but early board makers 13185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project just put the address in the first EEPROM locations. */ 13195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* This does memcmp(eedata, eedata+16, 8) */ 13205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < 8; i ++) 13215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (ee_data[i] != ee_data[16+i]) 13225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sa_offset = 20; 13235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (ee_data[0] == 0xff && ee_data[1] == 0xff && ee_data[2] == 0) { 13245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sa_offset = 2; /* Grrr, damn Matrox boards. */ 13255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < ETH_ALEN; i ++) { 13275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->node_addr[i] = ee_data[i + sa_offset]; 13285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project sum += ee_data[i + sa_offset]; 13295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Lite-On boards have the address byte-swapped. */ 13325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((nic->node_addr[0] == 0xA0 || nic->node_addr[0] == 0xC0) 13335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project && nic->node_addr[1] == 0x00) 13345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < ETH_ALEN; i+=2) { 13355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project char tmp = nic->node_addr[i]; 13365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->node_addr[i] = nic->node_addr[i+1]; 13375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->node_addr[i+1] = tmp; 13385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (sum == 0 || sum == ETH_ALEN*0xff) { 13415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: EEPROM not present!\n", tp->nic_name); 13425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < ETH_ALEN-1; i++) 13435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->node_addr[i] = last_phys_addr[i]; 13445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->node_addr[i] = last_phys_addr[i] + 1; 13455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < ETH_ALEN; i++) 13485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project last_phys_addr[i] = nic->node_addr[i]; 13495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: %! at ioaddr %hX\n", tp->nic_name, nic->node_addr, ioaddr); 13515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->chip_id = chip_idx; 13535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->revision = chip_rev; 13545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr0 = csr0; 13555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* BugFixes: The 21143-TD hangs with PCI Write-and-Invalidate cycles. 13575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project And the ASIX must have a burst limit or horrible things happen. */ 13585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (chip_idx == DC21143 && chip_rev == 65) 13595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr0 &= ~0x01000000; 13605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (tp->flags & IS_ASIX) 13615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr0 |= 0x2000; 13625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (media_cap[tp->default_port] & MediaIsMII) { 13645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 media2advert[] = { 0x20, 0x40, 0x03e0, 0x60, 0x80, 0x100, 0x200 }; 13655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->mii_advertise = media2advert[tp->default_port - 9]; 13665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->mii_advertise |= (tp->flags & HAS_8023X); /* Matching bits! */ 13675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* This is logically part of the probe routine, but too complex 13705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project to write inline. */ 13715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->flags & HAS_MEDIA_TABLE) { 13725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project memcpy(tp->eeprom, ee_data, sizeof(tp->eeprom)); 13735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project parse_eeprom(nic); 13745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 13755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project start_link(nic); 13775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* reset the device and make ready for tx and rx of packets */ 13795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_reset(nic); 13805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->reset = tulip_reset; 13825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->poll = tulip_poll; 13835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->transmit = tulip_transmit; 13845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nic->disable = tulip_disable; 13855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* give the board a chance to reset before returning */ 13875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tulip_wait(4*TICKS_PER_SEC); 13885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return nic; 13905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 13915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void start_link(struct nic *nic) 13935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 13945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 13955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 13965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 13975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("start_link\n"); 13985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 13995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 14005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((tp->flags & ALWAYS_CHECK_MII) || 14015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (tp->mtable && tp->mtable->has_mii) || 14025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ( ! tp->mtable && (tp->flags & HAS_MII))) { 14035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int phy, phy_idx; 14045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable && tp->mtable->has_mii) { 14055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < tp->mtable->leafcount; i++) 14065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable->mleaf[i].media == 11) { 14075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->cur_index = i; 14085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->saved_if_port = tp->if_port; 14095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project select_media(nic, 2); 14105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = tp->saved_if_port; 14115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 14125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 14155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Find the connected MII xcvrs. */ 14165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (phy = 0, phy_idx = 0; phy < 32 && phy_idx < sizeof(tp->phys); 14175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project phy++) { 14185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int mii_status = mdio_read(nic, phy, 1); 14195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((mii_status & 0x8301) == 0x8001 || 14205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ((mii_status & 0x8000) == 0 && (mii_status & 0x7800) != 0)) { 14215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int mii_reg0 = mdio_read(nic, phy, 0); 14225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int mii_advert = mdio_read(nic, phy, 4); 14235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int to_advert; 14245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 14255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mii_advertise) 14265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project to_advert = tp->mii_advertise; 14275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (tp->advertising[phy_idx]) 14285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project to_advert = tp->advertising[phy_idx]; 14295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else /* Leave unchanged. */ 14305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->mii_advertise = to_advert = mii_advert; 14315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 14325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->phys[phy_idx++] = phy; 14335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: MII transceiver %d config %hX status %hX advertising %hX.\n", 14345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, phy, mii_reg0, mii_status, mii_advert); 14355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Fixup for DLink with miswired PHY. */ 14365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (mii_advert != to_advert) { 14375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Advertising %hX on PHY %d previously advertising %hX.\n", 14385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, to_advert, phy, mii_advert); 14395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_write(nic, phy, 4, to_advert); 14405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Enable autonegotiation: some boards default to off. */ 14425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_write(nic, phy, 0, mii_reg0 | 14435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (tp->full_duplex ? 0x1100 : 0x1000) | 14445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (media_cap[tp->default_port]&MediaIs100 ? 0x2000:0)); 14455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->mii_cnt = phy_idx; 14485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable && tp->mtable->has_mii && phy_idx == 0) { 14495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: ***WARNING***: No MII transceiver found!\n", 14505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name); 14515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->phys[0] = 1; 14525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 14555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Reset the xcvr interface and turn on heartbeat. */ 14565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project switch (tp->chip_id) { 14575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case DC21040: 14585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000000, ioaddr + CSR13); 14595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000004, ioaddr + CSR13); 14605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 14615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case DC21041: 14625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* This is nway_start(). */ 14635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->sym_advertise == 0) 14645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->sym_advertise = 0x0061; 14655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000000, ioaddr + CSR13); 14665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0xFFFFFFFF, ioaddr + CSR14); 14675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000008, ioaddr + CSR15); /* Listen on AUI also. */ 14685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(inl(ioaddr + CSR6) | 0x0200, ioaddr + CSR6); 14695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000EF01, ioaddr + CSR13); 14705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 14715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case DC21140: default: 14725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable) 14735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->mtable->csr12dir | 0x100, ioaddr + CSR12); 14745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 14755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case DC21142: 14765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case PNIC2: 14775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mii_cnt || media_cap[tp->if_port] & MediaIsMII) { 14785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x82020000, ioaddr + CSR6); 14795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000, ioaddr + CSR13); 14805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000, ioaddr + CSR14); 14815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x820E0000, ioaddr + CSR6); 14825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else 14835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nway_start(nic); 14845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 14855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case LC82C168: 14865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ( ! tp->mii_cnt) { 14875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nway = 1; 14885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nwayset = 0; 14895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00420000, ioaddr + CSR6); 14905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x30, ioaddr + CSR12); 14915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0001F078, ioaddr + 0xB8); 14925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0201F078, ioaddr + 0xB8); /* Turn on autonegotiation. */ 14935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 14945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 14955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case MX98713: case COMPEX9881: 14965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000000, ioaddr + CSR6); 14975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x000711C0, ioaddr + CSR14); /* Turn on NWay. */ 14985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000001, ioaddr + CSR13); 14995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 15005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case MX98715: case MX98725: 15015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x01a80000, ioaddr + CSR6); 15025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0xFFFFFFFF, ioaddr + CSR14); 15035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00001000, ioaddr + CSR12); 15045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 15055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case COMET: 15065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* No initialization necessary. */ 15075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 15085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 15095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 15105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void nway_start(struct nic *nic) 15125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 15135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int csr14 = ((tp->sym_advertise & 0x0780) << 9) | 15145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ((tp->sym_advertise&0x0020)<<1) | 0xffbf; 15155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 15175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("nway_start\n"); 15185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 15195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 0; 15215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nway = tp->mediasense = 1; 15225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nwayset = tp->lpar = 0; 15235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == PNIC2) { 15245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x01000000 | (tp->sym_advertise & 0x0040 ? 0x0200 : 0); 15255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return; 15265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 15275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 15285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 15295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Restarting internal NWay autonegotiation, %X.\n", 15305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, csr14); 15315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 15325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0001, ioaddr + CSR13); 15335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr14, ioaddr + CSR14); 15345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x82420000 | (tp->sym_advertise & 0x0040 ? 0x0200 : 0); 15355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->csr6, ioaddr + CSR6); 15365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable && tp->mtable->csr15dir) { 15375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->mtable->csr15dir, ioaddr + CSR15); 15385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->mtable->csr15val, ioaddr + CSR15); 15395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (tp->chip_id != PNIC2) 15405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outw(0x0008, ioaddr + CSR15); 15415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == DC21041) /* Trigger NWAY. */ 15425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0xEF01, ioaddr + CSR12); 15435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else 15445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x1301, ioaddr + CSR12); 15455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 15465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void init_media(struct nic *nic) 15485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 15495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 15505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 15525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("init_media\n"); 15535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 15545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->saved_if_port = tp->if_port; 15565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->if_port == 0) 15575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = tp->default_port; 15585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Allow selecting a default media. */ 15605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project i = 0; 15615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable == NULL) 15625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project goto media_picked; 15635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->if_port) { 15645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int looking_for = media_cap[tp->if_port] & MediaIsMII ? 11 : 15655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (tp->if_port == 12 ? 0 : tp->if_port); 15665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < tp->mtable->leafcount; i++) 15675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable->mleaf[i].media == looking_for) { 15685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Using user-specified media %s.\n", 15695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, medianame[tp->if_port]); 15705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project goto media_picked; 15715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 15725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 15735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((tp->mtable->defaultmedia & 0x0800) == 0) { 15745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int looking_for = tp->mtable->defaultmedia & 15; 15755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < tp->mtable->leafcount; i++) 15765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mtable->mleaf[i].media == looking_for) { 15775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Using EEPROM-set media %s.\n", 15785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, medianame[looking_for]); 15795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project goto media_picked; 15805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 15815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 15825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Start sensing first non-full-duplex media. */ 15835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = tp->mtable->leafcount - 1; 15845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project (media_cap[tp->mtable->mleaf[i].media] & MediaAlwaysFD) && i > 0; i--) 15855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project ; 15865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project media_picked: 15875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0; 15895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->cur_index = i; 15905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nwayset = 0; 15915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 15925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->if_port) { 15935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->chip_id == DC21143 && media_cap[tp->if_port] & MediaIsMII) { 15945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* We must reset the media CSRs when we force-select MII mode. */ 15955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000, ioaddr + CSR13); 15965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000, ioaddr + CSR14); 15975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0008, ioaddr + CSR15); 15985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 15995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project select_media(nic, 1); 16005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return; 16015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 16025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project switch(tp->chip_id) { 16035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case DC21041: 16045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* tp->nway = 1;*/ 16055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nway_start(nic); 16065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case DC21142: 16085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mii_cnt) { 16095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project select_media(nic, 1); 16105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 16115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 16125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Using MII transceiver %d, status %hX.\n", 16135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, tp->phys[0], mdio_read(nic, tp->phys[0], 1)); 16145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 16155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x82020000, ioaddr + CSR6); 16165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x820E0000; 16175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 11; 16185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000, ioaddr + CSR13); 16195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000, ioaddr + CSR14); 16205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else 16215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nway_start(nic); 16225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case PNIC2: 16245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project nway_start(nic); 16255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case LC82C168: 16275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mii_cnt) { 16285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 11; 16295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x814C0000 | (tp->full_duplex ? 0x0200 : 0); 16305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0001, ioaddr + CSR15); 16315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (inl(ioaddr + CSR5) & TPLnkPass) 16325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project pnic_do_nway(nic); 16335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else { 16345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Start with 10mbps to do autonegotiation. */ 16355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x32, ioaddr + CSR12); 16365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x00420000; 16375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0001B078, ioaddr + 0xB8); 16385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0201B078, ioaddr + 0xB8); 16395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 16405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case MX98713: case COMPEX9881: 16425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 0; 16435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x01880000 | (tp->full_duplex ? 0x0200 : 0); 16445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0f370000 | inw(ioaddr + 0x80), ioaddr + 0x80); 16455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case MX98715: case MX98725: 16475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Provided by BOLO, Macronix - 12/10/1998. */ 16485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 0; 16495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x01a80200; 16505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0f370000 | inw(ioaddr + 0x80), ioaddr + 0x80); 16515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x11000 | inw(ioaddr + 0xa0), ioaddr + 0xa0); 16525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case COMET: 16545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 0; 16555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = 0x00040000; 16565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case AX88140: case AX88141: 16585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = tp->mii_cnt ? 0x00040100 : 0x00000100; 16595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 16605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project default: 16615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project select_media(nic, 1); 16625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 16635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 16645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 16655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void pnic_do_nway(struct nic *nic) 16665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 16675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 phy_reg = inl(ioaddr + 0xB8); 16685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 new_csr6 = tp->csr6 & ~0x40C40200; 16695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 16705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 16715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("pnic_do_nway\n"); 16725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 16735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 16745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (phy_reg & 0x78000000) { /* Ignore baseT4 */ 16755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (phy_reg & 0x20000000) tp->if_port = 5; 16765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (phy_reg & 0x40000000) tp->if_port = 3; 16775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (phy_reg & 0x10000000) tp->if_port = 4; 16785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else if (phy_reg & 0x08000000) tp->if_port = 0; 16795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nwayset = 1; 16805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = (tp->if_port & 1) ? 0x01860000 : 0x00420000; 16815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x32 | (tp->if_port & 1), ioaddr + CSR12); 16825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->if_port & 1) 16835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x1F868, ioaddr + 0xB8); 16845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (phy_reg & 0x30000000) { 16855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->full_duplex = 1; 16865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 |= 0x00000200; 16875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 16885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 16895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 16905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: PNIC autonegotiated status %X, %s.\n", 16915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, phy_reg, medianame[tp->if_port]); 16925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 16935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->csr6 != new_csr6) { 16945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = new_csr6; 16955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->csr6 | 0x0002, ioaddr + CSR6); /* Restart Tx */ 16965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(tp->csr6 | 0x2002, ioaddr + CSR6); 16975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 16985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 16995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 17005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 17015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* Set up the transceiver control registers for the selected media type. */ 17025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic void select_media(struct nic *nic, int startup) 17035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 17045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct mediatable *mtable = tp->mtable; 17055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 new_csr6; 17065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int i; 17075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 17085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG_WHERE 17095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project whereami("select_media\n"); 17105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 17115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 17125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (mtable) { 17135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct medialeaf *mleaf = &mtable->mleaf[tp->cur_index]; 17145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char *p = mleaf->leafdata; 17155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project switch (mleaf->type) { 17165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 0: /* 21140 non-MII xcvr. */ 17175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 17185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 17195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Using a 21140 non-MII transceiver" 17205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project " with control setting %hhX.\n", 17215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, p[1]); 17225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 17235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = p[0]; 17245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup) 17255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(mtable->csr12dir | 0x100, ioaddr + CSR12); 17265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(p[1], ioaddr + CSR12); 17275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x02000000 | ((p[2] & 0x71) << 18); 17285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 17295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 2: case 4: { 17305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 setup[5]; 17315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u32 csr13val, csr14val, csr15dir, csr15val; 17325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < 5; i++) 17335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project setup[i] = get_u16(&p[i*2 + 1]); 17345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 17355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = p[0] & 15; 17365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (media_cap[tp->if_port] & MediaAlwaysFD) 17375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->full_duplex = 1; 17385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 17395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup && mtable->has_reset) { 17405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project struct medialeaf *rleaf = &mtable->mleaf[mtable->has_reset]; 17415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned char *rst = rleaf->leafdata; 17425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 17435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 17445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Resetting the transceiver.\n", 17455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name); 17465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 17475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < rst[0]; i++) 17485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(get_u16(rst + 1 + (i<<1)) << 16, ioaddr + CSR15); 17495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 17505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 17515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 17525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: 21143 non-MII %s transceiver control " 17535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "%hX/%hX.\n", 17545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, medianame[tp->if_port], setup[0], setup[1]); 17555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 17565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (p[0] & 0x40) { /* SIA (CSR13-15) setup values are provided. */ 17575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr13val = setup[0]; 17585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr14val = setup[1]; 17595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr15dir = (setup[3]<<16) | setup[2]; 17605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr15val = (setup[4]<<16) | setup[2]; 17615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR13); 17625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr14val, ioaddr + CSR14); 17635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr15dir, ioaddr + CSR15); /* Direction */ 17645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr15val, ioaddr + CSR15); /* Data */ 17655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr13val, ioaddr + CSR13); 17665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 17675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr13val = 1; 17685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr14val = 0x0003FF7F; 17695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr15dir = (setup[0]<<16) | 0x0008; 17705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr15val = (setup[1]<<16) | 0x0008; 17715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->if_port <= 4) 17725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project csr14val = t21142_csr14[tp->if_port]; 17735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup) { 17745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0, ioaddr + CSR13); 17755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr14val, ioaddr + CSR14); 17765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 17775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr15dir, ioaddr + CSR15); /* Direction */ 17785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(csr15val, ioaddr + CSR15); /* Data */ 17795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup) outl(csr13val, ioaddr + CSR13); 17805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 17815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 17825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 17835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Setting CSR15 to %X/%X.\n", 17845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, csr15dir, csr15val); 17855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 17865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (mleaf->type == 4) 17875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x82020000 | ((setup[2] & 0x71) << 18); 17885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else 17895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x82420000; 17905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 17915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 17925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project case 1: case 3: { 17935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int phy_num = p[0]; 17945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int init_length = p[1]; 17955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 *misc_info; 17965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 17975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = 11; 17985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x020E0000; 17995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (mleaf->type == 3) { /* 21142 */ 18005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 *init_sequence = (u16*)(p+2); 18015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u16 *reset_sequence = &((u16*)(p+3))[init_length]; 18025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int reset_length = p[2 + init_length*2]; 18035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project misc_info = reset_sequence + reset_length; 18045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup) 18055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < reset_length; i++) 18065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(get_u16(&reset_sequence[i]) << 16, ioaddr + CSR15); 18075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < init_length; i++) 18085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(get_u16(&init_sequence[i]) << 16, ioaddr + CSR15); 18095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 18105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 *init_sequence = p + 2; 18115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project u8 *reset_sequence = p + 3 + init_length; 18125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int reset_length = p[2 + init_length]; 18135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project misc_info = (u16*)(reset_sequence + reset_length); 18145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup) { 18155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(mtable->csr12dir | 0x100, ioaddr + CSR12); 18165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < reset_length; i++) 18175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(reset_sequence[i], ioaddr + CSR12); 18185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 18195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project for (i = 0; i < init_length; i++) 18205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(init_sequence[i], ioaddr + CSR12); 18215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 18225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->advertising[phy_num] = get_u16(&misc_info[1]) | 1; 18235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup < 2) { 18245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mii_advertise == 0) 18255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->mii_advertise = tp->advertising[phy_num]; 18265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 18275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 18285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Advertising %hX on MII %d.\n", 18295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, tp->mii_advertise, tp->phys[phy_num]); 18305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 18315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project mdio_write(nic, tp->phys[phy_num], 4, tp->mii_advertise); 18325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 18335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project break; 18345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 18355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project default: 18365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Invalid media table selection %d.\n", 18375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, mleaf->type); 18385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x020E0000; 18395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 18405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 18415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 18425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Using media type %s, CSR12 is %hhX.\n", 18435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, medianame[tp->if_port], 18445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project inl(ioaddr + CSR12) & 0xff); 18455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 18465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (tp->chip_id == DC21041) { 18475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int port = tp->if_port <= 4 ? tp->if_port : 0; 18485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 18495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 18505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: 21041 using media %s, CSR12 is %hX.\n", 18515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, medianame[port == 3 ? 12: port], 18525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project inl(ioaddr + CSR12)); 18535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 18545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000000, ioaddr + CSR13); /* Reset the serial interface */ 18555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(t21041_csr14[port], ioaddr + CSR14); 18565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(t21041_csr15[port], ioaddr + CSR15); 18575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(t21041_csr13[port], ioaddr + CSR13); 18585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x80020000; 18595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (tp->chip_id == LC82C168) { 18605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (startup && ! tp->medialock) 18615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = tp->mii_cnt ? 11 : 0; 18625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 18635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 18645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: PNIC PHY status is %hX, media %s.\n", 18655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, inl(ioaddr + 0xB8), medianame[tp->if_port]); 18665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 18675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->mii_cnt) { 18685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x810C0000; 18695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0001, ioaddr + CSR15); 18705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0201B07A, ioaddr + 0xB8); 18715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (startup) { 18725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Start with 10mbps to do autonegotiation. */ 18735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x32, ioaddr + CSR12); 18745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x00420000; 18755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0001B078, ioaddr + 0xB8); 18765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0201B078, ioaddr + 0xB8); 18775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (tp->if_port == 3 || tp->if_port == 5) { 18785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x33, ioaddr + CSR12); 18795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x01860000; 18805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Trigger autonegotiation. */ 18815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(startup ? 0x0201F868 : 0x0001F868, ioaddr + 0xB8); 18825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 18835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x32, ioaddr + CSR12); 18845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x00420000; 18855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x1F078, ioaddr + 0xB8); 18865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 18875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (tp->chip_id == DC21040) { /* 21040 */ 18885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Turn on the xcvr interface. */ 18895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int csr12 = inl(ioaddr + CSR12); 18905b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 18915b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 18925b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: 21040 media type is %s, CSR12 is %hhX.\n", 18935b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, medianame[tp->if_port], csr12); 18945b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 18955b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (media_cap[tp->if_port] & MediaAlwaysFD) 18965b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->full_duplex = 1; 18975b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x20000; 18985b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project /* Set the full duplux match frame. */ 18995b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(FULL_DUPLEX_MAGIC, ioaddr + CSR11); 19005b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x00000000, ioaddr + CSR13); /* Reset the serial interface */ 19015b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (t21040_csr13[tp->if_port] & 8) { 19025b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0705, ioaddr + CSR14); 19035b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0006, ioaddr + CSR15); 19045b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { 19055b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0xffff, ioaddr + CSR14); 19065b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x0000, ioaddr + CSR15); 19075b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 19085b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project outl(0x8f01 | t21040_csr13[tp->if_port], ioaddr + CSR13); 19095b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else { /* Unknown chip type with no media table. */ 19105b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->default_port == 0) 19115b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->if_port = tp->mii_cnt ? 11 : 3; 19125b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (media_cap[tp->if_port] & MediaIsMII) { 19135b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x020E0000; 19145b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else if (media_cap[tp->if_port] & MediaIsFx) { 19155b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x028600000; 19165b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } else 19175b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = 0x038600000; 19185b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 19195b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 19205b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: No media description table, assuming " 19215b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "%s transceiver, CSR12 %hhX.\n", 19225b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, medianame[tp->if_port], 19235b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project inl(ioaddr + CSR12)); 19245b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 19255b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 19265b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19275b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = new_csr6 | (tp->csr6 & 0xfdff) | (tp->full_duplex ? 0x0200 : 0); 19285b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return; 19295b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 19305b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19315b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project/* 19325b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Check the MII negotiated duplex and change the CSR6 setting if 19335b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project required. 19345b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Return 0 if everything is OK. 19355b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project Return < 0 if the transceiver is missing or has no link beat. 19365b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project*/ 19375b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Projectstatic int tulip_check_duplex(struct nic *nic) 19385b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project{ 19395b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project unsigned int bmsr, lpa, negotiated, new_csr6; 19405b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19415b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project bmsr = mdio_read(nic, tp->phys[0], 1); 19425b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project lpa = mdio_read(nic, tp->phys[0], 5); 19435b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19445b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 19455b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 19465b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: MII status %#x, Link partner report " 19475b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "%#x.\n", tp->nic_name, bmsr, lpa); 19485b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 19495b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19505b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (bmsr == 0xffff) 19515b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return -2; 19525b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((bmsr & 4) == 0) { 19535b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project int new_bmsr = mdio_read(nic, tp->phys[0], 1); 19545b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if ((new_bmsr & 4) == 0) { 19555b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 19565b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 1) 19575b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: No link beat on the MII interface," 19585b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project " status %#x.\n", tp->nic_name, 19595b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_bmsr); 19605b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 19615b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return -1; 19625b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 19635b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 19645b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->full_duplex = lpa & 0x140; 19655b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19665b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project new_csr6 = tp->csr6; 19675b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project negotiated = lpa & tp->advertising[0]; 19685b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19695b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if(negotiated & 0x380) new_csr6 &= ~0x400000; 19705b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else new_csr6 |= 0x400000; 19715b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tp->full_duplex) new_csr6 |= 0x200; 19725b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project else new_csr6 &= ~0x200; 19735b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19745b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (new_csr6 != tp->csr6) { 19755b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->csr6 = new_csr6; 19765b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19775b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#ifdef TULIP_DEBUG 19785b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project if (tulip_debug > 0) 19795b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project printf("%s: Setting %s-duplex based on MII" 19805b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project "#%d link partner capability of %#x.\n", 19815b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->nic_name, 19825b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->full_duplex ? "full" : "half", 19835b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project tp->phys[0], lpa); 19845b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project#endif 19855b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 1; 19865b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project } 19875b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project 19885b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project return 0; 19895b1eb061628a97aae48a9c0bcaa96eb0bfa07aa4The Android Open Source Project} 1990