Updated: 2021/Apr/14


LIBNPF(3)                  Library Functions Manual                  LIBNPF(3)

NAME
     libnpf - NPF packet filter library

LIBRARY
     NPF Packet Filter Library (libnpf, -lnpf)

SYNOPSIS
     #include <npf.h>

     nl_config_t *
     npf_config_create(void);

     int
     npf_config_submit(nl_config_t *ncf, int fd, npf_error_t *errinfo);

     nl_config_t *
     npf_config_retrieve(int fd);

     int
     npf_config_flush(int fd);

     void
     npf_config_export(nl_config_t *ncf, size_t *len);

     nl_config_t *
     npf_config_import(const void *blob, size_t len);

     bool
     npf_config_active_p(nl_config_t *ncf);

     bool
     npf_config_loaded_p(nl_config_t *ncf);

     void
     npf_config_destroy(nl_config_t *ncf);

     nl_rule_t *
     npf_rule_create(const char *name, uint32_t attr, const char *ifname);

     int
     npf_rule_setcode(nl_rule_t *rl, int type, const void *code, size_t len);

     int
     npf_rule_setkey(nl_rule_t *rl, const void *key, size_t len);

     int
     npf_rule_setinfo(nl_rule_t *rl, const void *info, size_t len);

     int
     npf_rule_setprio(nl_rule_t *rl, int pri);

     int
     npf_rule_setproc(nl_rule_t *rl, const char *name);

     int
     npf_rule_insert(nl_config_t *ncf, nl_rule_t *parent, nl_rule_t *rl);

     bool
     npf_rule_exists_p(nl_config_t *ncf, const char *name);

     void *
     npf_rule_export(nl_rule_t *rl, size_t *length);

     void
     npf_rule_destroy(nl_rule_t *rl);

     nl_rproc_t *
     npf_rproc_create(const char *name);

     int
     npf_rproc_extcall(nl_rproc_t *rp, nl_ext_t *ext);

     bool
     npf_rproc_exists_p(nl_config_t *ncf, const char *name);

     int
     npf_rproc_insert(nl_config_t *ncf, nl_rproc_t *rp);

     nl_nat_t *
     npf_nat_create(int type, unsigned flags, const char *ifname);

     int
     npf_nat_setaddr(nl_nat_t *nt, int af, npf_addr_t *addr,
         npf_netmask_t mask);

     int
     npf_nat_setport(nl_nat_t *nt, in_port_t port);

     int
     npf_nat_insert(nl_config_t *ncf, nl_nat_t *nt);

     nl_table_t *
     npf_table_create(const char *name, unsigned id, int type);

     int
     npf_table_add_entry(nl_table_t *tl, int af, const npf_addr_t *addr,
         const npf_netmask_t mask);

     int
     npf_table_insert(nl_config_t *ncf, nl_table_t *tl);

     int
     npf_table_replace(int fd, nl_table_t *tl, npf_error_t *errinfo);

     void
     npf_table_destroy(nl_table_t *tl);

     int
     npf_ruleset_add(int fd, const char *name, nl_rule_t *rl, uint64_t *id);

     int
     npf_ruleset_remove(int fd, const char *name, uint64_t id);

     int
     npf_ruleset_remkey(int fd, const char *name, const void *key,
         size_t len);

     int
     npf_ruleset_flush(int fd, const char *name);

DESCRIPTION
     The libnpf library provides an interface to create an NPF configuration
     having rules, tables, procedures, or translation policies.  The
     configuration can be submitted to the kernel.

