stm32-lptimer-trigger.c 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153
  1. // SPDX-License-Identifier: GPL-2.0
  2. /*
  3. * STM32 Low-Power Timer Trigger driver
  4. *
  5. * Copyright (C) STMicroelectronics 2017
  6. *
  7. * Author: Fabrice Gasnier <fabrice.gasnier@st.com>.
  8. *
  9. * Inspired by Benjamin Gaignard's stm32-timer-trigger driver
  10. */
  11. #include <linux/export.h>
  12. #include <linux/iio/timer/stm32-lptim-trigger.h>
  13. #include <linux/mfd/stm32-lptimer.h>
  14. #include <linux/mod_devicetable.h>
  15. #include <linux/module.h>
  16. #include <linux/platform_device.h>
  17. #include <linux/property.h>
  18. /* Maximum triggers + one trailing null entry to indicate the end of array */
  19. #define MAX_TRIGGERS 3
  20. struct stm32_lptim_cfg {
  21. const char * const (*triggers)[MAX_TRIGGERS];
  22. unsigned int nb_triggers;
  23. };
  24. /* List Low-Power Timer triggers for H7, MP13, MP15 */
  25. static const char * const stm32_lptim_triggers[][MAX_TRIGGERS] = {
  26. { LPTIM1_OUT,},
  27. { LPTIM2_OUT,},
  28. { LPTIM3_OUT,},
  29. };
  30. /* List Low-Power Timer triggers for STM32MP25 */
  31. static const char * const stm32mp25_lptim_triggers[][MAX_TRIGGERS] = {
  32. { LPTIM1_CH1, LPTIM1_CH2, },
  33. { LPTIM2_CH1, LPTIM2_CH2, },
  34. { LPTIM3_CH1,},
  35. { LPTIM4_CH1,},
  36. { LPTIM5_OUT,},
  37. };
  38. static const struct stm32_lptim_cfg stm32mp15_lptim_cfg = {
  39. .triggers = stm32_lptim_triggers,
  40. .nb_triggers = ARRAY_SIZE(stm32_lptim_triggers),
  41. };
  42. static const struct stm32_lptim_cfg stm32mp25_lptim_cfg = {
  43. .triggers = stm32mp25_lptim_triggers,
  44. .nb_triggers = ARRAY_SIZE(stm32mp25_lptim_triggers),
  45. };
  46. struct stm32_lptim_trigger {
  47. struct device *dev;
  48. const char * const *triggers;
  49. };
  50. static int stm32_lptim_validate_device(struct iio_trigger *trig,
  51. struct iio_dev *indio_dev)
  52. {
  53. if (indio_dev->modes & INDIO_HARDWARE_TRIGGERED)
  54. return 0;
  55. return -EINVAL;
  56. }
  57. static const struct iio_trigger_ops stm32_lptim_trigger_ops = {
  58. .validate_device = stm32_lptim_validate_device,
  59. };
  60. /**
  61. * is_stm32_lptim_trigger
  62. * @trig: trigger to be checked
  63. *
  64. * return true if the trigger is a valid STM32 IIO Low-Power Timer Trigger
  65. * either return false
  66. */
  67. bool is_stm32_lptim_trigger(struct iio_trigger *trig)
  68. {
  69. return (trig->ops == &stm32_lptim_trigger_ops);
  70. }
  71. EXPORT_SYMBOL(is_stm32_lptim_trigger);
  72. static int stm32_lptim_setup_trig(struct stm32_lptim_trigger *priv)
  73. {
  74. const char * const *cur = priv->triggers;
  75. int ret;
  76. while (cur && *cur) {
  77. struct iio_trigger *trig;
  78. trig = devm_iio_trigger_alloc(priv->dev, "%s", *cur);
  79. if (!trig)
  80. return -ENOMEM;
  81. trig->dev.parent = priv->dev->parent;
  82. trig->ops = &stm32_lptim_trigger_ops;
  83. iio_trigger_set_drvdata(trig, priv);
  84. ret = devm_iio_trigger_register(priv->dev, trig);
  85. if (ret)
  86. return ret;
  87. cur++;
  88. }
  89. return 0;
  90. }
  91. static int stm32_lptim_trigger_probe(struct platform_device *pdev)
  92. {
  93. struct stm32_lptim_trigger *priv;
  94. struct stm32_lptim_cfg const *lptim_cfg;
  95. u32 index;
  96. priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
  97. if (!priv)
  98. return -ENOMEM;
  99. if (device_property_read_u32(&pdev->dev, "reg", &index))
  100. return -EINVAL;
  101. lptim_cfg = device_get_match_data(&pdev->dev);
  102. if (index >= lptim_cfg->nb_triggers)
  103. return -EINVAL;
  104. priv->dev = &pdev->dev;
  105. priv->triggers = lptim_cfg->triggers[index];
  106. return stm32_lptim_setup_trig(priv);
  107. }
  108. static const struct of_device_id stm32_lptim_trig_of_match[] = {
  109. { .compatible = "st,stm32-lptimer-trigger", .data = &stm32mp15_lptim_cfg },
  110. { .compatible = "st,stm32mp25-lptimer-trigger", .data = &stm32mp25_lptim_cfg},
  111. { }
  112. };
  113. MODULE_DEVICE_TABLE(of, stm32_lptim_trig_of_match);
  114. static struct platform_driver stm32_lptim_trigger_driver = {
  115. .probe = stm32_lptim_trigger_probe,
  116. .driver = {
  117. .name = "stm32-lptimer-trigger",
  118. .of_match_table = stm32_lptim_trig_of_match,
  119. },
  120. };
  121. module_platform_driver(stm32_lptim_trigger_driver);
  122. MODULE_AUTHOR("Fabrice Gasnier <fabrice.gasnier@st.com>");
  123. MODULE_ALIAS("platform:stm32-lptimer-trigger");
  124. MODULE_DESCRIPTION("STMicroelectronics STM32 LPTIM trigger driver");
  125. MODULE_LICENSE("GPL v2");