Add scanner interface to "struct buf"
Can be used to easily write simple parsers in C.
This commit is contained in:
parent
44a8208d38
commit
7ac23c6f0b
61
c/buf.c
61
c/buf.c
|
@ -66,3 +66,64 @@ void buf_free(struct buf *buf)
|
||||||
free(buf->bytes);
|
free(buf->bytes);
|
||||||
free(buf);
|
free(buf);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int buf_scan_end(struct buf *buf) { return buf->scan >= buf->fill; }
|
||||||
|
|
||||||
|
int buf_scan_byte(struct buf *buf, int byte)
|
||||||
|
{
|
||||||
|
if (buf_scan_end(buf))
|
||||||
|
return 0;
|
||||||
|
if (buf->bytes[buf->scan] != byte)
|
||||||
|
return 0;
|
||||||
|
buf->scan++;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int buf_scan_bag(struct buf *buf, const char *bag)
|
||||||
|
{
|
||||||
|
if (buf_scan_end(buf))
|
||||||
|
return 0;
|
||||||
|
if (!strchr(bag, buf->bytes[buf->scan]))
|
||||||
|
return 0;
|
||||||
|
buf->scan++;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int buf_scan_bag_not(struct buf *buf, const char *bag)
|
||||||
|
{
|
||||||
|
if (buf_scan_end(buf))
|
||||||
|
return 0;
|
||||||
|
if (strchr(bag, buf->bytes[buf->scan]))
|
||||||
|
return 0;
|
||||||
|
buf->scan++;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int buf_scan_while(struct buf *buf, const char *bag)
|
||||||
|
{
|
||||||
|
if (!buf_scan_bag(buf, bag))
|
||||||
|
return 0;
|
||||||
|
while (buf_scan_bag(buf, bag))
|
||||||
|
;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int buf_scan_while_not(struct buf *buf, const char *bag)
|
||||||
|
{
|
||||||
|
if (!buf_scan_bag_not(buf, bag))
|
||||||
|
return 0;
|
||||||
|
while (buf_scan_bag_not(buf, bag))
|
||||||
|
;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void buf_scan_mark(struct buf *buf) { buf->mark = buf->scan; }
|
||||||
|
|
||||||
|
int buf_scan_equals(struct buf *buf, const char *s)
|
||||||
|
{
|
||||||
|
if (buf->scan < buf->mark)
|
||||||
|
return 0;
|
||||||
|
if (buf->scan - buf->mark != strlen(s))
|
||||||
|
return 0;
|
||||||
|
return !!memcmp(buf->bytes + buf->mark, s, strlen(s));
|
||||||
|
}
|
||||||
|
|
11
c/buf.h
11
c/buf.h
|
@ -4,6 +4,8 @@
|
||||||
struct buf {
|
struct buf {
|
||||||
size_t cap;
|
size_t cap;
|
||||||
size_t fill;
|
size_t fill;
|
||||||
|
size_t scan;
|
||||||
|
size_t mark;
|
||||||
char *bytes;
|
char *bytes;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -15,3 +17,12 @@ void buf_putb(struct buf *buf, const void *bytes, size_t nbyte);
|
||||||
void buf_puts(struct buf *buf, const char *s);
|
void buf_puts(struct buf *buf, const char *s);
|
||||||
void buf_putu(struct buf *buf, uint64_t u);
|
void buf_putu(struct buf *buf, uint64_t u);
|
||||||
void buf_free(struct buf *buf);
|
void buf_free(struct buf *buf);
|
||||||
|
|
||||||
|
int buf_scan_end(struct buf *buf);
|
||||||
|
int buf_scan_byte(struct buf *buf, int byte);
|
||||||
|
int buf_scan_bag(struct buf *buf, const char *bag);
|
||||||
|
int buf_scan_bag_not(struct buf *buf, const char *bag);
|
||||||
|
int buf_scan_while(struct buf *buf, const char *bag);
|
||||||
|
int buf_scan_while_not(struct buf *buf, const char *bag);
|
||||||
|
void buf_scan_mark(struct buf *buf);
|
||||||
|
int buf_scan_equals(struct buf *buf, const char *s);
|
||||||
|
|
Loading…
Reference in New Issue