Skip to content

Commit 8111038

Browse files
jrfastabborkmann
authored andcommitted
bpf: sockmap, add hash map support
Sockmap is currently backed by an array and enforces keys to be four bytes. This works well for many use cases and was originally modeled after devmap which also uses four bytes keys. However, this has become limiting in larger use cases where a hash would be more appropriate. For example users may want to use the 5-tuple of the socket as the lookup key. To support this add hash support. Signed-off-by: John Fastabend <[email protected]> Acked-by: David S. Miller <[email protected]> Signed-off-by: Daniel Borkmann <[email protected]>
1 parent e5cd3ab commit 8111038

File tree

7 files changed

+611
-19
lines changed

7 files changed

+611
-19
lines changed

include/linux/bpf.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -668,13 +668,20 @@ static inline void bpf_map_offload_map_free(struct bpf_map *map)
668668

669669
#if defined(CONFIG_STREAM_PARSER) && defined(CONFIG_BPF_SYSCALL) && defined(CONFIG_INET)
670670
struct sock *__sock_map_lookup_elem(struct bpf_map *map, u32 key);
671+
struct sock *__sock_hash_lookup_elem(struct bpf_map *map, void *key);
671672
int sock_map_prog(struct bpf_map *map, struct bpf_prog *prog, u32 type);
672673
#else
673674
static inline struct sock *__sock_map_lookup_elem(struct bpf_map *map, u32 key)
674675
{
675676
return NULL;
676677
}
677678

679+
static inline struct sock *__sock_hash_lookup_elem(struct bpf_map *map,
680+
void *key)
681+
{
682+
return NULL;
683+
}
684+
678685
static inline int sock_map_prog(struct bpf_map *map,
679686
struct bpf_prog *prog,
680687
u32 type)
@@ -724,6 +731,7 @@ extern const struct bpf_func_proto bpf_get_current_comm_proto;
724731
extern const struct bpf_func_proto bpf_get_stackid_proto;
725732
extern const struct bpf_func_proto bpf_get_stack_proto;
726733
extern const struct bpf_func_proto bpf_sock_map_update_proto;
734+
extern const struct bpf_func_proto bpf_sock_hash_update_proto;
727735

728736
/* Shared helpers among cBPF and eBPF. */
729737
void bpf_user_rnd_init_once(void);

include/linux/bpf_types.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ BPF_MAP_TYPE(BPF_MAP_TYPE_HASH_OF_MAPS, htab_of_maps_map_ops)
4747
BPF_MAP_TYPE(BPF_MAP_TYPE_DEVMAP, dev_map_ops)
4848
#if defined(CONFIG_STREAM_PARSER) && defined(CONFIG_INET)
4949
BPF_MAP_TYPE(BPF_MAP_TYPE_SOCKMAP, sock_map_ops)
50+
BPF_MAP_TYPE(BPF_MAP_TYPE_SOCKHASH, sock_hash_ops)
5051
#endif
5152
BPF_MAP_TYPE(BPF_MAP_TYPE_CPUMAP, cpu_map_ops)
5253
#if defined(CONFIG_XDP_SOCKETS)

include/uapi/linux/bpf.h

Lines changed: 52 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,7 @@ enum bpf_map_type {
118118
BPF_MAP_TYPE_SOCKMAP,
119119
BPF_MAP_TYPE_CPUMAP,
120120
BPF_MAP_TYPE_XSKMAP,
121+
BPF_MAP_TYPE_SOCKHASH,
121122
};
122123

