readout software for 2 channels [0 and 1] of the tdc-gpx2 board with raspberry pi 3B SPI readout. This code is a fork of the original design by marvin.peter@physik.uni-giessen.de https://github.com/marvin5300/tdc-gpx2_software
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

128 lines
3.1 KiB

1 year ago
  1. #ifndef GPIO_H
  2. #define GPIO_H
  3. #include <vector>
  4. #include <mutex>
  5. #include <shared_mutex>
  6. #include <chrono>
  7. #include <future>
  8. #include <map>
  9. #include <memory>
  10. #include <linux/gpio.h>
  11. #include <gpiod.h>
  12. // TODO: check correctness of mutex'
  13. // TODO: implement and check init, step, shutdown, write functions
  14. enum class PinBias : std::uint8_t {
  15. OpenDrain = 0x01,
  16. OpenSource = 0x02,
  17. ActiveLow = 0x04,
  18. PullDown = 0x10,
  19. PullUp = 0x20
  20. };
  21. class gpio
  22. {
  23. public:
  24. constexpr static auto standard_timeout = std::chrono::seconds{10};
  25. struct event
  26. {
  27. enum Type
  28. {
  29. Invalid,
  30. Rising,
  31. Falling
  32. } type{ Invalid };
  33. std::size_t pin{};
  34. timespec ts;
  35. inline operator bool()
  36. {
  37. return type != Invalid;
  38. }
  39. };
  40. struct setting
  41. {
  42. [[nodiscard]] auto matches(const event& e) const -> bool;
  43. std::vector<unsigned> gpio_pins;
  44. };
  45. class callback
  46. {
  47. friend class gpio;
  48. public:
  49. [[nodiscard]] auto wait_async(std::chrono::milliseconds timeout)->std::future<event>;
  50. [[nodiscard]] auto wait(std::chrono::milliseconds timeout)->event;
  51. [[nodiscard]] auto write_async(const event& e)->std::future<bool>;
  52. [[nodiscard]] auto write(const event& e) -> bool;
  53. [[nodiscard]] auto read(unsigned pin_num) -> int;
  54. callback(setting s, gpio& handler);
  55. private:
  56. void notify(const event& e);
  57. setting m_setting{};
  58. event m_event {};
  59. std::condition_variable m_wait{};
  60. std::mutex m_wait_mutex{};
  61. std::shared_mutex m_access_mutex{};
  62. gpio& m_handler;
  63. };
  64. gpio(std::string consumer = "gpio", std::string chipname = "gpiochip0")
  65. : m_consumer{std::move(consumer)}
  66. , m_chipname{std::move(chipname)}
  67. {};
  68. virtual ~gpio();
  69. void start();
  70. void stop();
  71. void join();
  72. [[nodiscard]] auto list_callback(setting s)->std::shared_ptr<callback>;
  73. void remove_callback(std::size_t id);
  74. private:
  75. [[nodiscard]] auto setup() -> int;
  76. [[nodiscard]] auto step() -> int;
  77. [[nodiscard]] auto shutdown() -> int;
  78. [[nodiscard]] auto write(const event& e) -> bool;
  79. [[nodiscard]] auto read(unsigned pin_num) -> int;
  80. void notify_all(event e);
  81. std::string m_consumer;
  82. std::string m_chipname;
  83. const timespec c_wait_timeout{1,0};
  84. //std::shared_ptr<::gpiod_chip> chip{nullptr};
  85. //std::shared_ptr<::gpiod_line_bulk> lines{nullptr};
  86. gpiod_chip* chip{nullptr};
  87. gpiod_line_bulk* lines{nullptr};
  88. std::map< unsigned, gpiod_line* > other_lines{}; // map of other initialized lines which are requested but have no active event listening going on
  89. std::vector<unsigned> pins_used_by_listeners{};
  90. //inline static std::size_t global_id_counter{ 0 };
  91. std::size_t global_id_counter{ 0 };
  92. std::map < std::size_t, std::shared_ptr<callback> > m_callback{};
  93. std::future<int> m_result{};
  94. std::chrono::microseconds m_timeout{ 10 };
  95. std::atomic<bool> m_run{ true };
  96. std::vector<setting> m_settings{};
  97. };
  98. #endif // GPIO_H