[coreboot-gerrit] Change in coreboot[master]: soc/intel/apollolake: Add SD/MMC test support

Lee Leahy (Code Review) gerrit at coreboot.org
Fri Apr 7 21:42:18 CEST 2017


Lee Leahy has uploaded a new change for review. ( https://review.coreboot.org/19209 )

Change subject: soc/intel/apollolake: Add SD/MMC test support
......................................................................

soc/intel/apollolake: Add SD/MMC test support

* Build SD/MMC driver
* Add ramstage eMMC testing
* Select SDHC_DEBUG and SDHC_TRACE
* Set MMC_MODE_1V8_VDD
* Set MMC_MODE_HS400ES
* Don't pass in clock frequencies
* Use ctrlr instead of mmc_ctrlr
* Use new DRVR_CAP values
* Don't pass platform_info
* Pass in MmcMedia
* Switch host to mmc_ctrlr
* Use split driver
* remove typedefs
* Add eMMC test code to romstage
* Add eMMC test code to bootblock
* No eMMC test in bootblock
* Use storage APIs
* Read block 0 from each partition
* Don't build eMMC test by default

Change-Id: I569a592d324fa3aaf330cc0b8727848bfd548ec4
---
M src/soc/intel/apollolake/Kconfig
M src/soc/intel/apollolake/Makefile.inc
A src/soc/intel/apollolake/bootblock/emmc_test.c
A src/soc/intel/apollolake/emmc.c
A src/soc/intel/apollolake/emmc_test.c
A src/soc/intel/apollolake/include/soc/emmc_test.h
M src/soc/intel/apollolake/include/soc/iomap.h
M src/soc/intel/apollolake/include/soc/pci_ids.h
M src/soc/intel/apollolake/romstage.c
9 files changed, 275 insertions(+), 2 deletions(-)


  git pull ssh://review.coreboot.org:29418/coreboot refs/changes/09/19209/1

diff --git a/src/soc/intel/apollolake/Kconfig b/src/soc/intel/apollolake/Kconfig
index 70d2099..541fd7f 100644
--- a/src/soc/intel/apollolake/Kconfig
+++ b/src/soc/intel/apollolake/Kconfig
@@ -309,4 +309,13 @@
 	string
 	default "aplk"
 
+config STORAGE_TEST
+	bool "Enable SD/MMC/eMMC testing"
+	default n
+	select DRIVERS_STORAGE
+	select SDHCI_CONTROLLER
+	help
+	  Read block 0 from each parition of the storage device.  User must
+	  also enable one or both of DRIVERS_STORAGE_SD or DRIVERS_STORAGE_MMC.
+
 endif
diff --git a/src/soc/intel/apollolake/Makefile.inc b/src/soc/intel/apollolake/Makefile.inc
index 1e6aafd..701ef78 100644
--- a/src/soc/intel/apollolake/Makefile.inc
+++ b/src/soc/intel/apollolake/Makefile.inc
@@ -9,8 +9,9 @@
 subdirs-y += ../../../cpu/x86/cache
 
 bootblock-y += bootblock/bootblock.c
-bootblock-y += bootblock/bootblock.c
 bootblock-y += car.c
+#bootblock-$(CONFIG_STORAGE_TEST) += bootblock/emmc_test.c
+bootblock-$(CONFIG_STORAGE_TEST) += emmc_test.c
 bootblock-y += flash_ctrlr.c
 bootblock-y += gpio.c
 bootblock-y += heci.c
@@ -24,6 +25,7 @@
 bootblock-$(CONFIG_FSP_CAR) += bootblock/cache_as_ram_fsp.S
 
 romstage-y += car.c
+romstage-$(CONFIG_STORAGE_TEST) += emmc_test.c
 romstage-$(CONFIG_PLATFORM_USES_FSP2_0) += romstage.c
 romstage-y += flash_ctrlr.c
 romstage-y += gpio.c
@@ -54,6 +56,8 @@
 ramstage-y += chip.c
 ramstage-y += cse.c
 ramstage-y += elog.c
+ramstage-$(CONFIG_STORAGE_TEST) += emmc.c
+ramstage-$(CONFIG_STORAGE_TEST) += emmc_test.c
 ramstage-y += flash_ctrlr.c
 ramstage-y += dsp.c
 ramstage-y += gpio.c
@@ -82,6 +86,7 @@
 ramstage-y += xhci.c
 ramstage-y += sd.c
 
+postcar-$(CONFIG_STORAGE_TEST) += emmc_test.c
 postcar-y += flash_ctrlr.c
 postcar-y += memmap.c
 postcar-y += mmap_boot.c
@@ -92,6 +97,7 @@
 postcar-$(CONFIG_FSP_CAR) += exit_car_fsp.S
 
 verstage-y += car.c
+verstage-$(CONFIG_STORAGE_TEST) += emmc_test.c
 verstage-y += flash_ctrlr.c
 verstage-y += i2c_early.c
 verstage-y += heci.c
diff --git a/src/soc/intel/apollolake/bootblock/emmc_test.c b/src/soc/intel/apollolake/bootblock/emmc_test.c
new file mode 100644
index 0000000..a71b3b3
--- /dev/null
+++ b/src/soc/intel/apollolake/bootblock/emmc_test.c
@@ -0,0 +1,38 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyrigit 2017 Intel Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+#include <bootblock_common.h>
+#include <soc/iomap.h>
+#include <soc/emmc_test.h>
+#include <soc/pci_devs.h>
+
+void bootblock_soc_init(void)
+{
+	/* Test the eMMC device */
+	if (IS_ENABLED(CONFIG_STORAGE_TEST)) {
+		uint32_t bar;
+		dev_t dev;
+		uint32_t previous_bar;
+		uint16_t previous_command;
+
+		/* Enable the SD/MMC controller and run the test.  Restore
+		 * the BAR and command registers upon completion.
+		 */
+		dev = EMMC_DEV;
+		bar = emmc_test_init(dev, &previous_bar, &previous_command);
+		emmc_test(bar);
+		emmc_test_complete(dev, previous_bar, previous_command);
+	}
+}
diff --git a/src/soc/intel/apollolake/emmc.c b/src/soc/intel/apollolake/emmc.c
new file mode 100644
index 0000000..5eace7b
--- /dev/null
+++ b/src/soc/intel/apollolake/emmc.c
@@ -0,0 +1,52 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyrigit 2017 Intel Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#include <arch/io.h>
+#include <console/console.h>
+#include <device/device.h>
+#include <device/pci.h>
+#include <device/pci_ids.h>
+#include <device/sdhci.h>
+#include <device/storage.h>
+#include <lib.h>
+#include <soc/emmc_test.h>
+#include <soc/pci_ids.h>
+
+static void init(struct device *dev)
+{
+	/* Run the SD test */
+	if (IS_ENABLED(CONFIG_STORAGE_TEST)) {
+		uint32_t bar;
+		uint32_t previous_bar;
+		uint16_t previous_command;
+
+		bar = emmc_test_init(dev, &previous_bar, &previous_command);
+		emmc_test(bar);
+		emmc_test_complete(dev, previous_bar, previous_command);
+	}
+}
+
+static const struct device_operations device_ops = {
+	.read_resources		= pci_dev_read_resources,
+	.set_resources		= pci_dev_set_resources,
+	.enable_resources	= pci_dev_enable_resources,
+	.init			= init,
+};
+
+static const struct pci_driver pmc __pci_driver = {
+	.ops	= &device_ops,
+	.vendor	= PCI_VENDOR_ID_INTEL,
+	.device	= PCI_DEVICE_ID_APOLLOLAKE_EMMC,
+};
diff --git a/src/soc/intel/apollolake/emmc_test.c b/src/soc/intel/apollolake/emmc_test.c
new file mode 100644
index 0000000..bca810e
--- /dev/null
+++ b/src/soc/intel/apollolake/emmc_test.c
@@ -0,0 +1,110 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyrigit 2017 Intel Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#include <arch/io.h>
+#include <console/console.h>
+#include <device/sdhci.h>
+#include <device/storage.h>
+#include <lib.h>
+#include <soc/emmc_test.h>
+#include <soc/iomap.h>
+#include <soc/pci_devs.h>
+
+uint32_t emmc_test_init(dev_t dev, uint32_t *previous_bar,
+	uint16_t *previous_command)
+{
+	uint32_t bar;
+
+	/* Display the vendor/device IDs */
+	printk(BIOS_DEBUG, "Vendor ID: 0x%04x, Device ID: 0x%04x\n",
+		pci_read_config16(dev, PCI_VENDOR_ID),
+		pci_read_config16(dev, PCI_DEVICE_ID));
+
+	/* Set the temporary base address */
+	bar = pci_read_config32(dev, PCI_BASE_ADDRESS_0);
+	*previous_bar = bar;
+	bar &= ~PCI_BASE_ADDRESS_MEM_ATTR_MASK;
+	if (!bar) {
+		bar = PRERAM_EMMC_BASE_ADDRESS;
+		pci_write_config32(dev, PCI_BASE_ADDRESS_0, bar);
+	}
+
+	/* Enable the SD/MMC controller */
+	*previous_command = pci_read_config16(dev, PCI_COMMAND);
+	pci_write_config16(dev, PCI_COMMAND, *previous_command
+		| PCI_COMMAND_MEMORY);
+
+	/* Return the controller address */
+	return bar;
+}
+
+void emmc_test_complete(dev_t dev, uint32_t previous_bar,
+	uint16_t previous_command)
+{
+	pci_write_config16(dev, PCI_COMMAND, previous_command);
+	pci_write_config32(dev, PCI_BASE_ADDRESS_0, previous_bar);
+}
+
+void emmc_test(uint32_t bar)
+{
+	uint64_t blocks_read;
+	uint8_t buffer[512];
+	int err;
+	const char *name;
+	unsigned int partition;
+	unsigned int previous_partition;
+	struct sdhci_ctrlr sdhci_ctrlr;
+	struct storage_media media;
+
+	/* Initialize the controller */
+	printk(BIOS_DEBUG, "Initializing the SD/MMC controller\n");
+	err = sdhci_controller_init(&sdhci_ctrlr, (void *)bar);
+	if (err) {
+		printk(BIOS_ERR,
+			"ERROR - Controller failed to initialize, err = %d\n",
+			err);
+		return;
+	}
+	printk(BIOS_DEBUG, "Initializing the SD/MMC/eMMC device\n");
+	err = storage_setup_media(&media, &sdhci_ctrlr.sd_mmc_ctrlr);
+	if (err) {
+		printk(BIOS_ERR,
+			"ERROR: Device failed to initilaize failed, err = %d\n",
+			err);
+		return;
+	}
+
+	/* Save the current partition */
+	previous_partition = storage_get_current_partition(&media);
+
+	/* Read block 0 from each partition */
+	for (partition = 0; partition < ARRAY_SIZE(media.capacity);
+		partition++) {
+		if (media.capacity[partition] == 0)
+			continue;
+		name = storage_partition_name(&media, partition);
+		printk(BIOS_DEBUG, "%s%sReading block 0\n", name,
+			name[0] ? ": " : "");
+		err = storage_set_partition(&media, previous_partition);
+		if (err)
+			continue;
+		blocks_read = storage_block_read(&media, 0, 1, &buffer);
+		if (blocks_read)
+			hexdump(buffer, sizeof(buffer));
+	}
+
+	/* Restore the previous partition */
+	storage_set_partition(&media, previous_partition);
+}
diff --git a/src/soc/intel/apollolake/include/soc/emmc_test.h b/src/soc/intel/apollolake/include/soc/emmc_test.h
new file mode 100644
index 0000000..ff18a4c
--- /dev/null
+++ b/src/soc/intel/apollolake/include/soc/emmc_test.h
@@ -0,0 +1,34 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyrigit 2017 Intel Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#ifndef __EMMC_TEST_H__
+#define __EMMC_TEST_H__
+
+#include <device/device.h>
+#include <device/pci.h>
+
+#ifdef __SIMPLE_DEVICE__
+#define dev_t		uintptr_t
+#else
+#define dev_t		device_t
+#endif /* __SIMPLE_DEVICE__ */
+
+uint32_t emmc_test_init(dev_t dev, uint32_t *previous_bar,
+	uint16_t *previous_command);
+void emmc_test(uint32_t bar);
+void emmc_test_complete(dev_t dev, uint32_t previous_bar,
+	uint16_t previous_command);
+
+#endif /* __EMMC_TEST_H__ */
diff --git a/src/soc/intel/apollolake/include/soc/iomap.h b/src/soc/intel/apollolake/include/soc/iomap.h
index 3c94d1b..4565329 100644
--- a/src/soc/intel/apollolake/include/soc/iomap.h
+++ b/src/soc/intel/apollolake/include/soc/iomap.h
@@ -56,4 +56,7 @@
 /* Temporary BAR for early I2C bus access */
 #define PRERAM_I2C_BASE_ADDRESS(x)	(0xfe020000 + (0x1000 * (x)))
 
+/* Temporary BAR for EMMC */
+#define PRERAM_EMMC_BASE_ADDRESS	0xb0000000
+
 #endif /* _SOC_APOLLOLAKE_IOMAP_H_ */
diff --git a/src/soc/intel/apollolake/include/soc/pci_ids.h b/src/soc/intel/apollolake/include/soc/pci_ids.h
index 8b548ee..ba2c957 100644
--- a/src/soc/intel/apollolake/include/soc/pci_ids.h
+++ b/src/soc/intel/apollolake/include/soc/pci_ids.h
@@ -46,6 +46,7 @@
 #define PCI_DEVICE_ID_APOLLOLAKE_SPI0		0x5ac2		/* 00:19.0 */
 #define PCI_DEVICE_ID_APOLLOLAKE_SPI1		0x5ac4		/* 00:19.1 */
 #define PCI_DEVICE_ID_APOLLOLAKE_SPI2		0x5ac6		/* 00:19.2 */
+#define PCI_DEVICE_ID_APOLLOLAKE_EMMC		0x5acc		/* 00:1c.0 */
 #define PCI_DEVICE_ID_APOLLOLAKE_LPC		0x5ae8		/* 00:1f.0 */
 
 #endif /* _SOC_APOLLOLAKE_PCI_IDS_H_ */
diff --git a/src/soc/intel/apollolake/romstage.c b/src/soc/intel/apollolake/romstage.c
index 0270920..5d62569 100644
--- a/src/soc/intel/apollolake/romstage.c
+++ b/src/soc/intel/apollolake/romstage.c
@@ -1,7 +1,7 @@
 /*
  * This file is part of the coreboot project.
  *
- * Copyright (C) 2015 Intel Corp.
+ * Copyright (C) 2015 - 2017 Intel Corp.
  * (Written by Alexandru Gagniuc <alexandrux.gagniuc at intel.com> for Intel Corp.)
  * (Written by Andrey Petrov <andrey.petrov at intel.com> for Intel Corp.)
  *
@@ -28,10 +28,14 @@
 #include <cpu/x86/mtrr.h>
 #include <device/pci_def.h>
 #include <device/resource.h>
+#include <device/sdhci.h>
+#include <device/storage.h>
 #include <fsp/api.h>
 #include <fsp/memmap.h>
 #include <fsp/util.h>
+#include <lib.h>
 #include <soc/cpu.h>
+#include <soc/emmc_test.h>
 #include <soc/flash_ctrlr.h>
 #include <soc/intel/common/mrc_cache.h>
 #include <soc/iomap.h>
@@ -189,6 +193,22 @@
 
 	console_init();
 
+	/* Test the eMMC device */
+	if (IS_ENABLED(CONFIG_STORAGE_TEST)) {
+		uint32_t bar;
+		dev_t dev;
+		uint32_t previous_bar;
+		uint16_t previous_command;
+
+		/* Enable the SD/MMC controller and run the test.  Restore
+		 * the BAR and command registers upon completion.
+		 */
+		dev = EMMC_DEV;
+		bar = emmc_test_init(dev, &previous_bar, &previous_command);
+		emmc_test(bar);
+		emmc_test_complete(dev, previous_bar, previous_command);
+	}
+
 	s3wake = fill_power_state(ps) == ACPI_S3;
 	fsp_memory_init(s3wake);
 

-- 
To view, visit https://review.coreboot.org/19209
To unsubscribe, visit https://review.coreboot.org/settings

Gerrit-MessageType: newchange
Gerrit-Change-Id: I569a592d324fa3aaf330cc0b8727848bfd548ec4
Gerrit-PatchSet: 1
Gerrit-Project: coreboot
Gerrit-Branch: master
Gerrit-Owner: Lee Leahy <leroy.p.leahy at intel.com>



More information about the coreboot-gerrit mailing list