FAILED: patch "[PATCH] rtc: opal: Fix OPAL RTC driver OPAL_BUSY loops" failed to apply to 4.4-stable tree
Subsystems (3)
[email protected]
maintainerThe patch below does not apply to the 4.4-stable tree.
If someone wants it applied there, or to any other stable or longterm tree, then please email the backport, including the original git commit id to <[email protected]>.
thanks,
greg k-h
------------------ original commit in Linus's tree ------------------
Quoted 1 line
From
682e6b4da5cbe8e9a53f979a58c2a9d7dc997175Mon Sep 17 00:00:00 2001
From: Nicholas Piggin <[email protected]>
Date: Tue, 10 Apr 2018 21:49:32 +1000
Subject: [PATCH] rtc: opal: Fix OPAL RTC driver OPAL_BUSY loops
The OPAL RTC driver does not sleep in case it gets OPAL_BUSY or OPAL_BUSY_EVENT from firmware, which causes large scheduling latencies, up to 50 seconds have been observed here when RTC stops responding (BMC reboot can do it).
Fix this by converting it to the standard form OPAL_BUSY loop that sleeps.
arch/powerpc/platforms/powernv/opal-rtc.c +5 -3
@@ -48,10 +48,12 @@ unsigned long __init opal_get_boot_time(void)while (rc ==OPAL_BUSY || rc ==OPAL_BUSY_EVENT ) { rc =opal_rtc_read (&__y_m_d, &__h_m_s_ms); -if (rc ==OPAL_BUSY_EVENT ) +if (rc ==OPAL_BUSY_EVENT ) { +mdelay (OPAL_BUSY_DELAY_MS );opal_poll_events (NULL ); -else if (rc ==OPAL_BUSY ) -mdelay (10 ); + }else if (rc ==OPAL_BUSY ) { +mdelay (OPAL_BUSY_DELAY_MS ); + } }if (rc !=OPAL_SUCCESS )return 0 ;
drivers/rtc/rtc-opal.c +23 -14
@@ -57,7 +57,7 @@ static void tm_to_opal(struct rtc_time *tm, u32 *y_m_d, u64 *h_m_s_ms)static int opal_get_rtc_time (struct device *dev,struct rtc_time *tm) { -long rc =OPAL_BUSY ; +s64 rc =OPAL_BUSY ;int retries =10 ;u32 y_m_d;u64 h_m_s_ms;
@@ -66,13 +66,17 @@ static int opal_get_rtc_time(struct device *dev, struct rtc_time *tm)while (rc ==OPAL_BUSY || rc ==OPAL_BUSY_EVENT ) { rc =opal_rtc_read (&__y_m_d, &__h_m_s_ms); -if (rc ==OPAL_BUSY_EVENT ) +if (rc ==OPAL_BUSY_EVENT ) { +msleep (OPAL_BUSY_DELAY_MS );opal_poll_events (NULL ); -else if (retries-- && (rc ==OPAL_HARDWARE - || rc ==OPAL_INTERNAL_ERROR )) -msleep (10 ); -else if (rc !=OPAL_BUSY && rc !=OPAL_BUSY_EVENT ) -break ; + }else if (rc ==OPAL_BUSY ) { +msleep (OPAL_BUSY_DELAY_MS ); + }else if (rc ==OPAL_HARDWARE || rc ==OPAL_INTERNAL_ERROR ) { +if (retries--) { +msleep (10 );/* Wait 10ms before retry */ + rc =OPAL_BUSY ;/* go around again */ + } + } }if (rc !=OPAL_SUCCESS )
@@ -87,21 +91,26 @@ static int opal_get_rtc_time(struct device *dev, struct rtc_time *tm)static int opal_set_rtc_time (struct device *dev,struct rtc_time *tm) { -long rc =OPAL_BUSY ; +s64 rc =OPAL_BUSY ;int retries =10 ;u32 y_m_d =0 ;u64 h_m_s_ms =0 ;tm_to_opal (tm, &y_m_d, &h_m_s_ms); +while (rc ==OPAL_BUSY || rc ==OPAL_BUSY_EVENT ) { rc =opal_rtc_write (y_m_d, h_m_s_ms); -if (rc ==OPAL_BUSY_EVENT ) +if (rc ==OPAL_BUSY_EVENT ) { +msleep (OPAL_BUSY_DELAY_MS );opal_poll_events (NULL ); -else if (retries-- && (rc ==OPAL_HARDWARE - || rc ==OPAL_INTERNAL_ERROR )) -msleep (10 ); -else if (rc !=OPAL_BUSY && rc !=OPAL_BUSY_EVENT ) -break ; + }else if (rc ==OPAL_BUSY ) { +msleep (OPAL_BUSY_DELAY_MS ); + }else if (rc ==OPAL_HARDWARE || rc ==OPAL_INTERNAL_ERROR ) { +if (retries--) { +msleep (10 );/* Wait 10ms before retry */ + rc =OPAL_BUSY ;/* go around again */ + } + } }return rc ==OPAL_SUCCESS ?0 : -EIO ;