GroupStateStore.cpp 2.0 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586
  1. #include <GroupStateStore.h>
  2. #include <MiLightRemoteConfig.h>
  3. GroupStateStore::GroupStateStore(const size_t maxSize, const size_t flushRate)
  4. : cache(GroupStateCache(maxSize)),
  5. flushRate(flushRate),
  6. lastFlush(0)
  7. { }
  8. GroupState& GroupStateStore::get(const BulbId& id) {
  9. GroupState* state = cache.get(id);
  10. if (state == NULL) {
  11. trackEviction();
  12. GroupState loadedState = GroupState::defaultState(id.deviceType);
  13. persistence.get(id, loadedState);
  14. state = cache.set(id, loadedState);
  15. }
  16. return *state;
  17. }
  18. GroupState& GroupStateStore::set(const BulbId &id, const GroupState& state) {
  19. GroupState& storedState = get(id);
  20. storedState = state;
  21. if (id.groupId == 0) {
  22. const MiLightRemoteConfig* remote = MiLightRemoteConfig::fromType(id.deviceType);
  23. BulbId individualBulb(id);
  24. for (size_t i = 1; i < remote->numGroups; i++) {
  25. individualBulb.groupId = i;
  26. set(individualBulb, state);
  27. }
  28. }
  29. return storedState;
  30. }
  31. void GroupStateStore::trackEviction() {
  32. if (cache.isFull()) {
  33. evictedIds.add(cache.getLru());
  34. }
  35. }
  36. bool GroupStateStore::flush() {
  37. ListNode<GroupCacheNode*>* curr = cache.getHead();
  38. bool anythingFlushed = false;
  39. while (curr != NULL && curr->data->state.isDirty() && !anythingFlushed) {
  40. persistence.set(curr->data->id, curr->data->state);
  41. curr->data->state.clearDirty();
  42. #ifdef STATE_DEBUG
  43. BulbId bulbId = curr->data->id;
  44. printf(
  45. "Flushing dirty state for 0x%04X / %d / %s\n",
  46. bulbId.deviceId,
  47. bulbId.groupId,
  48. MiLightRemoteConfig::fromType(bulbId.deviceType)->name.c_str()
  49. );
  50. #endif
  51. curr = curr->next;
  52. anythingFlushed = true;
  53. }
  54. while (evictedIds.size() > 0 && !anythingFlushed) {
  55. persistence.clear(evictedIds.shift());
  56. anythingFlushed = true;
  57. }
  58. return anythingFlushed;
  59. }
  60. void GroupStateStore::limitedFlush() {
  61. unsigned long now = millis();
  62. if ((lastFlush + flushRate) < now) {
  63. if (flush()) {
  64. lastFlush = now;
  65. }
  66. }
  67. }