|
Packit |
c5a612 |
/*
|
|
Packit |
c5a612 |
* Copyright (c) 2019 Pablo Neira Ayuso <pablo@netfilter.org>
|
|
Packit |
c5a612 |
*
|
|
Packit |
c5a612 |
* This program is free software; you can redistribute it and/or modify
|
|
Packit |
c5a612 |
* it under the terms of the GNU General Public License version 2 (or any
|
|
Packit |
c5a612 |
* later) as published by the Free Software Foundation.
|
|
Packit |
c5a612 |
*/
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
#include <expression.h>
|
|
Packit |
c5a612 |
#include <statement.h>
|
|
Packit |
c5a612 |
#include <rule.h>
|
|
Packit |
c5a612 |
#include <erec.h>
|
|
Packit |
c5a612 |
#include <utils.h>
|
|
Packit |
c5a612 |
#include <cache.h>
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
static unsigned int evaluate_cache_add(struct cmd *cmd, unsigned int flags)
|
|
Packit |
c5a612 |
{
|
|
Packit |
c5a612 |
switch (cmd->obj) {
|
|
Packit |
c5a612 |
case CMD_OBJ_CHAIN:
|
|
Packit |
c5a612 |
case CMD_OBJ_SET:
|
|
Packit |
c5a612 |
case CMD_OBJ_COUNTER:
|
|
Packit |
c5a612 |
case CMD_OBJ_QUOTA:
|
|
Packit |
c5a612 |
case CMD_OBJ_LIMIT:
|
|
Packit |
c5a612 |
case CMD_OBJ_SECMARK:
|
|
Packit |
c5a612 |
case CMD_OBJ_FLOWTABLE:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_TABLE;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_OBJ_SETELEM:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_TABLE |
|
|
Packit |
c5a612 |
NFT_CACHE_CHAIN |
|
|
Packit |
c5a612 |
NFT_CACHE_SET |
|
|
Packit |
c5a612 |
NFT_CACHE_OBJECT |
|
|
Packit |
c5a612 |
NFT_CACHE_SETELEM;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_OBJ_RULE:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_TABLE |
|
|
Packit |
c5a612 |
NFT_CACHE_CHAIN |
|
|
Packit |
c5a612 |
NFT_CACHE_SET |
|
|
Packit |
c5a612 |
NFT_CACHE_OBJECT |
|
|
Packit |
c5a612 |
NFT_CACHE_FLOWTABLE;
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
if (cmd->handle.index.id ||
|
|
Packit |
c5a612 |
cmd->handle.position.id)
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_RULE | NFT_CACHE_UPDATE;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
default:
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
return flags;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
static unsigned int evaluate_cache_del(struct cmd *cmd, unsigned int flags)
|
|
Packit |
c5a612 |
{
|
|
Packit |
c5a612 |
switch (cmd->obj) {
|
|
Packit |
c5a612 |
case CMD_OBJ_SETELEM:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_SETELEM;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
default:
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
return flags;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
static unsigned int evaluate_cache_get(struct cmd *cmd, unsigned int flags)
|
|
Packit |
c5a612 |
{
|
|
Packit |
c5a612 |
switch (cmd->obj) {
|
|
Packit |
c5a612 |
case CMD_OBJ_SETELEM:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_TABLE |
|
|
Packit |
c5a612 |
NFT_CACHE_SET |
|
|
Packit |
c5a612 |
NFT_CACHE_SETELEM;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
default:
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
return flags;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
static unsigned int evaluate_cache_flush(struct cmd *cmd, unsigned int flags)
|
|
Packit |
c5a612 |
{
|
|
Packit |
c5a612 |
switch (cmd->obj) {
|
|
Packit |
c5a612 |
case CMD_OBJ_SET:
|
|
Packit |
c5a612 |
case CMD_OBJ_MAP:
|
|
Packit |
c5a612 |
case CMD_OBJ_METER:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_SET;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_OBJ_RULESET:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_FLUSHED;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
default:
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
return flags;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
static unsigned int evaluate_cache_rename(struct cmd *cmd, unsigned int flags)
|
|
Packit |
c5a612 |
{
|
|
Packit |
c5a612 |
switch (cmd->obj) {
|
|
Packit |
c5a612 |
case CMD_OBJ_CHAIN:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_CHAIN;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
default:
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
return flags;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
unsigned int cache_evaluate(struct nft_ctx *nft, struct list_head *cmds)
|
|
Packit |
c5a612 |
{
|
|
Packit |
c5a612 |
unsigned int flags = NFT_CACHE_EMPTY;
|
|
Packit |
c5a612 |
struct cmd *cmd;
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
list_for_each_entry(cmd, cmds, list) {
|
|
Packit |
c5a612 |
switch (cmd->op) {
|
|
Packit |
c5a612 |
case CMD_ADD:
|
|
Packit |
c5a612 |
case CMD_INSERT:
|
|
Packit |
c5a612 |
case CMD_CREATE:
|
|
Packit |
c5a612 |
flags = evaluate_cache_add(cmd, flags);
|
|
Packit |
c5a612 |
if (nft_output_echo(&nft->output))
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_FULL;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_REPLACE:
|
|
Packit |
c5a612 |
flags = NFT_CACHE_FULL;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_DELETE:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_TABLE |
|
|
Packit |
c5a612 |
NFT_CACHE_CHAIN |
|
|
Packit |
c5a612 |
NFT_CACHE_SET |
|
|
Packit |
c5a612 |
NFT_CACHE_FLOWTABLE |
|
|
Packit |
c5a612 |
NFT_CACHE_OBJECT;
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
flags = evaluate_cache_del(cmd, flags);
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_GET:
|
|
Packit |
c5a612 |
flags = evaluate_cache_get(cmd, flags);
|
|
Packit |
c5a612 |
break;
|
|
Packit Service |
b50565 |
case CMD_RESET:
|
|
Packit Service |
c72544 |
flags |= NFT_CACHE_TABLE;
|
|
Packit Service |
c72544 |
break;
|
|
Packit Service |
c72544 |
case CMD_LIST:
|
|
Packit |
c5a612 |
case CMD_EXPORT:
|
|
Packit |
c5a612 |
case CMD_MONITOR:
|
|
Packit |
c5a612 |
flags |= NFT_CACHE_FULL;
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_FLUSH:
|
|
Packit |
c5a612 |
flags = evaluate_cache_flush(cmd, flags);
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_RENAME:
|
|
Packit |
c5a612 |
flags = evaluate_cache_rename(cmd, flags);
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
case CMD_DESCRIBE:
|
|
Packit |
c5a612 |
case CMD_IMPORT:
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
default:
|
|
Packit |
c5a612 |
break;
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
}
|
|
Packit |
c5a612 |
|
|
Packit |
c5a612 |
return flags;
|
|
Packit |
c5a612 |
}
|