Implemented BGP community parsers logic (#895)

This commit is contained in:
Pavel Odintsov 2020-12-06 14:49:15 +00:00 committed by GitHub
parent 731d123323
commit a7357e3ee0
Signed by: GitHub
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 108 additions and 11 deletions

View File

@ -212,7 +212,7 @@ target_link_libraries(unified_parser fastnetmon_packet_parser)
# Our ipfix database library
add_library(ipfix_rfc STATIC ipfix_rfc.cpp)
add_library(bgp_protocol bgp_flow_spec.cpp)
add_library(bgp_protocol bgp_protocol.cpp)
# Our packet parser
add_library(fastnetmon_packet_parser STATIC fastnetmon_packet_parser.c)

View File

@ -1,4 +1,4 @@
#include "bgp_flow_spec.h"
#include "bgp_protocol.hpp"
#include "log4cpp/Appender.hh"
#include "log4cpp/BasicLayout.hh"
@ -9,6 +9,11 @@
#include "log4cpp/PatternLayout.hh"
#include "log4cpp/Priority.hh"
#include "all_logcpp_libraries.h"
// Get log4cpp logger from main programm
extern log4cpp::Category& logger;
// Enable custom casts from our own types
std::ostream& operator<<(std::ostream& os, bgp_flow_spec_protocol_t const& protocol) {
if (protocol == FLOW_SPEC_PROTOCOL_UDP) {
@ -63,3 +68,55 @@ std::ostream& operator<<(std::ostream& os, flow_spec_fragmentation_types_t const
}
}
bool read_bgp_community_from_string(std::string community_as_string, bgp_community_attribute_element_t& bgp_community_attribute_element) {
std::vector<std::string> community_as_vector;
split(community_as_vector, community_as_string, boost::is_any_of(":"), boost::token_compress_on);
if (community_as_vector.size() != 2) {
logger << log4cpp::Priority::WARN << "Could not parse community: " << community_as_string;
return false;
}
int asn_as_integer = 0;
if (!convert_string_to_positive_integer_safe(community_as_vector[0], asn_as_integer)) {
logger << log4cpp::Priority::WARN << "Could not parse ASN from raw format: " << community_as_vector[0];
return false;
}
int community_number_as_integer = 0;
if (!convert_string_to_positive_integer_safe(community_as_vector[1], community_number_as_integer)) {
logger << log4cpp::Priority::WARN << "Could not parse community from raw format: " << community_as_vector[0];
return false;
}
if (asn_as_integer < 0 or community_number_as_integer < 0) {
logger << log4cpp::Priority::WARN << "For some strange reasons we've got negative ASN or community numbers";
return false;
}
if (asn_as_integer > UINT16_MAX) {
logger << log4cpp::Priority::ERROR << "Your ASN value exceeds maximum allowed value " << UINT16_MAX;
return false;
}
if (community_number_as_integer > UINT16_MAX) {
logger << log4cpp::Priority::ERROR << "Your community value exceeds maximum allowed value " << UINT16_MAX;
return false;
}
bgp_community_attribute_element.asn_number = asn_as_integer;
bgp_community_attribute_element.community_number = community_number_as_integer;
return true;
}
// Wrapper function which just checks correctness of bgp community
bool is_bgp_community_valid(std::string community_as_string) {
bgp_community_attribute_element_t bgp_community_attribute_element;
return read_bgp_community_from_string(community_as_string, bgp_community_attribute_element);
}

View File

@ -1,5 +1,4 @@
#ifndef BGP_FLOW_SPEC_H
#define BGP_FLOW_SPEC_H
#pragma once
#include <stdint.h>
#include <string>
@ -64,6 +63,23 @@ enum bgp_flow_spec_protocol_t {
FLOW_SPEC_PROTOCOL_ICMP,
};
// Class for storing old style BGP communities which support only 16 bit ASN numbers
class __attribute__((__packed__)) bgp_community_attribute_element_t {
public:
uint16_t asn_number = 0;
uint16_t community_number = 0;
void host_byte_order_to_network_byte_order() {
asn_number = htons(asn_number);
community_number = htons(community_number);
}
};
bool read_bgp_community_from_string(std::string community_as_string, bgp_community_attribute_element_t& bgp_community_attribute_element);
static_assert(sizeof(bgp_community_attribute_element_t) == 4, "Broken size of bgp_community_attribute_element_t");
// Enable custom casts from our own types
std::ostream& operator<<(std::ostream& os, bgp_flow_spec_protocol_t const& protocol);
@ -524,4 +540,5 @@ class exabgp_flow_spec_rule_t : public flow_spec_rule_t {
void exabgp_flow_spec_rule_ban_manage(std::string action, flow_spec_rule_t flow_spec_rule);
#endif
bool read_bgp_community_from_string(std::string community_as_string, bgp_community_attribute_element_t& bgp_community_attribute_element);
bool is_bgp_community_valid(std::string community_as_string);

View File

@ -1439,3 +1439,26 @@ bool ip_belongs_to_patricia_tree_ipv6(patricia_tree_t* patricia_tree, struct in6
return patricia_search_best2(patricia_tree, &prefix_for_check_address, 1) != NULL;
}
// Safe way to convert string to positive integer.
// We accept only positive numbers here
bool convert_string_to_positive_integer_safe(std::string line, int& value) {
int temp_value = 0;
try {
temp_value = std::stoi(line);
} catch (...) {
// Could not parse number correctly
return false;
}
if (temp_value >= 0) {
value = temp_value;
return true;
} else {
// We do not expect negative values here
return false;
}
return true;
}

View File

@ -1,5 +1,4 @@
#ifndef FAST_LIBRARY_H
#define FAST_LIBRARY_H
#pragma once
#include "fastnetmon_types.h"
@ -121,4 +120,4 @@ bool set_boost_process_name(boost::thread* thread, std::string process_name);
std::string print_ipv6_cidr_subnet(subnet_ipv6_cidr_mask_t subnet);
std::string convert_any_ip_to_string(subnet_ipv6_cidr_mask_t subnet);
#endif
bool convert_string_to_positive_integer_safe(std::string line, int& value);

View File

@ -229,6 +229,7 @@ gobgp = off
gobgp_next_hop = 0.0.0.0
gobgp_announce_host = on
gobgp_announce_whole_subnet = off
gobgp_community = 65001:666
# Graphite monitoring
# InfluxDB is also supported, please check our reference:

View File

@ -23,7 +23,7 @@
#include <sys/resource.h>
#include <sys/stat.h>
#include "bgp_flow_spec.h"
#include "bgp_protocol.hpp"
#include "fast_library.h"
#include "fastnetmon_packet_parser.h"
#include "fastnetmon_types.h"

View File

@ -6,7 +6,7 @@
#include <vector>
#include "all_logcpp_libraries.h"
#include "bgp_flow_spec.h"
#include "bgp_protocol.hpp"
#include "fast_library.h"
#include "fast_platform.h"
#include "fastnetmon_packet_parser.h"

View File

@ -1,5 +1,5 @@
#include "fastnetmon_types.h"
#include "bgp_flow_spec.h"
#include "bgp_protocol.hpp"
#ifdef ENABLE_DPI
#include "fast_dpi.h"