0
0
mirror of https://gitlab.nic.cz/labs/bird.git synced 2024-12-22 17:51:53 +00:00
bird/client/print_cbor.c
2023-12-22 16:42:14 +01:00

671 lines
17 KiB
C

#include <time.h>
#include "nest/cbor_parse.c"
void print_with_size(byte *string, int len)
{
for (int i = 0; i < len; i++)
{
if (string[i] != '_')
putc(string[i], stdout);
else
putc(' ', stdout);
}
}
void print_with_size_(byte *string, int len)
{
for (int i = 0; i < len; i++)
{
putc(string[i], stdout);
}
}
void print_ip_addr(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read); // tag
val = get_value(buf_read); // bytestring
for (int i = 0; i < val.val-1; i++)
{
printf("%i.", buf_read->buff[buf_read->pt + i]);
}
printf("%i", buf_read->buff[buf_read->pt + val.val]);
buf_read->pt+=val.val;
}
void print_ip_prefix(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read); // tag
val = get_value(buf_read); // block
val = get_value(buf_read);
long prefix = val.val;
val = get_value(buf_read); // bytestring
for (int i = 0; i < val.val-1; i++)
{
printf("%i.", buf_read->buff[buf_read->pt + i]);
}
printf("%i/%li", buf_read->buff[buf_read->pt + val.val], prefix);
buf_read->pt+=val.val;
}
void print_distance(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(compare_buff_str(buf_read, val.val, "distance"));
buf_read->pt+=val.val;
val = get_value(buf_read);
if (val.major == UINT)
{
printf("\t\tdistance %li\n", val.val);
return;
}
else if (val.major == TEXT)
{
printf("\t\tdistance ");
print_with_size_(&buf_read->buff[buf_read->pt], val.val);
buf_read->pt+=val.val;
printf("\n");
return;
}
bug("print distance on incorrect type %i\n", val.major);
}
void discard_key(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
if(!(val.major == TEXT))
{
bug("key is not text but %i", val.major);
}
buf_read->pt+=val.val;
}
void print_time(int64_t time)
{
struct tm tm = *localtime(&time);
printf("%d-%02d-%02d %02d:%02d:%02d", tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday, tm.tm_hour, tm.tm_min, tm.tm_sec);
}
void print_lsa_router(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
discard_key(buf_read);
printf("\trouter ");
print_ip_addr(buf_read);
printf("\n");
print_distance(buf_read);
discard_key(buf_read); // vlink
val = get_value(buf_read);
ASSERT(val.major == ARRAY);
val = get_value(buf_read);
while (!val_is_break(val))
{
discard_key(buf_read);
printf("\t\tvlink ");
print_ip_addr(buf_read);
discard_key(buf_read);
val = get_value(buf_read);
printf(" metric %li\n", val.val);
val = get_value(buf_read);
}
discard_key(buf_read); // router metric
val = get_value(buf_read);
ASSERT(val.major == ARRAY);
val = get_value(buf_read);
while (!val_is_break(val))
{
discard_key(buf_read);
printf("\t\trouter ");
print_ip_addr(buf_read);
val = get_value(buf_read);
buf_read->pt+=val.val;
val = get_value(buf_read);
printf(" metric %li\n", val.val);
val = get_value(buf_read);
}
discard_key(buf_read); // network
val = get_value(buf_read);
ASSERT(val.major == ARRAY);
val = get_value(buf_read);
while (!val_is_break(val))
{
ASSERT(val.major == BLOCK);
int block_len = val.val;
discard_key(buf_read); // dummy id
val = get_value(buf_read); //id num
discard_key(buf_read); // network
int bracket = !(block_len == 4 && buf_read->buff[buf_read->pt + 8] == 'l');
printf("\t\tnetwork ");
if (bracket)
printf("[");
print_ip_addr(buf_read);
val = get_value(buf_read);
if (compare_buff_str(buf_read, val.val, "nif"))
{
printf("-");
buf_read->pt+=val.val;
val = get_value(buf_read);
printf("%li", val.val);
}
else if (compare_buff_str(buf_read, val.val, "len"))
{
printf("/");
buf_read->pt+=val.val;
val = get_value(buf_read);
printf("%li", val.val);
}
if (bracket)
printf("]");
discard_key(buf_read);
val = get_value(buf_read);
printf(" metric %li\n", val.val);
val = get_value(buf_read);
}
val = get_value(buf_read);
if (!val_is_break(val))
{
val = get_value(buf_read); // open list
while (!val_is_break(val))
{
buf_read->pt+=val.val; // stubnet
val = get_value(buf_read); // open block
discard_key(buf_read); // stubnet
printf("\t\tstubnet ");
val = get_value(buf_read);
print_ip_addr(buf_read);
discard_key(buf_read); // len
val = get_value(buf_read);
printf("/%li", val.val);
discard_key(buf_read); // metric
val = get_value(buf_read);
printf(" metric %li\n", val.val);
}
val = get_value(buf_read);
}
}
void print_lsa_network(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read);
ASSERT(val.major == TEXT);
if (compare_buff_str(buf_read, val.val, "ospf2"))
{
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == BLOCK);
discard_key(buf_read); // network
printf("\tnetwork ");
print_ip_addr(buf_read);
printf("/");
discard_key(buf_read); // optx
val = get_value(buf_read);
printf("%li\n", val.val);
discard_key(buf_read); // dr
printf("\t\tdr ");
print_ip_addr(buf_read);
printf("\n");
}
else if (compare_buff_str(buf_read, val.val, "ospf"))
{
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == BLOCK);
discard_key(buf_read); // network
printf("\tnetwork ");
print_ip_addr(buf_read);
discard_key(buf_read); // lsa id
val = get_value(buf_read);
printf("-%li\n", val.val);
}
print_distance(buf_read);
discard_key(buf_read); // routers
val = get_value(buf_read);
ASSERT(val.major == ARRAY);
val = get_value(buf_read);
while (!val_is_break(val))
{
discard_key(buf_read);
printf("\t\trouter ");
print_ip_addr(buf_read);
printf("\n");
val = get_value(buf_read);
}
}
void print_lsa_sum_net(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
discard_key(buf_read);
printf("\t\txnetwork ");
print_ip_prefix(buf_read);
discard_key(buf_read);
val = get_value(buf_read);
printf("metric %li\n", val.val);
}
void print_lsa_sum_rt(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
discard_key(buf_read);
printf("\t\txrouter ");
print_ip_addr(buf_read);
discard_key(buf_read);
val = get_value(buf_read);
printf("metric %li\n", val.val);
}
void print_lsa_external(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read);
int via = 0;
if (compare_buff_str(buf_read, val.val, "via"))
{
buf_read->pt+=val.val;
via = buf_read->pt;
val = get_value(buf_read); // tag
val = get_value(buf_read); // bytestring
buf_read->pt+=val.val;
val = get_value(buf_read);
}
long tag = -1;
if (compare_buff_str(buf_read, val.val, "tag"))
{
buf_read->pt+=val.val;
val = get_value(buf_read);
tag = val.val;
val = get_value(buf_read);
}
discard_key(buf_read); // lsa type
printf("\t\t");
val = get_value(buf_read);
print_with_size_(&buf_read->buff[buf_read->pt], val.val);
printf(" ");
discard_key(buf_read);
print_ip_addr(buf_read);
discard_key(buf_read);
printf(" metric");
val = get_value(buf_read);
if (compare_buff_str(buf_read, val.val, "lsa_type_num"))
{
buf_read->pt+=val.val;
val = get_value(buf_read);
printf("%li", val.val);
val = get_value(buf_read);
}
buf_read->pt+=val.val;
val = get_value(buf_read);
printf(" %li", val.val);
if (via)
{
printf(" via ");
int pt = buf_read->pt;
buf_read->pt = via;
print_ip_addr(buf_read);
buf_read->pt = pt;
}
if (tag >- 1)
{
printf(" tag %08lx", tag);
}
val = get_value(buf_read); // end of block
}
void print_lsa_prefix(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read);
if (val_is_break(val))
return;
discard_key(buf_read);
val = get_value(buf_read); // open block or break
while (!val_is_break(val))
{
val = get_value(buf_read);
if (compare_buff_str(buf_read, val.val, "stubnet"))
{
buf_read->pt+=val.val;
printf("\t\tstubnet ");
print_ip_prefix(buf_read);
discard_key(buf_read);
val = get_value(buf_read);
printf(" metric %li", val.val);
}
else
{
buf_read->pt+=val.val;
printf("\t\taddress ");
print_ip_prefix(buf_read);
}
printf("\n");
val = get_value(buf_read);
val = get_value(buf_read); // open block or break
}
val = get_value(buf_read);
print_ip_addr(buf_read);
}
void print_show_ospf(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read);
printf("\n");
if (compare_buff_str(buf_read, val.val, "error"))
{
buf_read->pt+=val.val;
val = get_value(buf_read);
printf("error: ");
print_with_size(&buf_read->buff[buf_read->pt], val.val);
printf("\n");
return;
}
if (compare_buff_str(buf_read, val.val, "not_implemented"))
{
buf_read->pt+=val.val;
val = get_value(buf_read);
printf("not implemented: ");
print_with_size(&buf_read->buff[buf_read->pt], val.val);
printf("\n");
return;
}
buf_read->pt+=val.val;
val = get_value(buf_read); // list
ASSERT(val.major == ARRAY);
int j = val.val;
for (int i = 0; i < j; i++)
{
val = get_value(buf_read); // open block
ASSERT(val.major == BLOCK);
discard_key(buf_read); // dummy id
val = get_value(buf_read);
ASSERT(val.major == UINT);
val = get_value(buf_read);
if (compare_buff_str(buf_read, val.val, "area"))
{
buf_read->pt+=val.val;
printf("area ");
print_ip_addr(buf_read);
printf("\n");
val = get_value(buf_read);
}
if (compare_buff_str(buf_read, val.val, "lsa_router"))
{
buf_read->pt+=val.val;
print_lsa_router(buf_read);
}
else if (compare_buff_str(buf_read, val.val, "lsa_network"))
{
buf_read->pt+=val.val;
print_lsa_network(buf_read);
}
else if (compare_buff_str(buf_read, val.val, "lsa_sum_net"))
{
buf_read->pt+=val.val;
print_lsa_sum_net(buf_read);
}
else if (compare_buff_str(buf_read, val.val, "lsa_sum_rt"))
{
buf_read->pt+=val.val;
print_lsa_sum_rt(buf_read);
}
else if (compare_buff_str(buf_read, val.val, "lsa_prefix"))
{
buf_read->pt+=val.val;
print_lsa_prefix(buf_read);
}
else if (compare_buff_str(buf_read, val.val, "lsa_external"))
{
buf_read->pt+=val.val;
print_lsa_external(buf_read);
}
val = get_value(buf_read);
}
discard_key(buf_read);
val = get_value(buf_read);
while (!val_is_break(val))
{
val = get_value(buf_read);
if (val_is_break(val))
return;
if (compare_buff_str(buf_read, val.val, "other_ABSRs"))
{
buf_read->pt+=val.val;
printf("other ABSRs\n");
val = get_value(buf_read); // null list
val = get_value(buf_read);
}
if (compare_buff_str(buf_read, val.val, "router"))
{
buf_read->pt+=val.val;
printf("router ");
print_ip_addr(buf_read);
val = get_value(buf_read);
}
buf_read->pt+=val.val;
print_lsa_external(buf_read);
val = get_value(buf_read);
val = get_value(buf_read);
}
}
void print_show_memory(struct buff_reader *buf_read)
{
printf("BIRD memory usage\n");
printf(" Effective Overhead\n");
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read); // header, may be it should be deleted
ASSERT(val.major == TEXT);
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == TEXT);
buf_read->pt+=val.val;
val = get_value(buf_read); // body
ASSERT(val.major == TEXT);
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read);
while (val.major == TEXT && buf_read->pt < buf_read->size)
{
print_with_size(&buf_read->buff[buf_read->pt], val.val);
for (unsigned long i = 0; i < strlen(" ") - val.val; i++)
{
putc(' ', stdout);
}
buf_read->pt+=val.val;
val = get_value(buf_read); // block open
val = get_value(buf_read);
ASSERT(val.major == TEXT);
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == UINT);
printf("%7li B ", val.val);
val = get_value(buf_read);
ASSERT(val.major == TEXT);
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == UINT);
printf("%7li B\n", val.val);
val = get_value(buf_read);
}
}
void print_show_status(struct buff_reader *buf_read)
{
/*
print("BIRD", answer["show_status:message"]["version"])
for key in answer["show_status:message"]["body"].keys():
name = key.replace("_", " ")
if key == "router_id":
print(name, self.addr_to_str( answer["show_status:message"]["body"][key]))
elif key in "server_time last_reboot last_reconfiguration":
print(name, datetime.datetime.fromtimestamp(answer["show_status:message"]["body"][key]))
else:
print(name, answer["show_status:message"]["body"][key])
print(answer["show_status:message"]["state"])
*/
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read);
ASSERT(val.major == TEXT);
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == TEXT);
printf("BIRD ");
print_with_size(&buf_read->buff[buf_read->pt], val.val);
printf("\n");
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == TEXT); // body
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == BLOCK);
val = get_value(buf_read);
ASSERT(val.major == TEXT); // router id
buf_read->pt+=val.val;
printf("router id: ");
print_ip_addr(buf_read);
printf("\n");
val = get_value(buf_read);
ASSERT(val.major == TEXT); // hostname
buf_read->pt+=val.val;
printf("hostname: ");
val = get_value(buf_read);
ASSERT(val.major == TEXT);
print_with_size(&buf_read->buff[buf_read->pt], val.val);
printf("\n");
buf_read->pt+=val.val;
for (int i =0; i<3; i++)
{
val = get_value(buf_read);
ASSERT(val.major == TEXT); // server time, last rebooot, last reconfiguration
print_with_size(&buf_read->buff[buf_read->pt], val.val);
buf_read->pt+=val.val;
printf(": ");
val = get_value(buf_read);
ASSERT(val.major == UINT);
print_time(val.val);
printf("\n");
}
val = get_value(buf_read);
if (val.major != TEXT)
val = get_value(buf_read);
ASSERT(val.major == TEXT); // state
printf("state: ");
buf_read->pt+=val.val;
val = get_value(buf_read);
ASSERT(val.major == TEXT);
print_with_size(&buf_read->buff[buf_read->pt], val.val);
printf("\n");
buf_read->pt+=val.val;
}
void print_show_symbols(struct buff_reader *buf_read)
{
struct value val = get_value(buf_read);
ASSERT(val.major == BLOCK);
discard_key(buf_read);
val = get_value(buf_read);
int one_item = 0;
if (val.val == 1)
one_item = 1;
if (val.val == 0)
return;
val = get_value(buf_read);
if (val_is_break(val))
{
printf("no names found\n");
return;
}
val = get_value(buf_read);
while (val.major == TEXT)
{
buf_read->pt+=val.val; //name
val = get_value(buf_read);
print_with_size_(&buf_read->buff[buf_read->pt], val.val);
for (int i = val.val; i < 15; i++)
{
printf(" ");
}
buf_read->pt+=val.val;
val = get_value(buf_read); //type
buf_read->pt+=val.val;
val = get_value(buf_read);
print_with_size_(&buf_read->buff[buf_read->pt], val.val);
printf("\n");
buf_read->pt+=val.val;
if (one_item)
return;
val = get_value(buf_read);
if (val_is_break(val))
return;
val = get_value(buf_read);
}
}
void print_cbor_response(byte *cbor, int len)
{
struct buff_reader buf_read;
buf_read.buff = cbor;
buf_read.size = len;
buf_read.pt = 0;
struct value val = get_value(&buf_read);
ASSERT(val.major == BLOCK);
ASSERT(val.val <=1);
val = get_value(&buf_read);
ASSERT(val.major == TEXT);
printf("\n");
if (compare_buff_str(&buf_read, val.val, "show_memory:message"))
{
buf_read.pt += val.val;
print_show_memory(&buf_read);
}
else if (compare_buff_str(&buf_read, val.val, "show_status:message"))
{
buf_read.pt += val.val;
print_show_status(&buf_read);
}
else if (compare_buff_str(&buf_read, val.val, "show_symbols:message"))
{
buf_read.pt += val.val;
print_show_symbols(&buf_read);
}
else if (compare_buff_str(&buf_read, val.val, "show_ospf:message"))
{
buf_read.pt += val.val;
print_show_ospf(&buf_read);
}
printf("\nbird>");
fflush(stdout);
}