Fix bugs.
This commit is contained in:
parent
fa83e2e807
commit
7f9845bb1d
|
@ -13,13 +13,13 @@ this notice are preserved. This file is offered as-is, without any warranty.
|
||||||
|
|
||||||
ctlseqs - helper library for terminal control sequences
|
ctlseqs - helper library for terminal control sequences
|
||||||
|
|
||||||
# Description
|
## About
|
||||||
|
|
||||||
The ctlseqs library provides C API for manipulating terminal emulators with control sequences.
|
The ctlseqs library provides C API for manipulating terminal emulators with control sequences.
|
||||||
|
|
||||||
ctlseqs is free software. you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
|
ctlseqs is free software. you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
|
||||||
|
|
||||||
# Getting Started
|
## Getting Started
|
||||||
|
|
||||||
To install and use the library, see [INSTALL.md](INSTALL.md) for details.
|
To install and use the library, see [INSTALL.md](INSTALL.md) for details.
|
||||||
|
|
||||||
|
|
|
@ -59,9 +59,13 @@
|
||||||
# define CTLSEQS_HOT
|
# define CTLSEQS_HOT
|
||||||
#endif // HAVE_FUNC_ATTRIBUTE_HOT
|
#endif // HAVE_FUNC_ATTRIBUTE_HOT
|
||||||
|
|
||||||
#ifndef CTLSEQS_TRIE_INIT_SIZE
|
#ifndef CTLSEQS_TRIE_NODE_POOL_INIT_SIZE
|
||||||
# define CTLSEQS_TRIE_INIT_SIZE 16
|
# define CTLSEQS_TRIE_NODE_POOL_INIT_SIZE 16
|
||||||
#endif // !CTLSEQS_TRIE_INIT_SIZE
|
#endif // !CTLSEQS_TRIE_NODE_POOL_INIT_SIZE
|
||||||
|
|
||||||
|
#ifndef CTLSEQS_TRIE_NODE_POOL_MAX_NUM
|
||||||
|
# define CTLSEQS_TRIE_NODE_POOL_MAX_NUM 8
|
||||||
|
#endif // !CTLSEQS_TRIE_NODE_POOL_MAX_NUM
|
||||||
|
|
||||||
#define CTLSEQS_VALUE_STR(stop_cond) \
|
#define CTLSEQS_VALUE_STR(stop_cond) \
|
||||||
for (cnt = 0; ; ++cnt) { \
|
for (cnt = 0; ; ++cnt) { \
|
||||||
|
@ -127,8 +131,9 @@ struct ctlseqs_match_ctx {
|
||||||
|
|
||||||
struct ctlseqs_matcher {
|
struct ctlseqs_matcher {
|
||||||
struct ctlseqs_trie_node root;
|
struct ctlseqs_trie_node root;
|
||||||
struct ctlseqs_trie_node *node_pool;
|
struct ctlseqs_trie_node *node_pools[CTLSEQS_TRIE_NODE_POOL_MAX_NUM];
|
||||||
size_t node_pool_size;
|
size_t pool_idx;
|
||||||
|
size_t pool_size;
|
||||||
struct ctlseqs_match_ctx *match_stack;
|
struct ctlseqs_match_ctx *match_stack;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -384,24 +389,25 @@ ctlseqs_match(struct ctlseqs_reader *reader, struct ctlseqs_matcher const *match
|
||||||
struct ctlseqs_matcher *
|
struct ctlseqs_matcher *
|
||||||
ctlseqs_matcher_init()
|
ctlseqs_matcher_init()
|
||||||
{
|
{
|
||||||
|
struct ctlseqs_trie_node *pool = malloc(sizeof(struct ctlseqs_trie_node) * CTLSEQS_TRIE_NODE_POOL_INIT_SIZE);
|
||||||
struct ctlseqs_matcher *matcher = malloc(sizeof(struct ctlseqs_matcher));
|
struct ctlseqs_matcher *matcher = malloc(sizeof(struct ctlseqs_matcher));
|
||||||
if (CTLSEQS_LIKELY(matcher != NULL)) {
|
if (CTLSEQS_UNLIKELY(pool == NULL || matcher == NULL)) {
|
||||||
*matcher = (struct ctlseqs_matcher) { .node_pool_size = 0 };
|
free(pool);
|
||||||
|
free(matcher);
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
*matcher = (struct ctlseqs_matcher) {
|
||||||
|
.node_pools = { pool },
|
||||||
|
.pool_size = CTLSEQS_TRIE_NODE_POOL_INIT_SIZE
|
||||||
|
};
|
||||||
return matcher;
|
return matcher;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
ctlseqs_matcher_config(struct ctlseqs_matcher *matcher, struct ctlseqs_matcher_options const *options)
|
ctlseqs_matcher_config(struct ctlseqs_matcher *matcher, struct ctlseqs_matcher_options const *options)
|
||||||
{
|
{
|
||||||
size_t node_pool_idx = 0, max_format_size = 0;
|
size_t node_idx = 0, max_format_size = 0;
|
||||||
if (matcher->node_pool == NULL) {
|
struct ctlseqs_trie_node *node_pool = matcher->node_pools[matcher->pool_idx];
|
||||||
matcher->node_pool_size = sizeof(struct ctlseqs_trie_node) * CTLSEQS_TRIE_INIT_SIZE;
|
|
||||||
matcher->node_pool = malloc(matcher->node_pool_size);
|
|
||||||
if (CTLSEQS_UNLIKELY(matcher->node_pool == NULL)) {
|
|
||||||
return CTLSEQS_NOMEM;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
matcher->root = (struct ctlseqs_trie_node) { .value = -1 };
|
matcher->root = (struct ctlseqs_trie_node) { .value = -1 };
|
||||||
for (size_t i = 0; i < options->npatterns; ++i) {
|
for (size_t i = 0; i < options->npatterns; ++i) {
|
||||||
char const *pattern = options->patterns[i];
|
char const *pattern = options->patterns[i];
|
||||||
|
@ -421,15 +427,19 @@ ctlseqs_matcher_config(struct ctlseqs_matcher *matcher, struct ctlseqs_matcher_o
|
||||||
if (node != NULL) {
|
if (node != NULL) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (CTLSEQS_UNLIKELY(++node_pool_idx >= matcher->node_pool_size)) {
|
if (CTLSEQS_UNLIKELY(++node_idx >= matcher->pool_size)) {
|
||||||
struct ctlseqs_trie_node *new_pool = realloc(matcher->node_pool, matcher->node_pool_size * 2);
|
if (CTLSEQS_UNLIKELY(++matcher->pool_idx >= CTLSEQS_TRIE_NODE_POOL_MAX_NUM)) {
|
||||||
if (CTLSEQS_UNLIKELY(new_pool == NULL)) {
|
|
||||||
return CTLSEQS_NOMEM;
|
return CTLSEQS_NOMEM;
|
||||||
}
|
}
|
||||||
matcher->node_pool = new_pool;
|
node_pool = malloc(sizeof(struct ctlseqs_trie_node) * matcher->pool_size * 2);
|
||||||
matcher->node_pool_size *= 2;
|
if (CTLSEQS_UNLIKELY(node_pool == NULL)) {
|
||||||
|
return CTLSEQS_NOMEM;
|
||||||
|
}
|
||||||
|
node_idx = 0;
|
||||||
|
matcher->node_pools[matcher->pool_idx] = node_pool;
|
||||||
|
matcher->pool_size *= 2;
|
||||||
}
|
}
|
||||||
old_node->children[ch] = node = &matcher->node_pool[node_pool_idx];
|
old_node->children[ch] = node = node_pool + node_idx;
|
||||||
*node = (struct ctlseqs_trie_node) {
|
*node = (struct ctlseqs_trie_node) {
|
||||||
.value = -1, // Value -1 indicates that there's no match on current node.
|
.value = -1, // Value -1 indicates that there's no match on current node.
|
||||||
.placeholder = ch < ctlseqs_ph_begin || ch >= ctlseqs_ph_end ? 0 : ch,
|
.placeholder = ch < ctlseqs_ph_begin || ch >= ctlseqs_ph_end ? 0 : ch,
|
||||||
|
@ -458,7 +468,10 @@ CTLSEQS_COLD void
|
||||||
ctlseqs_matcher_free(struct ctlseqs_matcher *matcher)
|
ctlseqs_matcher_free(struct ctlseqs_matcher *matcher)
|
||||||
{
|
{
|
||||||
if (matcher != NULL) {
|
if (matcher != NULL) {
|
||||||
free(matcher->node_pool);
|
for (size_t idx = 0; idx <= matcher->pool_idx; ++idx) {
|
||||||
|
free(matcher->node_pools[idx]);
|
||||||
|
}
|
||||||
|
free(matcher->match_stack);
|
||||||
free(matcher);
|
free(matcher);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -440,6 +440,9 @@ main(int argc, char **argv)
|
||||||
}
|
}
|
||||||
|
|
||||||
terminate:
|
terminate:
|
||||||
|
free(patterns);
|
||||||
|
ctlseqs_matcher_free(matcher);
|
||||||
|
ctlseqs_reader_free(reader);
|
||||||
tcsetattr(STDIN_FILENO, TCSANOW, &old_termios);
|
tcsetattr(STDIN_FILENO, TCSANOW, &old_termios);
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue