Hi Jordan, kernel test robot noticed the following build warnings: [auto build test WARNING on net-next/main] url: https://github.com/intel-lab-lkp/linux/commits/Jordan-Rife/wireguard-allowedips-Add-WGALLOWEDIP_F_REMOVE_ME-flag/20240831-034712 base: net-next/main patch link: https://lore.kernel.org/r/20240830194103.2186774-1-jrife%40google.com patch subject: [PATCH net-next] wireguard: allowedips: Add WGALLOWEDIP_F_REMOVE_ME flag config: i386-randconfig-062-20240901 (https://download.01.org/0day-ci/archive/20240901/202409011256.CWrnquxQ-lkp@xxxxxxxxx/config) compiler: gcc-12 (Debian 12.2.0-14) 12.2.0 reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20240901/202409011256.CWrnquxQ-lkp@xxxxxxxxx/reproduce) If you fix the issue in a separate patch/commit (i.e. not just a new version of the same patch/commit), kindly add following tags | Reported-by: kernel test robot <lkp@xxxxxxxxx> | Closes: https://lore.kernel.org/oe-kbuild-all/202409011256.CWrnquxQ-lkp@xxxxxxxxx/ sparse warnings: (new ones prefixed by >>) >> drivers/net/wireguard/allowedips.c:257:24: sparse: sparse: incorrect type in argument 1 (different address spaces) @@ expected struct list_head *entry @@ got struct list_head [noderef] __rcu * @@ drivers/net/wireguard/allowedips.c:257:24: sparse: expected struct list_head *entry drivers/net/wireguard/allowedips.c:257:24: sparse: got struct list_head [noderef] __rcu * >> drivers/net/wireguard/allowedips.c:258:9: sparse: sparse: cast removes address space '__rcu' of expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: cast removes address space '__rcu' of expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: cast removes address space '__rcu' of expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: cast removes address space '__rcu' of expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: cast removes address space '__rcu' of expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: cast removes address space '__rcu' of expression drivers/net/wireguard/allowedips.c:269:24: sparse: sparse: cast removes address space '__rcu' of expression drivers/net/wireguard/allowedips.c:270:26: sparse: sparse: cast removes address space '__rcu' of expression >> drivers/net/wireguard/allowedips.c:276:19: sparse: sparse: incorrect type in argument 1 (different address spaces) @@ expected struct callback_head *head @@ got struct callback_head [noderef] __rcu * @@ drivers/net/wireguard/allowedips.c:276:19: sparse: expected struct callback_head *head drivers/net/wireguard/allowedips.c:276:19: sparse: got struct callback_head [noderef] __rcu * drivers/net/wireguard/allowedips.c:294:18: sparse: sparse: incompatible types in comparison expression (different address spaces): drivers/net/wireguard/allowedips.c:294:18: sparse: struct wg_peer * drivers/net/wireguard/allowedips.c:294:18: sparse: struct wg_peer [noderef] __rcu * >> drivers/net/wireguard/allowedips.c:384:25: sparse: sparse: incorrect type in argument 1 (different address spaces) @@ expected struct allowedips_node [noderef] __rcu *node @@ got struct allowedips_node *[assigned] node @@ >> drivers/net/wireguard/allowedips.c:258:9: sparse: sparse: dereference of noderef expression >> drivers/net/wireguard/allowedips.c:258:9: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:259:22: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:259:38: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:261:17: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:264:44: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:265:50: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:268:25: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:269:24: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:269:24: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:270:26: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:270:26: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:271:26: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:274:25: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:274:25: sparse: sparse: dereference of noderef expression drivers/net/wireguard/allowedips.c:274:25: sparse: sparse: dereference of noderef expression vim +257 drivers/net/wireguard/allowedips.c 251 252 static void _remove(struct allowedips_node __rcu *node, struct mutex *lock) 253 { 254 struct allowedips_node *child, **parent_bit, *parent; 255 bool free_parent; 256 > 257 list_del_init(&node->peer_list); > 258 RCU_INIT_POINTER(node->peer, NULL); 259 if (node->bit[0] && node->bit[1]) 260 return; 261 child = rcu_dereference_protected(node->bit[!rcu_access_pointer(node->bit[0])], 262 lockdep_is_held(lock)); 263 if (child) 264 child->parent_bit_packed = node->parent_bit_packed; 265 parent_bit = (struct allowedips_node **)(node->parent_bit_packed & ~3UL); 266 *parent_bit = child; 267 parent = (void *)parent_bit - 268 offsetof(struct allowedips_node, bit[node->parent_bit_packed & 1]); 269 free_parent = !rcu_access_pointer(node->bit[0]) && 270 !rcu_access_pointer(node->bit[1]) && 271 (node->parent_bit_packed & 3) <= 1 && 272 !rcu_access_pointer(parent->peer); 273 if (free_parent) 274 child = rcu_dereference_protected(parent->bit[!(node->parent_bit_packed & 1)], 275 lockdep_is_held(lock)); > 276 call_rcu(&node->rcu, node_free_rcu); 277 if (!free_parent) 278 return; 279 if (child) 280 child->parent_bit_packed = parent->parent_bit_packed; 281 *(struct allowedips_node **)(parent->parent_bit_packed & ~3UL) = child; 282 call_rcu(&parent->rcu, node_free_rcu); 283 } 284 285 static int remove(struct allowedips_node __rcu **trie, u8 bits, const u8 *key, 286 u8 cidr, struct wg_peer *peer, struct mutex *lock) 287 { 288 struct allowedips_node *node; 289 290 if (unlikely(cidr > bits || !peer)) 291 return -EINVAL; 292 if (!rcu_access_pointer(*trie) || 293 !node_placement(*trie, key, cidr, bits, &node, lock) || 294 peer != node->peer) 295 return 0; 296 297 _remove(node, lock); 298 299 return 0; 300 } 301 302 void wg_allowedips_init(struct allowedips *table) 303 { 304 table->root4 = table->root6 = NULL; 305 table->seq = 1; 306 } 307 308 void wg_allowedips_free(struct allowedips *table, struct mutex *lock) 309 { 310 struct allowedips_node __rcu *old4 = table->root4, *old6 = table->root6; 311 312 ++table->seq; 313 RCU_INIT_POINTER(table->root4, NULL); 314 RCU_INIT_POINTER(table->root6, NULL); 315 if (rcu_access_pointer(old4)) { 316 struct allowedips_node *node = rcu_dereference_protected(old4, 317 lockdep_is_held(lock)); 318 319 root_remove_peer_lists(node); 320 call_rcu(&node->rcu, root_free_rcu); 321 } 322 if (rcu_access_pointer(old6)) { 323 struct allowedips_node *node = rcu_dereference_protected(old6, 324 lockdep_is_held(lock)); 325 326 root_remove_peer_lists(node); 327 call_rcu(&node->rcu, root_free_rcu); 328 } 329 } 330 331 int wg_allowedips_insert_v4(struct allowedips *table, const struct in_addr *ip, 332 u8 cidr, struct wg_peer *peer, struct mutex *lock) 333 { 334 /* Aligned so it can be passed to fls */ 335 u8 key[4] __aligned(__alignof(u32)); 336 337 ++table->seq; 338 swap_endian(key, (const u8 *)ip, 32); 339 return add(&table->root4, 32, key, cidr, peer, lock); 340 } 341 342 int wg_allowedips_insert_v6(struct allowedips *table, const struct in6_addr *ip, 343 u8 cidr, struct wg_peer *peer, struct mutex *lock) 344 { 345 /* Aligned so it can be passed to fls64 */ 346 u8 key[16] __aligned(__alignof(u64)); 347 348 ++table->seq; 349 swap_endian(key, (const u8 *)ip, 128); 350 return add(&table->root6, 128, key, cidr, peer, lock); 351 } 352 353 int wg_allowedips_remove_v4(struct allowedips *table, const struct in_addr *ip, 354 u8 cidr, struct wg_peer *peer, struct mutex *lock) 355 { 356 /* Aligned so it can be passed to fls */ 357 u8 key[4] __aligned(__alignof(u32)); 358 359 ++table->seq; 360 swap_endian(key, (const u8 *)ip, 32); 361 return remove(&table->root4, 32, key, cidr, peer, lock); 362 } 363 364 int wg_allowedips_remove_v6(struct allowedips *table, const struct in6_addr *ip, 365 u8 cidr, struct wg_peer *peer, struct mutex *lock) 366 { 367 /* Aligned so it can be passed to fls64 */ 368 u8 key[16] __aligned(__alignof(u64)); 369 370 ++table->seq; 371 swap_endian(key, (const u8 *)ip, 128); 372 return remove(&table->root6, 128, key, cidr, peer, lock); 373 } 374 375 void wg_allowedips_remove_by_peer(struct allowedips *table, 376 struct wg_peer *peer, struct mutex *lock) 377 { 378 struct allowedips_node *node, *tmp; 379 380 if (list_empty(&peer->allowedips_list)) 381 return; 382 ++table->seq; 383 list_for_each_entry_safe(node, tmp, &peer->allowedips_list, peer_list) { > 384 _remove(node, lock); 385 } 386 } 387 -- 0-DAY CI Kernel Test Service https://github.com/intel/lkp-tests/wiki