1546ac1ffSJohn Fastabend /* Copyright (c) 2017 Covalent IO, Inc. http://covalent.io 2546ac1ffSJohn Fastabend * 3546ac1ffSJohn Fastabend * This program is free software; you can redistribute it and/or 4546ac1ffSJohn Fastabend * modify it under the terms of version 2 of the GNU General Public 5546ac1ffSJohn Fastabend * License as published by the Free Software Foundation. 6546ac1ffSJohn Fastabend * 7546ac1ffSJohn Fastabend * This program is distributed in the hope that it will be useful, but 8546ac1ffSJohn Fastabend * WITHOUT ANY WARRANTY; without even the implied warranty of 9546ac1ffSJohn Fastabend * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 10546ac1ffSJohn Fastabend * General Public License for more details. 11546ac1ffSJohn Fastabend */ 12546ac1ffSJohn Fastabend 13546ac1ffSJohn Fastabend /* Devmaps primary use is as a backend map for XDP BPF helper call 14546ac1ffSJohn Fastabend * bpf_redirect_map(). Because XDP is mostly concerned with performance we 15546ac1ffSJohn Fastabend * spent some effort to ensure the datapath with redirect maps does not use 16546ac1ffSJohn Fastabend * any locking. This is a quick note on the details. 17546ac1ffSJohn Fastabend * 18546ac1ffSJohn Fastabend * We have three possible paths to get into the devmap control plane bpf 19546ac1ffSJohn Fastabend * syscalls, bpf programs, and driver side xmit/flush operations. A bpf syscall 20546ac1ffSJohn Fastabend * will invoke an update, delete, or lookup operation. To ensure updates and 21546ac1ffSJohn Fastabend * deletes appear atomic from the datapath side xchg() is used to modify the 22546ac1ffSJohn Fastabend * netdev_map array. Then because the datapath does a lookup into the netdev_map 23546ac1ffSJohn Fastabend * array (read-only) from an RCU critical section we use call_rcu() to wait for 24546ac1ffSJohn Fastabend * an rcu grace period before free'ing the old data structures. This ensures the 25546ac1ffSJohn Fastabend * datapath always has a valid copy. However, the datapath does a "flush" 26546ac1ffSJohn Fastabend * operation that pushes any pending packets in the driver outside the RCU 27546ac1ffSJohn Fastabend * critical section. Each bpf_dtab_netdev tracks these pending operations using 28546ac1ffSJohn Fastabend * an atomic per-cpu bitmap. The bpf_dtab_netdev object will not be destroyed 29546ac1ffSJohn Fastabend * until all bits are cleared indicating outstanding flush operations have 30546ac1ffSJohn Fastabend * completed. 31546ac1ffSJohn Fastabend * 32546ac1ffSJohn Fastabend * BPF syscalls may race with BPF program calls on any of the update, delete 33546ac1ffSJohn Fastabend * or lookup operations. As noted above the xchg() operation also keep the 34546ac1ffSJohn Fastabend * netdev_map consistent in this case. From the devmap side BPF programs 35546ac1ffSJohn Fastabend * calling into these operations are the same as multiple user space threads 36546ac1ffSJohn Fastabend * making system calls. 37546ac1ffSJohn Fastabend */ 38546ac1ffSJohn Fastabend #include <linux/bpf.h> 39546ac1ffSJohn Fastabend #include <linux/jhash.h> 40546ac1ffSJohn Fastabend #include <linux/filter.h> 41546ac1ffSJohn Fastabend #include <linux/rculist_nulls.h> 42546ac1ffSJohn Fastabend #include "percpu_freelist.h" 43546ac1ffSJohn Fastabend #include "bpf_lru_list.h" 44546ac1ffSJohn Fastabend #include "map_in_map.h" 45546ac1ffSJohn Fastabend 46546ac1ffSJohn Fastabend struct bpf_dtab_netdev { 47546ac1ffSJohn Fastabend struct net_device *dev; 48546ac1ffSJohn Fastabend int key; 49546ac1ffSJohn Fastabend struct rcu_head rcu; 50546ac1ffSJohn Fastabend struct bpf_dtab *dtab; 51546ac1ffSJohn Fastabend }; 52546ac1ffSJohn Fastabend 53546ac1ffSJohn Fastabend struct bpf_dtab { 54546ac1ffSJohn Fastabend struct bpf_map map; 55546ac1ffSJohn Fastabend struct bpf_dtab_netdev **netdev_map; 56546ac1ffSJohn Fastabend }; 57546ac1ffSJohn Fastabend 58546ac1ffSJohn Fastabend static struct bpf_map *dev_map_alloc(union bpf_attr *attr) 59546ac1ffSJohn Fastabend { 60546ac1ffSJohn Fastabend struct bpf_dtab *dtab; 61546ac1ffSJohn Fastabend u64 cost; 62546ac1ffSJohn Fastabend int err; 63546ac1ffSJohn Fastabend 64546ac1ffSJohn Fastabend /* check sanity of attributes */ 65546ac1ffSJohn Fastabend if (attr->max_entries == 0 || attr->key_size != 4 || 66546ac1ffSJohn Fastabend attr->value_size != 4 || attr->map_flags) 67546ac1ffSJohn Fastabend return ERR_PTR(-EINVAL); 68546ac1ffSJohn Fastabend 69546ac1ffSJohn Fastabend /* if value_size is bigger, the user space won't be able to 70546ac1ffSJohn Fastabend * access the elements. 71546ac1ffSJohn Fastabend */ 72546ac1ffSJohn Fastabend if (attr->value_size > KMALLOC_MAX_SIZE) 73546ac1ffSJohn Fastabend return ERR_PTR(-E2BIG); 74546ac1ffSJohn Fastabend 75546ac1ffSJohn Fastabend dtab = kzalloc(sizeof(*dtab), GFP_USER); 76546ac1ffSJohn Fastabend if (!dtab) 77546ac1ffSJohn Fastabend return ERR_PTR(-ENOMEM); 78546ac1ffSJohn Fastabend 79546ac1ffSJohn Fastabend /* mandatory map attributes */ 80546ac1ffSJohn Fastabend dtab->map.map_type = attr->map_type; 81546ac1ffSJohn Fastabend dtab->map.key_size = attr->key_size; 82546ac1ffSJohn Fastabend dtab->map.value_size = attr->value_size; 83546ac1ffSJohn Fastabend dtab->map.max_entries = attr->max_entries; 84546ac1ffSJohn Fastabend dtab->map.map_flags = attr->map_flags; 85546ac1ffSJohn Fastabend 86546ac1ffSJohn Fastabend err = -ENOMEM; 87546ac1ffSJohn Fastabend 88546ac1ffSJohn Fastabend /* make sure page count doesn't overflow */ 89546ac1ffSJohn Fastabend cost = (u64) dtab->map.max_entries * sizeof(struct bpf_dtab_netdev *); 90546ac1ffSJohn Fastabend if (cost >= U32_MAX - PAGE_SIZE) 91546ac1ffSJohn Fastabend goto free_dtab; 92546ac1ffSJohn Fastabend 93546ac1ffSJohn Fastabend dtab->map.pages = round_up(cost, PAGE_SIZE) >> PAGE_SHIFT; 94546ac1ffSJohn Fastabend 95546ac1ffSJohn Fastabend /* if map size is larger than memlock limit, reject it early */ 96546ac1ffSJohn Fastabend err = bpf_map_precharge_memlock(dtab->map.pages); 97546ac1ffSJohn Fastabend if (err) 98546ac1ffSJohn Fastabend goto free_dtab; 99546ac1ffSJohn Fastabend 100546ac1ffSJohn Fastabend dtab->netdev_map = bpf_map_area_alloc(dtab->map.max_entries * 101546ac1ffSJohn Fastabend sizeof(struct bpf_dtab_netdev *)); 102546ac1ffSJohn Fastabend if (!dtab->netdev_map) 103546ac1ffSJohn Fastabend goto free_dtab; 104546ac1ffSJohn Fastabend 105546ac1ffSJohn Fastabend return &dtab->map; 106546ac1ffSJohn Fastabend 107546ac1ffSJohn Fastabend free_dtab: 108546ac1ffSJohn Fastabend kfree(dtab); 109546ac1ffSJohn Fastabend return ERR_PTR(err); 110546ac1ffSJohn Fastabend } 111546ac1ffSJohn Fastabend 112546ac1ffSJohn Fastabend static void dev_map_free(struct bpf_map *map) 113546ac1ffSJohn Fastabend { 114546ac1ffSJohn Fastabend struct bpf_dtab *dtab = container_of(map, struct bpf_dtab, map); 115546ac1ffSJohn Fastabend int i; 116546ac1ffSJohn Fastabend 117546ac1ffSJohn Fastabend /* At this point bpf_prog->aux->refcnt == 0 and this map->refcnt == 0, 118546ac1ffSJohn Fastabend * so the programs (can be more than one that used this map) were 119546ac1ffSJohn Fastabend * disconnected from events. Wait for outstanding critical sections in 120546ac1ffSJohn Fastabend * these programs to complete. The rcu critical section only guarantees 121546ac1ffSJohn Fastabend * no further reads against netdev_map. It does __not__ ensure pending 122546ac1ffSJohn Fastabend * flush operations (if any) are complete. 123546ac1ffSJohn Fastabend */ 124546ac1ffSJohn Fastabend synchronize_rcu(); 125546ac1ffSJohn Fastabend 126546ac1ffSJohn Fastabend for (i = 0; i < dtab->map.max_entries; i++) { 127546ac1ffSJohn Fastabend struct bpf_dtab_netdev *dev; 128546ac1ffSJohn Fastabend 129546ac1ffSJohn Fastabend dev = dtab->netdev_map[i]; 130546ac1ffSJohn Fastabend if (!dev) 131546ac1ffSJohn Fastabend continue; 132546ac1ffSJohn Fastabend 133546ac1ffSJohn Fastabend dev_put(dev->dev); 134546ac1ffSJohn Fastabend kfree(dev); 135546ac1ffSJohn Fastabend } 136546ac1ffSJohn Fastabend 137546ac1ffSJohn Fastabend /* At this point bpf program is detached and all pending operations 138546ac1ffSJohn Fastabend * _must_ be complete 139546ac1ffSJohn Fastabend */ 140546ac1ffSJohn Fastabend bpf_map_area_free(dtab->netdev_map); 141546ac1ffSJohn Fastabend kfree(dtab); 142546ac1ffSJohn Fastabend } 143546ac1ffSJohn Fastabend 144546ac1ffSJohn Fastabend static int dev_map_get_next_key(struct bpf_map *map, void *key, void *next_key) 145546ac1ffSJohn Fastabend { 146546ac1ffSJohn Fastabend struct bpf_dtab *dtab = container_of(map, struct bpf_dtab, map); 147546ac1ffSJohn Fastabend u32 index = key ? *(u32 *)key : U32_MAX; 148546ac1ffSJohn Fastabend u32 *next = (u32 *)next_key; 149546ac1ffSJohn Fastabend 150546ac1ffSJohn Fastabend if (index >= dtab->map.max_entries) { 151546ac1ffSJohn Fastabend *next = 0; 152546ac1ffSJohn Fastabend return 0; 153546ac1ffSJohn Fastabend } 154546ac1ffSJohn Fastabend 155546ac1ffSJohn Fastabend if (index == dtab->map.max_entries - 1) 156546ac1ffSJohn Fastabend return -ENOENT; 157546ac1ffSJohn Fastabend 158546ac1ffSJohn Fastabend *next = index + 1; 159546ac1ffSJohn Fastabend return 0; 160546ac1ffSJohn Fastabend } 161546ac1ffSJohn Fastabend 162*97f91a7cSJohn Fastabend struct net_device *__dev_map_lookup_elem(struct bpf_map *map, u32 key) 163*97f91a7cSJohn Fastabend { 164*97f91a7cSJohn Fastabend struct bpf_dtab *dtab = container_of(map, struct bpf_dtab, map); 165*97f91a7cSJohn Fastabend struct bpf_dtab_netdev *dev; 166*97f91a7cSJohn Fastabend 167*97f91a7cSJohn Fastabend if (key >= map->max_entries) 168*97f91a7cSJohn Fastabend return NULL; 169*97f91a7cSJohn Fastabend 170*97f91a7cSJohn Fastabend dev = READ_ONCE(dtab->netdev_map[key]); 171*97f91a7cSJohn Fastabend return dev ? dev->dev : NULL; 172*97f91a7cSJohn Fastabend } 173*97f91a7cSJohn Fastabend 174546ac1ffSJohn Fastabend /* rcu_read_lock (from syscall and BPF contexts) ensures that if a delete and/or 175546ac1ffSJohn Fastabend * update happens in parallel here a dev_put wont happen until after reading the 176546ac1ffSJohn Fastabend * ifindex. 177546ac1ffSJohn Fastabend */ 178546ac1ffSJohn Fastabend static void *dev_map_lookup_elem(struct bpf_map *map, void *key) 179546ac1ffSJohn Fastabend { 180546ac1ffSJohn Fastabend struct bpf_dtab *dtab = container_of(map, struct bpf_dtab, map); 181546ac1ffSJohn Fastabend struct bpf_dtab_netdev *dev; 182546ac1ffSJohn Fastabend u32 i = *(u32 *)key; 183546ac1ffSJohn Fastabend 184546ac1ffSJohn Fastabend if (i >= map->max_entries) 185546ac1ffSJohn Fastabend return NULL; 186546ac1ffSJohn Fastabend 187546ac1ffSJohn Fastabend dev = READ_ONCE(dtab->netdev_map[i]); 188546ac1ffSJohn Fastabend return dev ? &dev->dev->ifindex : NULL; 189546ac1ffSJohn Fastabend } 190546ac1ffSJohn Fastabend 191546ac1ffSJohn Fastabend static void __dev_map_entry_free(struct rcu_head *rcu) 192546ac1ffSJohn Fastabend { 193546ac1ffSJohn Fastabend struct bpf_dtab_netdev *old_dev; 194546ac1ffSJohn Fastabend 195546ac1ffSJohn Fastabend old_dev = container_of(rcu, struct bpf_dtab_netdev, rcu); 196546ac1ffSJohn Fastabend dev_put(old_dev->dev); 197546ac1ffSJohn Fastabend kfree(old_dev); 198546ac1ffSJohn Fastabend } 199546ac1ffSJohn Fastabend 200546ac1ffSJohn Fastabend static int dev_map_delete_elem(struct bpf_map *map, void *key) 201546ac1ffSJohn Fastabend { 202546ac1ffSJohn Fastabend struct bpf_dtab *dtab = container_of(map, struct bpf_dtab, map); 203546ac1ffSJohn Fastabend struct bpf_dtab_netdev *old_dev; 204546ac1ffSJohn Fastabend int k = *(u32 *)key; 205546ac1ffSJohn Fastabend 206546ac1ffSJohn Fastabend if (k >= map->max_entries) 207546ac1ffSJohn Fastabend return -EINVAL; 208546ac1ffSJohn Fastabend 209546ac1ffSJohn Fastabend /* Use synchronize_rcu() here to ensure any rcu critical sections 210546ac1ffSJohn Fastabend * have completed, but this does not guarantee a flush has happened 211546ac1ffSJohn Fastabend * yet. Because driver side rcu_read_lock/unlock only protects the 212546ac1ffSJohn Fastabend * running XDP program. However, for pending flush operations the 213546ac1ffSJohn Fastabend * dev and ctx are stored in another per cpu map. And additionally, 214546ac1ffSJohn Fastabend * the driver tear down ensures all soft irqs are complete before 215546ac1ffSJohn Fastabend * removing the net device in the case of dev_put equals zero. 216546ac1ffSJohn Fastabend */ 217546ac1ffSJohn Fastabend old_dev = xchg(&dtab->netdev_map[k], NULL); 218546ac1ffSJohn Fastabend if (old_dev) 219546ac1ffSJohn Fastabend call_rcu(&old_dev->rcu, __dev_map_entry_free); 220546ac1ffSJohn Fastabend return 0; 221546ac1ffSJohn Fastabend } 222546ac1ffSJohn Fastabend 223546ac1ffSJohn Fastabend static int dev_map_update_elem(struct bpf_map *map, void *key, void *value, 224546ac1ffSJohn Fastabend u64 map_flags) 225546ac1ffSJohn Fastabend { 226546ac1ffSJohn Fastabend struct bpf_dtab *dtab = container_of(map, struct bpf_dtab, map); 227546ac1ffSJohn Fastabend struct net *net = current->nsproxy->net_ns; 228546ac1ffSJohn Fastabend struct bpf_dtab_netdev *dev, *old_dev; 229546ac1ffSJohn Fastabend u32 i = *(u32 *)key; 230546ac1ffSJohn Fastabend u32 ifindex = *(u32 *)value; 231546ac1ffSJohn Fastabend 232546ac1ffSJohn Fastabend if (unlikely(map_flags > BPF_EXIST)) 233546ac1ffSJohn Fastabend return -EINVAL; 234546ac1ffSJohn Fastabend 235546ac1ffSJohn Fastabend if (unlikely(i >= dtab->map.max_entries)) 236546ac1ffSJohn Fastabend return -E2BIG; 237546ac1ffSJohn Fastabend 238546ac1ffSJohn Fastabend if (unlikely(map_flags == BPF_NOEXIST)) 239546ac1ffSJohn Fastabend return -EEXIST; 240546ac1ffSJohn Fastabend 241546ac1ffSJohn Fastabend if (!ifindex) { 242546ac1ffSJohn Fastabend dev = NULL; 243546ac1ffSJohn Fastabend } else { 244546ac1ffSJohn Fastabend dev = kmalloc(sizeof(*dev), GFP_ATOMIC | __GFP_NOWARN); 245546ac1ffSJohn Fastabend if (!dev) 246546ac1ffSJohn Fastabend return -ENOMEM; 247546ac1ffSJohn Fastabend 248546ac1ffSJohn Fastabend dev->dev = dev_get_by_index(net, ifindex); 249546ac1ffSJohn Fastabend if (!dev->dev) { 250546ac1ffSJohn Fastabend kfree(dev); 251546ac1ffSJohn Fastabend return -EINVAL; 252546ac1ffSJohn Fastabend } 253546ac1ffSJohn Fastabend 254546ac1ffSJohn Fastabend dev->key = i; 255546ac1ffSJohn Fastabend dev->dtab = dtab; 256546ac1ffSJohn Fastabend } 257546ac1ffSJohn Fastabend 258546ac1ffSJohn Fastabend /* Use call_rcu() here to ensure rcu critical sections have completed 259546ac1ffSJohn Fastabend * Remembering the driver side flush operation will happen before the 260546ac1ffSJohn Fastabend * net device is removed. 261546ac1ffSJohn Fastabend */ 262546ac1ffSJohn Fastabend old_dev = xchg(&dtab->netdev_map[i], dev); 263546ac1ffSJohn Fastabend if (old_dev) 264546ac1ffSJohn Fastabend call_rcu(&old_dev->rcu, __dev_map_entry_free); 265546ac1ffSJohn Fastabend 266546ac1ffSJohn Fastabend return 0; 267546ac1ffSJohn Fastabend } 268546ac1ffSJohn Fastabend 269546ac1ffSJohn Fastabend const struct bpf_map_ops dev_map_ops = { 270546ac1ffSJohn Fastabend .map_alloc = dev_map_alloc, 271546ac1ffSJohn Fastabend .map_free = dev_map_free, 272546ac1ffSJohn Fastabend .map_get_next_key = dev_map_get_next_key, 273546ac1ffSJohn Fastabend .map_lookup_elem = dev_map_lookup_elem, 274546ac1ffSJohn Fastabend .map_update_elem = dev_map_update_elem, 275546ac1ffSJohn Fastabend .map_delete_elem = dev_map_delete_elem, 276546ac1ffSJohn Fastabend }; 277