Return-Path: Received: from smtp1.linuxfoundation.org (smtp1.linux-foundation.org [172.17.192.35]) by mail.linuxfoundation.org (Postfix) with ESMTPS id 3833D158F; Mon, 14 May 2018 09:24:00 +0000 (UTC) X-Greylist: from auto-whitelisted by SQLgrey-1.7.6 X-Greylist: from auto-whitelisted by SQLgrey-1.7.6 Received: from azure.erisian.com.au (cerulean.erisian.com.au [139.162.42.226]) by smtp1.linuxfoundation.org (Postfix) with ESMTPS id 7D94C196; Mon, 14 May 2018 09:23:59 +0000 (UTC) Received: from aj@azure.erisian.com.au (helo=sapphire.erisian.com.au) by azure.erisian.com.au with esmtpsa (Exim 4.84_2 #1 (Debian)) id 1fI9hz-0006tK-1N; Mon, 14 May 2018 19:23:57 +1000 Received: by sapphire.erisian.com.au (sSMTP sendmail emulation); Mon, 14 May 2018 19:23:29 +1000 Date: Mon, 14 May 2018 19:23:29 +1000 From: Anthony Towns To: Rusty Russell Message-ID: <20180514092329.GA17286@erisian.com.au> References: <871sewirni.fsf@gmail.com> <87sh73fe4h.fsf@gmail.com> <20180508144021.GA15921@erisian.com.au> <87in7we8h1.fsf@rustcorp.com.au> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <87in7we8h1.fsf@rustcorp.com.au> User-Agent: Mutt/1.5.23 (2014-03-12) X-Spam-Score: -1.9 X-Spam-Score-int: -18 X-Spam-Bar: - X-Spam-Status: No, score=-0.5 required=5.0 tests=BAYES_05,UNPARSEABLE_RELAY autolearn=ham version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on smtp1.linux-foundation.org Cc: Bitcoin Protocol Discussion , lightning-dev@lists.linuxfoundation.org Subject: Re: [bitcoin-dev] [Lightning-dev] BIP sighash_noinput X-BeenThere: bitcoin-dev@lists.linuxfoundation.org X-Mailman-Version: 2.1.12 Precedence: list List-Id: Bitcoin Protocol Discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 14 May 2018 09:24:00 -0000 On Thu, May 10, 2018 at 08:34:58AM +0930, Rusty Russell wrote: > > The big concern I have with _NOINPUT is that it has a huge failure > > case: if you use the same key for multiple inputs and sign one of them > > with _NOINPUT, you've spent all of them. The current proposal kind-of > > limits the potential damage by still committing to the prevout amount, > > but it still seems a big risk for all the people that reuse addresses, > > which seems to be just about everyone. > If I can convince you to sign with SIGHASH_NONE, it's already a problem > today. So, I don't find that very compelling: "there's already a way to lose your money, so it's fine to add other ways to lose your money". And again, I think NOINPUT is worse here, because a SIGHASH_NONE signature only lets others take the coin you're trying to spend, messing up when using NOINPUT can cause you to lose other coins as well (with caveats). > [...] > In a world where SIGHASH_NONE didn't exist, this might be an argument :) I could see either dropping support for SIGHASH_NONE for segwit v1 addresses, or possibly limiting SIGHASH_NONE in a similar way to limiting SIGHASH_NOINPUT. Has anyone dug through the blockchain to see if SIGHASH_NONE is actually used/useful? > That was also suggested by Mark Friedenbach, but I think we'll end up > with more "magic key" a-la Schnorr/taproot/graftroot and less script in > future. Taproot and graftroot aren't "less script" at all -- if anything they're the opposite in that suddenly every address can have a script path. I think NOINPUT has pretty much the same tradeoffs as taproot/graftroot scripts: in the normal case for both you just use a SIGHASH_ALL signature to spend your funds; in the abnormal case for NOINPUT, you use a SIGHASH_NOINPUT (multi)sig for unilateral eltoo closes or watchtower penalties, in the abnormal case for taproot/graftroot you use a script. > That means we'd actually want a different Segwit version for > "NOINPUT-can-be-used", which seems super ugly. That's backwards. If you introduce a new opcode, you can use the existing segwit version, rather than needing segwit v1. You certainly don't need v1 segwit for regular coins and v2 segwit for NOINPUT coins, if that's where you were going? For segwit v0, that would mean your addresses for a key "X", might be: [pubkey] X - not usable with NOINPUT [script] 2 X Y 2 CHECKMULTISIG - not usable with NOINPUT [script] 2 X Y 2 CHECKMULTISIG_1USE_VERIFY - usable with NOINPUT (or SIGHASH_ALL) CHECKMULTISIG_1USE_VERIFY being soft-forked in by replacing an OP_NOP, of course. Any output spendable via a NOINPUT signature would then have had to have been deliberately created as being spendable by NOINPUT. For a new segwit version with taproot that likewise includes an opcode, that might be: [taproot] X - not usable with NOINPUT [taproot] X or: X CHECKSIG_1USE - usable with NOINPUT If you had two UTXOs (with the same value), then if you construct a taproot witness script for the latter address it will look like: X [X CHECKSIG_1USE] [sig_X_NOINPUT] and that signature can't be used for addresses that were just intending to pay to X, because the NOINPUT sig/sighash simply isn't supported without a taproot path that includes the CHECKSIG_1USE opcode. In essence, with the above construction there's two sorts of addresses you generate from a public key X: addresses where you spend each coin individually, and different addresses where you spend the wallet of coins with that public key (and value) at once; and that remains the same even if you use a single key for both. I think it's slightly more reasonable to worry about signing with NOINPUT compared to signing with SIGHASH_NONE: you could pretty reasonably setup your (light) bitcoin wallet to not be able to sign (or verify) with SIGHASH_NONE ever; but if you want to use lightning v2, it seems pretty likely your wallet will be signing things with SIGHASH_NOINPUT. From there, it's a matter of having a bug or a mistake cause you to cross-contaminate keys into your lightning subsystem, and not be sufficiently protected by other measures (eg, muSig versus checkmultisig). (For me the Debian ssh key generation bug from a decade ago is sufficient evidence that people you'd think are smart and competent do make really stupid mistakes in real life; so defense in depth here makes sense even though you'd have to do really stupid things to get a benefit from it) The other benefit of a separate opcode is support can be soft-forked in independently of a new segwit version (either earlier or later). I don't think the code has to be much more complicated with a separate opcode; passing an extra flag to TransactionSignatureChecker::CheckSig() is probably close to enough. Some sort of flag remains needed anyway since v0 and pre-segwit signatures won't support NOINPUT. Cheers, aj