pvr_params.c 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147
  1. // SPDX-License-Identifier: GPL-2.0-only OR MIT
  2. /* Copyright (c) 2023 Imagination Technologies Ltd. */
  3. #include "pvr_params.h"
  4. #include <linux/cache.h>
  5. #include <linux/moduleparam.h>
  6. static struct pvr_device_params pvr_device_param_defaults __read_mostly = {
  7. #define X(type_, name_, value_, desc_, ...) .name_ = (value_),
  8. PVR_DEVICE_PARAMS
  9. #undef X
  10. };
  11. #define PVR_DEVICE_PARAM_NAMED(name_, type_, desc_) \
  12. module_param_named(name_, pvr_device_param_defaults.name_, type_, \
  13. 0400); \
  14. MODULE_PARM_DESC(name_, desc_);
  15. /*
  16. * This list of defines must contain every type specified in "pvr_params.h" as
  17. * ``PVR_PARAM_TYPE_*_C``.
  18. */
  19. #define PVR_PARAM_TYPE_X32_MODPARAM uint
  20. #define X(type_, name_, value_, desc_, ...) \
  21. PVR_DEVICE_PARAM_NAMED(name_, PVR_PARAM_TYPE_##type_##_MODPARAM, desc_);
  22. PVR_DEVICE_PARAMS
  23. #undef X
  24. int
  25. pvr_device_params_init(struct pvr_device_params *params)
  26. {
  27. /*
  28. * If heap-allocated parameters are added in the future (e.g.
  29. * modparam's charp type), they must be handled specially here (via
  30. * kstrdup() in the case of charp). Since that's not necessary yet,
  31. * a straight copy will do for now. This change will also require a
  32. * pvr_device_params_fini() function to free any heap-allocated copies.
  33. */
  34. *params = pvr_device_param_defaults;
  35. return 0;
  36. }
  37. #if defined(CONFIG_DEBUG_FS)
  38. #include "pvr_device.h"
  39. #include <linux/dcache.h>
  40. #include <linux/debugfs.h>
  41. #include <linux/export.h>
  42. #include <linux/fs.h>
  43. #include <linux/stddef.h>
  44. /*
  45. * This list of defines must contain every type specified in "pvr_params.h" as
  46. * ``PVR_PARAM_TYPE_*_C``.
  47. */
  48. #define PVR_PARAM_TYPE_X32_FMT "0x%08llx"
  49. #define X_SET(name_, mode_) X_SET_##mode_(name_)
  50. #define X_SET_DEF(name_, update_, mode_) X_SET_DEF_##mode_(name_, update_)
  51. #define X_SET_RO(name_) NULL
  52. #define X_SET_RW(name_) __pvr_device_param_##name_##set
  53. #define X_SET_DEF_RO(name_, update_)
  54. #define X_SET_DEF_RW(name_, update_) \
  55. static int \
  56. X_SET_RW(name_)(void *data, u64 val) \
  57. { \
  58. struct pvr_device *pvr_dev = data; \
  59. /* This is not just (update_) to suppress -Waddress. */ \
  60. if ((void *)(update_) != NULL) \
  61. (update_)(pvr_dev, pvr_dev->params.name_, val); \
  62. pvr_dev->params.name_ = val; \
  63. return 0; \
  64. }
  65. #define X(type_, name_, value_, desc_, mode_, update_) \
  66. static int \
  67. __pvr_device_param_##name_##_get(void *data, u64 *val) \
  68. { \
  69. struct pvr_device *pvr_dev = data; \
  70. *val = pvr_dev->params.name_; \
  71. return 0; \
  72. } \
  73. X_SET_DEF(name_, update_, mode_) \
  74. static int \
  75. __pvr_device_param_##name_##_open(struct inode *inode, \
  76. struct file *file) \
  77. { \
  78. __simple_attr_check_format(PVR_PARAM_TYPE_##type_##_FMT, \
  79. 0ull); \
  80. return simple_attr_open(inode, file, \
  81. __pvr_device_param_##name_##_get, \
  82. X_SET(name_, mode_), \
  83. PVR_PARAM_TYPE_##type_##_FMT); \
  84. }
  85. PVR_DEVICE_PARAMS
  86. #undef X
  87. #undef X_SET
  88. #undef X_SET_RO
  89. #undef X_SET_RW
  90. #undef X_SET_DEF
  91. #undef X_SET_DEF_RO
  92. #undef X_SET_DEF_RW
  93. static struct {
  94. #define X(type_, name_, value_, desc_, mode_, update_) \
  95. const struct file_operations name_;
  96. PVR_DEVICE_PARAMS
  97. #undef X
  98. } pvr_device_param_debugfs_fops = {
  99. #define X(type_, name_, value_, desc_, mode_, update_) \
  100. .name_ = { \
  101. .owner = THIS_MODULE, \
  102. .open = __pvr_device_param_##name_##_open, \
  103. .release = simple_attr_release, \
  104. .read = simple_attr_read, \
  105. .write = simple_attr_write, \
  106. .llseek = generic_file_llseek, \
  107. },
  108. PVR_DEVICE_PARAMS
  109. #undef X
  110. };
  111. void
  112. pvr_params_debugfs_init(struct pvr_device *pvr_dev, struct dentry *dir)
  113. {
  114. #define X_MODE(mode_) X_MODE_##mode_
  115. #define X_MODE_RO 0400
  116. #define X_MODE_RW 0600
  117. #define X(type_, name_, value_, desc_, mode_, update_) \
  118. debugfs_create_file(#name_, X_MODE(mode_), dir, pvr_dev, \
  119. &pvr_device_param_debugfs_fops.name_);
  120. PVR_DEVICE_PARAMS
  121. #undef X
  122. #undef X_MODE
  123. #undef X_MODE_RO
  124. #undef X_MODE_RW
  125. }
  126. #endif