FUNCTIONS
   Configuration
     npf_config_create()
           Create a new configuration object.

     npf_config_submit(ncf, fd, errinfo)
           Submit the configuration object, specified by ncf, to the kernel.
           On failure, the error information is written into the structure
           specified by errinfo.

     npf_config_export(ncf, len)
           Serialize the given configuration and return the binary object as
           well as its length in len parameter.  The binary object is
           dynamically allocated and should be destroyed using free(3).

     npf_config_import(blob, len)
           Read the configuration from a binary object of the specified
           length, unserialize, and return the configuration object.

     npf_config_flush(fd)
           Flush the current configuration.

     npf_config_retrieve(fd)
           Retrieve and return the loaded configuration from the kernel.

     npf_config_active_p(ncf)
           Indicate whether the retrieved configuration is active i.e. packet
           filtering is enabled (true if yes and false otherwise).

     npf_config_loaded_p(ncf)
           Indicate whether the retrieved configuration is loaded i.e. has any
           rules (true if yes and false otherwise).

     npf_config_destroy(ncf)
           Destroy the configuration object, specified by ncf.

   Rule interface
     npf_rule_create(name, attr, ifname)
           Create a rule with a given name, attributes and priority.  If the
           name is specified, then it should be unique within the
           configuration object.  Otherwise, the name can be NULL, in which
           case the rule will have no identifier.  The following attributes,
           which can be ORed, are available:

           NPF_RULE_PASS
                   The decision of this rule shall be "pass".  If this
                   attribute is not specified, then "block" (drop the packet)
                   is the default.

           NPF_RULE_IN
                   Match the incoming packets.

           NPF_RULE_OUT
                   Match the outgoing packets.

           NPF_RULE_FINAL
                   Indicate that on rule match, further processing of the
                   ruleset should be stopped and this rule should be applied
                   instantly.

           NPF_RULE_STATEFUL
                   Create a state (session) on match, track the connection and
                   pass the backwards stream (the returning packets) without
                   the ruleset inspection.  The state is uniquely identified
                   by an n-tuple key.

           NPF_RULE_GSTATEFUL
                   Exclude the interface identifier from the state key (n-
                   tuple).  This makes the state global with respect to the
                   network interfaces.  The state is also picked for packets
                   travelling in different direction than originally.

           NPF_RULE_RETRST
                   Return TCP RST packet in a case of packet block.

           NPF_RULE_RETICMP
                   Return ICMP destination unreachable in a case of packet
                   block.

           NPF_RULE_GROUP
                   Allow this rule to have sub-rules.  If this flag is used
                   with the NPF_RULE_DYNAMIC flag set, then it is a dynamic
                   group.  The sub-rules can be added dynamically to a dynamic
                   group, also meaning that the sub-rules must have the
                   NPF_RULE_DYNAMIC flag set.  Otherwise rules must be added
                   statically i.e. created with the configuration.

           NPF_RULE_DYNAMIC
                   Indicate that the rule is dynamic.  Such rules can only be
                   added to the dynamic groups.

           The interface is specified by the ifname string.  NULL indicates
           any interface.

     npf_rule_setcode(rl, type, code, len)
           Assign the code for the rule specified by rl.  The code is used to
           implement the filter criteria.  The pointer to the binary code is
           specified by code, the size of the memory area by len, and the type
           of the code is specified by type.  Currently, only the BPF byte-
           code is supported and the NPF_CODE_BPF constant should be passed.

     npf_rule_setkey(rl, key, len)
           Assign a key for the rule specified by rl.  The binary key is
           specified by key, and its size by len.  The size shall not exceed
           NPF_RULE_MAXKEYLEN.  The kernel does not check whether key is
           unique, therefore it is the responsibility of the caller.

     npf_rule_setinfo(rl, info, len)
           Associate an arbitrary information blob specified by info, and its
           size by len.  This may be used for such purposes as the byte-code
           annotation.

     npf_rule_setprio(rl, pri)
           Set priority to the rule.  Negative priorities are invalid.

           The priority is the order of the rule in the ruleset.  The lower
           value means first to process, the higher value - last to process.
           If multiple rules are inserted with the same priority, then the
           order is unspecified.

           The special constants NPF_PRI_FIRST and NPF_PRI_LAST can be passed
           to indicate that the rule should be inserted into the beginning or
           the end of the priority level 0 in the ruleset.  All rules inserted
           using these constants will have the priority 0 assigned and will
           share this level in the ordered way.

     npf_rule_setproc(rl, name)
           Set a procedure for the specified rule.

     npf_rule_insert(ncf, parent, rl)
           Insert the rule into the set of the parent rule specified by
           parent.  If the value of parent is NULL, then insert into the main
           ruleset.  The rule will be consumed (the relevant resourced will be
           freed) and it must not be referenced after insertion.

     npf_rule_exists_p(ncf, name)
           Check whether the rule with a given name is already in the
           configuration.

     npf_rule_export(rl, length)
           Serialize the rule (including the byte-code), return a binary
           object and set its length.  The binary object is dynamically
           allocated and should be destroyed using free(3).

     npf_rule_destroy(rl)
           Destroy the given rule object.

   Rule procedure interface
     npf_rproc_create(name)
           Create a rule procedure with a given name.  Thr name must be unique
           for each procedure.

     npf_rproc_insert(ncf, rp)
           Insert the rule procedure into the specified configuration object.
           The rule procedure must not be referenced after insertion.

   Translation interface
     npf_nat_create(type, flags, ifname)
           Create a NAT policy of a specified type.  There are two types:

           NPF_NATIN         Inbound NAT policy (rewrite destination).

           NPF_NATOUT        Outbound NAT policy (rewrite source).

           A bi-directional NAT is obtained by combining two policies.  The
           following flags are supported:

           NPF_NAT_STATIC    Perform static (stateless) translation rather
                             than dynamic (stateful).

           NPF_NAT_PORTS     Perform the port translation.  If this flag is
                             not specified, then the port translation is not
                             performed and the port parameter is ignored.

           NPF_NAT_PORTMAP   Create a port map and select a random port for
                             translation.  If enabled, then the value
                             specified by the port parameter is ignored.  This
                             flag is effective only if the NPF_NAT_PORTS flag
                             is set.

           The network interface on which the policy will be applicable is
           specified by ifname.

     npf_nat_setaddr(nt, af, addr, mask)
           Set the translation address, as specified by addr, and its family
           by af.  The family must be either AF_INET for IPv4 or AF_INET6 for
           IPv6 address.  Additionally, mask may be specified to indicate the
           translation network; otherwise, it should be set to NPF_NO_NETMASK.

           In order to use the translation network, a custom algorithm may
           need to be specified using the npf_nat_setalgo() function.

     npf_nat_setport(nt, port)
           Set the translation port, specified by port.

     npf_nat_setalgo(nt, algo)
           Set a particular NAT algorithm.  Currently, the following
           algorithms are supported with dynamic NAT:

           NPF_ALGO_IPHASH  Hash of the source and destination addresses.

           NPF_ALGO_RR      Round-robin for the translation addresses.

           NPF_ALGO_NETMAP  Network-to-network map as described below, but
                            with state tracking.  It is used when it is
                            necessary to translate the ports.

           The following are support with static NAT:

           NPF_ALGO_NETMAP  Network-to-network map where the translation
                            network prefix (address after applying the mask)
                            is bitwise OR-ed with the host part of the
                            original address (zero bits of the mask).

           NPF_ALGO_NPT66   IPv6-to-IPv6 Network Prefix Translation (NPTv6,
                            defined in RFC 6296).

     npf_nat_insert(ncf, nt)
           Insert the NAT policy, its rule, into the specified configuration.
           The NAT rule must not be referenced after insertion.

   Table interface
     npf_table_create(name, index, type)
           Create an NPF table of a specified type.  The table is identified
           by the name and index, which should be in the range between 1 and
           NPF_MAX_TABLES.

           The following types are supported:

           NPF_TABLE_IPSET  Indicates to use a regular associative array for
                            storage of IP sets.  Currently implemented as a
                            hashmap.

           NPF_TABLE_LPM    Indicates to the table can contain networks (as
                            well as hosts) and the longest prefix match should
                            be performed on lookup.

           NPF_TABLE_CONST  Indicates that the table contents will be constant
                            and the table can be considered immutable (no
                            inserts/removes after load).  If such constraint
                            is acceptable, this table type will provide the
                            best performance.  It is currently implemented as
                            a perfect hash table, generated on table insertion
                            into the configuration.

     npf_table_add_entry(tl, af, addr, mask)
           Add an entry of IP address and mask, specified by addr and mask, to
           the table specified by tl.  The family, specified by af, must be
           either AF_INET for IPv4 or AF_INET6 for IPv6 address.  If there is
           no mask, then mask should be set to NPF_NO_NETMASK.

     npf_table_insert(ncf, tl)
           Add the table to the configuration object.  This routine performs a
           check for duplicate table IDs.  The table must not be referenced
           after insertion.

     npf_table_replace(fd, tl, errinfo)
           Submit the table object, specified by tl, to the kernel, to replace
           the existing table with the corresponding table name and ID.  On
           failure, the error information is written into the structure
           specified by errinfo.

     npf_table_destroy(tl)
           Destroy the specified table.

   Ruleset interface
     npf_ruleset_add(fd, name, rl, id)
           Add a given rule, specified by rl, into the dynamic ruleset named
           name.  On success, return 0 and a unique rule ID in the id
           parameter.

     npf_ruleset_remove(fd, name, id)
           Remove a rule from the dynamic ruleset, specified by name.  The
           rule is specified by its unique ID in the id parameter.

     npf_ruleset_remkey(fd, name, key, len)
           Remove a rule from the dynamic ruleset, specified by name.  The
           rule is specified by its key, in the key and len parameters.  The
           key for the rule must have been set during its construction, using
           the npf_rule_setkey() routine.

     npf_ruleset_flush(fd, name)
           Clear the dynamic ruleset, specified by name, by removing all its
           rules.

SEE ALSO
     bpf(4), npf(7), npfctl(8)

HISTORY
     The NPF library first appeared in NetBSD 6.0.

NetBSD 9.99                      May 30, 2020                      NetBSD 9.99