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.

io.h 2.6KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112
  1. #ifndef L2_IO_H
  2. #define L2_IO_H
  3. #include <stdio.h>
  4. #include <string.h>
  5. #define L2_IO_BUFSIZ 1024
  6. struct l2_io_reader {
  7. size_t (*read)(struct l2_io_reader *self, char *buf, size_t len);
  8. };
  9. struct l2_io_writer {
  10. void (*write)(struct l2_io_writer *self, const char *buf, size_t len);
  11. };
  12. struct l2_bufio_reader {
  13. struct l2_io_reader *r;
  14. size_t len;
  15. size_t idx;
  16. char buf[L2_IO_BUFSIZ];
  17. };
  18. void l2_bufio_reader_init(struct l2_bufio_reader *b, struct l2_io_reader *r);
  19. void l2_bufio_shift(struct l2_bufio_reader *b);
  20. int l2_bufio_shift_peek(struct l2_bufio_reader *b, size_t count);
  21. int l2_bufio_shift_get(struct l2_bufio_reader *b);
  22. static inline int l2_bufio_peek(struct l2_bufio_reader *b, size_t count);
  23. static inline int l2_bufio_get(struct l2_bufio_reader *b);
  24. struct l2_bufio_writer {
  25. struct l2_io_writer *w;
  26. size_t idx;
  27. char buf[L2_IO_BUFSIZ];
  28. };
  29. void l2_bufio_writer_init(struct l2_bufio_writer *b, struct l2_io_writer *w);
  30. void l2_bufio_flush(struct l2_bufio_writer *b);
  31. static inline void l2_bufio_put(struct l2_bufio_writer *b, char ch);
  32. static inline void l2_bufio_put_n(struct l2_bufio_writer *b, const char *ptr, size_t len);
  33. /*
  34. * Useful readers and writers
  35. */
  36. struct l2_io_mem_reader {
  37. struct l2_io_reader r;
  38. size_t idx;
  39. size_t len;
  40. const char *mem;
  41. };
  42. size_t l2_io_mem_read(struct l2_io_reader *self, char *buf, size_t len);
  43. struct l2_io_file_reader {
  44. struct l2_io_reader r;
  45. FILE *f;
  46. };
  47. size_t l2_io_file_read(struct l2_io_reader *self, char *buf, size_t len);
  48. struct l2_io_mem_writer {
  49. struct l2_io_writer w;
  50. size_t len;
  51. char *mem;
  52. };
  53. void l2_io_mem_write(struct l2_io_writer *self, const char *buf, size_t len);
  54. struct l2_io_file_writer {
  55. struct l2_io_writer w;
  56. FILE *f;
  57. };
  58. void l2_io_file_write(struct l2_io_writer *self, const char *buf, size_t len);
  59. /*
  60. * Defined in the header to let the compiler inline
  61. */
  62. static inline int l2_bufio_peek(struct l2_bufio_reader *b, size_t count) {\
  63. size_t offset = count - 1;
  64. if (b->idx + offset < b->len) {
  65. return b->buf[b->idx + offset];
  66. } else {
  67. return l2_bufio_shift_peek(b, count);
  68. }
  69. }
  70. static inline int l2_bufio_get(struct l2_bufio_reader *b) {
  71. if (b->idx < b->len) {
  72. return b->buf[b->idx++];
  73. } else {
  74. return l2_bufio_shift_get(b);
  75. }
  76. }
  77. static inline void l2_bufio_put(struct l2_bufio_writer *b, char ch) {
  78. if (b->idx >= sizeof(b->buf)) {
  79. l2_bufio_flush(b);
  80. }
  81. b->buf[b->idx++] = ch;
  82. }
  83. static inline void l2_bufio_put_n(struct l2_bufio_writer *b, const char *ptr, size_t len) {
  84. size_t freespace = sizeof(b->buf) - b->idx;
  85. if (len < freespace) {
  86. memcpy(b->buf + b->idx, ptr, len);
  87. b->idx += len;
  88. } else {
  89. l2_bufio_flush(b);
  90. b->w->write(b->w, ptr, len);
  91. }
  92. }
  93. #endif