Fork of the espurna firmware for `mhsw` switches
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.

134 lines
3.1 KiB

  1. /*
  2. TUYA MODULE
  3. Copyright (C) 2019 by Maxim Prokhorov <prokhorov dot max at outlook dot com>
  4. */
  5. #pragma once
  6. #include <cstdint>
  7. #include <vector>
  8. #include "tuya_types.h"
  9. #include "tuya_transport.h"
  10. namespace Tuya {
  11. class DataFrame {
  12. public:
  13. using container = std::vector<uint8_t>;
  14. using const_iterator = container::const_iterator;
  15. DataFrame(DataFrame& rhs) = delete;
  16. ~DataFrame() = default;
  17. DataFrame(DataFrame&& rhs) = default;
  18. DataFrame(uint8_t command) :
  19. command(command),
  20. length(0)
  21. {}
  22. DataFrame(Command command) :
  23. DataFrame(static_cast<uint8_t>(command))
  24. {}
  25. DataFrame(Command command, uint16_t length,
  26. const const_iterator begin,
  27. const const_iterator end) :
  28. command(static_cast<uint8_t>(command)),
  29. length(length),
  30. _begin(begin),
  31. _end(end)
  32. {}
  33. DataFrame(uint8_t version, uint8_t command, uint16_t length,
  34. const const_iterator begin,
  35. const const_iterator end) :
  36. version(version),
  37. command(command),
  38. length(length),
  39. _begin(begin),
  40. _end(end)
  41. {}
  42. DataFrame(Command command, std::initializer_list<uint8_t> data) :
  43. command(static_cast<uint8_t>(command)),
  44. length(data.size()),
  45. _data(data),
  46. _begin(_data.cbegin()),
  47. _end(_data.cend())
  48. {}
  49. DataFrame(Command command, std::vector<uint8_t>&& data) :
  50. command(static_cast<uint8_t>(command)),
  51. length(data.size()),
  52. _data(std::move(data)),
  53. _begin(_data.cbegin()),
  54. _end(_data.cend())
  55. {}
  56. DataFrame(const_iterator iter) :
  57. version(iter[2]),
  58. command(iter[3]),
  59. length((iter[4] << 8) + iter[5]),
  60. _begin(iter + 6),
  61. _end(iter + 6 + length)
  62. {}
  63. DataFrame(const Transport& input) :
  64. DataFrame(input.cbegin())
  65. {}
  66. bool commandEquals(Command command) const {
  67. return (static_cast<uint8_t>(command) == this->command);
  68. }
  69. const_iterator cbegin() const {
  70. return _begin;
  71. };
  72. const_iterator cend() const {
  73. return _end;
  74. };
  75. uint8_t operator[](size_t i) const {
  76. if (!length) return 0;
  77. return _begin[i];
  78. }
  79. container serialize() const {
  80. container result;
  81. result.reserve(6 + length);
  82. result.assign({
  83. version, command,
  84. uint8_t(length >> 8),
  85. uint8_t(length & 0xff)
  86. });
  87. if (length && (_begin != _end)) {
  88. result.insert(result.end(), _begin, _end);
  89. }
  90. return result;
  91. }
  92. uint8_t version = 0;
  93. uint8_t command = 0;
  94. uint16_t length = 0;
  95. protected:
  96. container _data;
  97. const_iterator _begin;
  98. const_iterator _end;
  99. };
  100. }