Right, there are 2 different things (or flows within LoadWalletInternal). First what I tried to explain in my previous comment (at least in my head) was that the migration process won't reach those lines (inside the if condition) because when that flow goes thru LoadWalletInternal it does it with the purpose of creating the target descriptor wallet so at that check/ condition the wallet is always a descriptor already. You can execute the migration using the old node (self.old_node.migratewallet) and will be the same thing. The second point is the "loading" behaviour of LoadWalletInternal, in order to hit it you had to call loadwallet RPC for a legacy wallet using the old node (v28 node or earlier), a legacy can't be loaded on the master node anymore (a validation cuts the flow earlier), that's why it's dead code (you can see that the test validating that warning was removed from test/functional/wallet_backwards_compatibility.py in #31250). Maybe you were saying the same thing but just wanted to clarify this for other ppl that could ever read this. Having LoadWalletIternal these 2 different behaviours (loading and creating) seems incorrect and brings confusion, I see there's already some interest in order to fix this in #32636. Thanks for your review!