From: Richard Zhu Date: Wed, 14 Dec 2011 04:54:11 +0000 (+0800) Subject: ENGR00170244-1 ARM: AHCI: Enable PDDQ mode when no disk is attached X-Git-Tag: v3.0.35-fsl~1768 X-Git-Url: https://git.karo-electronics.de/?a=commitdiff_plain;h=93652918b750231d2248cab3ca7cf7bd68d495dc;p=karo-tx-linux.git ENGR00170244-1 ARM: AHCI: Enable PDDQ mode when no disk is attached In order to save the power consumption, enable the PDDQ mode of AHCI PHY when there is no sata disk on the port Signed-off-by: Richard Zhu --- diff --git a/arch/arm/plat-mxc/ahci_sata.c b/arch/arm/plat-mxc/ahci_sata.c index ab4fcf86bc4c..0d78a123a469 100644 --- a/arch/arm/plat-mxc/ahci_sata.c +++ b/arch/arm/plat-mxc/ahci_sata.c @@ -22,6 +22,7 @@ #include #include #include +#include #include int write_phy_ctl_ack_polling(u32 data, void __iomem *mmio, @@ -37,7 +38,7 @@ int write_phy_ctl_ack_polling(u32 data, void __iomem *mmio, if (val == exp_val) return 0; if (i == max_iterations) { - printk(KERN_ERR "Wait for CR ACK error!\n"); + pr_err("Wait for CR ACK error!\n"); return 1; } usleep_range(100, 200); @@ -137,6 +138,7 @@ int sata_phy_cr_read(u32 *data, void __iomem *mmio) int sata_init(void __iomem *addr, unsigned long timer1ms) { u32 tmpdata; + int iterations = 20; /* Reset HBA */ writel(HOST_RESET, addr + HOST_CTL); @@ -146,7 +148,7 @@ int sata_init(void __iomem *addr, unsigned long timer1ms) while (readl(addr + HOST_VERSIONR) == 0) { tmpdata++; if (tmpdata > 100000) { - printk(KERN_ERR "Can't recover from RESET HBA!\n"); + pr_err("Can't recover from RESET HBA!\n"); break; } } @@ -164,5 +166,22 @@ int sata_init(void __iomem *addr, unsigned long timer1ms) writel(timer1ms, addr + HOST_TIMER1MS); + /* Release resources when there is no device on the port */ + do { + if ((readl(addr + PORT_SATA_SR) & 0xF) == 0) + msleep(25); + else + break; + + if (iterations == 0) { + pr_info("No sata disk.\n"); + /* Enter into PDDQ mode, save power */ + tmpdata = readl(addr + PORT_PHY_CTL); + writel(tmpdata | PORT_PHY_CTL_PDDQ_LOC, + addr + PORT_PHY_CTL); + return -ENODEV; + } + } while (iterations-- > 0); + return 0; } diff --git a/arch/arm/plat-mxc/include/mach/ahci_sata.h b/arch/arm/plat-mxc/include/mach/ahci_sata.h index edca22b4fc04..48b93e55eea0 100755 --- a/arch/arm/plat-mxc/include/mach/ahci_sata.h +++ b/arch/arm/plat-mxc/include/mach/ahci_sata.h @@ -39,6 +39,7 @@ enum { PORT_PHY_CTL_CAP_DAT_LOC = 0x20000, PORT_PHY_CTL_WRITE_LOC = 0x40000, PORT_PHY_CTL_READ_LOC = 0x80000, + PORT_PHY_CTL_PDDQ_LOC = 0x100000, /* Port0 PHY Status */ PORT_PHY_SR = 0x17c, /* PORT_PHY_SR */