aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/memory
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/memory')
-rw-r--r--drivers/memory/emif.c36
1 files changed, 28 insertions, 8 deletions
diff --git a/drivers/memory/emif.c b/drivers/memory/emif.c
index bda11ebb25cd..249222905c94 100644
--- a/drivers/memory/emif.c
+++ b/drivers/memory/emif.c
@@ -715,6 +715,8 @@ static u32 get_pwr_mgmt_ctrl(u32 freq, struct emif_data *emif, u32 ip_rev)
715 u32 timeout_perf = EMIF_LP_MODE_TIMEOUT_PERFORMANCE; 715 u32 timeout_perf = EMIF_LP_MODE_TIMEOUT_PERFORMANCE;
716 u32 timeout_pwr = EMIF_LP_MODE_TIMEOUT_POWER; 716 u32 timeout_pwr = EMIF_LP_MODE_TIMEOUT_POWER;
717 u32 freq_threshold = EMIF_LP_MODE_FREQ_THRESHOLD; 717 u32 freq_threshold = EMIF_LP_MODE_FREQ_THRESHOLD;
718 u32 mask;
719 u8 shift;
718 720
719 struct emif_custom_configs *cust_cfgs = emif->plat_data->custom_configs; 721 struct emif_custom_configs *cust_cfgs = emif->plat_data->custom_configs;
720 722
@@ -743,27 +745,45 @@ static u32 get_pwr_mgmt_ctrl(u32 freq, struct emif_data *emif, u32 ip_rev)
743 745
744 switch (lpmode) { 746 switch (lpmode) {
745 case EMIF_LP_MODE_CLOCK_STOP: 747 case EMIF_LP_MODE_CLOCK_STOP:
746 pwr_mgmt_ctrl = (timeout << CS_TIM_SHIFT) | 748 shift = CS_TIM_SHIFT;
747 SR_TIM_MASK | PD_TIM_MASK; 749 mask = CS_TIM_MASK;
748 break; 750 break;
749 case EMIF_LP_MODE_SELF_REFRESH: 751 case EMIF_LP_MODE_SELF_REFRESH:
750 /* Workaround for errata i735 */ 752 /* Workaround for errata i735 */
751 if (timeout < 6) 753 if (timeout < 6)
752 timeout = 6; 754 timeout = 6;
753 755
754 pwr_mgmt_ctrl = (timeout << SR_TIM_SHIFT) | 756 shift = SR_TIM_SHIFT;
755 CS_TIM_MASK | PD_TIM_MASK; 757 mask = SR_TIM_MASK;
756 break; 758 break;
757 case EMIF_LP_MODE_PWR_DN: 759 case EMIF_LP_MODE_PWR_DN:
758 pwr_mgmt_ctrl = (timeout << PD_TIM_SHIFT) | 760 shift = PD_TIM_SHIFT;
759 CS_TIM_MASK | SR_TIM_MASK; 761 mask = PD_TIM_MASK;
760 break; 762 break;
761 case EMIF_LP_MODE_DISABLE: 763 case EMIF_LP_MODE_DISABLE:
762 default: 764 default:
763 pwr_mgmt_ctrl = CS_TIM_MASK | 765 mask = 0;
764 PD_TIM_MASK | SR_TIM_MASK; 766 shift = 0;
767 break;
768 }
769 /* Round to maximum in case of overflow, BUT warn! */
770 if (lpmode != EMIF_LP_MODE_DISABLE && timeout > mask >> shift) {
771 pr_err("TIMEOUT Overflow - lpmode=%d perf=%d pwr=%d freq=%d\n",
772 lpmode,
773 timeout_perf,
774 timeout_pwr,
775 freq_threshold);
776 WARN(1, "timeout=0x%02x greater than 0x%02x. Using max\n",
777 timeout, mask >> shift);
778 timeout = mask >> shift;
765 } 779 }
766 780
781 /* Setup required timing */
782 pwr_mgmt_ctrl = (timeout << shift) & mask;
783 /* setup a default mask for rest of the modes */
784 pwr_mgmt_ctrl |= (SR_TIM_MASK | CS_TIM_MASK | PD_TIM_MASK) &
785 ~mask;
786
767 /* No CS_TIM in EMIF_4D5 */ 787 /* No CS_TIM in EMIF_4D5 */
768 if (ip_rev == EMIF_4D5) 788 if (ip_rev == EMIF_4D5)
769 pwr_mgmt_ctrl &= ~CS_TIM_MASK; 789 pwr_mgmt_ctrl &= ~CS_TIM_MASK;