So basically, this gives you an extra peace of mind because it guarantees when you make a transaction, the change address where the fund will be sent does indeed exist on both your watch-only wallet and on your actual wallet. This is basic. It is panic inducing to think that you may lose your funds without this check enabled.
If this is the concern, then it's easily mitigated by simply visually double-checking the transaction before signing it.
I remember mentioning it in your previous thread that there's a visible indicator in Knots/Core to know if an output is yours.
IIRC, I tested that with and without bip32derivs in the PSBT.
Quoting myself:
So what about that? I want to mitigate risks but not end up with change addresses that are do not match between the watch-only and airgap wallet. So could someone explain the workflow for this?
Bitcoin Knots keeps a huge keypool with 1000 gap limit per descriptor so it will know if any of the outputs doesn't match your change addresses even without "
bip32derivs".
So then in your workflow above during the signing process, just check the displayed addresses if there's a note saying: "
(own address)".
If you expect a change address and none of that showed, then do not sign the transaction.
The way it was worded here I read it as if I would lose the "(change)" check on the GUI:
Looks like a good path.. Two extra sanity checks I use before letting a watch-only touch the network: try to do things that require keys and confirm hard failure. In Core, dumpwallet should error with "private keys are disabled," and signrawtransactionwithwallet on a dummy tx should refuse to sign.
And one more tip that might be helpful: PSBTs can leak derivation paths and global xpubs. If you ever hand a PSBT to anything other than your offline box, create it with bip32derivs=false or strip derivs first. That keeps your keys unspilled and your privacy intact.
Could you develop on this?
To do a PSBT transaction you are going to need to place the file on your online box last time I checked, so it's not like you can avoid this. I did a number of test transactions on the testnet to practice the PSBT workflow and I think it was something like this:
0) Enable the "Enable PSBT Controls" checkbox
1) Go on the watch-only wallet and with Coin Control pick addresses as needed.
2) Click on "Create unsigned" and save .psbt file
3) Get this file into the airgap laptop and sign with the "File->Load PSBT from file..." GUI menu by clicking on "Sign Tx"
4) Save this now signed psbt file and move it back into watch-only laptop wallet
5) Load the file with "File->Load PSBT from file..." and click on "Broadcast Tx"
So as you can see, the psbt file is created on the online wallet already since step 1, so I don't understand why you claim " If you ever hand a PSBT to anything other than your offline box" since it's unavoidable, and I also do not understand what the other "bip32derivs=false or strip derivs first." thing does. If you could please elaborate and explain what this does and exact steps.
Confirmed, PSBTs can carry two kinds of wallet-structure data: per-key BIP32 derivation paths and a global xpubs map. Both aid signers, and both reveal account structure to anyone who sees the PSBT.
In Bitcoin Core, `walletcreatefundedpsbt` has a `bip32derivs` switch. It was default *false* in 0.19, and is default *true* by 22-23+. Set it to *false* on the watch-only box if you don't want derivation paths in the PSBT.
Derivation data on *outputs* lets a device verify the change address. If you omit it, you lose that automatic check, so verify change manually or use a fixed change address from your descriptor. Flow that matches your setup:
1). Create PSBT on the watch-only wallet with derivs off.
bitcoin-cli -rpcwallet=watch -named walletcreatefundedpsbt \
inputs='[]' outputs='{"bc1...":0.001}' options='{"add_inputs":true}' bip32derivs=false
2). Check it contains no xpubs or derivs:
bitcoin-cli decodepsbt "$PSBT" | grep -Ei 'xpub|bip32_derivs' # no hits
3). Move PSBT to the air-gapped wallet and sign:
SIGNED=$(bitcoin-cli -rpcwallet=airgap walletprocesspsbt "$PSBT" true | jq -r .psbt)
RAW=$(bitcoin-cli finalizepsbt "$SIGNED" true | jq -r .hex)
4). Broadcast only the raw hex from the online node:
bitcoin-cli sendrawtransaction "$RAW"
If I want to disable it, I need to create a new watch-only wallet again? Do I need to use that command or is there a way to do it without RPC? I have RPC disabled.
So the way I understand it now is that this is irrelevant if you use Bitcoin Core/Knots for the whole process (node+wallet) and this is only useful if you use other wallets or hardware wallets? If so, then I guess it's safe to disable it. I mean, that guy said that this was disabled by default until 0.22. Why was it changed? I guess to avoid loss of funds for those that use devices with Bitcoin Core/Knots as a node?
If I disable it, then I just process as usual with the GUI with the usual workflow?
0) Enable the "Enable PSBT Controls" checkbox
1) Go on the watch-only wallet and with Coin Control pick addresses as needed.
2) Click on "Create unsigned" and save .psbt file
3) Get this file into the airgap laptop and sign with the "File->Load PSBT from file..." GUI menu by clicking on "Sign Tx"
4) Save this now signed psbt file and move it back into watch-only laptop wallet
5) Load the file with "File->Load PSBT from file..." and click on "Broadcast Tx"
So assuming disabling this does not screw anything up, the "(change)" notice should be there. But just to triple check, how can I know that I own the change address on the airgap laptop given that that address was not generated yet? I remember there was a command for this I think.
Btw, on a theoretical attack were someone steals your PSBT file, what is exactly leaked? Like what could they do with it? with and without the bip32 enabled, to see the difference. Like, they could bruteforce any keys on your wallet? or only the addresses involved on the PSBT transaction? etc.