releng/13.1 context: sys/contrib/openzfs/module/avl/avl.c 's avl_destroy_nodes : lack of appropriately locked context for its use? Wild pointer?
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Sun, 26 Feb 2023 21:44:13 UTC
Note: This question came up while looking at one type of crash backtrace reported in: https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=267028 There is the code: void * avl_destroy_nodes(avl_tree_t *tree, void **cookie) { . . . /* * If we just removed a right child or there isn't one, go up to parent. */ if (child == 1 || parent->avl_child[1] == NULL) { node = parent; parent = AVL_XPARENT(parent); goto done; } /* * Do parent's right child, then leftmost descendent. */ node = parent->avl_child[1]; while (node->avl_child[0] != NULL) { parent = node; node = node->avl_child[0]; } . . . some gdb backtraces report that the "while" line above had a "signal handler called" result. If the avl tree were invariant over avl_destroy_nodes it looks like a wild pointer would need to be the value in a accessed node->avl_child[0] in order for the code to fail. But, if the avl tree was being separately updated during the avl_destroy_nodes activity, that could substitute in a NULL that "node = node->avl_child[0];" could get a copy of. Does anyone know which of these is a possibility? Both? The information would be good to add to the bugzilla submittal's comments if it helps narrow down anything. (I supposed a failed context synchronization across some context change, say a cpu migration, could be another way to get an odd value.) For reference, one of the example backtraces is: #6 <signal handler called> #7 avl_destroy_nodes (tree=tree@entry=0xfffff8003fa1bea0, cookie=cookie@entry=0xfffffe0075f2fdd0) at /usr/src/sys/contrib/openzfs/module/avl/avl.c:1023 #8 0xffffffff823dd768 in mze_destroy (zap=0xfffff8003fa1bd80) at /usr/src/sys/contrib/openzfs/module/zfs/zap_micro.c:402 #9 zap_evict_sync (dbu=0xfffff8003fa1bd80) at /usr/src/sys/contrib/openzfs/module/zfs/zap_micro.c:887 #10 0xffffffff822ae74a in dbuf_evict_user (db=0xfffff800391f3378) at /usr/src/sys/contrib/openzfs/module/zfs/dbuf.c:570 #11 dbuf_clear_data (db=0xfffff800391f3378) at /usr/src/sys/contrib/openzfs/module/zfs/dbuf.c:1131 #12 dbuf_destroy (db=0xfffff800391f3378) at /usr/src/sys/contrib/openzfs/module/zfs/dbuf.c:2804 #13 0xffffffff822b4129 in dbuf_evict_one () at /usr/src/sys/contrib/openzfs/module/zfs/dbuf.c:704 #14 0xffffffff822ac43d in dbuf_evict_thread (unused=unused@entry=0x0) at /usr/src/sys/contrib/openzfs/module/zfs/dbuf.c:742 #15 0xffffffff80bd8a9e in fork_exit ( callout=0xffffffff822ac120 <dbuf_evict_thread>, arg=0x0, frame=0xfffffe0075f2ff40) at /usr/src/sys/kern/kern_fork.c:1093 #16 <signal handler called> #17 mi_startup () at /usr/src/sys/kern/init_main.c:322 #18 0xffffffff80f76c49 in swapper () at /usr/src/sys/vm/vm_swapout.c:755 #19 0xffffffff80385022 in btext () at /usr/src/sys/amd64/amd64/locore.S:80 === Mark Millard marklmi at yahoo.com