Pieter Wuille [ARCHIVE] on Nostr: 📅 Original date posted:2015-12-13 📝 Original message:On Sun, Dec 13, 2015 at ...
📅 Original date posted:2015-12-13
📝 Original message:On Sun, Dec 13, 2015 at 4:25 PM, jl2012--- via bitcoin-dev
<bitcoin-dev at lists.linuxfoundation.org> wrote:
> I'm trying to list the minimal consensus rule changes needed for segwit
> softfork. The list does not cover the changes in non-consensus critical
> behaviors, such as relay of witness data.
>
> 1. OP_NOP4 is renamed as OP_SEGWIT
> 2. A script with OP_SEGWIT must fail if the scriptSig is not completely
> empty
> 3. If OP_SEGWIT is used in the scriptPubKey, it must be the only and the
> last OP code in the scriptPubKey, or the script must fail
> 4. The OP_SEGWIT must be preceded by exactly one data push (the "serialized
> script") with at least one byte, or the script must fail
The use of a NOP opcode to indicate a witness script was something I
considered at first too, but it's not really needed. You wouldn't be
able to use that opcode in any place a normal opcode could occur, as
it needs to be able to inspect the full scriptSig (rather than just
its resulting stack) anyway. So both in practice and conceptually it
is only really working as a template that gets assigned a special
meaning (like P2SH did). We don't need an opcode for that, and instead
we could say that any scriptPubKey (or redeemscript) that consists of
a single push is a witness program.
> 5. The most significant byte of serialized script is the version byte, an
> unsigned number
> 6. If the version byte is 0x00, the script must fail
What is that good for?
> 7. If the version byte is 0x02 to 0xff, the rest of the serialized script is
> ignored and the output is spendable with any form of witness (even if the
> witness contains something invalid in the current script system, e.g.
> OP_RETURN)
Do you mean the scriptPubKey itself, or the script that follows after
the version byte?
* The scriptPubKey itself: that's in contradiction with your rule 4,
as segwit scripts are by definition only a push (+ opcode), so they
can't be an OP_RETURN.
* The script after the version byte: agree - though it doesn't
actually need to be a script at all even (see further).
> 8. If the version byte is 0x01,
> 8a. rest of the serialized script is deserialized, and be interpreted as the
> scriptPubKey.
> 8b. the witness is interpreted as the scriptSig.
> 8c. the script runs with existing rules (including P2SH)
I don't think it's very useful to allow P2SH inside segwit, as we can
actually do better and allow segwit scripts to push the (perhaps 256
bit) hash of the redeemscript in the scriptPubKey, and have the full
redeemscript in the witness. See further for details. The numbers I
showed in the presentation were created using a simulation that used
that model already.
It is useful however to allow segwit inside P2SH (so the witness
program including version byte goes into the redeemscript, inside the
scriptSig). This allows old clients to send to new wallets without any
modifications (at slightly lower efficiency). The rules in this case
must say that the scriptSig is exactly a push of the redeemscript
(which itself contains the witness program), to provide both
compatibility with old consensus rules and malleability protection.
So let me summarize by giving an equivalent to your list above,
reflecting how my current prototype works:
A) A scriptPubKey or P2SH redeemscript that consists of a single push
of 2 to 41 bytes gets a new special meaning, and the byte vector
pushed by it is called the witness program.
A.1) In case the scriptPubKey pushes a witness program directly, the
scriptSig must be exactly empty.
A.2) In case the redeemscript pushes a witness program, the scriptSig
must be exactly the single push of the redeemscript.
B) The first byte of a witness program is the version byte.
B.1) If the witness version byte is 0, the rest of the witness program
is the actual script, which is executed after normal script evaluation
but with data from the witness rather than the scriptSig. The program
must not fail and result in a single TRUE on the stack, and nothing
else (to prevent stuffing the witness with pointless data during relay
of transactions).
B.2) if the witness version byte is 1, the rest of the witness program
must be 32 bytes, and a SHA256 hash of the actual script. The witness
must consist of an input stack to feed to the program, followed by the
serialized program itself (whose hash must match the hash pushed in
the witness program). It is executed after normal script evluation,
and must not fail and result in a single TRUE on the stack, and
nothing else.
B.3) if the witness version byte is 2 or higher, no further
interpretation of the data happens, but can be softforked in.
I'll write a separate mail on the block commitment structure.
--
Pieter
Published at
2023-06-07 17:46:08Event JSON
{
"id": "261875f76141f3862500142b1e9de1444331a1718f384cdc242ae1871d4488c1",
"pubkey": "5cb21bf5d7f25a9d46879713cbd32433bbc10e40ef813a3c28fe7355f49854d6",
"created_at": 1686159968,
"kind": 1,
"tags": [
[
"e",
"12a84dc161497f5ec3fbb3e9fb726708fb1bb0268a8834c07e1f631c1bbca295",
"",
"root"
],
[
"e",
"3b4e7577eae61e79096d50d643c6f93cdc8474e53230b2fe6caa2263080d59be",
"",
"reply"
],
[
"p",
"b61e2e7ccbf4abd7f49715c62f4ac7a93cbdd5ead0316279c5f5fe9b18dd0aaa"
]
],
"content": "📅 Original date posted:2015-12-13\n📝 Original message:On Sun, Dec 13, 2015 at 4:25 PM, jl2012--- via bitcoin-dev\n\u003cbitcoin-dev at lists.linuxfoundation.org\u003e wrote:\n\u003e I'm trying to list the minimal consensus rule changes needed for segwit\n\u003e softfork. The list does not cover the changes in non-consensus critical\n\u003e behaviors, such as relay of witness data.\n\u003e\n\u003e 1. OP_NOP4 is renamed as OP_SEGWIT\n\u003e 2. A script with OP_SEGWIT must fail if the scriptSig is not completely\n\u003e empty\n\u003e 3. If OP_SEGWIT is used in the scriptPubKey, it must be the only and the\n\u003e last OP code in the scriptPubKey, or the script must fail\n\u003e 4. The OP_SEGWIT must be preceded by exactly one data push (the \"serialized\n\u003e script\") with at least one byte, or the script must fail\n\nThe use of a NOP opcode to indicate a witness script was something I\nconsidered at first too, but it's not really needed. You wouldn't be\nable to use that opcode in any place a normal opcode could occur, as\nit needs to be able to inspect the full scriptSig (rather than just\nits resulting stack) anyway. So both in practice and conceptually it\nis only really working as a template that gets assigned a special\nmeaning (like P2SH did). We don't need an opcode for that, and instead\nwe could say that any scriptPubKey (or redeemscript) that consists of\na single push is a witness program.\n\n\u003e 5. The most significant byte of serialized script is the version byte, an\n\u003e unsigned number\n\u003e 6. If the version byte is 0x00, the script must fail\n\nWhat is that good for?\n\n\u003e 7. If the version byte is 0x02 to 0xff, the rest of the serialized script is\n\u003e ignored and the output is spendable with any form of witness (even if the\n\u003e witness contains something invalid in the current script system, e.g.\n\u003e OP_RETURN)\n\nDo you mean the scriptPubKey itself, or the script that follows after\nthe version byte?\n* The scriptPubKey itself: that's in contradiction with your rule 4,\nas segwit scripts are by definition only a push (+ opcode), so they\ncan't be an OP_RETURN.\n* The script after the version byte: agree - though it doesn't\nactually need to be a script at all even (see further).\n\n\u003e 8. If the version byte is 0x01,\n\u003e 8a. rest of the serialized script is deserialized, and be interpreted as the\n\u003e scriptPubKey.\n\u003e 8b. the witness is interpreted as the scriptSig.\n\u003e 8c. the script runs with existing rules (including P2SH)\n\nI don't think it's very useful to allow P2SH inside segwit, as we can\nactually do better and allow segwit scripts to push the (perhaps 256\nbit) hash of the redeemscript in the scriptPubKey, and have the full\nredeemscript in the witness. See further for details. The numbers I\nshowed in the presentation were created using a simulation that used\nthat model already.\n\nIt is useful however to allow segwit inside P2SH (so the witness\nprogram including version byte goes into the redeemscript, inside the\nscriptSig). This allows old clients to send to new wallets without any\nmodifications (at slightly lower efficiency). The rules in this case\nmust say that the scriptSig is exactly a push of the redeemscript\n(which itself contains the witness program), to provide both\ncompatibility with old consensus rules and malleability protection.\n\nSo let me summarize by giving an equivalent to your list above,\nreflecting how my current prototype works:\nA) A scriptPubKey or P2SH redeemscript that consists of a single push\nof 2 to 41 bytes gets a new special meaning, and the byte vector\npushed by it is called the witness program.\nA.1) In case the scriptPubKey pushes a witness program directly, the\nscriptSig must be exactly empty.\nA.2) In case the redeemscript pushes a witness program, the scriptSig\nmust be exactly the single push of the redeemscript.\nB) The first byte of a witness program is the version byte.\nB.1) If the witness version byte is 0, the rest of the witness program\nis the actual script, which is executed after normal script evaluation\nbut with data from the witness rather than the scriptSig. The program\nmust not fail and result in a single TRUE on the stack, and nothing\nelse (to prevent stuffing the witness with pointless data during relay\nof transactions).\nB.2) if the witness version byte is 1, the rest of the witness program\nmust be 32 bytes, and a SHA256 hash of the actual script. The witness\nmust consist of an input stack to feed to the program, followed by the\nserialized program itself (whose hash must match the hash pushed in\nthe witness program). It is executed after normal script evluation,\nand must not fail and result in a single TRUE on the stack, and\nnothing else.\nB.3) if the witness version byte is 2 or higher, no further\ninterpretation of the data happens, but can be softforked in.\n\nI'll write a separate mail on the block commitment structure.\n\n-- \nPieter",
"sig": "c33f53a5f57fd9eb44b9814504d62b3a1cc4ae802049db595ab93adb1d3d9699631c9511054dedd38048c03f786d8ab124d9fc691e10e116f7f395ce70e8492e"
}