LCOV - code coverage report
Current view: top level - waltz/ip - fd_fib4.h (source / functions) Hit Total Coverage
Test: cov.lcov Lines: 9 13 69.2 %
Date: 2026-08-16 04:31:21 Functions: 2 39 5.1 %

          Line data    Source code
       1             : #ifndef HEADER_fd_src_waltz_ip_fd_fib4_h
       2             : #define HEADER_fd_src_waltz_ip_fd_fib4_h
       3             : 
       4             : /* A fib4 stores IPv4 routes in a query-optimized data structure.
       5             : 
       6             :    fib4 does not scale well to large numbers of routes.  Every route
       7             :    lookup is O(n) where n is the number of routes in the FIB.
       8             : 
       9             :    fib4 only supports a minimal set of features required for end devices
      10             :    to operate.  Packet forwarding is not supported.
      11             : 
      12             :    A fib4 always has a dummy route at index 0.
      13             : 
      14             :    FIXME: CONSIDER TRIE BASED DATA STRUCTURE
      15             : 
      16             :    Trivia: https://en.wikipedia.org/wiki/Forwarding_information_base */
      17             : 
      18             : #include "../../util/fd_util_base.h"
      19             : 
      20             : #define FD_FIB4_ALIGN (128UL)
      21             : 
      22             : /* FD_FIB4_RTYPE_{...} enumerate route types.
      23             :    These match Linux RTN_UNICAST, etc. */
      24             : 
      25        5364 : #define FD_FIB4_RTYPE_UNSPEC    (0) /* invalid */
      26         168 : #define FD_FIB4_RTYPE_UNICAST   (1) /* "normal" path */
      27          45 : #define FD_FIB4_RTYPE_LOCAL     (2) /* address on local host */
      28          72 : #define FD_FIB4_RTYPE_BROADCAST (3) /* reserved for future use */
      29           0 : #define FD_FIB4_RTYPE_MULTICAST (5) /* reserved for future use */
      30           3 : #define FD_FIB4_RTYPE_BLACKHOLE (6) /* drop packet */
      31          78 : #define FD_FIB4_RTYPE_THROW     (9) /* continue in next table */
      32             : 
      33             : /* fd_fib4_t is a local handle to a fib4 object. Use fd_fib4_{join,leave}
      34             :    to join the fd_fib4_t to the shmem fib4. A fd_fib4_t can be stack declared,
      35             :    e.g. fd_fib4_t fib4[1]; */
      36             : 
      37             : struct fd_fib4_priv;
      38             : typedef struct fd_fib4_priv fd_fib4_priv_t;
      39             : struct fd_fib4 {
      40             :    /* local ptr to shared fib4_priv_t */
      41             :    fd_fib4_priv_t * priv;
      42             : 
      43             :    /* local join to the hmap - punned internally */
      44             :    uchar            hmap_join[64] __attribute__((aligned(8)));
      45             :  };
      46             : typedef struct fd_fib4 fd_fib4_t;
      47             : 
      48             : /* fd_fib4_hop_t holds a FIB lookup result (see fd_fib4_lookup) */
      49             : 
      50             : struct __attribute__((aligned(16))) fd_fib4_hop {
      51             :   uint  ip4_gw;   /* gateway address (big endian) */
      52             :   uint  if_idx;   /* output interface index */
      53             :   uint  ip4_src;  /* override source address (big endian). 0 implies unset */
      54             :   uchar rtype;    /* route type (e.g. FD_FIB4_RTYPE_UNICAST) */
      55             :   uchar scope;    /* used to select source address */
      56             :   uchar flags;    /* app-specific flags */
      57             : };
      58             : 
      59           0 : #define FD_FIB4_FLAG_RTA_UNSUPPORTED   ((uchar)0x01U) /* unsupported route attribute */
      60           0 : #define FD_FIB4_FLAG_RTA_PARSE_ERR     ((uchar)0x02U) /* failed to interpret route attribute */
      61           0 : #define FD_FIB4_FLAG_RTYPE_UNSUPPORTED ((uchar)0x03U) /* unsupported route type */
      62             : 
      63             : typedef struct fd_fib4_hop fd_fib4_hop_t;
      64             : 
      65             : FD_PROTOTYPES_BEGIN
      66             : 
      67             : /* Constructor APIs ******************************************************/
      68             : 
      69             : FD_FN_CONST ulong
      70             : fd_fib4_align( void );
      71             : 
      72             : FD_FN_CONST ulong
      73             : fd_fib4_footprint( ulong route_max,
      74             :                    ulong route_peer_max );
      75             : 
      76             : /* fd_fib4_new formats a shared memory region mem with alignment and footprint
      77             :    suitable for a fib4. It expects at most route_peer_max /32 routes, and
      78             :    at most route_max non-/32 routes. Returns mem on success and NULL on failure.
      79             :    Takes seed to be used for the hashmap. */
      80             : 
      81             : void *
      82             : fd_fib4_new( void * mem,
      83             :              ulong  route_max,
      84             :              ulong  route_peer_max,
      85             :              ulong  route_peer_seed );
      86             : 
      87             : /* fd_fib4_join joins the caller to a shared memory region shmem holding a fib4.
      88             :    fib4 should be a pointer to the local join to populate, and shmem should be a
      89             :    pointer in the caller's address space to the shared memory region formatted
      90             :    using fd_fib4_new. Returns fib4 on success and NULL on failure. */
      91             : 
      92             : fd_fib4_t *
      93             : fd_fib4_join( fd_fib4_t * fib4,
      94             :               void *      shmem );
      95             : 
      96             : void *
      97             : fd_fib4_leave( fd_fib4_t * fib4 );
      98             : 
      99             : void *
     100             : fd_fib4_delete( void * mem );
     101             : 
     102             : /* Write APIs ************************************************************/
     103             : 
     104             : /* fd_fib4_clear removes all route table entries but the first. Remove all
     105             :    entries in the route hmap. Sets the first route table entry to
     106             :    "throw 0.0.0.0/0 metric ((2<<32)-1)". */
     107             : 
     108             : void
     109             : fd_fib4_clear( fd_fib4_t * fib );
     110             : 
     111             : /* fd_fib4_insert attempts to add a new route entry to the FIB routing table.
     112             :    Routes with /32 netmask prefix are stored in hashmap for faster lookup.
     113             :    Other routes use the main table.  A route with the same destination,
     114             :    prefix, and priority replaces the existing route.  Returns 1 on success,
     115             :    0 if the internal data structures are full (logs warning in that case). */
     116             : 
     117             : int
     118             : fd_fib4_insert( fd_fib4_t *           fib,
     119             :                 uint                  ip4_dst,
     120             :                 int                   prefix,
     121             :                 uint                  prio,
     122             :                 fd_fib4_hop_t const * hop );
     123             : 
     124             : /* fd_fib4_remove removes the route identified by destination, prefix, and
     125             :    priority.  Returns 1 if a route was removed and 0 if no exact match exists. */
     126             : 
     127             : int
     128             : fd_fib4_remove( fd_fib4_t * fib,
     129             :                 uint        ip4_dst,
     130             :                 int         prefix,
     131             :                 uint        prio );
     132             : 
     133             : /* Read APIs *************************************************************/
     134             : 
     135             : /* fd_fib4_lookup resolves the next hop for an arbitrary IPv4 address.
     136             :    If multiple /32 routes match, selects the route with the lowest
     137             :    priority value. If route was not found, retval.rtype is set to
     138             :    FD_FIB4_RTYPE_THROW. */
     139             : 
     140             : fd_fib4_hop_t
     141             : fd_fib4_lookup( fd_fib4_t const * fib,
     142             :                 uint              ip4_dst,
     143             :                 ulong             flags );
     144             : 
     145             : /* fd_fib4_hop_or is a helper to chain together multiple FIB lookups. */
     146             : 
     147             : FD_FN_PURE static inline fd_fib4_hop_t const *
     148             : fd_fib4_hop_or( fd_fib4_hop_t const * left,
     149          48 :                 fd_fib4_hop_t const * right ) {
     150          48 :   return left->rtype!=FD_FIB4_RTYPE_THROW ? left : right;
     151          48 : }
     152             : 
     153             : /* fd_fib4_max returns the max number of routes in the table. */
     154             : 
     155             : FD_FN_PURE ulong
     156             : fd_fib4_max( fd_fib4_t const * fib );
     157             : 
     158             : /* fd_fib4_peer_max returns the max number of /32 routes (backed by a hashmap). */
     159             : 
     160             : FD_FN_PURE ulong
     161             : fd_fib4_peer_max( fd_fib4_t const * fib );
     162             : 
     163             : /* fd_fib4_cnt returns the total number of routes stored in the fib4.
     164             :    This also includes /32 routes. */
     165             : 
     166             : FD_FN_PURE ulong
     167             : fd_fib4_cnt( fd_fib4_t const * fib );
     168             : 
     169             : #if FD_HAS_HOSTED
     170             : 
     171             : /* fd_fib4_fprintf prints the routing table and hash map to the given FILE *
     172             :    pointer (or target equivalent).  Order of routes is undefined but
     173             :    guaranteed to be stable between calls.  Outputs ASCII encoding with LF
     174             :    newlines.  Returns errno on failure and 0 on success. */
     175             : 
     176             : int
     177             : fd_fib4_fprintf( fd_fib4_t const * fib,
     178             :                  void *            file );
     179             : 
     180             : #endif
     181             : 
     182             : FD_PROTOTYPES_END
     183             : 
     184             : #endif /* HEADER_fd_src_waltz_ip_fd_fib4_h */

Generated by: LCOV version 1.14