123124
enum bpf_prog_type {
@@ -1828,7 +1829,6 @@ union bpf_attr {
18281829
* Return
18291830
* 0 on success, or a negative error in case of failure.
18301831
*
1831-
*
18321832
* int bpf_fib_lookup(void *ctx, struct bpf_fib_lookup *params, int plen, u32 flags)
18331833
* Description
18341834
* Do FIB lookup in kernel tables using parameters in *params*.
@@ -1855,6 +1855,53 @@ union bpf_attr {
18551855
* Egress device index on success, 0 if packet needs to continue
18561856
* up the stack for further processing or a negative error in case
18571857
* of failure.
1858+
*
1859+
* int bpf_sock_hash_update(struct bpf_sock_ops_kern *skops, struct bpf_map *map, void *key, u64 flags)
1860+
* Description
1861+
* Add an entry to, or update a sockhash *map* referencing sockets.
1862+
* The *skops* is used as a new value for the entry associated to
1863+
* *key*. *flags* is one of:
1864+
*
1865+
* **BPF_NOEXIST**
1866+
* The entry for *key* must not exist in the map.
1867+
* **BPF_EXIST**
1868+
* The entry for *key* must already exist in the map.
1869+
* **BPF_ANY**
1870+
* No condition on the existence of the entry for *key*.
1871+
*
1872+
* If the *map* has eBPF programs (parser and verdict), those will
1873+
* be inherited by the socket being added. If the socket is
1874+
* already attached to eBPF programs, this results in an error.
1875+
* Return
1876+
* 0 on success, or a negative error in case of failure.
1877+
*
1878+
* int bpf_msg_redirect_hash(struct sk_msg_buff *msg, struct bpf_map *map, void *key, u64 flags)
1879+
* Description
1880+
* This helper is used in programs implementing policies at the
1881+
* socket level. If the message *msg* is allowed to pass (i.e. if
1882+
* the verdict eBPF program returns **SK_PASS**), redirect it to
1883+
* the socket referenced by *map* (of type
1884+
* **BPF_MAP_TYPE_SOCKHASH**) using hash *key*. Both ingress and
1885+
* egress interfaces can be used for redirection. The
1886+
* **BPF_F_INGRESS** value in *flags* is used to make the
1887+
* distinction (ingress path is selected if the flag is present,
1888+
* egress path otherwise). This is the only flag supported for now.
1889+
* Return
1890+
* **SK_PASS** on success, or **SK_DROP** on error.
1891+
*
1892+
* int bpf_sk_redirect_hash(struct sk_buff *skb, struct bpf_map *map, void *key, u64 flags)
1893+
* Description
1894+
* This helper is used in programs implementing policies at the
1895+
* skb socket level. If the sk_buff *skb* is allowed to pass (i.e.
1896+
* if the verdeict eBPF program returns **SK_PASS**), redirect it
1897+
* to the socket referenced by *map* (of type
1898+
* **BPF_MAP_TYPE_SOCKHASH**) using hash *key*. Both ingress and
1899+
* egress interfaces can be used for redirection. The
1900+
* **BPF_F_INGRESS** value in *flags* is used to make the
1901+
* distinction (ingress path is selected if the flag is present,
1902+
* egress otherwise). This is the only flag supported for now.
1903+
* Return
1904+
* **SK_PASS** on success, or **SK_DROP** on error.
18581905
*/
18591906
#define __BPF_FUNC_MAPPER(FN) \
18601907
FN(unspec), \
@@ -1926,7 +1973,10 @@ union bpf_attr {
19261973
FN(skb_get_xfrm_state), \
19271974
FN(get_stack), \
19281975
FN(skb_load_bytes_relative), \
1929-
FN(fib_lookup),
1976+
FN(fib_lookup), \
1977+
FN(sock_hash_update), \
1978+
FN(msg_redirect_hash), \
1979+
FN(sk_redirect_hash),
19301980

19311981
/* integer value in 'imm' field of BPF_CALL instruction selects which helper
19321982
* function eBPF program intends to call

kernel/bpf/core.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1707,6 +1707,7 @@ const struct bpf_func_proto bpf_get_current_pid_tgid_proto __weak;
17071707
const struct bpf_func_proto bpf_get_current_uid_gid_proto __weak;
17081708
const struct bpf_func_proto bpf_get_current_comm_proto __weak;
17091709
const struct bpf_func_proto bpf_sock_map_update_proto __weak;
1710+
const struct bpf_func_proto bpf_sock_hash_update_proto __weak;
17101711

17111712
const struct bpf_func_proto * __weak bpf_get_trace_printk_proto(void)
17121713
{

0 commit comments

Comments
 (0)