From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1Jw4Hu-00044e-LX for qemu-devel@nongnu.org; Tue, 13 May 2008 19:52:06 -0400 Received: from exim by lists.gnu.org with spam-scanned (Exim 4.43) id 1Jw4Hs-000439-5k for qemu-devel@nongnu.org; Tue, 13 May 2008 19:52:05 -0400 Received: from [199.232.76.173] (port=45764 helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1Jw4Hr-00042y-LD for qemu-devel@nongnu.org; Tue, 13 May 2008 19:52:03 -0400 Received: from savannah.gnu.org ([199.232.41.3]:35807 helo=sv.gnu.org) by monty-python.gnu.org with esmtps (TLS-1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.60) (envelope-from ) id 1Jw4Hr-0000mf-Ku for qemu-devel@nongnu.org; Tue, 13 May 2008 19:52:03 -0400 Received: from cvs.savannah.gnu.org ([199.232.41.69]) by sv.gnu.org with esmtp (Exim 4.63) (envelope-from ) id 1Jw4Hp-00037T-Od for qemu-devel@nongnu.org; Tue, 13 May 2008 23:52:02 +0000 Received: from edgar_igl by cvs.savannah.gnu.org with local (Exim 4.63) (envelope-from ) id 1Jw4Hn-000373-41 for qemu-devel@nongnu.org; Tue, 13 May 2008 23:51:59 +0000 MIME-Version: 1.0 Errors-To: edgar_igl Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit From: "Edgar E. Iglesias" Message-Id: Date: Tue, 13 May 2008 23:51:59 +0000 Subject: [Qemu-devel] [4456] ETRAX: Add some kind of support for simulating 802. 3 auto-negotiation. Reply-To: qemu-devel@nongnu.org List-Id: qemu-devel.nongnu.org List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Revision: 4456 http://svn.sv.gnu.org/viewvc/?view=rev&root=qemu&revision=4456 Author: edgar_igl Date: 2008-05-13 23:51:49 +0000 (Tue, 13 May 2008) Log Message: ----------- ETRAX: Add some kind of support for simulating 802.3 auto-negotiation. * Add support for link partner ability and diagnostics reg. * Correct the endianess for MDIO responses. * Dont trash PHY registers after reads. Modified Paths: -------------- trunk/hw/etraxfs_eth.c Modified: trunk/hw/etraxfs_eth.c =================================================================== --- trunk/hw/etraxfs_eth.c 2008-05-13 18:50:56 UTC (rev 4455) +++ trunk/hw/etraxfs_eth.c 2008-05-13 23:51:49 UTC (rev 4456) @@ -30,18 +30,18 @@ #define D(x) -#define R_STAT 0x2c -#define RW_MGM_CTRL 0x28 -#define FS_ETH_MAX_REGS 0x5c - - - +/* + * The MDIO extensions in the TDK PHY model were reversed engineered from the + * linux driver (PHYID and Diagnostics reg). + * TODO: Add friendly names for the register nums. + */ struct qemu_phy { uint32_t regs[32]; unsigned int (*read)(struct qemu_phy *phy, unsigned int req); - void (*write)(struct qemu_phy *phy, unsigned int req, unsigned int data); + void (*write)(struct qemu_phy *phy, unsigned int req, + unsigned int data); }; static unsigned int tdk_read(struct qemu_phy *phy, unsigned int req) @@ -61,11 +61,35 @@ r |= (1 << 3); /* Autoneg able. */ r |= (1 << 2); /* Link. */ break; + case 5: + /* Link partner ability. + We are kind; always agree with whatever best mode + the guest advertises. */ + r = 1 << 14; /* Success. */ + /* Copy advertised modes. */ + r |= phy->regs[4] & (15 << 5); + /* Autoneg support. */ + r |= 1; + break; + case 18: + { + /* Diagnostics reg. */ + int duplex = 0; + int speed_100 = 0; + + /* Are we advertising 100 half or 100 duplex ? */ + speed_100 = !!(phy->regs[4] & 0x180); + /* Are we advertising 10 duplex or 100 duplex ? */ + duplex = !!(phy->regs[4] & 0x180); + r = (speed_100 << 10) | (duplex << 11); + } + break; + default: r = phy->regs[regnum]; break; } - D(printf("%s %x = reg[%d]\n", __func__, r, regnum)); + D(printf("\n%s %x = reg[%d]\n", __func__, r, regnum)); return r; } @@ -86,6 +110,13 @@ static void tdk_init(struct qemu_phy *phy) { + phy->regs[0] = 0x3100; + /* PHY Id. */ + phy->regs[2] = 0x0300; + phy->regs[3] = 0xe400; + /* Autonegotiation advertisement reg. */ + phy->regs[4] = 0x01E1; + phy->read = tdk_read; phy->write = tdk_write; } @@ -230,8 +261,8 @@ case DATA: if (!bus->mdc) { if (bus->drive) { - bus->mdio = bus->data & 1; - bus->data >>= 1; + bus->mdio = !!(bus->data & (1 << 15)); + bus->data <<= 1; } } else { if (!bus->drive) { @@ -241,7 +272,9 @@ if (bus->cnt == 16 * 2) { bus->cnt = 0; bus->state = PREAMBLE; - mdio_write_req(bus); + if (!bus->drive) + mdio_write_req(bus); + bus->drive = 0; } } break; @@ -250,7 +283,12 @@ } } +/* ETRAX-FS Ethernet MAC block starts here. */ +#define R_STAT 0x2c +#define RW_MGM_CTRL 0x28 +#define FS_ETH_MAX_REGS 0x5c + struct fs_eth { CPUState *env; @@ -398,15 +436,15 @@ } static CPUReadMemoryFunc *eth_read[] = { - ð_rinvalid, - ð_rinvalid, - ð_readl, + ð_rinvalid, + ð_rinvalid, + ð_readl, }; static CPUWriteMemoryFunc *eth_write[] = { - ð_winvalid, - ð_winvalid, - ð_writel, + ð_winvalid, + ð_winvalid, + ð_writel, }; void *etraxfs_eth_init(NICInfo *nd, CPUState *env,