summaryrefslogtreecommitdiffstats
path: root/drivers/pcmcia
diff options
context:
space:
mode:
authorRussell King <rmk+kernel@armlinux.org.uk>2016-08-31 08:49:46 +0100
committerRussell King <rmk+kernel@armlinux.org.uk>2016-09-22 09:39:00 +0100
commit6ac95d821216f3baab16821a893d52ab385824be (patch)
tree8183c33b98ba4f77168b1f6e9d26cab1998fe0a5 /drivers/pcmcia
parent535e0abc0534b139b067d496bb93663acffb72ce (diff)
downloadop-kernel-dev-6ac95d821216f3baab16821a893d52ab385824be.zip
op-kernel-dev-6ac95d821216f3baab16821a893d52ab385824be.tar.gz
pcmcia: soc_common: restore previous socket state on error
If an attempt to set a socket state returns an error, restore the previous socket state. If restoring the previous socket state fails, warn about this. This allows us to have simple error handling in the socket state configuration handlers - there is no need for every handler implementation to manually undo the updates, which can be complex when regulators are involved. Signed-off-by: Russell King <rmk+kernel@armlinux.org.uk>
Diffstat (limited to 'drivers/pcmcia')
-rw-r--r--drivers/pcmcia/soc_common.c14
1 files changed, 10 insertions, 4 deletions
diff --git a/drivers/pcmcia/soc_common.c b/drivers/pcmcia/soc_common.c
index f772127..9373d99 100644
--- a/drivers/pcmcia/soc_common.c
+++ b/drivers/pcmcia/soc_common.c
@@ -286,6 +286,14 @@ static int soc_common_pcmcia_config_skt(
int ret;
ret = skt->ops->configure_socket(skt, state);
+ if (ret < 0) {
+ pr_err("soc_common_pcmcia: unable to configure socket %d\n",
+ skt->nr);
+ /* restore the previous state */
+ WARN_ON(skt->ops->configure_socket(skt, &skt->cs_state));
+ return ret;
+ }
+
if (ret == 0) {
struct gpio_desc *descs[2];
int values[2], n = 0;
@@ -318,10 +326,6 @@ static int soc_common_pcmcia_config_skt(
skt->cs_state = *state;
}
- if (ret < 0)
- printk(KERN_ERR "soc_common_pcmcia: unable to configure "
- "socket %d\n", skt->nr);
-
return ret;
}
@@ -770,6 +774,8 @@ int soc_pcmcia_add_one(struct soc_pcmcia_socket *skt)
{
int ret;
+ skt->cs_state = dead_socket;
+
setup_timer(&skt->poll_timer, soc_common_pcmcia_poll_event,
(unsigned long)skt);
skt->poll_timer.expires = jiffies + SOC_PCMCIA_POLL_PERIOD;
OpenPOWER on IntegriCloud