<h2>Recoverable -> DER</h2>

<p>Use <a href="https://github.com/ofek/coincurve/blob/529b798d03bc19cd50d25d9ed1856a2be147e1eb/coincurve/ecdsa.py#L110" rel="nofollow noreferrer"><code>recoverable_convert</code></a>. (which calls <code>secp256k1_ecdsa_sign_recoverable</code>)</p>

<h2>DER -> Recoverable</h2>

<p>Use <a href="https://github.com/ofek/coincurve/blob/529b798d03bc19cd50d25d9ed1856a2be147e1eb/coincurve/keys.py#L45" rel="nofollow noreferrer"><code>sign_recoverable</code></a>. (which calls <code>secp256k1_ecdsa_recoverable_signature_convert</code>)</p>

<p>^^I couldn't find an easier way.</p>

CC BY-SA 4.0
2019-04-14T12:50:47.680Z
I am not sure if I understand but

`pk = coincurve.PrivateKey()
message = b"this is a test!"
s = pk.sign_recoverable(message)
print(recoverable_convert(s))`

gives me the error: TypeError: initializer for ctype 'secp256k1_ecdsa_recoverable_signature *' must be a cdata pointer, not bytes
makkiato
CC BY-SA 4.0
2021-12-30T02:00:24.973Z
Obviously this is an old question, but you need to deserialise the recoverable signature first: `recoverable_convert(deserialize_recoverable(s))`
meshcollider
CC BY-SA 4.0
2019-04-14T11:33:53.943Z
2019-04-14T11:33:53.943Z
MCCCS
<p>I am a noob with cryptography, just trying to learn using python and the library Coincurve ( <a href="https://github.com/ofek/coincurve" rel="nofollow noreferrer">https://github.com/ofek/coincurve</a> ) which is a mature Python binding for libsecp256k1.</p>

<p>The following code creates a private key and produces a signature of the string "Hello world!". </p>

<pre><code>pk = coincurve.PrivateKey()
message = b"this is a test!"
s = pk.sign_recoverable(message)
</code></pre>

<p>The signature <em>s</em> is a sequence 65 bytes.</p>

<p>The signature is recoverable: i can extract the public key of <em>pk</em> from <em>s</em>.</p>

<pre><code>pub = pk.public_key
pub2 = coincurve.PublicKey.from_signature_and_message(s,message)
assert(pub == pub2)
</code></pre>

<p>So far all good! However I can't understand how to use the verify method. The following code</p>

<pre><code>valid = coincurve.verify_signature(s,message,pub)
</code></pre>

<p>gives the following error:</p>

<pre><code>ValueError: The DER-encoded signature could not be parsed.
</code></pre>

<p>So the problem is that the method <em>verify_signature</em> expects a signature in DER format. This is normally produced using the <em>sign</em> method, as opposed to the <em>sign_recoverable</em> method:</p>

<pre><code>t = pk.sign(message)
valid = coincurve.verify_signature(t,message,pub.format())
</code></pre>

<p>which works fine.</p>

<p>So my question is:</p>

<p><strong>QUESTION:</strong> How do I move back and forth from the "DER" format to the "recoverable" format in the Python library coincurve?</p>

<p>THANKS!</p>

CC BY-SA 4.0
2019-04-15T00:22:08.703Z
I don't know the coincurve package, but want to point out that you can't trivially move from the DER format to the compact recoverable format, as they don't contain the same information. There can be up to 4 (but typically only 2) valid public keys for a given message/signature combination, so the recoverable format contains a flag byte that indicates which of those public keys is to be recovered. This flag byte can't be computed from just the signature and message.
Pieter Wuille
<python><secp256k1>
Question about Python library coincurve/libsecp256k
makkiato
# Question about Python library coincurve/libsecp256k

(Asked by: username_0 on 2019-04-14)

I am a noob with cryptography, just trying to learn using python and the library Coincurve ( https://github.com/ofek/coincurve ) which is a mature Python binding for libsecp256k1.
The following code creates a private key and produces a signature of the string "Hello world!". 
pk = coincurve.PrivateKey()
message = b"this is a test!"
s = pk.sign_recoverable(message)

The signature s is a sequence 65 bytes.
The signature is recoverable: i can extract the public key of pk from s.
pub = pk.public_key
pub2 = coincurve.PublicKey.from_signature_and_message(s,message)
assert(pub == pub2)

So far all good! However I can't understand how to use the verify method. The following code
valid = coincurve.verify_signature(s,message,pub)

gives the following error:
ValueError: The DER-encoded signature could not be parsed.

So the problem is that the method verify_signature expects a signature in DER format. This is normally produced using the sign method, as opposed to the sign_recoverable method:
t = pk.sign(message)
valid = coincurve.verify_signature(t,message,pub.format())

which works fine.
So my question is:
QUESTION: How do I move back and forth from the "DER" format to the "recoverable" format in the Python library coincurve?
THANKS!

**Tags:** python, secp256k1

> **Comments:**
> **username_1**: I don't know the coincurve package, but want to point out that you can't trivially move from the DER format to the compact recoverable format, as they don't contain the same information. There can be up to 4 (but typically only 2) valid public keys for a given message/signature combination, so the recoverable format contains a flag byte that indicates which of those public keys is to be recovered. This flag byte can't be computed from just the signature and message.  

---

## 1 answers

### Answer by username_2 on 2019-04-14. Score: 2

## Recoverable -> DER

Use [`recoverable_convert`](https://github.com/ofek/coincurve/blob/529b798d03bc19cd50d25d9ed1856a2be147e1eb/coincurve/ecdsa.py#L110). (which calls `secp256k1_ecdsa_sign_recoverable`)

## DER -> Recoverable

Use [`sign_recoverable`](https://github.com/ofek/coincurve/blob/529b798d03bc19cd50d25d9ed1856a2be147e1eb/coincurve/keys.py#L45). (which calls `secp256k1_ecdsa_recoverable_signature_convert`)

^^I couldn't find an easier way.

> **Comments:**
> **username_0**: I am not sure if I understand but  `pk = coincurve.PrivateKey() message = b"this is a test!" s = pk.sign_recoverable(message) print(recoverable_convert(s))`  gives me the error: TypeError: initializer for ctype 'secp256k1_ecdsa_recoverable_signature *' must be a cdata pointer, not bytes  
> **username_3**: Obviously this is an old question, but you need to deserialise the recoverable signature first: `recoverable_convert(deserialize_recoverable(s))`  

---

