Skip to content
This repository has been archived by the owner on Apr 28, 2024. It is now read-only.

Commit

Permalink
Changed logging option to -M with arbitrary filename, reordered argp …
Browse files Browse the repository at this point in the history
…options, code consolidation in zfw_tc_ingress.c
  • Loading branch information
r-caamano committed Jan 5, 2024
1 parent db1ca7f commit 594846b
Show file tree
Hide file tree
Showing 3 changed files with 152 additions and 73 deletions.
6 changes: 4 additions & 2 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,15 @@
All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

---
# [0.5.5] - 2024-01-02
# [0.5.5] - 2024-01-05

###

-- Changed ICMP Unreachable logging to default level
-- Added -M logging output to /var/log/zfw.log
-- Added -L, --write-log option to -M, --monitor output to a specified log file
-- Removed redundant check on ifname in process_events
-- Code consolidation in zfw_tc_ingress.c

# [0.5.4] - 2023-12-24

###
Expand Down
174 changes: 125 additions & 49 deletions src/zfw.c
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@ bool ebpf_disable = false;
bool list_diag = false;
bool monitor = false;
bool tun = false;
bool logging = false;
struct in_addr dcidr;
struct in_addr scidr;
unsigned short dplen;
Expand Down Expand Up @@ -147,6 +148,7 @@ char *tun_interface;
char *vrrp_interface;
char *monitor_interface;
char *tc_interface;
char *log_file_name;
char *object_file;
char *direction_string;
const char *argp_program_version = "0.5.5";
Expand Down Expand Up @@ -1603,52 +1605,81 @@ static int process_events(void *ctx, void *data, size_t len){
char *ifname = if_indextoname(evt->ifindex, buf);
char *ts = get_ts(evt->tstamp);
char message[250];
int res = 0;
if(((ifname && monitor_interface && !strcmp(monitor_interface, ifname)) || all_interface) && ts)
{
if(evt->error_code){
if(evt->error_code == IP_HEADER_TOO_BIG){
sprintf(message,"%s : %s : %s : IP Header Too Big\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == NO_IP_OPTIONS_ALLOWED){
sprintf(message, "%s : %s : %s : No IP Options Allowed\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == UDP_HEADER_TOO_BIG){
sprintf(message, "%s : %s : %s : UDP Header Too Big\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == GENEVE_HEADER_TOO_BIG){
sprintf(message, "%s : %s : %s : Geneve Header Too Big\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == GENEVE_HEADER_LENGTH_VERSION_ERROR){
sprintf(message,"%s : %s : %s : Geneve Header Length: Version Error\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == SKB_ADJUST_ERROR){
sprintf(message, "%s : %s : %s : SKB Adjust Error\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == ICMP_HEADER_TOO_BIG){
sprintf(message, "%s : %s : %s : ICMP Header Too Big\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == IF_LIST_MATCH_ERROR){
sprintf(message, "%s : %s : %s : Interface did not match and per interface filtering is enabled\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(evt->error_code == NO_REDIRECT_STATE_FOUND){
sprintf(message, "%s : %s : %s : No Redirect State found\n", ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS");
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
}
else{
Expand All @@ -1670,16 +1701,22 @@ static int process_events(void *ctx, void *data, size_t len){
sprintf(message, "%s : %s : %s :%s:%d[%x:%x:%x:%x:%x:%x] > %s:%d[%x:%x:%x:%x:%x:%x] redirect ---> %s\n", ts, ifname, protocol,saddr, ntohs(evt->sport),
evt->source[0], evt->source[1], evt->source[2], evt->source[3], evt->source[4], evt->source[5], daddr, ntohs(evt->dport),
evt->dest[0],evt->dest[1], evt->dest[2], evt->dest[3], evt->dest[4], evt->dest[5], tun_ifname);
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
}
else if(evt->tport && ifname){
sprintf(message, "%s : %s : %s : %s :%s:%d > %s:%d | tproxy ---> 127.0.0.1:%d\n",
ts, ifname, (evt->direction == INGRESS) ? "INGRESS" : "EGRESS", protocol,saddr, ntohs(evt->sport),
daddr, ntohs(evt->dport), ntohs(evt->tport));
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
else if(((evt->proto == IPPROTO_TCP) | (evt->proto == IPPROTO_UDP)) && evt->tracking_code && ifname){
char *state = NULL;
Expand Down Expand Up @@ -1724,17 +1761,23 @@ static int process_events(void *ctx, void *data, size_t len){
if(state){
sprintf(message, "%s : %s : %s : %s :%s:%d > %s:%d outbound_tracking ---> %s\n", ts, ifname,
(evt->direction == INGRESS) ? "INGRESS" : "EGRESS", protocol,saddr, ntohs(evt->sport), daddr, ntohs(evt->dport), state);
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
}
else if(evt->proto == IPPROTO_ICMP && ifname){
__u16 code = evt->tracking_code;
if(code == 4){
sprintf(message, "%s : %s : %s : %s :%s --> reported next hop mtu:%d > FRAGMENTATION NEEDED IN PATH TO:%s:%d\n", ts, ifname,
(evt->direction == INGRESS) ? "INGRESS" : "EGRESS", protocol,saddr, ntohs(evt->sport), daddr, ntohs(evt->dport));
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}else{
char *code_string = NULL;
char *protocol_string = NULL;
Expand All @@ -1760,16 +1803,22 @@ static int process_events(void *ctx, void *data, size_t len){
if(code_string){
sprintf(message, "%s : %s : %s : %s :%s --> REPORTED:%s > in PATH TO:%s:%s:%d\n", ts, ifname,
(evt->direction == INGRESS) ? "INGRESS" : "EGRESS", protocol,saddr, code_string, daddr, protocol_string, ntohs(evt->dport));
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
}
}
else if(ifname){
sprintf(message, "%s : %s : %s : %s :%s:%d > %s:%d\n", ts, ifname,
(evt->direction == INGRESS) ? "INGRESS" : "EGRESS", protocol,saddr, ntohs(evt->sport), daddr, ntohs(evt->dport));
printf("%s", message);
write_log("/var/log/zfw.log", message);
if(logging){
res = write_log(log_file_name, message);
}else{
printf("%s", message);
}
}
if(saddr){
free(saddr);
Expand All @@ -1782,6 +1831,13 @@ static int process_events(void *ctx, void *data, size_t len){
free(ts);
}
}
if(res){
printf("Unable to write to log\n");
if(ring_buffer){
ring_buffer__free(ring_buffer);
close_maps(1);
}
}
return 0;
}

Expand Down Expand Up @@ -2346,36 +2402,37 @@ void map_list_all()

// commandline parser options
static struct argp_option options[] = {
{"insert", 'I', NULL, 0, "Insert map rule", 0},
{"delete", 'D', NULL, 0, "Delete map rule", 0},
{"list", 'L', NULL, 0, "List map rules", 0},
{"list-diag", 'E', NULL, 0, "", 0},
{"flush", 'F', NULL, 0, "Flush all map rules", 0},
{"set-tun-mode", 'T', "", 0, "Set tun mode on interface", 0},
{"disable-ebpf", 'Q', NULL, 0, "Delete tc from all interface and remove all maps", 0},
{"insert", 'I', NULL, 0, "Insert map rule", 0},
{"list", 'L', NULL, 0, "List map rules", 0},
{"monitor", 'M', "", 0, "Monitor ebpf events for interface", 0},
{"interface", 'N', "", 0, "Interface <optional insert>", 0},
{"object-file", 'O', "", 0, "Set object file", 0},
{"per-interface-rules", 'P', "", 0, "Set interface to per interface rule aware", 0},
{"disable-ssh", 'x', "", 0, "Disable inbound ssh to interface (default enabled)", 0},
{"dcidr-block", 'c', "", 0, "Set dest ip prefix i.e. 192.168.1.0 <mandatory for insert/delete/list>", 0},
{"icmp-echo", 'e', "", 0, "Enable inbound icmp echo to interface", 0},
{"verbose", 'v', "", 0, "Enable verbose tracing on interface", 0},
{"disable-ebpf", 'Q', NULL, 0, "Delete tc from all interface and remove all maps", 0},
{"vrrp-enable", 'R', "", 0, "Enable vrrp passthrough on interface", 0},
{"set-tun-mode", 'T', "", 0, "Set tun mode on interface", 0},
{"write-log", 'W', "", 0, "Write to monitor output to /var/log/<log file name> <optional for monitor>", 0},
{"set-tc-filter", 'X', "", 0, "Add/remove TC filter to/from interface", 0},
{"dcidr-block", 'c', "", 0, "Set dest ip prefix i.e. 192.168.1.0 <mandatory for insert/delete/list>", 0},
{"disable", 'd', NULL, 0, "Disable associated diag operation i.e. -e eth0 -d to disable inbound echo on eth0", 0},
{"ocidr-block", 'o', "", 0, "Set origin ip prefix i.e. 192.168.1.0 <mandatory for insert/delete/list>", 0},
{"icmp-echo", 'e', "", 0, "Enable inbound icmp echo to interface", 0},
{"passthrough", 'f', NULL, 0, "List passthrough rules <optional list>", 0},
{"high-port", 'h', "", 0, "Set high-port value (1-65535)> <mandatory for insert>", 0},
{"intercepts", 'i', NULL, 0, "List intercept rules <optional for list>", 0},
{"low-port", 'l', "", 0, "Set low-port value (1-65535)> <mandatory insert/delete>", 0},
{"dprefix-len", 'm', "", 0, "Set dest prefix length (1-32) <mandatory for insert/delete/list >", 0},
{"oprefix-len", 'n', "", 0, "Set origin prefix length (1-32) <mandatory for insert/delete/list >", 0},
{"low-port", 'l', "", 0, "Set low-port value (1-65535)> <mandatory insert/delete>", 0},
{"high-port", 'h', "", 0, "Set high-port value (1-65535)> <mandatory for insert>", 0},
{"tproxy-port", 't', "", 0, "Set high-port value (0-65535)> <mandatory for insert>", 0},
{"ocidr-block", 'o', "", 0, "Set origin ip prefix i.e. 192.168.1.0 <mandatory for insert/delete/list>", 0},
{"protocol", 'p', "", 0, "Set protocol (tcp or udp) <mandatory insert/delete>", 0},
{"route", 'r', NULL, 0, "Add or Delete static ip/prefix for intercept dest to lo interface <optional insert/delete>", 0},
{"intercepts", 'i', NULL, 0, "List intercept rules <optional for list>", 0},
{"passthrough", 'f', NULL, 0, "List passthrough rules <optional list>", 0},
{"monitor", 'M', "", 0, "Monitor ebpf events for interface", 0},
{"interface", 'N', "", 0, "Interface <optional insert>", 0},
{"list-diag", 'E', NULL, 0, "", 0},
{"set-tc-filter", 'X', "", 0, "Add/remove TC filter to/from interface", 0},
{"object-file", 'O', "", 0, "Set object file", 0},
{"direction", 'z', "", 0, "Set direction", 0},
{"tproxy-port", 't', "", 0, "Set high-port value (0-65535)> <mandatory for insert>", 0},
{"verbose", 'v', "", 0, "Enable verbose tracing on interface", 0},
{"enable-eapol", 'w', "", 0, "enable 802.1X eapol packets inbound on interface", 0},
{"disable-ssh", 'x', "", 0, "Disable inbound ssh to interface (default enabled)", 0},
{"direction", 'z', "", 0, "Set direction", 0},
{0}};

static error_t parse_opt(int key, char *arg, struct argp_state *state)
Expand Down Expand Up @@ -2528,6 +2585,16 @@ static error_t parse_opt(int key, char *arg, struct argp_state *state)
tun_interface = arg;
}
break;
case 'W':
if (!strlen(arg) || (strchr(arg, '-') != NULL))
{
fprintf(stderr, "logfile name -W, --write-log: %s\n", arg);
fprintf(stderr, "%s --help for more info\n", program_name);
exit(1);
}
logging = true;
log_file_name = arg;
break;
case 'X':
if (!strlen(arg) || (strchr(arg, '-') != NULL))
{
Expand Down Expand Up @@ -2843,6 +2910,15 @@ int main(int argc, char **argv)
usage("-X, --set-tc-filter requires -z, --direction for add operation");
}

if (logging)
{
if ((tcfilter || echo || ssh_disable || verbose || per_interface
|| add || delete || list || flush || eapol) || (!monitor))
{
usage("W, --write-log can only be used in combination call to -M, --monitor");
}
}

if (ebpf_disable)
{
if (tcfilter || echo || ssh_disable || verbose || per_interface || add || delete || list || flush || monitor || eapol)
Expand Down
Loading

0 comments on commit 594846b

Please sign in to comment.