mirror of
https://gitlab.nic.cz/labs/bird.git
synced 2025-01-20 16:01:53 +00:00
Merge commit 'ac5745134847c044b21c311e5ab11d92d05bacc1' into integrated
This commit is contained in:
commit
a013bd08e3
@ -282,7 +282,7 @@ protocol rip {
|
|||||||
<tag>include "<m/filename/"</tag>
|
<tag>include "<m/filename/"</tag>
|
||||||
This statement causes inclusion of a new file. The maximal depth is set to 5.
|
This statement causes inclusion of a new file. The maximal depth is set to 5.
|
||||||
|
|
||||||
<tag>log "<m/filename/"|syslog [name <m/name/]|stderr all|{ <m/list of classes/ }</tag>
|
<tag><label id="dsc-log">log "<m/filename/"|syslog [name <m/name/]|stderr all|{ <m/list of classes/ }</tag>
|
||||||
Set logging of messages having the given class (either <cf/all/ or <cf/{
|
Set logging of messages having the given class (either <cf/all/ or <cf/{
|
||||||
error, trace }/ etc.) into selected destination (a file specified as a filename string,
|
error, trace }/ etc.) into selected destination (a file specified as a filename string,
|
||||||
syslog with optional name argument, or the stderr output). Classes are:
|
syslog with optional name argument, or the stderr output). Classes are:
|
||||||
@ -651,9 +651,6 @@ This argument can be omitted if there exists only a single instance.
|
|||||||
<p>Here is a brief list of supported functions:
|
<p>Here is a brief list of supported functions:
|
||||||
|
|
||||||
<descrip>
|
<descrip>
|
||||||
<tag>dump resources|sockets|interfaces|neighbors|attributes|routes|protocols</tag>
|
|
||||||
Dump contents of internal data structures to the debugging output.
|
|
||||||
|
|
||||||
<tag>show status</tag>
|
<tag>show status</tag>
|
||||||
Show router status, that is BIRD version, uptime and time from last reconfiguration.
|
Show router status, that is BIRD version, uptime and time from last reconfiguration.
|
||||||
|
|
||||||
@ -812,6 +809,17 @@ This argument can be omitted if there exists only a single instance.
|
|||||||
|
|
||||||
<tag>debug <m/protocol/|<m/pattern/|all all|off|{ states | routes | filters | events | packets }</tag>
|
<tag>debug <m/protocol/|<m/pattern/|all all|off|{ states | routes | filters | events | packets }</tag>
|
||||||
Control protocol debugging.
|
Control protocol debugging.
|
||||||
|
|
||||||
|
<tag>dump resources|sockets|interfaces|neighbors|attributes|routes|protocols</tag>
|
||||||
|
Dump contents of internal data structures to the debugging output.
|
||||||
|
|
||||||
|
<tag>echo all|off|{ <m/list of log classes/ } [ <m/buffer-size/ ]</tag>
|
||||||
|
Control echoing of log messages to the command-line output.
|
||||||
|
See <ref id="dsc-log" name="log option"> for a list of log classes.
|
||||||
|
|
||||||
|
<tag>eval <m/expr/</tag>
|
||||||
|
Evaluate given expression.
|
||||||
|
|
||||||
</descrip>
|
</descrip>
|
||||||
|
|
||||||
<chapt>Filters
|
<chapt>Filters
|
||||||
|
@ -31,6 +31,7 @@ Reply codes of BIRD command-line interface
|
|||||||
0020 Configuration OK
|
0020 Configuration OK
|
||||||
0021 Undo requested
|
0021 Undo requested
|
||||||
0022 Undo scheduled
|
0022 Undo scheduled
|
||||||
|
0023 Evaluation of expression
|
||||||
|
|
||||||
1000 BIRD version
|
1000 BIRD version
|
||||||
1001 Interface list
|
1001 Interface list
|
||||||
@ -61,6 +62,7 @@ Reply codes of BIRD command-line interface
|
|||||||
8005 Protocol is down => cannot dump
|
8005 Protocol is down => cannot dump
|
||||||
8006 Reload failed
|
8006 Reload failed
|
||||||
8007 Access denied
|
8007 Access denied
|
||||||
|
8008 Evaluation runtime error
|
||||||
|
|
||||||
9000 Command too long
|
9000 Command too long
|
||||||
9001 Parse error
|
9001 Parse error
|
||||||
|
@ -440,8 +440,6 @@ val_in_range(struct f_val v1, struct f_val v2)
|
|||||||
return CMP_ERROR;
|
return CMP_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void val_print(struct f_val v);
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
tree_node_print(struct f_tree *t, char **sep)
|
tree_node_print(struct f_tree *t, char **sep)
|
||||||
{
|
{
|
||||||
@ -474,7 +472,7 @@ tree_print(struct f_tree *t)
|
|||||||
/*
|
/*
|
||||||
* val_print - format filter value
|
* val_print - format filter value
|
||||||
*/
|
*/
|
||||||
static void
|
void
|
||||||
val_print(struct f_val v)
|
val_print(struct f_val v)
|
||||||
{
|
{
|
||||||
char buf2[1024];
|
char buf2[1024];
|
||||||
@ -558,6 +556,8 @@ static struct rate_limit rl_runtime_err;
|
|||||||
#define TWOARGS_C TWOARGS \
|
#define TWOARGS_C TWOARGS \
|
||||||
if (v1.type != v2.type) \
|
if (v1.type != v2.type) \
|
||||||
runtime( "Can't operate with values of incompatible types" );
|
runtime( "Can't operate with values of incompatible types" );
|
||||||
|
#define ACCESS_RTE \
|
||||||
|
do { if (!f_rte) runtime("No route to access"); } while (0)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* interpret
|
* interpret
|
||||||
@ -821,6 +821,7 @@ interpret(struct f_inst *what)
|
|||||||
break;
|
break;
|
||||||
case 'a': /* rta access */
|
case 'a': /* rta access */
|
||||||
{
|
{
|
||||||
|
ACCESS_RTE;
|
||||||
struct rta *rta = (*f_rte)->attrs;
|
struct rta *rta = (*f_rte)->attrs;
|
||||||
res.type = what->aux;
|
res.type = what->aux;
|
||||||
switch(res.type) {
|
switch(res.type) {
|
||||||
@ -845,6 +846,7 @@ interpret(struct f_inst *what)
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case P('a','S'):
|
case P('a','S'):
|
||||||
|
ACCESS_RTE;
|
||||||
ONEARG;
|
ONEARG;
|
||||||
if (what->aux != v1.type)
|
if (what->aux != v1.type)
|
||||||
runtime( "Attempt to set static attribute to incompatible type" );
|
runtime( "Attempt to set static attribute to incompatible type" );
|
||||||
@ -877,6 +879,7 @@ interpret(struct f_inst *what)
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case P('e','a'): /* Access to extended attributes */
|
case P('e','a'): /* Access to extended attributes */
|
||||||
|
ACCESS_RTE;
|
||||||
{
|
{
|
||||||
eattr *e = NULL;
|
eattr *e = NULL;
|
||||||
if (!(f_flags & FF_FORCE_TMPATTR))
|
if (!(f_flags & FF_FORCE_TMPATTR))
|
||||||
@ -944,6 +947,7 @@ interpret(struct f_inst *what)
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case P('e','S'):
|
case P('e','S'):
|
||||||
|
ACCESS_RTE;
|
||||||
ONEARG;
|
ONEARG;
|
||||||
{
|
{
|
||||||
struct ea_list *l = lp_alloc(f_pool, sizeof(struct ea_list) + sizeof(eattr));
|
struct ea_list *l = lp_alloc(f_pool, sizeof(struct ea_list) + sizeof(eattr));
|
||||||
@ -1021,10 +1025,12 @@ interpret(struct f_inst *what)
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 'P':
|
case 'P':
|
||||||
|
ACCESS_RTE;
|
||||||
res.type = T_INT;
|
res.type = T_INT;
|
||||||
res.val.i = (*f_rte)->pref;
|
res.val.i = (*f_rte)->pref;
|
||||||
break;
|
break;
|
||||||
case P('P','S'):
|
case P('P','S'):
|
||||||
|
ACCESS_RTE;
|
||||||
ONEARG;
|
ONEARG;
|
||||||
if (v1.type != T_INT)
|
if (v1.type != T_INT)
|
||||||
runtime( "Can't set preference to non-integer" );
|
runtime( "Can't set preference to non-integer" );
|
||||||
@ -1246,6 +1252,7 @@ interpret(struct f_inst *what)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
ACCESS_RTE;
|
||||||
v1.val.px.ip = (*f_rte)->net->n.prefix;
|
v1.val.px.ip = (*f_rte)->net->n.prefix;
|
||||||
v1.val.px.len = (*f_rte)->net->n.pxlen;
|
v1.val.px.len = (*f_rte)->net->n.pxlen;
|
||||||
|
|
||||||
@ -1478,22 +1485,27 @@ f_run(struct filter *filter, struct rte **rte, struct ea_list **tmp_attrs, struc
|
|||||||
return res.val.i;
|
return res.val.i;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct f_val
|
||||||
|
f_eval(struct f_inst *expr, struct linpool *tmp_pool)
|
||||||
|
{
|
||||||
|
f_flags = 0;
|
||||||
|
f_tmp_attrs = NULL;
|
||||||
|
f_rte = NULL;
|
||||||
|
f_pool = tmp_pool;
|
||||||
|
|
||||||
|
log_reset();
|
||||||
|
return interpret(expr);
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
f_eval_int(struct f_inst *expr)
|
f_eval_int(struct f_inst *expr)
|
||||||
{
|
{
|
||||||
/* Called independently in parse-time to eval expressions */
|
/* Called independently in parse-time to eval expressions */
|
||||||
struct f_val res;
|
struct f_val res = f_eval(expr, cfg_mem);
|
||||||
|
|
||||||
f_flags = 0;
|
|
||||||
f_tmp_attrs = NULL;
|
|
||||||
f_rte = NULL;
|
|
||||||
f_pool = cfg_mem;
|
|
||||||
|
|
||||||
log_reset();
|
|
||||||
res = interpret(expr);
|
|
||||||
|
|
||||||
if (res.type != T_INT)
|
if (res.type != T_INT)
|
||||||
cf_error("Integer expression expected");
|
cf_error("Integer expression expected");
|
||||||
|
|
||||||
return res.val.i;
|
return res.val.i;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -109,6 +109,7 @@ struct ea_list;
|
|||||||
struct rte;
|
struct rte;
|
||||||
|
|
||||||
int f_run(struct filter *filter, struct rte **rte, struct ea_list **tmp_attrs, struct linpool *tmp_pool, int flags);
|
int f_run(struct filter *filter, struct rte **rte, struct ea_list **tmp_attrs, struct linpool *tmp_pool, int flags);
|
||||||
|
struct f_val f_eval(struct f_inst *expr, struct linpool *tmp_pool);
|
||||||
int f_eval_int(struct f_inst *expr);
|
int f_eval_int(struct f_inst *expr);
|
||||||
u32 f_eval_asn(struct f_inst *expr);
|
u32 f_eval_asn(struct f_inst *expr);
|
||||||
|
|
||||||
@ -120,6 +121,8 @@ int i_same(struct f_inst *f1, struct f_inst *f2);
|
|||||||
int val_compare(struct f_val v1, struct f_val v2);
|
int val_compare(struct f_val v1, struct f_val v2);
|
||||||
int tree_compare(const void *p1, const void *p2);
|
int tree_compare(const void *p1, const void *p2);
|
||||||
|
|
||||||
|
void val_print(struct f_val v);
|
||||||
|
|
||||||
#define F_NOP 0
|
#define F_NOP 0
|
||||||
#define F_NONL 1
|
#define F_NONL 1
|
||||||
#define F_ACCEPT 2 /* Need to preserve ordering: accepts < rejects! */
|
#define F_ACCEPT 2 /* Need to preserve ordering: accepts < rejects! */
|
||||||
|
20
nest/cmds.c
20
nest/cmds.c
@ -13,6 +13,7 @@
|
|||||||
#include "nest/cmds.h"
|
#include "nest/cmds.h"
|
||||||
#include "lib/string.h"
|
#include "lib/string.h"
|
||||||
#include "lib/resource.h"
|
#include "lib/resource.h"
|
||||||
|
#include "filter/filter.h"
|
||||||
|
|
||||||
extern int shutting_down;
|
extern int shutting_down;
|
||||||
extern int configuring;
|
extern int configuring;
|
||||||
@ -90,3 +91,22 @@ cmd_show_memory(void)
|
|||||||
print_size("Total:", rmemsize(&root_pool));
|
print_size("Total:", rmemsize(&root_pool));
|
||||||
cli_msg(0, "");
|
cli_msg(0, "");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
extern const char *log_buffer_ptr;
|
||||||
|
|
||||||
|
void
|
||||||
|
cmd_eval(struct f_inst *expr)
|
||||||
|
{
|
||||||
|
struct f_val v = f_eval(expr, this_cli->parser_pool);
|
||||||
|
log_reset();
|
||||||
|
|
||||||
|
if (v.type == T_RETURN)
|
||||||
|
{
|
||||||
|
cli_msg(8008, "runtime error");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
val_print(v);
|
||||||
|
cli_msg(23, "%s", log_buffer_ptr);
|
||||||
|
log_reset();
|
||||||
|
}
|
||||||
|
@ -11,6 +11,9 @@ struct sym_show_data {
|
|||||||
struct symbol *sym;
|
struct symbol *sym;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct f_inst;
|
||||||
|
|
||||||
void cmd_show_status(void);
|
void cmd_show_status(void);
|
||||||
void cmd_show_symbols(struct sym_show_data *sym);
|
void cmd_show_symbols(struct sym_show_data *sym);
|
||||||
void cmd_show_memory(void);
|
void cmd_show_memory(void);
|
||||||
|
void cmd_eval(struct f_inst *expr);
|
||||||
|
@ -619,7 +619,11 @@ CF_CLI(DUMP ROUTES,,, [[Dump routing table]])
|
|||||||
CF_CLI(DUMP PROTOCOLS,,, [[Dump protocol information]])
|
CF_CLI(DUMP PROTOCOLS,,, [[Dump protocol information]])
|
||||||
{ protos_dump_all(); cli_msg(0, ""); } ;
|
{ protos_dump_all(); cli_msg(0, ""); } ;
|
||||||
|
|
||||||
CF_CLI(ECHO, echo_mask echo_size, [all | off | <mask>] [<buffer-size>], [[Configure echoing of log messages]]) {
|
CF_CLI(EVAL, term, <expr>, [[Evaluate an expression]])
|
||||||
|
{ cmd_eval($2); } ;
|
||||||
|
|
||||||
|
CF_CLI_HELP(ECHO, ..., [[Control echoing of log messages]])
|
||||||
|
CF_CLI(ECHO, echo_mask echo_size, (all | off | { debug | trace | info | remote | warning | error | auth }) [<buffer-size>], [[Control echoing of log messages]]) {
|
||||||
cli_set_log_echo(this_cli, $2, $3);
|
cli_set_log_echo(this_cli, $2, $3);
|
||||||
cli_msg(0, "");
|
cli_msg(0, "");
|
||||||
} ;
|
} ;
|
||||||
@ -627,7 +631,7 @@ CF_CLI(ECHO, echo_mask echo_size, [all | off | <mask>] [<buffer-size>], [[Config
|
|||||||
echo_mask:
|
echo_mask:
|
||||||
ALL { $$ = ~0; }
|
ALL { $$ = ~0; }
|
||||||
| OFF { $$ = 0; }
|
| OFF { $$ = 0; }
|
||||||
| NUM
|
| '{' log_mask_list '}' { $$ = $2; }
|
||||||
;
|
;
|
||||||
|
|
||||||
echo_size:
|
echo_size:
|
||||||
|
@ -254,6 +254,8 @@ void bgp_log_error(struct bgp_proto *p, u8 class, char *msg, unsigned code, unsi
|
|||||||
#define BS_ESTABLISHED 5
|
#define BS_ESTABLISHED 5
|
||||||
#define BS_CLOSE 6 /* Used during transition to BS_IDLE */
|
#define BS_CLOSE 6 /* Used during transition to BS_IDLE */
|
||||||
|
|
||||||
|
#define BS_MAX 7
|
||||||
|
|
||||||
/* BGP start states
|
/* BGP start states
|
||||||
*
|
*
|
||||||
* Used in PS_START for fine-grained specification of starting state.
|
* Used in PS_START for fine-grained specification of starting state.
|
||||||
|
@ -24,6 +24,13 @@
|
|||||||
|
|
||||||
static struct rate_limit rl_rcv_update, rl_snd_update;
|
static struct rate_limit rl_rcv_update, rl_snd_update;
|
||||||
|
|
||||||
|
/* Table for state -> RFC 6608 FSM error subcodes */
|
||||||
|
static byte fsm_err_subcode[BS_MAX] = {
|
||||||
|
[BS_OPENSENT] = 1,
|
||||||
|
[BS_OPENCONFIRM] = 2,
|
||||||
|
[BS_ESTABLISHED] = 3
|
||||||
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* MRT Dump format is not semantically specified.
|
* MRT Dump format is not semantically specified.
|
||||||
* We will use these values in appropriate fields:
|
* We will use these values in appropriate fields:
|
||||||
@ -720,7 +727,7 @@ bgp_rx_open(struct bgp_conn *conn, byte *pkt, int len)
|
|||||||
|
|
||||||
/* Check state */
|
/* Check state */
|
||||||
if (conn->state != BS_OPENSENT)
|
if (conn->state != BS_OPENSENT)
|
||||||
{ bgp_error(conn, 5, 0, NULL, 0); return; }
|
{ bgp_error(conn, 5, fsm_err_subcode[conn->state], NULL, 0); return; }
|
||||||
|
|
||||||
/* Check message contents */
|
/* Check message contents */
|
||||||
if (len < 29 || len != 29 + pkt[28])
|
if (len < 29 || len != 29 + pkt[28])
|
||||||
@ -1060,7 +1067,7 @@ bgp_rx_update(struct bgp_conn *conn, byte *pkt, int len)
|
|||||||
bgp_conn_enter_established_state(conn);
|
bgp_conn_enter_established_state(conn);
|
||||||
|
|
||||||
if (conn->state != BS_ESTABLISHED)
|
if (conn->state != BS_ESTABLISHED)
|
||||||
{ bgp_error(conn, 5, 0, NULL, 0); return; }
|
{ bgp_error(conn, 5, fsm_err_subcode[conn->state], NULL, 0); return; }
|
||||||
bgp_start_timer(conn->hold_timer, conn->hold_time);
|
bgp_start_timer(conn->hold_timer, conn->hold_time);
|
||||||
|
|
||||||
/* Find parts of the packet and check sizes */
|
/* Find parts of the packet and check sizes */
|
||||||
@ -1122,7 +1129,10 @@ static struct {
|
|||||||
{ 3, 10, "Invalid network field" },
|
{ 3, 10, "Invalid network field" },
|
||||||
{ 3, 11, "Malformed AS_PATH" },
|
{ 3, 11, "Malformed AS_PATH" },
|
||||||
{ 4, 0, "Hold timer expired" },
|
{ 4, 0, "Hold timer expired" },
|
||||||
{ 5, 0, "Finite state machine error" },
|
{ 5, 0, "Finite state machine error" }, /* Subcodes are according to [RFC6608] */
|
||||||
|
{ 5, 1, "Unexpected message in OpenSent state" },
|
||||||
|
{ 5, 2, "Unexpected message in OpenConfirm state" },
|
||||||
|
{ 5, 3, "Unexpected message in Established state" },
|
||||||
{ 6, 0, "Cease" }, /* Subcodes are according to [RFC4486] */
|
{ 6, 0, "Cease" }, /* Subcodes are according to [RFC4486] */
|
||||||
{ 6, 1, "Maximum number of prefixes reached" },
|
{ 6, 1, "Maximum number of prefixes reached" },
|
||||||
{ 6, 2, "Administrative shutdown" },
|
{ 6, 2, "Administrative shutdown" },
|
||||||
@ -1253,7 +1263,7 @@ bgp_rx_keepalive(struct bgp_conn *conn)
|
|||||||
case BS_ESTABLISHED:
|
case BS_ESTABLISHED:
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
bgp_error(conn, 5, 0, NULL, 0);
|
bgp_error(conn, 5, fsm_err_subcode[conn->state], NULL, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1265,7 +1275,7 @@ bgp_rx_route_refresh(struct bgp_conn *conn, byte *pkt, int len)
|
|||||||
BGP_TRACE(D_PACKETS, "Got ROUTE-REFRESH");
|
BGP_TRACE(D_PACKETS, "Got ROUTE-REFRESH");
|
||||||
|
|
||||||
if (conn->state != BS_ESTABLISHED)
|
if (conn->state != BS_ESTABLISHED)
|
||||||
{ bgp_error(conn, 5, 0, NULL, 0); return; }
|
{ bgp_error(conn, 5, fsm_err_subcode[conn->state], NULL, 0); return; }
|
||||||
|
|
||||||
if (!p->cf->enable_refresh)
|
if (!p->cf->enable_refresh)
|
||||||
{ bgp_error(conn, 1, 3, pkt+18, 1); return; }
|
{ bgp_error(conn, 1, 3, pkt+18, 1); return; }
|
||||||
|
@ -70,6 +70,8 @@ static char log_buffer[LOG_BUFFER_SIZE];
|
|||||||
static char *log_buffer_pos;
|
static char *log_buffer_pos;
|
||||||
static int log_buffer_remains;
|
static int log_buffer_remains;
|
||||||
|
|
||||||
|
const char *log_buffer_ptr = log_buffer;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* log_reset - reset the log buffer
|
* log_reset - reset the log buffer
|
||||||
|
Loading…
Reference in New Issue
Block a user