diff options
author | Alexander Shiyan <shc_work@mail.ru> | 2013-08-19 07:39:19 -0400 |
---|---|---|
committer | Marc Kleine-Budde <mkl@pengutronix.de> | 2013-08-21 03:28:29 -0400 |
commit | 1ddff7da0faecffdcdeab3d981fb8241453cea44 (patch) | |
tree | 7388e85b2a844917fe3103c47bdb044799fba95f /drivers/net/can/mcp251x.c | |
parent | 954c396756e3d31985f7bc6a414a988a4736a7d0 (diff) |
can: mcp251x: Replace power callbacks with regulator API
This patch replaces power callbacks to the regulator API. To improve
the readability of the code, helper for the regulator enable/disable
was added.
Acked-by: Haojian Zhuang <haojian.zhuang@gmail.com>
Signed-off-by: Alexander Shiyan <shc_work@mail.ru>
Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
Diffstat (limited to 'drivers/net/can/mcp251x.c')
-rw-r--r-- | drivers/net/can/mcp251x.c | 83 |
1 files changed, 43 insertions, 40 deletions
diff --git a/drivers/net/can/mcp251x.c b/drivers/net/can/mcp251x.c index 8cda23bf0614..d2c54888b211 100644 --- a/drivers/net/can/mcp251x.c +++ b/drivers/net/can/mcp251x.c | |||
@@ -37,9 +37,6 @@ | |||
37 | * | 37 | * |
38 | * static struct mcp251x_platform_data mcp251x_info = { | 38 | * static struct mcp251x_platform_data mcp251x_info = { |
39 | * .oscillator_frequency = 8000000, | 39 | * .oscillator_frequency = 8000000, |
40 | * .board_specific_setup = &mcp251x_setup, | ||
41 | * .power_enable = mcp251x_power_enable, | ||
42 | * .transceiver_enable = NULL, | ||
43 | * }; | 40 | * }; |
44 | * | 41 | * |
45 | * static struct spi_board_info spi_board_info[] = { | 42 | * static struct spi_board_info spi_board_info[] = { |
@@ -76,6 +73,7 @@ | |||
76 | #include <linux/slab.h> | 73 | #include <linux/slab.h> |
77 | #include <linux/spi/spi.h> | 74 | #include <linux/spi/spi.h> |
78 | #include <linux/uaccess.h> | 75 | #include <linux/uaccess.h> |
76 | #include <linux/regulator/consumer.h> | ||
79 | 77 | ||
80 | /* SPI interface instruction set */ | 78 | /* SPI interface instruction set */ |
81 | #define INSTRUCTION_WRITE 0x02 | 79 | #define INSTRUCTION_WRITE 0x02 |
@@ -264,6 +262,8 @@ struct mcp251x_priv { | |||
264 | #define AFTER_SUSPEND_POWER 4 | 262 | #define AFTER_SUSPEND_POWER 4 |
265 | #define AFTER_SUSPEND_RESTART 8 | 263 | #define AFTER_SUSPEND_RESTART 8 |
266 | int restart_tx; | 264 | int restart_tx; |
265 | struct regulator *power; | ||
266 | struct regulator *transceiver; | ||
267 | }; | 267 | }; |
268 | 268 | ||
269 | #define MCP251X_IS(_model) \ | 269 | #define MCP251X_IS(_model) \ |
@@ -667,16 +667,25 @@ static int mcp251x_hw_probe(struct spi_device *spi) | |||
667 | return (st1 == 0x80 && st2 == 0x07) ? 1 : 0; | 667 | return (st1 == 0x80 && st2 == 0x07) ? 1 : 0; |
668 | } | 668 | } |
669 | 669 | ||
670 | static int mcp251x_power_enable(struct regulator *reg, int enable) | ||
671 | { | ||
672 | if (IS_ERR(reg)) | ||
673 | return 0; | ||
674 | |||
675 | if (enable) | ||
676 | return regulator_enable(reg); | ||
677 | else | ||
678 | return regulator_disable(reg); | ||
679 | } | ||
680 | |||
670 | static void mcp251x_open_clean(struct net_device *net) | 681 | static void mcp251x_open_clean(struct net_device *net) |
671 | { | 682 | { |
672 | struct mcp251x_priv *priv = netdev_priv(net); | 683 | struct mcp251x_priv *priv = netdev_priv(net); |
673 | struct spi_device *spi = priv->spi; | 684 | struct spi_device *spi = priv->spi; |
674 | struct mcp251x_platform_data *pdata = spi->dev.platform_data; | ||
675 | 685 | ||
676 | free_irq(spi->irq, priv); | 686 | free_irq(spi->irq, priv); |
677 | mcp251x_hw_sleep(spi); | 687 | mcp251x_hw_sleep(spi); |
678 | if (pdata->transceiver_enable) | 688 | mcp251x_power_enable(priv->transceiver, 0); |
679 | pdata->transceiver_enable(0); | ||
680 | close_candev(net); | 689 | close_candev(net); |
681 | } | 690 | } |
682 | 691 | ||
@@ -684,7 +693,6 @@ static int mcp251x_stop(struct net_device *net) | |||
684 | { | 693 | { |
685 | struct mcp251x_priv *priv = netdev_priv(net); | 694 | struct mcp251x_priv *priv = netdev_priv(net); |
686 | struct spi_device *spi = priv->spi; | 695 | struct spi_device *spi = priv->spi; |
687 | struct mcp251x_platform_data *pdata = spi->dev.platform_data; | ||
688 | 696 | ||
689 | close_candev(net); | 697 | close_candev(net); |
690 | 698 | ||
@@ -704,8 +712,7 @@ static int mcp251x_stop(struct net_device *net) | |||
704 | 712 | ||
705 | mcp251x_hw_sleep(spi); | 713 | mcp251x_hw_sleep(spi); |
706 | 714 | ||
707 | if (pdata->transceiver_enable) | 715 | mcp251x_power_enable(priv->transceiver, 0); |
708 | pdata->transceiver_enable(0); | ||
709 | 716 | ||
710 | priv->can.state = CAN_STATE_STOPPED; | 717 | priv->can.state = CAN_STATE_STOPPED; |
711 | 718 | ||
@@ -939,8 +946,7 @@ static int mcp251x_open(struct net_device *net) | |||
939 | } | 946 | } |
940 | 947 | ||
941 | mutex_lock(&priv->mcp_lock); | 948 | mutex_lock(&priv->mcp_lock); |
942 | if (pdata->transceiver_enable) | 949 | mcp251x_power_enable(priv->transceiver, 1); |
943 | pdata->transceiver_enable(1); | ||
944 | 950 | ||
945 | priv->force_quit = 0; | 951 | priv->force_quit = 0; |
946 | priv->tx_skb = NULL; | 952 | priv->tx_skb = NULL; |
@@ -956,8 +962,7 @@ static int mcp251x_open(struct net_device *net) | |||
956 | flags, DEVICE_NAME, priv); | 962 | flags, DEVICE_NAME, priv); |
957 | if (ret) { | 963 | if (ret) { |
958 | dev_err(&spi->dev, "failed to acquire irq %d\n", spi->irq); | 964 | dev_err(&spi->dev, "failed to acquire irq %d\n", spi->irq); |
959 | if (pdata->transceiver_enable) | 965 | mcp251x_power_enable(priv->transceiver, 0); |
960 | pdata->transceiver_enable(0); | ||
961 | close_candev(net); | 966 | close_candev(net); |
962 | goto open_unlock; | 967 | goto open_unlock; |
963 | } | 968 | } |
@@ -1026,6 +1031,19 @@ static int mcp251x_can_probe(struct spi_device *spi) | |||
1026 | CAN_CTRLMODE_LOOPBACK | CAN_CTRLMODE_LISTENONLY; | 1031 | CAN_CTRLMODE_LOOPBACK | CAN_CTRLMODE_LISTENONLY; |
1027 | priv->model = spi_get_device_id(spi)->driver_data; | 1032 | priv->model = spi_get_device_id(spi)->driver_data; |
1028 | priv->net = net; | 1033 | priv->net = net; |
1034 | |||
1035 | priv->power = devm_regulator_get(&spi->dev, "vdd"); | ||
1036 | priv->transceiver = devm_regulator_get(&spi->dev, "xceiver"); | ||
1037 | if ((PTR_ERR(priv->power) == -EPROBE_DEFER) || | ||
1038 | (PTR_ERR(priv->transceiver) == -EPROBE_DEFER)) { | ||
1039 | ret = -EPROBE_DEFER; | ||
1040 | goto error_power; | ||
1041 | } | ||
1042 | |||
1043 | ret = mcp251x_power_enable(priv->power, 1); | ||
1044 | if (ret) | ||
1045 | goto error_power; | ||
1046 | |||
1029 | spi_set_drvdata(spi, priv); | 1047 | spi_set_drvdata(spi, priv); |
1030 | 1048 | ||
1031 | priv->spi = spi; | 1049 | priv->spi = spi; |
@@ -1068,13 +1086,6 @@ static int mcp251x_can_probe(struct spi_device *spi) | |||
1068 | } | 1086 | } |
1069 | } | 1087 | } |
1070 | 1088 | ||
1071 | if (pdata->power_enable) | ||
1072 | pdata->power_enable(1); | ||
1073 | |||
1074 | /* Call out to platform specific setup */ | ||
1075 | if (pdata->board_specific_setup) | ||
1076 | pdata->board_specific_setup(spi); | ||
1077 | |||
1078 | SET_NETDEV_DEV(net, &spi->dev); | 1089 | SET_NETDEV_DEV(net, &spi->dev); |
1079 | 1090 | ||
1080 | /* Configure the SPI bus */ | 1091 | /* Configure the SPI bus */ |
@@ -1084,14 +1095,11 @@ static int mcp251x_can_probe(struct spi_device *spi) | |||
1084 | 1095 | ||
1085 | /* Here is OK to not lock the MCP, no one knows about it yet */ | 1096 | /* Here is OK to not lock the MCP, no one knows about it yet */ |
1086 | if (!mcp251x_hw_probe(spi)) { | 1097 | if (!mcp251x_hw_probe(spi)) { |
1087 | dev_info(&spi->dev, "Probe failed\n"); | 1098 | ret = -ENODEV; |
1088 | goto error_probe; | 1099 | goto error_probe; |
1089 | } | 1100 | } |
1090 | mcp251x_hw_sleep(spi); | 1101 | mcp251x_hw_sleep(spi); |
1091 | 1102 | ||
1092 | if (pdata->transceiver_enable) | ||
1093 | pdata->transceiver_enable(0); | ||
1094 | |||
1095 | ret = register_candev(net); | 1103 | ret = register_candev(net); |
1096 | if (ret) | 1104 | if (ret) |
1097 | goto error_probe; | 1105 | goto error_probe; |
@@ -1109,13 +1117,13 @@ error_rx_buf: | |||
1109 | if (!mcp251x_enable_dma) | 1117 | if (!mcp251x_enable_dma) |
1110 | kfree(priv->spi_tx_buf); | 1118 | kfree(priv->spi_tx_buf); |
1111 | error_tx_buf: | 1119 | error_tx_buf: |
1112 | free_candev(net); | ||
1113 | if (mcp251x_enable_dma) | 1120 | if (mcp251x_enable_dma) |
1114 | dma_free_coherent(&spi->dev, PAGE_SIZE, | 1121 | dma_free_coherent(&spi->dev, PAGE_SIZE, |
1115 | priv->spi_tx_buf, priv->spi_tx_dma); | 1122 | priv->spi_tx_buf, priv->spi_tx_dma); |
1123 | mcp251x_power_enable(priv->power, 0); | ||
1124 | error_power: | ||
1125 | free_candev(net); | ||
1116 | error_alloc: | 1126 | error_alloc: |
1117 | if (pdata->power_enable) | ||
1118 | pdata->power_enable(0); | ||
1119 | dev_err(&spi->dev, "probe failed\n"); | 1127 | dev_err(&spi->dev, "probe failed\n"); |
1120 | error_out: | 1128 | error_out: |
1121 | return ret; | 1129 | return ret; |
@@ -1123,12 +1131,10 @@ error_out: | |||
1123 | 1131 | ||
1124 | static int mcp251x_can_remove(struct spi_device *spi) | 1132 | static int mcp251x_can_remove(struct spi_device *spi) |
1125 | { | 1133 | { |
1126 | struct mcp251x_platform_data *pdata = spi->dev.platform_data; | ||
1127 | struct mcp251x_priv *priv = spi_get_drvdata(spi); | 1134 | struct mcp251x_priv *priv = spi_get_drvdata(spi); |
1128 | struct net_device *net = priv->net; | 1135 | struct net_device *net = priv->net; |
1129 | 1136 | ||
1130 | unregister_candev(net); | 1137 | unregister_candev(net); |
1131 | free_candev(net); | ||
1132 | 1138 | ||
1133 | if (mcp251x_enable_dma) { | 1139 | if (mcp251x_enable_dma) { |
1134 | dma_free_coherent(&spi->dev, PAGE_SIZE, | 1140 | dma_free_coherent(&spi->dev, PAGE_SIZE, |
@@ -1138,8 +1144,9 @@ static int mcp251x_can_remove(struct spi_device *spi) | |||
1138 | kfree(priv->spi_rx_buf); | 1144 | kfree(priv->spi_rx_buf); |
1139 | } | 1145 | } |
1140 | 1146 | ||
1141 | if (pdata->power_enable) | 1147 | mcp251x_power_enable(priv->power, 0); |
1142 | pdata->power_enable(0); | 1148 | |
1149 | free_candev(net); | ||
1143 | 1150 | ||
1144 | return 0; | 1151 | return 0; |
1145 | } | 1152 | } |
@@ -1149,7 +1156,6 @@ static int mcp251x_can_remove(struct spi_device *spi) | |||
1149 | static int mcp251x_can_suspend(struct device *dev) | 1156 | static int mcp251x_can_suspend(struct device *dev) |
1150 | { | 1157 | { |
1151 | struct spi_device *spi = to_spi_device(dev); | 1158 | struct spi_device *spi = to_spi_device(dev); |
1152 | struct mcp251x_platform_data *pdata = spi->dev.platform_data; | ||
1153 | struct mcp251x_priv *priv = spi_get_drvdata(spi); | 1159 | struct mcp251x_priv *priv = spi_get_drvdata(spi); |
1154 | struct net_device *net = priv->net; | 1160 | struct net_device *net = priv->net; |
1155 | 1161 | ||
@@ -1163,15 +1169,14 @@ static int mcp251x_can_suspend(struct device *dev) | |||
1163 | netif_device_detach(net); | 1169 | netif_device_detach(net); |
1164 | 1170 | ||
1165 | mcp251x_hw_sleep(spi); | 1171 | mcp251x_hw_sleep(spi); |
1166 | if (pdata->transceiver_enable) | 1172 | mcp251x_power_enable(priv->transceiver, 0); |
1167 | pdata->transceiver_enable(0); | ||
1168 | priv->after_suspend = AFTER_SUSPEND_UP; | 1173 | priv->after_suspend = AFTER_SUSPEND_UP; |
1169 | } else { | 1174 | } else { |
1170 | priv->after_suspend = AFTER_SUSPEND_DOWN; | 1175 | priv->after_suspend = AFTER_SUSPEND_DOWN; |
1171 | } | 1176 | } |
1172 | 1177 | ||
1173 | if (pdata->power_enable) { | 1178 | if (!IS_ERR(priv->power)) { |
1174 | pdata->power_enable(0); | 1179 | regulator_disable(priv->power); |
1175 | priv->after_suspend |= AFTER_SUSPEND_POWER; | 1180 | priv->after_suspend |= AFTER_SUSPEND_POWER; |
1176 | } | 1181 | } |
1177 | 1182 | ||
@@ -1181,16 +1186,14 @@ static int mcp251x_can_suspend(struct device *dev) | |||
1181 | static int mcp251x_can_resume(struct device *dev) | 1186 | static int mcp251x_can_resume(struct device *dev) |
1182 | { | 1187 | { |
1183 | struct spi_device *spi = to_spi_device(dev); | 1188 | struct spi_device *spi = to_spi_device(dev); |
1184 | struct mcp251x_platform_data *pdata = spi->dev.platform_data; | ||
1185 | struct mcp251x_priv *priv = spi_get_drvdata(spi); | 1189 | struct mcp251x_priv *priv = spi_get_drvdata(spi); |
1186 | 1190 | ||
1187 | if (priv->after_suspend & AFTER_SUSPEND_POWER) { | 1191 | if (priv->after_suspend & AFTER_SUSPEND_POWER) { |
1188 | pdata->power_enable(1); | 1192 | mcp251x_power_enable(priv->power, 1); |
1189 | queue_work(priv->wq, &priv->restart_work); | 1193 | queue_work(priv->wq, &priv->restart_work); |
1190 | } else { | 1194 | } else { |
1191 | if (priv->after_suspend & AFTER_SUSPEND_UP) { | 1195 | if (priv->after_suspend & AFTER_SUSPEND_UP) { |
1192 | if (pdata->transceiver_enable) | 1196 | mcp251x_power_enable(priv->transceiver, 1); |
1193 | pdata->transceiver_enable(1); | ||
1194 | queue_work(priv->wq, &priv->restart_work); | 1197 | queue_work(priv->wq, &priv->restart_work); |
1195 | } else { | 1198 | } else { |
1196 | priv->after_suspend = 0; | 1199 | priv->after_suspend = 0; |