Filter olsrv2.lan settings to clear the host bits
authorHenning Rogge <henning.rogge@fkie.fraunhofer.de>
Tue, 26 May 2015 11:36:07 +0000 (13:36 +0200)
committerHenning Rogge <henning.rogge@fkie.fraunhofer.de>
Tue, 26 May 2015 11:36:07 +0000 (13:36 +0200)
src-api/common/netaddr.c
src-api/common/netaddr.h
src-plugins/olsrv2/olsrv2/olsrv2.c
src-plugins/olsrv2/olsrv2/olsrv2_reader.c
src-plugins/olsrv2/olsrv2/olsrv2_routing.c

index 9a22d5f..f321143 100644 (file)
@@ -389,6 +389,41 @@ netaddr_create_prefix(struct netaddr *prefix, const struct netaddr *host,
   return 0;
 }
 
+/**
+ * Clear the bits outside of the prefix length of an address
+ * @param dst trucated destination buffer
+ * @param src source IP
+ */
+void
+netaddr_truncate(struct netaddr *dst, const struct netaddr *src) {
+  static uint8_t MASK[] = { 0, 0x80, 0xc0, 0xe0, 0xf0, 0xf8, 0xfc, 0xfe };
+  int byte_prefix, bit_prefix;
+
+  /* calulate byte/bit part of prefix */
+  byte_prefix = src->_prefix_len / 8;
+  bit_prefix = src->_prefix_len & 7;
+
+  if (src != dst) {
+    /* copy type and prefix length */
+    dst->_prefix_len = src->_prefix_len;
+    dst->_type = src->_type;
+
+    /* copy constant octets */
+    memcpy(dst->_addr, src->_addr, byte_prefix);
+  }
+
+  if (bit_prefix) {
+    /* modify bitwise */
+    dst->_addr[byte_prefix] = src->_addr[byte_prefix] & MASK[bit_prefix];
+    byte_prefix++;
+  }
+
+  if (byte_prefix < 16) {
+    /* zero rest of address */
+    memset(&dst->_addr[byte_prefix], 0, 16 - byte_prefix);
+  }
+}
+
 /**
  * Initialize a netaddr_socket with a netaddr and a port number
  * @param combined pointer to netaddr_socket to be initialized
index b80c48d..3a00bc9 100644 (file)
@@ -156,6 +156,7 @@ EXPORT int netaddr_create_host_bin(struct netaddr *host, const struct netaddr *n
     const void *number, size_t num_length);
 EXPORT int netaddr_create_prefix(struct netaddr *prefix, const struct netaddr *host,
     const struct netaddr *netmask, bool truncate);
+EXPORT void netaddr_truncate(struct netaddr *dst, const struct netaddr *src);
 
 EXPORT int netaddr_socket_init(union netaddr_socket *combined,
     const struct netaddr *addr, uint16_t port, unsigned if_index);
index ab7728a..9ed03cc 100644 (file)
@@ -619,6 +619,10 @@ _parse_lan_array(struct cfg_named_section *section, bool add) {
     if (netaddr_from_string(&prefix, addr_buf.buf)) {
       continue;
     }
+
+    /* truncate address */
+    netaddr_truncate(&prefix, &prefix);
+
     if (_parse_lan_parameters(&data, ptr)) {
       continue;
     }
index a9d3002..7bbdbaa 100644 (file)
@@ -303,6 +303,7 @@ _cb_addresstlvs(struct rfc5444_reader_tlvblock_context *context __attribute__((u
   uint32_t cost_in[NHDP_MAXIMUM_DOMAINS];
   uint32_t cost_out[NHDP_MAXIMUM_DOMAINS];
   struct rfc7181_metric_field metric_value;
+  struct netaddr truncated;
   size_t i;
 #ifdef OONF_LOG_DEBUG_INFO
   struct netaddr_str buf;
@@ -383,8 +384,11 @@ _cb_addresstlvs(struct rfc5444_reader_tlvblock_context *context __attribute__((u
       continue;
     }
 
+    /* truncate address */
+    netaddr_truncate(&truncated, &context->addr);
+
     /* parse attached network */
-    end = olsrv2_tc_endpoint_add(_current.node, &context->addr, false);
+    end = olsrv2_tc_endpoint_add(_current.node, &truncated, false);
     if (!end) {
       continue;
     }
index ae86ca6..d56d1dc 100644 (file)
@@ -362,7 +362,7 @@ _add_entry(struct nhdp_domain *domain, struct netaddr *prefix) {
 static void
 _remove_entry(struct olsrv2_routing_entry *entry) {
   /* remove entry from database if its still there */
-  if (list_is_node_added(&entry->_node.list)) {
+  if (avl_is_node_added(&entry->_node)) {
     avl_remove(&_routing_tree[entry->domain->index], &entry->_node);
   }
   oonf_class_free(&_rtset_entry, entry);
@@ -844,6 +844,11 @@ _cb_route_finished(struct os_route *route, int error) {
               strerror(error), error);
     }
 
+    if (error == EEXIST && rtentry->set) {
+      /* exactly this route already exists */
+      return;
+    }
+
     /* revert attempted change */
     if (rtentry->set) {
       _remove_entry(rtentry);