diff options
author | Tom Rini <trini@konsulko.com> | 2017-08-01 19:38:32 (GMT) |
---|---|---|
committer | Tom Rini <trini@konsulko.com> | 2017-08-01 19:38:32 (GMT) |
commit | 07d778382200a05a8b86cc135f79ec48e386f25a (patch) | |
tree | 624dc01190640212a9a8a45f4d12d4bd7489145d /drivers | |
parent | 5c6631beb27491f3f78b6a0ad888d38810e3d96b (diff) | |
parent | 24357dfd2aec4118b9178d8bf639fb8fc02e1859 (diff) | |
download | u-boot-07d778382200a05a8b86cc135f79ec48e386f25a.tar.xz |
Merge git://git.denx.de/u-boot-x86
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/ata/Kconfig | 6 | ||||
-rw-r--r-- | drivers/ata/Makefile | 1 | ||||
-rw-r--r-- | drivers/ata/ahci-pci.c | 42 | ||||
-rw-r--r-- | drivers/block/ide.c | 2 | ||||
-rw-r--r-- | drivers/gpio/Kconfig | 6 | ||||
-rw-r--r-- | drivers/mmc/pci_mmc.c | 86 | ||||
-rw-r--r-- | drivers/pci/Kconfig | 2 | ||||
-rw-r--r-- | drivers/timer/Kconfig | 1 | ||||
-rw-r--r-- | drivers/timer/tsc_timer.c | 52 |
9 files changed, 141 insertions, 57 deletions
diff --git a/drivers/ata/Kconfig b/drivers/ata/Kconfig index a1bd12e..803064a 100644 --- a/drivers/ata/Kconfig +++ b/drivers/ata/Kconfig @@ -22,6 +22,12 @@ config SATA menu "SATA/SCSI device support" +config AHCI_PCI + bool "Support for PCI-based AHCI controller" + depends on DM_SCSI + help + Enables support for the PCI-based AHCI controller. + config SATA_CEVA bool "Ceva Sata controller" depends on AHCI diff --git a/drivers/ata/Makefile b/drivers/ata/Makefile index c48184c..4e2de93 100644 --- a/drivers/ata/Makefile +++ b/drivers/ata/Makefile @@ -7,6 +7,7 @@ obj-$(CONFIG_DWC_AHCI) += dwc_ahci.o obj-$(CONFIG_AHCI) += ahci-uclass.o +obj-$(CONFIG_AHCI_PCI) += ahci-pci.o obj-$(CONFIG_SCSI_AHCI) += ahci.o obj-$(CONFIG_DWC_AHSATA) += dwc_ahsata.o obj-$(CONFIG_FSL_SATA) += fsl_sata.o diff --git a/drivers/ata/ahci-pci.c b/drivers/ata/ahci-pci.c new file mode 100644 index 0000000..f46fad8 --- /dev/null +++ b/drivers/ata/ahci-pci.c @@ -0,0 +1,42 @@ +/* + * Copyright (C) 2017, Bin Meng <bmeng.cn@gmail.com> + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include <common.h> +#include <ahci.h> +#include <dm.h> +#include <pci.h> + +static int ahci_pci_bind(struct udevice *dev) +{ + struct udevice *scsi_dev; + + return ahci_bind_scsi(dev, &scsi_dev); +} + +static int ahci_pci_probe(struct udevice *dev) +{ + return ahci_probe_scsi(dev); +} + +static const struct udevice_id ahci_pci_ids[] = { + { .compatible = "ahci-pci" }, + { } +}; + +U_BOOT_DRIVER(ahci_pci) = { + .name = "ahci_pci", + .id = UCLASS_AHCI, + .of_match = ahci_pci_ids, + .bind = ahci_pci_bind, + .probe = ahci_pci_probe, +}; + +static struct pci_device_id ahci_pci_supported[] = { + { PCI_DEVICE_CLASS(PCI_CLASS_STORAGE_SATA_AHCI, ~0) }, + {}, +}; + +U_BOOT_PCI_DEVICE(ahci_pci, ahci_pci_supported); diff --git a/drivers/block/ide.c b/drivers/block/ide.c index 308ad73..edcf87b 100644 --- a/drivers/block/ide.c +++ b/drivers/block/ide.c @@ -469,7 +469,9 @@ static void atapi_inquiry(struct blk_desc *dev_desc) device = dev_desc->devnum; dev_desc->type = DEV_TYPE_UNKNOWN; /* not yet valid */ +#ifndef CONFIG_BLK dev_desc->block_read = atapi_read; +#endif memset(ccb, 0, sizeof(ccb)); memset(iobuf, 0, sizeof(iobuf)); diff --git a/drivers/gpio/Kconfig b/drivers/gpio/Kconfig index 15135e5..63951e0 100644 --- a/drivers/gpio/Kconfig +++ b/drivers/gpio/Kconfig @@ -67,6 +67,12 @@ config INTEL_BROADWELL_GPIO driver from the common Intel ICH6 driver. It supports a total of 95 GPIOs which can be configured from the device tree. +config INTEL_ICH6_GPIO + bool "Intel ICH6 compatible legacy GPIO driver" + depends on DM_GPIO + help + Say yes here to select Intel ICH6 compatible legacy GPIO driver. + config IMX_RGPIO2P bool "i.MX7ULP RGPIO2P driver" depends on DM diff --git a/drivers/mmc/pci_mmc.c b/drivers/mmc/pci_mmc.c index e39b476..6db8977 100644 --- a/drivers/mmc/pci_mmc.c +++ b/drivers/mmc/pci_mmc.c @@ -6,37 +6,71 @@ */ #include <common.h> +#include <dm.h> #include <errno.h> #include <malloc.h> +#include <mapmem.h> #include <sdhci.h> #include <asm/pci.h> -int pci_mmc_init(const char *name, struct pci_device_id *mmc_supported) +struct pci_mmc_plat { + struct mmc_config cfg; + struct mmc mmc; +}; + +struct pci_mmc_priv { + struct sdhci_host host; + void *base; +}; + +static int pci_mmc_probe(struct udevice *dev) { - struct sdhci_host *mmc_host; - u32 iobase; + struct mmc_uclass_priv *upriv = dev_get_uclass_priv(dev); + struct pci_mmc_plat *plat = dev_get_platdata(dev); + struct pci_mmc_priv *priv = dev_get_priv(dev); + struct sdhci_host *host = &priv->host; + u32 ioaddr; int ret; - int i; - - for (i = 0; ; i++) { - struct udevice *dev; - - ret = pci_find_device_id(mmc_supported, i, &dev); - if (ret) - return ret; - mmc_host = malloc(sizeof(struct sdhci_host)); - if (!mmc_host) - return -ENOMEM; - - mmc_host->name = name; - dm_pci_read_config32(dev, PCI_BASE_ADDRESS_0, &iobase); - mmc_host->ioaddr = (void *)(ulong)iobase; - mmc_host->quirks = 0; - mmc_host->max_clk = 0; - ret = add_sdhci(mmc_host, 0, 0); - if (ret) - return ret; - } - - return 0; + + dm_pci_read_config32(dev, PCI_BASE_ADDRESS_0, &ioaddr); + host->ioaddr = map_sysmem(ioaddr, 0); + host->name = dev->name; + ret = sdhci_setup_cfg(&plat->cfg, host, 0, 0); + if (ret) + return ret; + host->mmc = &plat->mmc; + host->mmc->priv = &priv->host; + host->mmc->dev = dev; + upriv->mmc = host->mmc; + + return sdhci_probe(dev); } + +static int pci_mmc_bind(struct udevice *dev) +{ + struct pci_mmc_plat *plat = dev_get_platdata(dev); + + return sdhci_bind(dev, &plat->mmc, &plat->cfg); +} + +U_BOOT_DRIVER(pci_mmc) = { + .name = "pci_mmc", + .id = UCLASS_MMC, + .bind = pci_mmc_bind, + .probe = pci_mmc_probe, + .ops = &sdhci_ops, + .priv_auto_alloc_size = sizeof(struct pci_mmc_priv), + .platdata_auto_alloc_size = sizeof(struct pci_mmc_plat), +}; + +static struct pci_device_id mmc_supported[] = { + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BYT_SDIO) }, + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BYT_SD) }, + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BYT_EMMC2) }, + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_QRK_SDIO) }, + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_TCF_SDIO_0) }, + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_TCF_SDIO_1) }, + {}, +}; + +U_BOOT_PCI_DEVICE(pci_mmc, mmc_supported); diff --git a/drivers/pci/Kconfig b/drivers/pci/Kconfig index 692a398..e2a1c0a 100644 --- a/drivers/pci/Kconfig +++ b/drivers/pci/Kconfig @@ -1,6 +1,6 @@ menuconfig PCI bool "PCI support" - default y if PPC || X86 + default y if PPC help Enable support for PCI (Peripheral Interconnect Bus), a type of bus used on some devices to allow the CPU to communicate with its diff --git a/drivers/timer/Kconfig b/drivers/timer/Kconfig index 17e7dfe..c666303 100644 --- a/drivers/timer/Kconfig +++ b/drivers/timer/Kconfig @@ -36,7 +36,6 @@ config SANDBOX_TIMER config X86_TSC_TIMER bool "x86 Time-Stamp Counter (TSC) timer support" depends on TIMER && X86 - default y if X86 help Select this to enable Time-Stamp Counter (TSC) timer for x86. diff --git a/drivers/timer/tsc_timer.c b/drivers/timer/tsc_timer.c index 5c4ec00..4d1fc9c 100644 --- a/drivers/timer/tsc_timer.c +++ b/drivers/timer/tsc_timer.c @@ -11,18 +11,13 @@ #include <dm.h> #include <malloc.h> #include <timer.h> +#include <asm/cpu.h> #include <asm/io.h> #include <asm/i8254.h> #include <asm/ibmpc.h> #include <asm/msr.h> #include <asm/u-boot-x86.h> -/* CPU reference clock frequency: in KHz */ -#define FREQ_83 83200 -#define FREQ_100 99840 -#define FREQ_133 133200 -#define FREQ_166 166400 - #define MAX_NUM_FREQS 8 DECLARE_GLOBAL_DATA_PTR; @@ -45,17 +40,17 @@ struct freq_desc { static struct freq_desc freq_desc_tables[] = { /* PNW */ - { 6, 0x27, 0, { 0, 0, 0, 0, 0, FREQ_100, 0, FREQ_83 } }, + { 6, 0x27, 0, { 0, 0, 0, 0, 0, 99840, 0, 83200 } }, /* CLV+ */ - { 6, 0x35, 0, { 0, FREQ_133, 0, 0, 0, FREQ_100, 0, FREQ_83 } }, - /* TNG */ - { 6, 0x4a, 1, { 0, FREQ_100, FREQ_133, 0, 0, 0, 0, 0 } }, - /* VLV2 */ - { 6, 0x37, 1, { FREQ_83, FREQ_100, FREQ_133, FREQ_166, 0, 0, 0, 0 } }, + { 6, 0x35, 0, { 0, 133200, 0, 0, 0, 99840, 0, 83200 } }, + /* TNG - Intel Atom processor Z3400 series */ + { 6, 0x4a, 1, { 0, 100000, 133300, 0, 0, 0, 0, 0 } }, + /* VLV2 - Intel Atom processor E3000, Z3600, Z3700 series */ + { 6, 0x37, 1, { 83300, 100000, 133300, 116700, 80000, 0, 0, 0 } }, + /* ANN - Intel Atom processor Z3500 series */ + { 6, 0x5a, 1, { 83300, 100000, 133300, 100000, 0, 0, 0, 0 } }, /* Ivybridge */ { 6, 0x3a, 2, { 0, 0, 0, 0, 0, 0, 0, 0 } }, - /* ANN */ - { 6, 0x5a, 1, { FREQ_83, FREQ_100, FREQ_133, FREQ_100, 0, 0, 0, 0 } }, }; static int match_cpu(u8 family, u8 model) @@ -76,35 +71,40 @@ static int match_cpu(u8 family, u8 model) (freq_desc_tables[cpu_index].freqs[freq_id]) /* - * Do MSR calibration only for known/supported CPUs. + * TSC on Intel Atom SoCs capable of determining TSC frequency by MSR is + * reliable and the frequency is known (provided by HW). + * + * On these platforms PIT/HPET is generally not available so calibration won't + * work at all and there is no other clocksource to act as a watchdog for the + * TSC, so we have no other choice than to trust it. * - * Returns the calibration value or 0 if MSR calibration failed. + * Returns the TSC frequency in MHz or 0 if HW does not provide it. */ -static unsigned long __maybe_unused try_msr_calibrate_tsc(void) +static unsigned long __maybe_unused cpu_mhz_from_msr(void) { u32 lo, hi, ratio, freq_id, freq; unsigned long res; int cpu_index; + if (gd->arch.x86_vendor != X86_VENDOR_INTEL) + return 0; + cpu_index = match_cpu(gd->arch.x86, gd->arch.x86_model); if (cpu_index < 0) return 0; if (freq_desc_tables[cpu_index].msr_plat) { rdmsr(MSR_PLATFORM_INFO, lo, hi); - ratio = (lo >> 8) & 0x1f; + ratio = (lo >> 8) & 0xff; } else { rdmsr(MSR_IA32_PERF_STATUS, lo, hi); ratio = (hi >> 8) & 0x1f; } debug("Maximum core-clock to bus-clock ratio: 0x%x\n", ratio); - if (!ratio) - goto fail; - if (freq_desc_tables[cpu_index].msr_plat == 2) { /* TODO: Figure out how best to deal with this */ - freq = FREQ_100; + freq = 100000; debug("Using frequency: %u KHz\n", freq); } else { /* Get FSB FREQ ID */ @@ -114,18 +114,12 @@ static unsigned long __maybe_unused try_msr_calibrate_tsc(void) debug("Resolved frequency ID: %u, frequency: %u KHz\n", freq_id, freq); } - if (!freq) - goto fail; /* TSC frequency = maximum resolved freq * maximum resolved bus ratio */ res = freq * ratio / 1000; debug("TSC runs at %lu MHz\n", res); return res; - -fail: - debug("Fast TSC calibration using MSR failed\n"); - return 0; } /* @@ -347,7 +341,7 @@ static int tsc_timer_probe(struct udevice *dev) if (!uc_priv->clock_rate) { unsigned long fast_calibrate; - fast_calibrate = try_msr_calibrate_tsc(); + fast_calibrate = cpu_mhz_from_msr(); if (!fast_calibrate) { fast_calibrate = quick_pit_calibrate(); if (!fast_calibrate) |