<p>The way that <code>VerifyingKey</code> works is that it will actually hash the message before it verifies. The default hashing algorithm is <code>sha1</code>, so you will need to specify it to be <code>sha256</code> as that is what Bitcoin uses. Furthermore, you are passing it the fully hashed message. What you need to do is pass it the step before hashing the message. Since Bitcoin uses SHA256 double, you need to give it the result of the first SHA256 hash and let it generate the second SHA256 hash by itself.</p>

<p>So your message should actually be</p>

<pre><code>083867478cb0d1d8bb864175bbc49728cffcc114bc2e762c6df64f2c965a9a66
</code></pre>

<p>and your verify call should look like</p>

<pre><code>vk.verify(bytes.fromhex(sig), bytes.fromhex(message), hashlib.sha256)
</code></pre>

CC BY-SA 3.0
2017-11-12T13:02:06.417Z
This worked. I always thought my error lay somewhere in the bitcoin part, but turns out it was in the ecdsa part. Thank you.
Samarth Hattangady
CC BY-SA 3.0
2017-11-11T18:59:26.603Z
2017-11-11T18:59:26.603Z
Ava Chow
<p>When trying to implement <code>OP_CHECKSIG</code>, I am unable to figure out how to do the actual signature verification in python (python3)</p>

<p><a href="https://bitcoin.stackexchange.com/questions/32305/how-does-the-ecdsa-verification-algorithm-work-during-transaction">I obtained the signature, public key, and hashed message digest of a transaction</a>, and now I want to verify the signature.</p>

<pre><code>message = '692678553d1b85ccf87d4d4443095f276cdf600f2bb7dd44f6effbd7458fd4c2'
pubkey = '042e930f39ba62c6534ee98ed20ca98959d34aa9e057cda01cfd422c6bab3667b76426529382c23f42b9b08d7832d4fee1d6b437a8526e59667ce9c4e9dcebcabb'
signature = '30450221009908144ca6539e09512b9295c8a27050d478fbb96f8addbc3d075544dc41328702201aa528be2b907d316d2da068dd9eb1e23243d97e444d59290d2fddf25269ee0e'
</code></pre>

<p>Since <code>python-ecdsa</code> requires 64 byte input for creating the verifying key, I removed the first byte myself.</p>

<pre><code>pubkey = pubkey[2:]
</code></pre>

<p>I also extracted <code>r</code> and <code>s</code> from the <a href="https://bitcoin.stackexchange.com/questions/12554/why-the-signature-is-always-65-13232-bytes-long">DER encoded signature</a>, and concatenated these to create a 64 byte signature as <code>python-ecdsa</code> requires.</p>

<pre><code>r = '9908144ca6539e09512b9295c8a27050d478fbb96f8addbc3d075544dc413287'
s = '1aa528be2b907d316d2da068dd9eb1e23243d97e444d59290d2fddf25269ee0e'
sig = r + s
</code></pre>

<p>However when I try to verify the message, I get a <code>BadSignatureError</code> signifying that the verification failed.</p>

<pre><code>from ecdsa import VerifyingKey, SECP256k1
vk = VerifyingKey.from_string(bytes.fromhex(pubkey), curve=SECP256k1)
vk.verify(bytes.fromhex(sig), bytes.fromhex(message))
</code></pre>

<p>I am looking for a way to verify signatures that I have extracted from bitcoin transactions. </p>

<p>Thank you.</p>

<script><ecdsa><checksig>
Signature verification in python
Samarth Hattangady
# Signature verification in python

(Asked by: username_0 on 2017-11-11)

When trying to implement OP_CHECKSIG, I am unable to figure out how to do the actual signature verification in python (python3)
I obtained the signature, public key, and hashed message digest of a transaction, and now I want to verify the signature.
message = '692678553d1b85ccf87d4d4443095f276cdf600f2bb7dd44f6effbd7458fd4c2'
pubkey = '042e930f39ba62c6534ee98ed20ca98959d34aa9e057cda01cfd422c6bab3667b76426529382c23f42b9b08d7832d4fee1d6b437a8526e59667ce9c4e9dcebcabb'
signature = '30450221009908144ca6539e09512b9295c8a27050d478fbb96f8addbc3d075544dc41328702201aa528be2b907d316d2da068dd9eb1e23243d97e444d59290d2fddf25269ee0e'

Since python-ecdsa requires 64 byte input for creating the verifying key, I removed the first byte myself.
pubkey = pubkey[2:]

I also extracted r and s from the DER encoded signature, and concatenated these to create a 64 byte signature as python-ecdsa requires.
r = '9908144ca6539e09512b9295c8a27050d478fbb96f8addbc3d075544dc413287'
s = '1aa528be2b907d316d2da068dd9eb1e23243d97e444d59290d2fddf25269ee0e'
sig = r + s

However when I try to verify the message, I get a BadSignatureError signifying that the verification failed.
from ecdsa import VerifyingKey, SECP256k1
vk = VerifyingKey.from_string(bytes.fromhex(pubkey), curve=SECP256k1)
vk.verify(bytes.fromhex(sig), bytes.fromhex(message))

I am looking for a way to verify signatures that I have extracted from bitcoin transactions. 
Thank you.

**Tags:** script, ecdsa, checksig


---

## 1 answers

### Answer by username_1 on 2017-11-11. Score: 2 | Accepted answer

The way that VerifyingKey works is that it will actually hash the message before it verifies. The default hashing algorithm is sha1, so you will need to specify it to be sha256 as that is what Bitcoin uses. Furthermore, you are passing it the fully hashed message. What you need to do is pass it the step before hashing the message. Since Bitcoin uses SHA256 double, you need to give it the result of the first SHA256 hash and let it generate the second SHA256 hash by itself.
So your message should actually be
083867478cb0d1d8bb864175bbc49728cffcc114bc2e762c6df64f2c965a9a66

and your verify call should look like
vk.verify(bytes.fromhex(sig), bytes.fromhex(message), hashlib.sha256)

> **Comments:**
> **username_0**: This worked. I always thought my error lay somewhere in the bitcoin part, but turns out it was in the ecdsa part. Thank you.  

---

