S&B Volcano vaporizer remote control with Pi Pico W
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.

ring.c 2.2KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192
  1. /*
  2. * ring.c
  3. *
  4. * Copyright (c) 2023 Thomas Buck (thomas@xythobuz.de)
  5. *
  6. * This program is free software: you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License as published by
  8. * the Free Software Foundation, either version 3 of the License, or
  9. * (at your option) any later version.
  10. *
  11. * This program is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. * GNU General Public License for more details.
  15. *
  16. * See <http://www.gnu.org/licenses/>.
  17. */
  18. #include "config.h"
  19. #include "ring.h"
  20. void rb_add(struct ring_buffer *rb, const uint8_t *data, size_t length) {
  21. for (size_t i = 0; i < length; i++) {
  22. rb->buffer[rb->head] = data[i];
  23. if (rb->full && (++(rb->tail) == rb->size)) {
  24. rb->tail = 0;
  25. }
  26. if (++(rb->head) == rb->size) {
  27. rb->head = 0;
  28. }
  29. rb->full = ((rb->head) == (rb->tail));
  30. }
  31. }
  32. size_t rb_len(struct ring_buffer *rb) {
  33. if (rb->head == rb->tail) {
  34. if (rb->full) {
  35. return rb->size;
  36. } else {
  37. return 0;
  38. }
  39. } else if (rb->head > rb->tail) {
  40. return rb->head - rb->tail;
  41. } else {
  42. return rb->size - rb->tail + rb->head;
  43. }
  44. }
  45. void rb_dump(struct ring_buffer *rb, void (*write)(const uint8_t *, size_t)) {
  46. if (rb_len(rb) == 0) {
  47. return;
  48. }
  49. if (rb->head > rb->tail) {
  50. write(rb->buffer + rb->tail, rb->head - rb->tail);
  51. } else {
  52. write(rb->buffer + rb->tail, rb->size - rb->tail);
  53. write(rb->buffer, rb->head);
  54. }
  55. }
  56. void rb_move(struct ring_buffer *rb, void (*write)(const uint8_t *, size_t)) {
  57. rb_dump(rb, write);
  58. rb->head = 0;
  59. rb->tail = 0;
  60. rb->full = false;
  61. }
  62. uint8_t rb_peek(struct ring_buffer *rb) {
  63. if (rb_len(rb) == 0) {
  64. return 0;
  65. }
  66. uint8_t v = rb->buffer[rb->tail];
  67. return v;
  68. }
  69. uint8_t rb_pop(struct ring_buffer *rb) {
  70. if (rb_len(rb) == 0) {
  71. return 0;
  72. }
  73. uint8_t v = rb->buffer[rb->tail++];
  74. if (rb->tail >= rb->size) {
  75. rb->tail = 0;
  76. }
  77. return v;
  78. }