Created
January 7, 2018 01:04
-
-
Save Miouyouyou/12b79c0c02856f6d779baa040bfb121d to your computer and use it in GitHub Desktop.
ASUS Tinkerboard reboot patch. The less ugly one.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
From 302cd9b8a9f1f8a7735fabea3b9a7645dc40f9cc Mon Sep 17 00:00:00 2001 | |
From: Myy Miouyouyou <[email protected]> | |
Date: Sun, 7 Jan 2018 01:52:44 +0100 | |
Subject: [PATCH] drivers: mmc: dw-mci-rockchip: Handle ASUS Tinkerboard reboot | |
On ASUS Tinkerboard systems, if the SDMMC hardware is shutdown before | |
rebooting, the system will be dead, as the SDMMC is the only way to | |
boot anything, and the hardware doesn't power up the SDMMC hardware | |
automatically when rebooting. | |
So, when using an ASUS Tinkerboard system, a new reboot handler is | |
installed. This reboot handler takes care of powering the SDMMC | |
hardware again before restarting the system, resolving the issue. | |
The code was inspired by the pwrseq_emmc.c, which seems to overcome | |
similar effects with eMMC hardware. | |
Signed-off-by: Myy Miouyouyou <[email protected]> | |
--- | |
drivers/mmc/host/dw_mmc-rockchip.c | 66 ++++++++++++++++++++++++++++++++++++++ | |
1 file changed, 66 insertions(+) | |
diff --git a/drivers/mmc/host/dw_mmc-rockchip.c b/drivers/mmc/host/dw_mmc-rockchip.c | |
index a3f1c2b30..7eac1f221 100644 | |
--- a/drivers/mmc/host/dw_mmc-rockchip.c | |
+++ b/drivers/mmc/host/dw_mmc-rockchip.c | |
@@ -16,6 +16,11 @@ | |
#include <linux/pm_runtime.h> | |
#include <linux/slab.h> | |
+#include <linux/regulator/consumer.h> | |
+#include <linux/reboot.h> | |
+#include <linux/delay.h> | |
+#include "../core/core.h" | |
+ | |
#include "dw_mmc.h" | |
#include "dw_mmc-pltfm.h" | |
@@ -334,6 +339,66 @@ static const struct of_device_id dw_mci_rockchip_match[] = { | |
}; | |
MODULE_DEVICE_TABLE(of, dw_mci_rockchip_match); | |
+struct dw_mci_rockchip_broken_boards_data { | |
+ struct notifier_block reset_nb; | |
+ struct platform_device *pdev; | |
+}; | |
+ | |
+/* This reboot handler handles cases where disabling the SDMMC on | |
+ * reboot will cause the hardware to be unable to start correctly | |
+ * after rebooting. | |
+ * | |
+ * This happens with Tinkerboard systems... | |
+ */ | |
+static int dw_mci_rockchip_broken_boards_reset_nb( | |
+ struct notifier_block *this, | |
+ unsigned long mode, void *cmd) | |
+{ | |
+ struct dw_mci_rockchip_broken_boards_data const *data = | |
+ container_of(this, | |
+ struct dw_mci_rockchip_broken_boards_data, | |
+ reset_nb); | |
+ struct dw_mci *host = platform_get_drvdata(data->pdev); | |
+ struct mmc_host *mmc = host->slot->mmc; | |
+ | |
+ printk(KERN_ERR "Meow.\n"); | |
+ | |
+ mmc_power_off(mmc); | |
+ | |
+ mdelay(20); | |
+ | |
+ if (!IS_ERR(mmc->supply.vmmc)) | |
+ regulator_enable(mmc->supply.vmmc); | |
+ | |
+ if (!IS_ERR(mmc->supply.vqmmc)) | |
+ regulator_set_voltage(mmc->supply.vqmmc, 3000000, 3300000); | |
+ | |
+ printk(KERN_ERR "woeM.\n"); | |
+ | |
+ return NOTIFY_DONE; | |
+} | |
+ | |
+static void dw_mci_rockchip_register_broken_boards_reboot_handler( | |
+ struct platform_device *pdev) | |
+{ | |
+ struct dw_mci_rockchip_broken_boards_data *data; | |
+ | |
+ if (!of_machine_is_compatible("asus,rk3288-tinker")) | |
+ return; | |
+ | |
+ data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); | |
+ | |
+ if (!data) | |
+ return; | |
+ | |
+ data->reset_nb.notifier_call = | |
+ dw_mci_rockchip_broken_boards_reset_nb; | |
+ data->reset_nb.priority = 255; | |
+ register_restart_handler(&data->reset_nb); | |
+ | |
+ data->pdev = pdev; | |
+} | |
+ | |
static int dw_mci_rockchip_probe(struct platform_device *pdev) | |
{ | |
const struct dw_mci_drv_data *drv_data; | |
@@ -361,6 +426,7 @@ static int dw_mci_rockchip_probe(struct platform_device *pdev) | |
} | |
pm_runtime_put_autosuspend(&pdev->dev); | |
+ dw_mci_rockchip_register_broken_boards_reboot_handler(pdev); | |
return 0; | |
} | |
-- | |
2.14.1 | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment