-
Notifications
You must be signed in to change notification settings - Fork 5.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Update BIP 118 for taproot, rename to ANYPREVOUT #943
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Gave it a quick read and didn't spot anything objectionable. One micro-nit.
I suggest that you get a new BIP number for ANYPREVOUT and add "not recommended for implementation" to bip118 (including reasoning, please ;-). The two approaches are conceptually distinct and it's worth keeping the other idea around for historical purposes, even if it's not pursued going forward. BIP118 as a segwit version has been around for over 3 years now. Please just give us one or the other! We're dying out here! ;-) |
Concept ACK for updating. The original BIP118 proposal will remain available via git history, so no information is lost by updating it. Noinput as its own separate segwit version never had any traction AFAICT---I think almost everyone has wanted this to be either a part of a larger soft fork or an add-on soft fork. |
b001d42
to
ac73eed
Compare
That was the rationale for proposing an update instead of leaving noinput lingering. noinput alone was lacking the details to make it work within taproot, and the update adds all the necessary details to make the proposal compatible with taproot. Given the timing of the taproot and the noinput proposal we tried to make the two independent by not adding any dependencies between them. With taproot making good progress, and the shrinking probability of a raw noinput proposal without taproot integration making progress, it is desirable imho to replace the raw proposal with the integrated one. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It might be worth adding a section about recommendations for wallet devs on how to handle if funds are received to an address that has BIP 118 pub key, I would expect that they should immediately spend it to another address if they already given out a SIGHASH_ANYPREVOUTANYSCRIPT
signature and do not want the newly received funds spendable by the parties with the signature.
bip-0118.mediawiki
Outdated
Further, for a chain of transactions using the same <code>scriptPubKey</code> and value, and only authenticated via ANYPREVOUT signatures (as envisioned in eltoo for failure cases), it may be possible for any third party to malleate the transactions (and their txids) without having access to any of the private keys, particularly by omitting intermediate transactions. | ||
|
||
This form of malleation can be dealt with by the child transactions also using ANYPREVOUT signatures -- when a parent transaction is malleated, its children can simply be adjusted to reference the new txid as the input and the ANYPREVOUT signatures remain valid. | ||
|
||
However child transactions that are authorised by a <code>SIGHASH_ALL</code> or <code>SIGHASH_ANYONECANPAY</code> signature will need new signatures if their inputs are malleated in this way. | ||
This risk may be mitigated somewhat by using [[bip-0068.mediawiki|BIP 68]]/[[bip-0112.mediawiki|BIP 112]] relative time locks before spending a UTXO that had been authorised via an ANYPREVOUT signature with <code>SIGHASH_ALL</code> or <code>SIGHASH_ANYONECANPAY</code>: a relative timelock can ensure that the inputs have enough confirmations that they can only be replaced in the event of a large block reorg. | ||
Note that this approach has drawbacks: relative timelocks prevent fee-bumping via child-pays-for-parent, and have the obvious drawback of making the funds temporarily unusable until the timelock expires. | ||
|
||
==== Privacy considerations ==== | ||
|
||
It is expected that ANYPREVOUT signatures will only be rarely used in practice. | ||
Protocol and wallet designers should aim to have their transactions use Taproot key path spends whenever possible, both for efficiency reasons due to the lower transaction weight, but also for privacy reasons to avoid third parties being able to distinguish their transactions from those of other protocols. | ||
|
||
Transactions that do use ANYPREVOUT signatures will therefore reveal information about the transaction, potentially including that cooperation was impossible, or what protocol or software in use (due to the details of the script). | ||
|
||
In order to maximise privacy, it is therefore recommended that protocol designers only use BIP 118 public keys in scripts that will be spent using at least one ANYPREVOUT signature, and either use key path spends or alternate scripts in the taproot merkle tree for any spends that can be authorised without ANYPREVOUT signatures. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: change these "ANYPREVOUT"s to "ANYPREVOUT
"
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've left "ANYPREVOUT signatures" as regular text since it's talking about the concept, and only used <code>
markup for SIGHASH_ANYPREVOUT
and SIGHASH_ANYPREVOUTANYSCRIPT
. I think that's reasonable, so keeping it that way at present... (Have made a couple of tweaks while rebasing though)
Our usual approach to this is "if you don't know how to handle ANYPREVOUT scripts you should not signal support for BIP118", and the wallets sending to you should never use BIP118". Having consumer wallets that do not require BIP118 support handle it is undesirable, and imho any guidance on how to handle them might give the contrary impression. |
What is the status here? Can we merge it? |
I just want to say that it is horribly confusing to have a standards document be completely rewritten to describe a totally different idea. This is a very atypical thing to do. If it's a new approach, please make a new BIP. |
It's not really new, it just adds the details for Taproot and addresses some concerns that have been raised during the discussion regarding replay-attacks. IMHO this is exactly the goal of updates to the BIPs. |
Indeed, it's not like it was even Proposed yet, just a Draft. |
I'll soon have a bit more time to dig into BIP 118, and I have spoken with a number of people willing to join a review club to work through the proposal. If anybody is interested in joining a public discussion we can set something up :-) But don't want to distract from the Taproot effort, which deserves all the attention it can get, and is the basis for anyprevout. |
I think now is a good time to revive public discussion efforts? |
Rebased, removed "draft" marker on PR, so should be okay for ACKs and eventual merge |
There's a lot of style changes mixed in with contextual changes so it's hard to determine what is a style fix vs what is new content. It would be helpful if commit number 1 was a pure style tweak followed by the actual changes in subsequent commit(s). |
It's pretty much entirely new content, I don't think there's much you can extract as just a style fix? |
Is there a current reference implementation? Trying to figure out presently if the BIP is trying to imply a tap leaf with 0x01 CHECKSIG has the effect of being equivalent to <0x01 || internal key> checksig or not (it seems implied by the bip language but not explicit enough imo). |
There's a reference implementation at https://github.com/ajtowns/bitcoin/tree/202101-anyprevout but it's not current both in that it's missing at least the change to have ANYPREVOUTANYSCRIPT not commit to the amount, is some months out of date, and may be buggy.
I'm not sure what's unclear about:
If your internal key is G, ie, "79BE667E F9DCBBAC 55A06295 CE870B07 029BFCDB 2DCE28D9 59F2815B 16F81798" then doing either |
I'm not in love with the 0x01 to mean an anyprevout key based on the internal PK. I think that this sort of mechanism is more generally useful (e.g., I imagine the script I also think that 0x01 makes it so that there is a public key which is "computable" using script math, which is kind of weird (or at least merits consideration)? I mean I suppose |
You could define the single-byte pubkey "0x81" (ie the value OP_1NEGATE pushes onto the stack) to be treated as the internal public key with the bip342 signature digest and get that sort of behaviour. The key and/or signature needs to encode what digest is going to be used however; but if you're happy for the signature to encode the digest, then just using the APO capable OP_1 with a non-ANYPREVOUT signature works.
CAT would also make public keys "computable" in this sense, except moreso since there would actually be multiple keys you could compute. But you can already write scripts that simply accept the pubkey as an input which is more flexible, and already in use since that's how P2PKH works. |
bip-0118.mediawiki
Outdated
It is expected that ANYPREVOUT signatures will only be rarely used in practice. | ||
Protocol and wallet designers should aim to have their transactions use Taproot key path spends whenever possible, both for efficiency reasons due to the lower transaction weight, but also for privacy reasons to avoid third parties being able to distinguish their transactions from those of other protocols. | ||
|
||
Transactions that do use ANYPREVOUT signatures will therefore reveal information about the transaction, potentially including that cooperation was impossible, or what protocol or software in use (due to the details of the script). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Small fix for a typo:
Transactions that do use ANYPREVOUT signatures will therefore reveal information about the transaction, potentially including that cooperation was impossible, or what protocol or software in use (due to the details of the script). | |
Transactions that do use ANYPREVOUT signatures will therefore reveal information about the transaction, potentially including that cooperation was impossible, or what protocol or software was used (due to the details of the script). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
@cdecker Think this is mergable? Even if not perfect, it can continue to be revised... |
As a result, a single signature for a third, even later transaction must be able to spend both the prior transactions, even though they have a different tapscript. | ||
On the other hand, these cases also provide a good reason to have the option to commit to the script: because each transaction has a new script, committing to the script allows you to produce a signature that applies to precisely one of these transactions. | ||
In the eltoo case, this allows you to have a signature for an update transaction that can be applied to any prior update, and a signature for a settlement transaction that applies only to the corresponding update transaction, while using the same key for both, which in turn allows for a more compact script. | ||
</ref> and value <ref>'''Why (and why not) commit to the input value?''' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If i understand correctly:
APO: Commits to value
APOAS: Doesn't commit to value
Can you better justify why we don't also want ANYPREVOUTANYVALUE and ANYPREVOUTANYSCRIPTSPECIFICVALUE?
In general, one thing that strikes me is that when anyprevout is used for eltoo you're generally doing a script like:
This means that you're overloading the CLTV clause, which means it's impossible to use Eltoo and use a absolute lock time, it also means you have to use fewer than a billion sequences, and if you pick a random # to mask how many payments you've done / pick random gaps let's say that reduces your numbers in half. That may be enough, but is still relatively limited. There is also the issue that multiple inputs cannot be combined into a transaction if they have signed on different locktimes. Since Eltoo is the primary motivation for ANYPREVOUT, it's worth making sure we have all the parts we'd need bundled together to see it be successful. A few options come to mind that might be desirable in order to better serve the eltoo usecase
Then, posession of a higher signed sequence would allow for the use of the update path. However, the downside is that there would be no guarantee that the new state provided for update would be higher than the past one without a more advanced covenant. E.g.
To satisfy this clause, a signature Overall I'm somewhat partial to option 3 as it seems to be closest to making ANYPREVOUT more precisely designed to support Eltoo. It would also be possible to make it such that if the tag N=1, then the behavior is identical to the proposal currently. |
It occurs to me this might be the wrong venue to discuss the above as this is larger change outside the changes to the BIP outstanding, so I will move discussion to the mailing list. |
I think it is excellent, let's ship it 🤓 We can do fine-tuning and corrections in separate PRs, agreed |
Lots of updates to BIP 118 in light of taproot. cc @cdecker