diff --git a/spec/20190515-may-upgrade.md b/spec/20190515-may-upgrade.md new file mode 100644 index 000000000..6975980a0 --- /dev/null +++ b/spec/20190515-may-upgrade.md @@ -0,0 +1,72 @@ +--- +layout: specification +title: 2019-MAY-15 Network Upgrade Specification +date: 2018-10-16 +activation: 1557921600 +version: 0.1 DRAFT SUBJECT TO CHANGE +--- + +## Summary + +When the median time past [1] of the most recent 11 blocks (MTP-11) is greater than or equal to UNIX timestamp 1557921600, Bitcoin Cash will execute an upgrade of the network consensus rules according to this specification. Starting from the next block these consensus rules changes will take effect: + +* Enable the following opcodes + * OP_MUL + * OP_INVERT + * OP_LSHIFT + * OP_RSHIFT +* Enable Schnorr signatures +* Enforce minimal pushdata +* Enforce NULLDUMMY (BIP0147) +* Replace transaction size >100 byte requirement with transaction size not equal 64 bytes. + +The following are not consensus changes, but are recommended changes for Bitcoin Cash implementations: + +* Automatic replay protection for future upgrade + +## OpCodes + +The following opcodes will be re-enabled per [20190515-reenabled-opcodes.md](2019-may-opcodes.md): + +* OP_MUL +* OP_INVERT +* OP_LSHIFT +* OP_RSHIFT + +## Schnorr Signatures + +Support schnorr signatures per [schnorr-signatures.md](schnorr-signatures.md): + +## Enforce minimal pushdata + +As per existing standardness checks, enforce that all pushed data is a minimal representation at the script layer. + +## Enforce NULLDUMMY (BIP0147) + +As per BIP0147, enforce that the dummy element in OP_CHECKMULSIG(VERIFY) is a null +stack element. This will go into effect at the consensus layer. + +## Allow transactions <100 bytes, except 64 bytes specifically + +Replace transaction size >100 byte requirement with transaction size not equal 64 bytes. + +This rule prevents a hash griding attack, where SPV wallets can confuse a 64 byte transaction for a merkle node. +The amount of entropy in each 32-byte sections of the transaction is insufficient to prevent a preimage attack. +In this case, a valid transaction could be found with a hash equal +to the first, or last, 32 bytes of a 64-byte transaction. + +## Automatic Replay Protection + +When the median time past [2] of the most recent 11 blocks (MTP-11) is less than UNIX timestamp 1573819200 (Nov 2019 upgrade) Bitcoin Cash full nodes MUST enforce the following rule: + + * `forkid` [1] to be equal to 0. + +When the median time past [1] of the most recent 11 blocks (MTP-11) is greater than or equal to UNIX timestamp 1573819200 (Nov 2019 upgrade) Bitcoin Cash full nodes implementing the May 2019 consensus rules SHOULD enforce the following change: + + * Update `forkid` [1] to be equal to 0xFF0002. ForkIDs beginning with 0xFF will be reserved for future protocol upgrades. + +This particular consensus rule MUST NOT be implemented by Bitcoin Cash wallet software. Wallets that follow the upgrade should not have to change anything. + +## References + +[1] The `forkId` is defined as per the [replay protected sighash](replay-protected-sighash.md) specification. diff --git a/spec/20190515-reenabled-opcodes.md b/spec/20190515-reenabled-opcodes.md new file mode 100644 index 000000000..1f77f0c31 --- /dev/null +++ b/spec/20190515-reenabled-opcodes.md @@ -0,0 +1,212 @@ +--- +layout: specification +title: Specification for Re-enabling old Opcodes, May 2019 +date: 2018-08-03 +version: 1.0 +updated: 2018-08-13 +--- + +# Introduction + +In May 2018 several disabled opcodes were reintroduced to the Bitcoin Cash scripting engine2. The scope of that change was limited in order to focus developer attention rather than attempting to reintroduce all of the disabled opcodes at once. This specification expands upon that change by reintroducing additional opcodes. + +This specifications describes the opcodes that are proposed to be added in the May 2019 protocol upgrade. + +The opcodes to be added are: + +| Word | OpCode | Hex | Input | Output | Description | +| :--- | :----- | :-- | :---- | :----- | :---------- | +| OP_MUL | 149 | 0x95 | n1 | n2 | out | Multiplies two numbers | +| OP_RSHIFT | 153 | 0x99 | b | n | out | Right shift b by n bits | +| OP_LSHIFT | 152 | 0x98 | b | n | out | Left shift b by n bits | +| OP_INVERT | 131 | 0x83 | b | out | Bitwise | NOT | + +## Data types + +Script data values are byte sequences but may be interpreted as numeric values by some opcodes. Specification of the data types used by Script is beyond the scope of this document. + +For accuracy in this specification, byte sequence values are represented as a sequence of byte values surrounded by curly brackets, such as {0x01, 0x02, 0x03}. This sequence is three bytes long, it begins with a byte of value 1 and ends with a byte of value 3. + +Numeric data values are represented in this document as decimal numbers, such as 35315. + +In this specification, a variable representing a byte sequence is named using the symbol b. A variable representing a numeric value is named using the symbol n. + +## Overflow + +Conceptually overflow means that the result of the operation is out-of-bounds. + +For consistency with previous opcodes and to avoid exposing underlying implementation details, all of the opcodes defined in this document give no indication of overflow. + +Note that divide by zero is a separate error and reported as such. + +## Definitions +Operand order: In keeping with convention, where multiple operands are specified the top most stack item is the last operand. For example: +``` +n1 n2 OP_MUL → out +``` +is the same as + +1. Push n1 onto stack +2. Push n2 onto stack +3. Execute OP_MUL + +The result is that n2 and n1 are popped from the stack and replaced by out. + +## Global Conditions + +The following conditions apply to all opcodes. These conditions must be checked by the implementation to ensure that no violations occur: + +1. for all b : elements on the stack, 0 <= len(b) <= MAX_SCRIPT_ELEMENT_SIZE +2. for each opcode, the prerequisite number of operands are present on the stack when the +opcode is executed + +These unit tests should be included for every opcode: + +1. Executing the opcode with an input element of length greater than +MAX_SCRIPT_ELEMENT_SIZE fails. +2. Executing the opcode with an insufficient number of operands on the stack fails. + +## Operand Consumption + +In all cases the opcode and operand stack elements are consumed by the opcode and replaced with the output. + +# Arithmetic Operators + +## OP_MUL + +Opcode (decimal): 149 +Opcode (hex): 0x95 +Description: Multiply two operands. + +``` +n1 n2 OP_MUL → out, +where out is the product (multiplication) of n1 and n2. +``` + +### Examples: +* 4 7 OP_MUL → 28 +* -4 7 OP_MUL → -28 + +Any overflow is ignored. The result of the opcode may be a byte sequence that is too large to be interpreted as a numeric value. + +Impact of successful execution: + +* The number of elements on stack is reduced by one. + +### Unit Tests + +1. b1 b2 OP_MUL -> FAIL - where b1 is not a valid numerical value or b2 is not a valid +numerical value, or both +2. The following test will be repeated with various values for n1 and n2. The values of n1 and n2 must include values which have byte sequence representations of size 1 to 4 bytes inclusive. The tests will be repeated with values n1,n2 and -n1,n2 and n1,-n2 and -n1,-n2. + a. n1 n2 OP_MUL → n1*n2 + b. n1 1 OP_MUL → n1 + c. n1 0 OP_MUL → 0 3. n1 n2 OP_MUL -> b - where (n1 * n2) is too large to be represented in 4 bytes. The result b must be a byte sequence which is a representation of (n1*n2) but larger than 4 bytes. + +# Bitwise Operators + +The result produced by these opcodes is always the same size as the operand. +The execution cost of these opcodes is proportional to the length of the operand. + +## OP_RSHIFT + +Opcode (decimal): 153 +Opcode (hex): 0x99 +Description: Right shift b by n bits. + +``` +b n OP_RSHIFT → out, +where out is the byte sequence created by a right shift of the binary bit pattern b by n bits. +``` + +There is no limit imposed on the value of n except that n must be a valid numerical value and must be non-negative. If n is negative, the script fails. + +If n is greater than the number of bits in the byte sequence, the result is a zero filled byte sequence equal in length to the original byte sequence. This is consistent with the interpretation of b n OP_RSHIFT as equal to b 1 OP_RSHIFT repeated n times. This amounts to a logical, rather than arithmetic shift. + +Impact of successful execution: + +* The number of elements on stack is reduced by one. + +### Unit Tests + +These tests may be repeated with a number of values for b and n. + +1. b 0 OP_RSHIFT → b +2. b n OP_RSHIFT → out with for various n > 0, including when n > len(b) +3. b n OP_RSHIFT → fails with error with n < 0 + +## OP_LSHIFT + +Opcode (decimal): 152 +Opcode (hex): 0x98 +Description: Left shift b by n bits. + +``` +b n OP_LSHIFT → out, +where out is the byte sequence created by a left shift of binary bit pattern b by n bits. +``` + +There is no limit imposed on the value of n except that n must be a valid numerical value and must be non-negative. If n is negative, the script fails. + +If n is greater than the number of bits in the byte sequence, the result is a zero filled byte sequence equal in length to the original byte sequence. This is consistent with the interpretation of b n OP_LSHIFT as equal to b 1 OP_LSHIFT repeated n times. + +Impact of successful execution: + +* The number of elements on stack is reduced by one. + +### Unit Tests + +These tests must be repeated with a number of values for b and n. + +1. b 0 OP_LSHIFT → b +2. b n OP_LSHIFT → out with for various n > 0, including when n > len(b) +3. b n OP_LSHIFT → fails with error with n < 0 + +## OP_INVERT + +Opcode (decimal): 131 +Opcode (hex): 0x83 +Description: Bitwise invert. + +``` +b OP_INVERT → out, +where out is b bitwise inverted. +``` + +Impact of successful execution: + +* The number of elements on stack is unchanged. + +### Unit Tests + +1. {} OP_INVERT → {} +2. b OP_INVERT → bitwise invert(x) for various b and various sizes of b. E.g. {0x80, 0x12, 0x34} → {0x7F, 0xED, 0xCB} + +# References + +[1] [https://en.bitcoin.it/wiki/Script#Opcodes](https://en.bitcoin.it/wiki/Script#Opcodes) + +[2] [may-2018-reenabled-opcodes.md](https://github.com/bitcoincashorg/bitcoincash.org/blob/master/spec/may-2018-reenabled-opcodes.md) + +# Specification Status + +This document is a final draft in Google Doc format. It will be made available for public comment. It will also be transcribed into Markdown format and submitted to the bitcoincashorg GitHub repository. +This document is a specification document. It was produced following a proposal, community discussions in the “[WG] OpCodes” telegram group, and a workshop style meeting. +The proposal document is [here](https://docs.google.com/document/d/1KaX9IUJRBXl_r7ZsjYEt67s07x22jcaTw06zFhCFYdw/edit). +The meeting was held on 19th July 2018, the agenda is [here](https://drive.google.com/file/d/14xYdMV-7yAhWWElJ5GVMpaydQmNI9EpT/view). + +# Document History + +* 2018-08-13 - Daniel Connolly, nChain Ltd - included license +* 2018-08-13 - Daniel Connolly, nChain Ltd - version 1.0 +* 2018-08-06 - Daniel Connolly, nChain Ltd - minor edits, grammar, typos +* 2018-08-03 - Shaun O’Kane, nChain Ltd - initial version + +# License + +Copyright 2018 nChain Ltd + +Permission is hereby granted, free of charge, to any person obtaining a copy of this specification, to deal in the specification without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the specification, and to permit persons to whom the specification is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the specification. + +THE SPECIFICATION IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SPECIFICATION OR THE USE OR OTHER DEALINGS IN THE SPECIFICATION. diff --git a/spec/20190515-schnorr.md b/spec/20190515-schnorr.md new file mode 100644 index 000000000..be85a911f --- /dev/null +++ b/spec/20190515-schnorr.md @@ -0,0 +1,358 @@ +--- +layout: specification +title: 2019-MAY-15 Schnorr Signature specification +date: 2018-10-16 +activation: 1557921600 +version: 0.1 +author: Pieter Wuille +--- + +==Introduction== + +===Abstract=== + +This document proposes a standard for 64-byte Schnorr signatures over the elliptic curve ''secp256k1''. + +===Copyright=== + +This document is licensed under the 2-clause BSD license. + +===Motivation=== + +Bitcoin has traditionally used +[https://en.wikipedia.org/wiki/Elliptic_Curve_Digital_Signature_Algorithm ECDSA] signatures over the secp256k1 curve for authenticating +transactions. These are [http://www.secg.org/sec2-v2.pdf standardized], but have a number of downsides +compared to [https://en.wikipedia.org/wiki/Schnorr_signature Schnorr signatures] over the same curve: + +* '''Security proof''': The security of Schnorr signatures is easily [http://core.ac.uk/download/pdf/20772288.pdf provable] in the random oracle model assuming the elliptic curve discrete logarithm problem (ECDLP) is hard. Such a proof does not exist for ECDSA. +* '''Non-malleability''': ECDSA signatures are inherently malleable; a third party without access to the private key can alter an existing valid signature for a given public key and message into another signature that is valid for the same key and message. This issue is discussed in [https://github.com/bitcoin/bips/blob/master/bip-0062.mediawiki BIP62] and [https://github.com/bitcoin/bips/blob/master/bip-0066.mediawiki BIP66]. On the other hand, Schnorr signatures are provably non-malleable.More precisely they are '' '''strongly''' unforgeable under chosen message attacks '' (SUF-CMA), which informally means that without knowledge of the secret key but given a valid signature of a message, it is not possible to come up with a second valid signature for the same message. A security proof in the random oracle model can be found for example in [https://pdfs.semanticscholar.org/0e43/be818bd4664e667154533fd2badb7be2e3b5.pdf a paper by Kiltz, Masny and Pan], which essentially restates [http://core.ac.uk/download/pdf/20772288.pdf the original security proof of Schnorr signatures by Pointcheval and Stern] more explicitly. These proofs are for the Schnorr signature variant using ''(e,s)'' instead of ''(R,s)'' (see Design below). Since we use a unique encoding of ''R'', there is an efficiently computable bijection that maps ''(R, s)'' to ''(e, s)'', which allows to convert a successful SUF-CMA attacker for the ''(e, s)'' variant to a successful SUF-CMA attacker for the ''(r, s)'' variant (and vice-versa). Furthermore, the aforementioned proofs consider a variant of Schnorr signatures without key prefixing (see Design below), but it can be verified that the proofs are also correct for the variant with key prefixing. As a result, the aforementioned security proofs apply to the variant of Schnorr signatures proposed in this document. +* '''Linearity''': Schnorr signatures have the remarkable property that multiple parties can collaborate to produce a signature that is valid for the sum of their public keys. This is the building block for various higher-level constructions that improve efficiency and privacy, such as multisignatures and others (see Applications below). + +For all these advantages, there are virtually no disadvantages, apart +from not being standardized. This document seeks to change that. As we +propose a new standard, a number of improvements not specific to Schnorr signatures can be +made: + +* '''Signature encoding''': Instead of [https://en.wikipedia.org/wiki/X.690#DER_encoding DER]-encoding for signatures (which are variable size, and up to 72 bytes), we can use a simple fixed 64-byte format. +* '''Batch validation''': The specific formulation of ECDSA signatures that is standardized cannot be validated more efficiently in batch compared to individually, unless additional witness data is added. Changing the signature scheme offers an opportunity to avoid this. + +[[File:bip-schnorr/speedup-batch.png|frame|This graph shows the ratio between the time it takes to verify ''n'' signatures individually and to verify a batch of ''n'' signatures. This ratio goes up logarithmically with the number of signatures, or in other words: the total time to verify ''n'' signatures grows with ''O(n / log n)''.]] + +By reusing the same curve as Bitcoin has used for ECDSA, private and public keys remain identical for Schnorr signatures, and we avoid introducing new assumptions about elliptic curve group security. + +== Description == + +We first build up the algebraic formulation of the signature scheme by +going through the design choices. Afterwards, we specify the exact +encodings and operations. + +=== Design === + +'''Schnorr signature variant''' Elliptic Curve Schnorr signatures for message ''m'' and public key ''P'' generally involve a point ''R'', integers ''e'' and ''s'' picked by the signer, and generator ''G'' which satisfy ''e = H(R || m)'' and ''sG = R + eP''. Two formulations exist, depending on whether the signer reveals ''e'' or ''R'': +# Signatures are ''(e,s)'' that satisfy ''e = H(sG - eP || m)''. This avoids the difficulty of encoding a point ''R'' in the signature. +# Signatures are ''(R,s)'' that satisfy ''sG = R + H(R || m)P''. This supports batch validation, as there are no elliptic curve operations inside the hashes. + +We choose the ''R''-option to support batch validation. + +'''Key prefixing''' When using the validation rule above directly, it is possible for a third party to convert a signature ''(R,s)'' for key ''P'' into a signature ''(R,s + aH(R || m))'' for key ''P + aG'' and the same message, for any integer ''a''. This is not a concern for Bitcoin currently, as all signature hashes indirectly commit to the public keys. However, this may change with proposals such as SIGHASH_NOINPUT ([https://github.com/bitcoin/bips/blob/master/bip-0118.mediawiki BIP 118]), or when the signature scheme is used for other purposes—especially in combination with schemes like [https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki BIP32]'s unhardened derivation. To combat this, we choose ''key prefixed''A limitation of committing to the public key (rather than to a short hash of it, or not at all) is that it removes the ability for public key recovery or verifying signatures against a short public key hash. These constructions are generally incompatible with batch validation. Schnorr signatures; changing the equation to ''sG = R + H(R || P || m)P''. + +'''Encoding the sign of R''' As we chose the ''R''-option above, we're required to encode the point ''R'' into the signature. Several possibilities exist: +# Encoding the full X and Y coordinate of R, resulting in a 96-byte signature. +# Encoding the full X coordinate, but only whether Y is even or odd (like compressed public keys). This would result in 65-byte signatures. +# Encoding only the X coordinate, leaving us with 64-byte signature. + +Using the first option would be slightly more efficient for validation (around 5%), but we prioritize compactness, and therefore choose option 3. + +'''Implicit Y coordinate''' In order to support batch validation, the Y coordinate of ''R'' cannot be ambiguous (every valid X coordinate has two possible Y coordinates). We have a choice between several options for symmetry breaking: +# Implicitly choosing the Y coordinate that is in the lower half. +# Implicitly choosing the Y coordinate that is evenSince ''p'' is odd, negation modulo ''p'' will map even numbers to odd numbers and the other way around. This means that for a valid X coordinate, one of the corresponding Y coordinates will be even, and the other will be odd.. +# Implicitly choosing the Y coordinate that is a quadratic residue (has a square root modulo the field size)A product of two numbers is a quadratic residue when either both or none of the factors are quadratic residues. As ''-1'' is not a quadratic residue, and the two Y coordinates corresponding to a given X coordinate are each other's negation, this means exactly one of the two must be a quadratic residue.. + +The third option is slower at signing time but a bit faster to verify, as the quadratic residue of the Y coordinate can be computed directly for points represented in +[https://en.wikibooks.org/wiki/Cryptography/Prime_Curve/Jacobian_Coordinates Jacobian coordinates] (a common optimization to avoid modular inverses +for elliptic curve operations). The two other options require a possibly +expensive conversion to affine coordinates first. This would even be the case if the sign or oddness were explicitly coded (option 2 in the previous design choice). We therefore choose option 3. + +'''Final scheme''' As a result, our final scheme ends up using signatures ''(r,s)'' where ''r'' is the X coordinate of a point ''R'' on the curve whose Y coordinate is a quadratic residue, and which satisfies ''sG = R + H(r || P || m)P''. + +=== Specification === + +We first describe the verification algorithm, and then the signature algorithm. + +The following convention is used, with constants as defined for secp256k1: +* Lowercase variables represent integers or byte arrays. +** The constant ''p'' refers to the field size, ''0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F''. +** The constant ''n'' refers to the curve order, ''0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141''. +* Uppercase variables refer to points on the curve with equation ''y2 = x3 + 7'' over the integers modulo ''p''. +** ''infinite(P)'' returns whether or not ''P'' is the point at infinity. +** ''x(P)'' and ''y(P)'' refer to the X and Y coordinates of a point ''P'' (assuming it is not infinity). +** The constant ''G'' refers to the generator, for which ''x(G) = 0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798'' and ''y(G) = 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8''. +** ''oncurve(P)'' returns whether a point ''P'' is on the curve and not infinite. +** Addition of points refers to the usual [https://en.wikipedia.org/wiki/Elliptic_curve#The_group_law elliptic curve group operation]. +** [https://en.wikipedia.org/wiki/Elliptic_curve_point_multiplication Multiplication of an integer and a point] refers to the repeated application of the group operation. +* Functions and operations: +** ''||'' refers to byte array concatenation. +** The function ''bytes(x)'', where ''x'' is an integer, returns the 32 byte encoding of ''x'', most significant byte first. +** The function ''bytes(P)'', where ''P'' is a point, returns ''byte(0x02 + (y(P) & 1)) || bytes(x(P))''This matches the ''compressed'' encoding for elliptic curve points used in Bitcoin already, following section 2.3.3 of the [http://www.secg.org/sec1-v2.pdf SEC 1] standard.. +** The function ''int(x)'', where ''x'' is a 32 byte array, returns the 256-bit unsigned integer whose most significant byte encoding is ''x''. +** The function ''x[i:j]'', where ''x'' is a 32 byte array, returns a ''j - i'' byte array with a copy of the ''i''-th byte (inclusive) to the ''j''-th byte (exclusive) of ''x''. +** The function ''hash(x)'', where ''x'' is a byte array, returns the 32 byte SHA256 hash of ''x''. +** The function ''jacobi(x)'', where ''x'' is an integer, returns the [https://en.wikipedia.org/wiki/Jacobi_symbol Jacobi symbol] of ''x / p''. It is equal to ''x(p-1)/2 mod p'' ([https://en.wikipedia.org/wiki/Euler%27s_criterion Euler's criterion])For points ''P'' on the secp256k1 curve it holds that ''jacobi(y(P)) ≠ 0''. + +==== Verification ==== + +Input: +* The public key ''P'': a point +* The message ''m'': a 32 byte array +* A signature ''sig'': a 64 byte array + +The signature is valid if and only if the algorithm below does not fail. +* Fail if ''not oncurve(P)''. +* Let ''r = int(sig[0:32])''; fail if ''r ≥ p''. +* Let ''s = int(sig[32:64])''; fail if ''s ≥ n''. +* Let ''e = int(hash(bytes(r) || bytes(P) || m)) mod n''. +* Let ''R = sG - eP''. +* Fail if ''infinite(R)'' or ''jacobi(y(R)) ≠ 1'' or ''x(R) ≠ r''. + +==== Batch verification ==== + +Input: +* The number of signatures ''u''. +* The public keys ''P1...u'': ''u'' points +* The messages ''m1...u'': ''u'' 32 byte arrays. +* The signatures ''sig1...u'': ''u'' 64 byte arrays. +* Random numbers ''a2...u'' in the range ''1...n-1'': ''u-1'' integers. These can either be generated deterministically using a [https://en.wikipedia.org/wiki/Cryptographically_secure_pseudorandom_number_generator CSPRNG] seeded by a cryptographic hash (e.g., SHA256) of all the other inputs, or be randomly generated independently for each batch of verifications. + +All provided signatures are valid if and only if the algorithm below does not fail. +* For ''i = 1 .. u'': +** Fail if ''not oncurve(Pi)''. +** Let ''r = int(sigi[0:32])''; fail if ''r ≥ p''. +** Let ''si = int(sigi[32:64])''; fail if ''si ≥ n''. +** Let ''ei = int(hash(bytes(r) || bytes(Pi) || mi)) mod n''. +** Let ''c = r3 + 7 mod p''. +** Let ''y = c(p+1)/4 mod p''The Y coordinates are the square roots of ''c'' and they can be computed as ''y = ±c(p+1)/4 mod p'' (see [https://en.wikipedia.org/wiki/Quadratic_residue#Prime_or_prime_power_modulus Quadratic residue]) if they exist, which can be checked by squaring and comparing with ''c''. Due to [https://en.wikipedia.org/wiki/Euler%27s_criterion Euler's criterion] it then holds that ''c(p-1)/2 = 1 mod p''. The same criterion applied to ''y'' results in ''y(p-1)/2 mod p= ±c(p+1)/4(p-1)/2 mod p = ±1 mod p''. Therefore ''y = +c(p+1)/4 mod p'' is a quadratic residue and ''-y mod p'' is not.. +** Fail if ''y2 ≠ c''. +** Let ''Ri = (r, y)''. +* Fail if ''(s1 + a2s2 + ... + ausu)G ≠ R1 + a2R2 + ... + auRu + e1P1 + (a2e2)P2 + ... + (aueu)Pu''. + +==== Signing ==== + +Input: +* The secret key ''d'': an integer in the range ''1..n-1''. +* The message ''m'': an array of 32 bytes + +To sign ''m'' for public key ''dG'': +* Let ''k' = int(hash(bytes(d) || m)) mod n''Note that in general, taking the output of a hash function modulo the curve order will produce an unacceptably biased result. However, for the secp256k1 curve, the order is sufficiently close to ''2256'' that this bias is not observable (''1 - n / 2256'' is around ''1.27 * 2-128'').. +* Fail if ''k' = 0'' +* Let ''R = k'G''. +* Let ''k = k' '' if ''jacobi(y(R)) = 1'', otherwise let ''k = n - k' ''. +* Let ''e = int(hash(bytes(x(R)) || bytes(dG) || m)) mod n''. +* The signature is ''bytes(x(R)) || bytes(k + ed mod n)''. + +Note that this is not a ''unique signature'' scheme: while this algorithm will always produce the same signature for a given message and public key, ''k'' (and hence ''R'') may be generated in other ways (such as by a CSPRNG) producing a different, but still valid, signature. + +=== Optimizations === + +Many techniques are known for optimizing elliptic curve implementations. Several of them apply here, but are out of scope for this document. Two are listed below however, as they are relevant to the design decisions: + +'''Jacobi symbol''' The function ''jacobi(x)'' is defined as above, but can be computed more efficiently using an [https://en.wikipedia.org/wiki/Jacobi_symbol#Calculating_the_Jacobi_symbol extended GCD algorithm]. + +'''Jacobian coordinates''' Elliptic Curve operations can be implemented more efficiently by using [https://en.wikibooks.org/wiki/Cryptography/Prime_Curve/Jacobian_Coordinates Jacobian coordinates]. Elliptic Curve operations implemented this way avoid many intermediate modular inverses (which are computationally expensive), and the scheme proposed in this document is in fact designed to not need any inversions at all for validation. When operating on a point ''P'' with Jacobian coordinates ''(x,y,z)'' which is not the point at infinity and for which ''x(P)'' is defined as ''x / z2'' and ''y(P)'' is defined as ''y / z3'': +* ''oncurve(P)'' can be implemented as ''y2 = x3 + 7z6 mod p''. +* ''jacobi(y(P))'' can be implemented as ''jacobi(yz mod p)''. +* ''x(P) ≠ r'' can be implemented as ''x ≠ z2r mod p''. + +== Applications == + +There are several interesting applications beyond simple signatures. +While recent academic papers claim that they are also possible with ECDSA, consensus support for Schnorr signature verification would significantly simplify the constructions. + +===Multisignatures and Threshold Signatures=== + +By means of an interactive scheme such as [https://eprint.iacr.org/2018/068 MuSig], participants can produce a combined public key which they can jointly sign for. This allows n-of-n multisignatures which, from a verifier's perspective, are no different from ordinary signatures, giving improved privacy and efficiency versus ''CHECKMULTISIG'' or other means. + +Further, by combining Schnorr signatures with [https://link.springer.com/content/pdf/10.1007/3-540-46766-1_9.pdf Pedersen Secret Sharing], it is possible to obtain [http://cacr.uwaterloo.ca/techreports/2001/corr2001-13.ps an interactive threshold signature scheme] that ensures that signatures can only be produced by arbitrary but predetermined sets of signers. For example, k-of-n threshold signatures can be realized this way. Furthermore, it is possible to replace the combination of participant keys in this scheme with MuSig, though the security of that combination still needs analysis. + +===Adaptor Signatures=== + +[https://download.wpsoftware.net/bitcoin/wizardry/mw-slides/2018-05-l2/slides.pdf Adaptor signatures] can be produced by a signer by offsetting his public nonce with a known point ''T = tG'', but not offsetting his secret nonce. +A correct signature (or partial signature, as individual signers' contributions to a multisignature are called) on the same message with same nonce will then be equal to the adaptor signature offset by ''t'', meaning that learning ''t'' is equivalent to learning a correct signature. +This can be used to enable atomic swaps or even [https://eprint.iacr.org/2018/472 general payment channels] in which the atomicity of disjoint transactions is ensured using the signatures themselves, rather than Bitcoin script support. The resulting transactions will appear to validators to be no different from ordinary single-signer transactions, except perhaps for the inclusion of locktime refund logic. + +Adaptor signatures, beyond the efficiency and privacy benefits of encoding script semantics into constant-sized signatures, have additional benefits over traditional hash-based payment channels. Specifically, the secret values ''t'' may be reblinded between hops, allowing long chains of transactions to be made atomic while even the participants cannot identify which transactions are part of the chain. Also, because the secret values are chosen at signing time, rather than key generation time, existing outputs may be repurposed for different applications without recourse to the blockchain, even multiple times. + +===Blind Signatures=== + +Schnorr signatures admit a very [https://www.math.uni-frankfurt.de/~dmst/research/papers/schnorr.blind_sigs_attack.2001.pdf simple '''blind signature''' construction] which is a signature that a signer produces at the behest of another party without learning what he has signed. +These can for example be used in [https://github.com/jonasnick/scriptless-scripts/blob/blind-swaps/md/partially-blind-swap.md Partially Blind Atomic Swaps], a construction to enable transferring of coins, mediated by an untrusted escrow agent, without connecting the transactors in the public blockchain transaction graph. + +While the traditional Schnorr blind signatures are vulnerable to [http://www.enseignement.polytechnique.fr/profs/informatique/Francois.Morain/Master1/Crypto/projects/Wagner02.pdf Wagner's attack], there are [https://www.math.uni-frankfurt.de/~dmst/teaching/SS2012/Vorlesung/EBS5.pdf a number of mitigations] which allow them to be usable in practice without any known attacks. Nevertheless, more analysis is required to be confident about the security of the blind signature scheme. + +== Test vectors == + +All data fields below are given as byte arrays, encoded in hexadecimal. + +The following triplets of (public key, message, signature) should pass verification. Furthermore, compliant signers must produce the specified signature given the (private key, message) pairHowever, non-compliant signers ''can'' produce different signatures that are valid to verifiers.: + +* Test vector 1 +** Private key: 0000000000000000000000000000000000000000000000000000000000000001 +** Public key: 0279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798 +** Message: 0000000000000000000000000000000000000000000000000000000000000000 +** Signature: 787A848E71043D280C50470E8E1532B2DD5D20EE912A45DBDD2BD1DFBF187EF67031A98831859DC34DFFEEDDA86831842CCD0079E1F92AF177F7F22CC1DCED05 + +* Test vector 2 +** Private key: B7E151628AED2A6ABF7158809CF4F3C762E7160F38B4DA56A784D9045190CFEF +** Public key: 02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 +** Message: 243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89 +** Signature: 2A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1D1E51A22CCEC35599B8F266912281F8365FFC2D035A230434A1A64DC59F7013FD + +* Test vector 3 +** Private key: C90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B14E5C7 +** Public key: 03FAC2114C2FBB091527EB7C64ECB11F8021CB45E8E7809D3C0938E4B8C0E5F84B +** Message: 5E2D58D8B3BCDF1ABADEC7829054F90DDA9805AAB56C77333024B9D0A508B75C +** Signature: 00DA9B08172A9B6F0466A2DEFD817F2D7AB437E0D253CB5395A963866B3574BE00880371D01766935B92D2AB4CD5C8A2A5837EC57FED7660773A05F0DE142380 + +The following triple of (public key, message, signature) should pass verification: + +* Test vector 4 +** Public key: 03DEFDEA4CDB677750A420FEE807EACF21EB9898AE79B9768766E4FAA04A2D4A34 +** Message: 4DF3C3F68FCC83B27E9D42C90431A72499F17875C81A599B566C9889B9696703 +** Signature: 00000000000000000000003B78CE563F89A0ED9414F5AA28AD0D96D6795F9C6302A8DC32E64E86A333F20EF56EAC9BA30B7246D6D25E22ADB8C6BE1AEB08D49D + +* Test vector 4B +** Public key: 031B84C5567B126440995D3ED5AABA0565D71E1834604819FF9C17F5E9D5DD078F +** Message: 0000000000000000000000000000000000000000000000000000000000000000 +** Signature: 52818579ACA59767E3291D91B76B637BEF062083284992F2D95F564CA6CB4E3530B1DA849C8E8304ADC0CFE870660334B3CFC18E825EF1DB34CFAE3DFC5D8187 + +The following triples of (public key, message, signature) should not pass verification. + +* Test vector 5 +** Public key: 03EEFDEA4CDB677750A420FEE807EACF21EB9898AE79B9768766E4FAA04A2D4A34 +** Message: 4DF3C3F68FCC83B27E9D42C90431A72499F17875C81A599B566C9889B9696703 +** Signature: 00000000000000000000003B78CE563F89A0ED9414F5AA28AD0D96D6795F9C6302A8DC32E64E86A333F20EF56EAC9BA30B7246D6D25E22ADB8C6BE1AEB08D49D +** Reason: public key not on the curve + +* Test vector 6 +** Public key: 02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 +** Message: 243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89 +** Signature: 2A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1DFA16AEE06609280A19B67A24E1977E4697712B5FD2943914ECD5F730901B4AB7 +** Reason: incorrect R residuosity + +* Test vector 7 +** Public key: 03FAC2114C2FBB091527EB7C64ECB11F8021CB45E8E7809D3C0938E4B8C0E5F84B +** Message: 5E2D58D8B3BCDF1ABADEC7829054F90DDA9805AAB56C77333024B9D0A508B75C +** Signature 00DA9B08172A9B6F0466A2DEFD817F2D7AB437E0D253CB5395A963866B3574BED092F9D860F1776A1F7412AD8A1EB50DACCC222BC8C0E26B2056DF2F273EFDEC +** Reason: negated message hash + +* Test vector 8 +** Public key: 0279BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798 +** Message: 0000000000000000000000000000000000000000000000000000000000000000 +** Signature: 787A848E71043D280C50470E8E1532B2DD5D20EE912A45DBDD2BD1DFBF187EF68FCE5677CE7A623CB20011225797CE7A8DE1DC6CCD4F754A47DA6C600E59543C +** Reason: negated s value + +* Test vector 9 +** Public key: 03DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 +** Message: 243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89 +** Signature: 2A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1D1E51A22CCEC35599B8F266912281F8365FFC2D035A230434A1A64DC59F7013FD +** Reason: negated public key + +* Test vector 10 +** Public key: 02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 +** Message: 243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89 +** Signature: 2A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1D8C3428869A663ED1E954705B020CBB3E7BB6AC31965B9EA4C73E227B17C5AF5A +** Reason: ''sG - eP'' is infinite + +* Test vector 11 +** Public key: 02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 +** Message: 243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89 +** Signature: 4A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1D1E51A22CCEC35599B8F266912281F8365FFC2D035A230434A1A64DC59F7013FD +** Reason: ''sig[0:32]'' is not an X coordinate on the curve + +* Test vector 12 +** Public key: 02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 +** Message: 243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89 +** Signature: FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC2F1E51A22CCEC35599B8F266912281F8365FFC2D035A230434A1A64DC59F7013FD +** Reason: ''sig[0:32]'' is equal to field size + +* Test vector 13 +** Public key: 02DFF1D77F2A671C5F36183726DB2341BE58FEAE1DA2DECED843240F7B502BA659 +** Message: 243F6A8885A308D313198A2E03707344A4093822299F31D0082EFA98EC4E6C89 +** Signature: 2A298DACAE57395A15D0795DDBFD1DCB564DA82B0F269BC70A74F8220429BA1DFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 +** Reason: ''sig[32:64]'' is equal to curve order + +== Appendix A: Reference code == + +A naive but highly inefficient and non-constant time pure Python 3.2 implementation of the signing and verification algorithm can be found below. +The reference code is for demonstration purposes only and not to be used in production environments. + + +import hashlib +import binascii + +p = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F +n = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 +G = (0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798, 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8) + +def point_add(p1, p2): + if (p1 is None): + return p2 + if (p2 is None): + return p1 + if (p1[0] == p2[0] and p1[1] != p2[1]): + return None + if (p1 == p2): + lam = (3 * p1[0] * p1[0] * pow(2 * p1[1], p - 2, p)) % p + else: + lam = ((p2[1] - p1[1]) * pow(p2[0] - p1[0], p - 2, p)) % p + x3 = (lam * lam - p1[0] - p2[0]) % p + return (x3, (lam * (p1[0] - x3) - p1[1]) % p) + +def point_mul(p, n): + r = None + for i in range(256): + if ((n >> i) & 1): + r = point_add(r, p) + p = point_add(p, p) + return r + +def bytes_point(p): + return (b'\x03' if p[1] & 1 else b'\x02') + p[0].to_bytes(32, byteorder="big") + +def sha256(b): + return int.from_bytes(hashlib.sha256(b).digest(), byteorder="big") + +def on_curve(point): + return (pow(point[1], 2, p) - pow(point[0], 3, p)) % p == 7 + +def jacobi(x): + return pow(x, (p - 1) // 2, p) + +def schnorr_sign(msg, seckey): + k = sha256(seckey.to_bytes(32, byteorder="big") + msg) % n + R = point_mul(G, k) + if jacobi(R[1]) != 1: + k = n - k + e = sha256(R[0].to_bytes(32, byteorder="big") + bytes_point(point_mul(G, seckey)) + msg) % n + return R[0].to_bytes(32, byteorder="big") + ((k + e * seckey) % n).to_bytes(32, byteorder="big") + +def schnorr_verify(msg, pubkey, sig): + if (not on_curve(pubkey)): + return False + r = int.from_bytes(sig[0:32], byteorder="big") + s = int.from_bytes(sig[32:64], byteorder="big") + if r >= p or s >= n: + return False + e = sha256(sig[0:32] + bytes_point(pubkey) + msg) % n + R = point_add(point_mul(G, s), point_mul(pubkey, n - e)) + if R is None or jacobi(R[1]) != 1 or R[0] != r: + return False + return True + + +== Footnotes == + + + +== Acknowledgements == + +This document is the result of many discussions around Schnorr based signatures over the years, and had input from Johnson Lau, Greg Maxwell, Jonas Nick, Andrew Poelstra, Tim Ruffing, Rusty Russell, and Anthony Towns.