blob: edfc5844e5abe6fbe8379dd0204e702254d4287c [file] [log] [blame]
Eric Biederman83b991a2003-10-11 06:20:25 +00001/*
Martin Rothebace9f2018-05-26 18:56:17 -06002 * This file is part of the coreboot project.
3 *
4 * (C) 2004 Linux Networx
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; version 2 of the License.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
Eric Biederman83b991a2003-10-11 06:20:25 +000014 */
Martin Rothebace9f2018-05-26 18:56:17 -060015
Eric Biederman83b991a2003-10-11 06:20:25 +000016#include <console/console.h>
17#include <device/device.h>
18#include <device/pci.h>
19#include <device/pci_ids.h>
20#include <device/pci_ops.h>
arch import user (historical)bc5be472005-07-06 16:48:04 +000021#include <arch/io.h>
Myles Watson43bb9cd2008-12-18 18:24:11 +000022#include <delay.h>
Eric Biederman83b991a2003-10-11 06:20:25 +000023#include "amd8111.h"
24
25
Kevin Paul Herbert4104e6c2015-02-25 00:36:51 -080026#define CMD3 0x54
arch import user (historical)bc5be472005-07-06 16:48:04 +000027
28typedef enum {
29 VAL3 = (1 << 31), /* VAL bit for byte 3 */
30 VAL2 = (1 << 23), /* VAL bit for byte 2 */
31 VAL1 = (1 << 15), /* VAL bit for byte 1 */
32 VAL0 = (1 << 7), /* VAL bit for byte 0 */
33}VAL_BITS;
34
35typedef enum {
36 /* VAL3 */
37 ASF_INIT_DONE_ALIAS = (1 << 29),
38 /* VAL2 */
39 JUMBO = (1 << 21),
Stefan Reinauer14e22772010-04-27 06:56:47 +000040 VSIZE = (1 << 20),
arch import user (historical)bc5be472005-07-06 16:48:04 +000041 VLONLY = (1 << 19),
Stefan Reinauer14e22772010-04-27 06:56:47 +000042 VL_TAG_DEL = (1 << 18),
arch import user (historical)bc5be472005-07-06 16:48:04 +000043 /* VAL1 */
Stefan Reinauer14e22772010-04-27 06:56:47 +000044 EN_PMGR = (1 << 14),
arch import user (historical)bc5be472005-07-06 16:48:04 +000045 INTLEVEL = (1 << 13),
Stefan Reinauer14e22772010-04-27 06:56:47 +000046 FORCE_FULL_DUPLEX = (1 << 12),
47 FORCE_LINK_STATUS = (1 << 11),
48 APEP = (1 << 10),
49 MPPLBA = (1 << 9),
arch import user (historical)bc5be472005-07-06 16:48:04 +000050 /* VAL0 */
Stefan Reinauer14e22772010-04-27 06:56:47 +000051 RESET_PHY_PULSE = (1 << 2),
52 RESET_PHY = (1 << 1),
53 PHY_RST_POL = (1 << 0),
arch import user (historical)bc5be472005-07-06 16:48:04 +000054}CMD3_BITS;
55
56static void nic_init(struct device *dev)
57{
58 struct southbridge_amd_amd8111_config *conf;
59 struct resource *resource;
Kevin Paul Herbertbde6d302014-12-24 18:43:20 -080060 u8 *mmio;
arch import user (historical)bc5be472005-07-06 16:48:04 +000061
62 conf = dev->chip_info;
63 resource = find_resource(dev, PCI_BASE_ADDRESS_0);
Kevin Paul Herbertbde6d302014-12-24 18:43:20 -080064 mmio = res2mmio(resource, 0, 0);
arch import user (historical)bc5be472005-07-06 16:48:04 +000065
66 /* Hard Reset PHY */
Paul Menzel4159a802013-07-14 00:24:31 +020067 printk(BIOS_DEBUG, "Resetting PHY... ");
arch import user (historical)bc5be472005-07-06 16:48:04 +000068 if (conf->phy_lowreset) {
Stefan Reinauer50776fa2010-03-17 04:40:15 +000069 write32((mmio + CMD3), VAL0 | PHY_RST_POL | RESET_PHY);
arch import user (historical)bc5be472005-07-06 16:48:04 +000070 } else {
Stefan Reinauer50776fa2010-03-17 04:40:15 +000071 write32((mmio + CMD3), VAL0 | RESET_PHY);
arch import user (historical)bc5be472005-07-06 16:48:04 +000072 }
73 mdelay(15);
Stefan Reinauer50776fa2010-03-17 04:40:15 +000074 write32((mmio + CMD3), RESET_PHY);
Stefan Reinauerc02b4fc2010-03-22 11:42:32 +000075 printk(BIOS_DEBUG, "Done\n");
arch import user (historical)bc5be472005-07-06 16:48:04 +000076}
77
Elyes HAOUAS39733a02018-05-19 14:45:20 +020078static void lpci_set_subsystem(struct device *dev, unsigned vendor,
79 unsigned device)
arch import user (historical)bc5be472005-07-06 16:48:04 +000080{
81 pci_write_config32(dev, 0xc8,
82 ((device & 0xffff) << 16) | (vendor & 0xffff));
83}
84
85static struct pci_operations lops_pci = {
86 .set_subsystem = lpci_set_subsystem,
87};
Stefan Reinauer14e22772010-04-27 06:56:47 +000088
Eric Biederman83b991a2003-10-11 06:20:25 +000089static struct device_operations nic_ops = {
90 .read_resources = pci_dev_read_resources,
91 .set_resources = pci_dev_set_resources,
92 .enable_resources = pci_dev_enable_resources,
arch import user (historical)bc5be472005-07-06 16:48:04 +000093 .init = nic_init,
Eric Biederman83b991a2003-10-11 06:20:25 +000094 .scan_bus = 0,
arch import user (historical)bc5be472005-07-06 16:48:04 +000095 .enable = amd8111_enable,
96 .ops_pci = &lops_pci,
Eric Biederman83b991a2003-10-11 06:20:25 +000097};
98
Stefan Reinauerf1cf1f72007-10-24 09:08:58 +000099static const struct pci_driver nic_driver __pci_driver = {
Eric Biederman83b991a2003-10-11 06:20:25 +0000100 .ops = &nic_ops,
101 .vendor = PCI_VENDOR_ID_AMD,
arch import user (historical)bc5be472005-07-06 16:48:04 +0000102 .device = PCI_DEVICE_ID_AMD_8111_NIC,
Eric Biederman83b991a2003-10-11 06:20:25 +0000103};