diff options
author | Davide Ciminaghi <ciminaghi@gnudd.com> | 2012-11-09 09:19:59 -0500 |
---|---|---|
committer | Samuel Ortiz <sameo@linux.intel.com> | 2012-11-20 06:21:16 -0500 |
commit | dba6c1aeea4dd0e251e41c3f585abf4a06a4f057 (patch) | |
tree | ac7830cb39625b8dd2be1e82f10fd1430bc22098 | |
parent | e885ba298098959d03c58d946c6fad8f8ed4a1c7 (diff) |
mfd: sta2x11-mfd: Add scr (otp registers) platform driver
Signed-off-by: Davide Ciminaghi <ciminaghi@gnudd.com>
Acked-by: Alessandro Rubini <rubini@gnudd.com>
Signed-off-by: Samuel Ortiz <sameo@linux.intel.com>
-rw-r--r-- | drivers/mfd/sta2x11-mfd.c | 52 | ||||
-rw-r--r-- | include/linux/mfd/sta2x11-mfd.h | 7 |
2 files changed, 58 insertions, 1 deletions
diff --git a/drivers/mfd/sta2x11-mfd.c b/drivers/mfd/sta2x11-mfd.c index da65839f1d86..7365f0f89df2 100644 --- a/drivers/mfd/sta2x11-mfd.c +++ b/drivers/mfd/sta2x11-mfd.c | |||
@@ -175,10 +175,16 @@ static void sta2x11_regmap_unlock(void *__lock) | |||
175 | spin_unlock(lock); | 175 | spin_unlock(lock); |
176 | } | 176 | } |
177 | 177 | ||
178 | /* OTP (one time programmable registers do not require locking */ | ||
179 | static void sta2x11_regmap_nolock(void *__lock) | ||
180 | { | ||
181 | } | ||
182 | |||
178 | static const char *sta2x11_mfd_names[sta2x11_n_mfd_plat_devs] = { | 183 | static const char *sta2x11_mfd_names[sta2x11_n_mfd_plat_devs] = { |
179 | [sta2x11_sctl] = STA2X11_MFD_SCTL_NAME, | 184 | [sta2x11_sctl] = STA2X11_MFD_SCTL_NAME, |
180 | [sta2x11_apbreg] = STA2X11_MFD_APBREG_NAME, | 185 | [sta2x11_apbreg] = STA2X11_MFD_APBREG_NAME, |
181 | [sta2x11_apb_soc_regs] = STA2X11_MFD_APB_SOC_REGS_NAME, | 186 | [sta2x11_apb_soc_regs] = STA2X11_MFD_APB_SOC_REGS_NAME, |
187 | [sta2x11_scr] = STA2X11_MFD_SCR_NAME, | ||
182 | }; | 188 | }; |
183 | 189 | ||
184 | static bool sta2x11_sctl_writeable_reg(struct device *dev, unsigned int reg) | 190 | static bool sta2x11_sctl_writeable_reg(struct device *dev, unsigned int reg) |
@@ -196,6 +202,28 @@ static struct regmap_config sta2x11_sctl_regmap_config = { | |||
196 | .writeable_reg = sta2x11_sctl_writeable_reg, | 202 | .writeable_reg = sta2x11_sctl_writeable_reg, |
197 | }; | 203 | }; |
198 | 204 | ||
205 | static bool sta2x11_scr_readable_reg(struct device *dev, unsigned int reg) | ||
206 | { | ||
207 | return (reg == STA2X11_SECR_CR) || | ||
208 | __reg_within_range(reg, STA2X11_SECR_FVR0, STA2X11_SECR_FVR1); | ||
209 | } | ||
210 | |||
211 | static bool sta2x11_scr_writeable_reg(struct device *dev, unsigned int reg) | ||
212 | { | ||
213 | return false; | ||
214 | } | ||
215 | |||
216 | static struct regmap_config sta2x11_scr_regmap_config = { | ||
217 | .reg_bits = 32, | ||
218 | .reg_stride = 4, | ||
219 | .val_bits = 32, | ||
220 | .lock = sta2x11_regmap_nolock, | ||
221 | .unlock = sta2x11_regmap_nolock, | ||
222 | .max_register = STA2X11_SECR_FVR1, | ||
223 | .readable_reg = sta2x11_scr_readable_reg, | ||
224 | .writeable_reg = sta2x11_scr_writeable_reg, | ||
225 | }; | ||
226 | |||
199 | static bool sta2x11_apbreg_readable_reg(struct device *dev, unsigned int reg) | 227 | static bool sta2x11_apbreg_readable_reg(struct device *dev, unsigned int reg) |
200 | { | 228 | { |
201 | /* Two blocks (CAN and MLB, SARAC) 0x100 bytes apart */ | 229 | /* Two blocks (CAN and MLB, SARAC) 0x100 bytes apart */ |
@@ -279,9 +307,10 @@ sta2x11_mfd_regmap_configs[sta2x11_n_mfd_plat_devs] = { | |||
279 | [sta2x11_sctl] = &sta2x11_sctl_regmap_config, | 307 | [sta2x11_sctl] = &sta2x11_sctl_regmap_config, |
280 | [sta2x11_apbreg] = &sta2x11_apbreg_regmap_config, | 308 | [sta2x11_apbreg] = &sta2x11_apbreg_regmap_config, |
281 | [sta2x11_apb_soc_regs] = &sta2x11_apb_soc_regs_regmap_config, | 309 | [sta2x11_apb_soc_regs] = &sta2x11_apb_soc_regs_regmap_config, |
310 | [sta2x11_scr] = &sta2x11_scr_regmap_config, | ||
282 | }; | 311 | }; |
283 | 312 | ||
284 | /* Probe for the three platform devices */ | 313 | /* Probe for the four platform devices */ |
285 | 314 | ||
286 | static int sta2x11_mfd_platform_probe(struct platform_device *dev, | 315 | static int sta2x11_mfd_platform_probe(struct platform_device *dev, |
287 | enum sta2x11_mfd_plat_dev index) | 316 | enum sta2x11_mfd_plat_dev index) |
@@ -339,6 +368,11 @@ static int sta2x11_apb_soc_regs_probe(struct platform_device *dev) | |||
339 | return sta2x11_mfd_platform_probe(dev, sta2x11_apb_soc_regs); | 368 | return sta2x11_mfd_platform_probe(dev, sta2x11_apb_soc_regs); |
340 | } | 369 | } |
341 | 370 | ||
371 | static int sta2x11_scr_probe(struct platform_device *dev) | ||
372 | { | ||
373 | return sta2x11_mfd_platform_probe(dev, sta2x11_scr); | ||
374 | } | ||
375 | |||
342 | /* The three platform drivers */ | 376 | /* The three platform drivers */ |
343 | static struct platform_driver sta2x11_sctl_platform_driver = { | 377 | static struct platform_driver sta2x11_sctl_platform_driver = { |
344 | .driver = { | 378 | .driver = { |
@@ -382,6 +416,21 @@ static int __init sta2x11_apb_soc_regs_init(void) | |||
382 | return platform_driver_register(&sta2x11_apb_soc_regs_platform_driver); | 416 | return platform_driver_register(&sta2x11_apb_soc_regs_platform_driver); |
383 | } | 417 | } |
384 | 418 | ||
419 | static struct platform_driver sta2x11_scr_platform_driver = { | ||
420 | .driver = { | ||
421 | .name = STA2X11_MFD_SCR_NAME, | ||
422 | .owner = THIS_MODULE, | ||
423 | }, | ||
424 | .probe = sta2x11_scr_probe, | ||
425 | }; | ||
426 | |||
427 | static int __init sta2x11_scr_init(void) | ||
428 | { | ||
429 | pr_info("%s\n", __func__); | ||
430 | return platform_driver_register(&sta2x11_scr_platform_driver); | ||
431 | } | ||
432 | |||
433 | |||
385 | /* | 434 | /* |
386 | * What follows are the PCI devices that host the above pdevs. | 435 | * What follows are the PCI devices that host the above pdevs. |
387 | * Each logic block is 4kB and they are all consecutive: we use this info. | 436 | * Each logic block is 4kB and they are all consecutive: we use this info. |
@@ -631,6 +680,7 @@ static int __init sta2x11_mfd_init(void) | |||
631 | subsys_initcall(sta2x11_apbreg_init); | 680 | subsys_initcall(sta2x11_apbreg_init); |
632 | subsys_initcall(sta2x11_sctl_init); | 681 | subsys_initcall(sta2x11_sctl_init); |
633 | subsys_initcall(sta2x11_apb_soc_regs_init); | 682 | subsys_initcall(sta2x11_apb_soc_regs_init); |
683 | subsys_initcall(sta2x11_scr_init); | ||
634 | rootfs_initcall(sta2x11_mfd_init); | 684 | rootfs_initcall(sta2x11_mfd_init); |
635 | 685 | ||
636 | MODULE_LICENSE("GPL v2"); | 686 | MODULE_LICENSE("GPL v2"); |
diff --git a/include/linux/mfd/sta2x11-mfd.h b/include/linux/mfd/sta2x11-mfd.h index 058de2bacf76..08cad95758c6 100644 --- a/include/linux/mfd/sta2x11-mfd.h +++ b/include/linux/mfd/sta2x11-mfd.h | |||
@@ -482,6 +482,13 @@ u32 sta2x11_apb_soc_regs_mask(struct pci_dev *pdev, u32 reg, u32 mask, u32 val) | |||
482 | #define COMPENSATION_REG3 0x3cc | 482 | #define COMPENSATION_REG3 0x3cc |
483 | #define TEST_CTL_REG 0x3d0 | 483 | #define TEST_CTL_REG 0x3d0 |
484 | 484 | ||
485 | /* | ||
486 | * SECR (OTP) registers | ||
487 | */ | ||
488 | #define STA2X11_SECR_CR 0x00 | ||
489 | #define STA2X11_SECR_FVR0 0x10 | ||
490 | #define STA2X11_SECR_FVR1 0x14 | ||
491 | |||
485 | extern int sta2x11_mfd_get_regs_data(struct platform_device *pdev, | 492 | extern int sta2x11_mfd_get_regs_data(struct platform_device *pdev, |
486 | enum sta2x11_mfd_plat_dev index, | 493 | enum sta2x11_mfd_plat_dev index, |
487 | void __iomem **regs, | 494 | void __iomem **regs, |