void set_cache_add(struct set *set, struct table *table);
struct set *set_cache_find(const struct table *table, const char *name);
+struct cache {
+ struct list_head *ht;
+ struct list_head list;
+};
+
+struct cache_item {
+ struct list_head hlist;
+ struct list_head list;
+};
+
+void cache_init(struct cache *cache);
+void cache_free(struct cache *cache);
+void cache_add(struct cache_item *item, struct cache *cache, uint32_t hash);
+void cache_del(struct cache_item *item);
+
#endif /* _NFT_CACHE_H_ */
struct handle handle;
struct location location;
struct scope scope;
- struct list_head *cache_chain_ht;
- struct list_head cache_chain;
+ struct cache chain_cache;
+ struct cache set_cache;
struct list_head chains;
- struct list_head *cache_set_ht;
- struct list_head cache_set;
struct list_head sets;
struct list_head objs;
struct list_head flowtables;
*/
struct chain {
struct list_head list;
- struct list_head cache_hlist;
- struct list_head cache_list;
+ struct cache_item cache;
struct handle handle;
struct location location;
unsigned int refcnt;
*/
struct set {
struct list_head list;
- struct list_head cache_hlist;
- struct list_head cache_list;
+ struct cache_item cache;
struct handle handle;
struct location location;
unsigned int refcnt;
chain = netlink_delinearize_chain(ctx->nlctx, nlc);
if (chain->flags & CHAIN_F_BINDING) {
- list_add_tail(&chain->cache_list, &ctx->table->chain_bindings);
+ list_add_tail(&chain->cache.list, &ctx->table->chain_bindings);
} else {
- list_add_tail(&chain->cache_hlist, &ctx->table->cache_chain_ht[hash]);
- list_add_tail(&chain->cache_list, &ctx->table->cache_chain);
+ cache_add(&chain->cache, &ctx->table->chain_cache, hash);
}
nftnl_chain_list_del(nlc);
uint32_t hash;
hash = djb_hash(chain->handle.chain.name) % NFT_CACHE_HSIZE;
- list_add_tail(&chain->cache_hlist, &table->cache_chain_ht[hash]);
- list_add_tail(&chain->cache_list, &table->cache_chain);
+ cache_add(&chain->cache, &table->chain_cache, hash);
}
struct chain *chain_cache_find(const struct table *table, const char *name)
uint32_t hash;
hash = djb_hash(name) % NFT_CACHE_HSIZE;
- list_for_each_entry(chain, &table->cache_chain_ht[hash], cache_hlist) {
+ list_for_each_entry(chain, &table->chain_cache.ht[hash], cache.hlist) {
if (!strcmp(chain->handle.chain.name, name))
return chain;
}
set_name = nftnl_set_get_str(nls, NFTNL_SET_NAME);
hash = djb_hash(set_name) % NFT_CACHE_HSIZE;
- list_add_tail(&set->cache_hlist, &ctx->table->cache_set_ht[hash]);
- list_add_tail(&set->cache_list, &ctx->table->cache_set);
+ cache_add(&set->cache, &ctx->table->set_cache, hash);
return 0;
}
uint32_t hash;
hash = djb_hash(set->handle.set.name) % NFT_CACHE_HSIZE;
- list_add_tail(&set->cache_hlist, &table->cache_set_ht[hash]);
- list_add_tail(&set->cache_list, &table->cache_set);
+ cache_add(&set->cache, &table->set_cache, hash);
}
struct set *set_cache_find(const struct table *table, const char *name)
uint32_t hash;
hash = djb_hash(name) % NFT_CACHE_HSIZE;
- list_for_each_entry(set, &table->cache_set_ht[hash], cache_hlist) {
+ list_for_each_entry(set, &table->set_cache.ht[hash], cache.hlist) {
if (!strcmp(set->handle.set.name, name))
return set;
}
}
}
if (flags & NFT_CACHE_SETELEM_BIT) {
- list_for_each_entry(set, &table->cache_set, cache_list) {
+ list_for_each_entry(set, &table->set_cache.list, cache.list) {
ret = netlink_list_setelems(ctx, &set->handle,
set);
if (ret < 0) {
cache->genid = 0;
cache->flags = NFT_CACHE_EMPTY;
}
+
+void cache_init(struct cache *cache)
+{
+ int i;
+
+ cache->ht = xmalloc(sizeof(struct list_head) * NFT_CACHE_HSIZE);
+ for (i = 0; i < NFT_CACHE_HSIZE; i++)
+ init_list_head(&cache->ht[i]);
+
+ init_list_head(&cache->list);
+}
+
+void cache_free(struct cache *cache)
+{
+ xfree(cache->ht);
+}
+
+void cache_add(struct cache_item *item, struct cache *cache, uint32_t hash)
+{
+ list_add_tail(&item->hlist, &cache->ht[hash]);
+ list_add_tail(&item->list, &cache->list);
+}
+
+void cache_del(struct cache_item *item)
+{
+ list_del(&item->hlist);
+ list_del(&item->list);
+}
tmp = obj_print_json(obj);
json_array_append_new(root, tmp);
}
- list_for_each_entry(set, &table->cache_set, cache_list) {
+ list_for_each_entry(set, &table->set_cache.list, cache.list) {
if (set_is_anonymous(set->flags))
continue;
tmp = set_print_json(&ctx->nft->output, set);
tmp = flowtable_print_json(flowtable);
json_array_append_new(root, tmp);
}
- list_for_each_entry(chain, &table->cache_chain, cache_list) {
+ list_for_each_entry(chain, &table->chain_cache.list, cache.list) {
tmp = chain_print_json(chain);
json_array_append_new(root, tmp);
struct chain *chain;
struct rule *rule;
- list_for_each_entry(chain, &table->cache_chain, cache_list) {
+ list_for_each_entry(chain, &table->chain_cache.list, cache.list) {
if (chain->handle.family != cmd->handle.family ||
strcmp(cmd->handle.chain.name, chain->handle.chain.name))
continue;
cmd->handle.family != table->handle.family)
continue;
- list_for_each_entry(chain, &table->cache_chain, cache_list) {
+ list_for_each_entry(chain, &table->chain_cache.list, cache.list) {
json_t *tmp = chain_print_json(chain);
json_array_append_new(root, tmp);
cmd->handle.family != table->handle.family)
continue;
- list_for_each_entry(set, &table->cache_set, cache_list) {
+ list_for_each_entry(set, &table->set_cache.list, cache.list) {
if (cmd->obj == CMD_OBJ_SETS &&
!set_is_literal(set->flags))
continue;
string_misspell_init(&st);
list_for_each_entry(table, &cache->list, list) {
- list_for_each_entry(set, &table->cache_set, cache_list) {
+ list_for_each_entry(set, &table->set_cache.list, cache.list) {
if (set_is_anonymous(set->flags))
continue;
if (!strcmp(set->handle.set.name, set_name)) {
{
struct chain *chain;
- list_for_each_entry(chain, &table->chain_bindings, cache_list) {
+ list_for_each_entry(chain, &table->chain_bindings, cache.list) {
if (!strcmp(chain->handle.chain.name, chain_name))
return chain;
}
string_misspell_init(&st);
list_for_each_entry(table, &cache->list, list) {
- list_for_each_entry(chain, &table->cache_chain, cache_list) {
+ list_for_each_entry(chain, &table->chain_cache.list, cache.list) {
if (!strcmp(chain->handle.chain.name, h->chain.name)) {
*t = table;
return chain;
struct table *table_alloc(void)
{
struct table *table;
- int i;
table = xzalloc(sizeof(*table));
init_list_head(&table->chains);
- init_list_head(&table->cache_chain);
init_list_head(&table->sets);
- init_list_head(&table->cache_set);
init_list_head(&table->objs);
init_list_head(&table->flowtables);
init_list_head(&table->chain_bindings);
init_list_head(&table->scope.symbols);
table->refcnt = 1;
- table->cache_chain_ht =
- xmalloc(sizeof(struct list_head) * NFT_CACHE_HSIZE);
- for (i = 0; i < NFT_CACHE_HSIZE; i++)
- init_list_head(&table->cache_chain_ht[i]);
-
- table->cache_set_ht =
- xmalloc(sizeof(struct list_head) * NFT_CACHE_HSIZE);
- for (i = 0; i < NFT_CACHE_HSIZE; i++)
- init_list_head(&table->cache_set_ht[i]);
+ cache_init(&table->chain_cache);
+ cache_init(&table->set_cache);
return table;
}
xfree(table->comment);
list_for_each_entry_safe(chain, next, &table->chains, list)
chain_free(chain);
- list_for_each_entry_safe(chain, next, &table->chain_bindings, cache_list)
+ list_for_each_entry_safe(chain, next, &table->chain_bindings, cache.list)
chain_free(chain);
/* this is implicitly releasing chains in the hashtable cache */
- list_for_each_entry_safe(chain, next, &table->cache_chain, cache_list)
+ list_for_each_entry_safe(chain, next, &table->chain_cache.list, cache.list)
chain_free(chain);
list_for_each_entry_safe(set, nset, &table->sets, list)
set_free(set);
/* this is implicitly releasing sets in the hashtable cache */
- list_for_each_entry_safe(set, nset, &table->cache_set, cache_list)
+ list_for_each_entry_safe(set, nset, &table->set_cache.list, cache.list)
set_free(set);
list_for_each_entry_safe(ft, nft, &table->flowtables, list)
flowtable_free(ft);
obj_free(obj);
handle_free(&table->handle);
scope_release(&table->scope);
- xfree(table->cache_chain_ht);
- xfree(table->cache_set_ht);
+ cache_free(&table->chain_cache);
+ cache_free(&table->set_cache);
xfree(table);
}
obj_print(obj, octx);
delim = "\n";
}
- list_for_each_entry(set, &table->cache_set, cache_list) {
+ list_for_each_entry(set, &table->set_cache.list, cache.list) {
if (set_is_anonymous(set->flags))
continue;
nft_print(octx, "%s", delim);
flowtable_print(flowtable, octx);
delim = "\n";
}
- list_for_each_entry(chain, &table->cache_chain, cache_list) {
+ list_for_each_entry(chain, &table->chain_cache.list, cache.list) {
nft_print(octx, "%s", delim);
chain_print(chain, octx);
delim = "\n";
family2str(table->handle.family),
table->handle.table.name);
- list_for_each_entry(set, &table->cache_set, cache_list) {
+ list_for_each_entry(set, &table->set_cache.list, cache.list) {
if (cmd->obj == CMD_OBJ_SETS &&
!set_is_literal(set->flags))
continue;
table_print_declaration(table, &ctx->nft->output);
- list_for_each_entry(chain, &table->cache_chain, cache_list) {
+ list_for_each_entry(chain, &table->chain_cache.list, cache.list) {
if (chain->handle.family != cmd->handle.family ||
strcmp(cmd->handle.chain.name, chain->handle.chain.name) != 0)
continue;
table_print_declaration(table, &ctx->nft->output);
- list_for_each_entry(chain, &table->cache_chain, cache_list) {
+ list_for_each_entry(chain, &table->chain_cache.list, cache.list) {
chain_print_declaration(chain, &ctx->nft->output);
nft_print(&ctx->nft->output, "\t}\n");
}