Wallets&Exchanges

The Unstoppable JPG In Private Keys

Abstract: We look again at the OP_Return policy limit issue and the related topic of storing images in the blockchain. The argument is not going away, with up to 17% of nodes running Bitcoin Knots, a client which supports the idea of filtering the images. We discuss “information theory” and explain how images can be included in fake Bitcoin addresses and why it’s unfeasible to prevent this. We go on to explain that private keys are also just random data, which can also be used to store images. We create an example transaction, with an even more “unstoppable image” inside the private keys, deliberately vulnerable private keys, such that they can be calculated from the data available on the blockchain.

Overview

In June 2025, Bitcoin Core developers merged a pull request which essentially removed the OP_Return  size limit policy in the software. We have already written about this topic, expressing our view that in the long term, the fee market is the tool we should use to fight spam, not policy limits and filters. Anyway, the decision to remove the OP_Return size limit proved somewhat controversial among some groups of Bitcoiners, with some claiming this encourages spam transactions, such as JPG images. Another complaint was that the Core developers have not taken sufficient action to fight spam and have done nothing to stop JPGs on the Blockchain. When Udi Wertheimer taunted the anti-spam people by putting images on the Blockchain in the form of “Taproot Wizards”, the anti-spam or pro-filter group wanted or hoped that the Bitcoin Core developers would do something to stop it, but they didn’t. As a result of this, people have been increasingly running Bitcoin Knots, a client which is said to do more to fight spam with filters. According to data from Coin.Dance, as at 25 August 2025, around 17% of reachable nodes are running Bitcoin Knots.

Information Theory

While some criticised Bitcoin Core developers for not fighting against the images, others responded by saying that Bitcoin Core developers should not play “whack-a-mole”, because this is a waste of time. This essentially means that Bitcoin Core could do something to fight the images, but that this would only be temporarily effective as the spammers would find a way around the defense. It is an asymmetric battle, in that for each move the spammers make, they would have to spend far less effort than those trying to stop the spam. And it is a war that would reach an eventual endgame, in which the spammers would win. Why should Bitcoin Core developers have an obligation to invest time and effort in a battle that they would eventually lose? It is therefore understandable that many developers do not want to fight in this battle. From the pro-filter perspective, they probably acknowledge this, but contend the filters are there to increase the cost of spam, even if they can be circumvented if sufficient put into it.

When it comes to stopping spam with filters, one may argue that this is losing battle due to “information theory”. This is a theory formalised by Claude Shannon in the 1940s and involves the study of communication of information. Claude Shannon introduces some of the core concepts in computer science and the transmission of information. Therefore, perhaps it’s slightly unreasonable to say the pro-filter is definitely wrong because of “information theory”. It is more that information theory can be thought of as a field of science, in which one can argue that images can always be stored in seemingly random data, data that is needed for Bitcoin transactions. It is probably not fair to say that “information theory” proves anything here.

At the very basic level, financial Bitcoin transactions have some necessary components which ensure the transactions can work. Namely, for each transaction, one needs a public key and signature. It is not clear how Bitcoin can work without these two core components. As a very minimum, these components must go onchain. When receiving Bitcoin, one supplies a Bitcoin address. Since these addresses are generated by a hash function, the  address is therefore indistinguishable from random data. Image related data can therefore be used as a “fake address” and coins can be sent to these addresses. These fake addresses will then go onto the public blockchain, in the form of an output hash. These coins can never be recovered, since there is no known public key associated with the addresses to which they were sent. Understanding this can be thought of as “information theory”, in that a hash function is a random process, which results in entropy, that can be used to transmit information. This cannot really be stopped, no matter what filters are used. These fake addresses have been used in Bitcoin’s past and some examples are shown below.

Fake Addresses

In December 2013 someone used the “fake address” process to encode an image of former South African president Nelson Mandela into the Bitcoin Blockchain. This image is shown below.

Sources: https://mempool.space/tx/78f0e6de0ce007f4dd4a09085e649d7e354f70bc7da06d697b167f353f115b8e, https://mempool.space/tx/8881a937a437ff6ce83be3a89d77ea88ee12315f37f7ef0dd3742c30eef92dba, List of associated fake addresses: https://bitfossil.com/78f0e6de0ce007f4dd4a09085e649d7e354f70bc7da06d697b167f353f115b8e/ADD

Even earlier than this, in May 2011, fake unspendable addresses were used to store the Bitcoin logo in the Bitcoin blockchain.

Source: https://mempool.space/tx/ceb1a7fb57ef8b75ac59b56dd859d5cb3ab5c31168aa55eb3819cd5ddbd3d806

It should be noted that spam like this, with fake addresses, does make it harder to run a node, as it may bloats the UTXO set. This is part of the justification for allowing OP_Returns.

Banning Fake Addresses

If one wants to stop the fake addresses, this might actually be possible. But that would require a fundamental re-architecturing of Bitcoin and a change to the Bitcoin protocol. The way to block such addresses could be to require that transaction outputs contain a digital signature, thereby proving there is a public private key pair and that the address is “real”. Therefore, both transaction inputs and outputs would require a signature.

While this could work in theory, this is a monumental task and has the following downsides:

  • All existing wallets would be incompatible with the new transaction format, with old style transactions being banned. Banning old transactions has not happened in the past, monetary sovereignty would be threatened and people could lose funds.
  • The transaction process would need to change, as the receiver would not only need to supply an address to the sender, but also a digital signature.
  • There would be more signatures onchain, with transaction sizes getting much larger, damaging the scaling properties of Bitcoin.
  • Address re-use could be encouraged, damaging privacy.
  • This would be a protocol change and require widespread consensus. This would probably need to be a hardfork.
  • Many of the capabilities in Bitcoin, such as P2SH or Taproot, may need to be removed. Or at least, we cannot have the benefits of P2SH.
  • Bitcoin would be more vulnerable to Quantum attacks, with more public keys visible.

As one can see, the above would be totally unfeasible and an unmitigated disaster. However, even this extreme change might not stop the JPGs. After carefully closing all the other options, one could still store images in private keys, afterall, private keys are just random data and they are a necessary component of Bitcoin. Therefore, this would still be a losing battle for the Bitcoin developers. They would have engaged in a mammoth task to completely re-architecture Bitcoin and all wallets, only for the spammers to move on to something else, relatively easily.

JPGs As Private Keys

A Bitcoin private key is just a random 256 bit number. Such a number is mathematically equivalent to a 16 by 16 pixel image, where each pixel is either black or white. All private keys can be represented by these tiny images. We created a Bitcoin private key, by creating such an image below, an image of a person. We saved the image in JPG format, as shown below.

While drawing a picture to generate a private key might not always be the most secure way to use Bitcoin, from the pro-filter perspective, this could be considered as illegitimate. It could be considered as spam, because from certain perspectives, we are putting JPGs on the blockchain or using JPGs in the blockchain. However, of course restricting the use of Bitcoin like this, using filters, is mathematically impossible, since these images are mathematically equivalent to any other way of expressing private keys.

To generate a private key from the image, each pixel can be assigned a one or zero, based on whether it’s black or white, as the 256 bit number below indicates.

0000000000000000
0000011111100000
0000100000010000
0000100000010000
0000011111100000
0000000110000000
0000011111100000
0001100110011000
0000000110000000
0000000110000000
0000000110000000
0000001001000000
0000001001000000
0000010000100000
0000010000100000
0000000000000000

One of the many Bitcoin addresses which results from the above private key is as follows:

1JfvNAje3G3Gvt41hL4P7Eh96NLj79o5v7

This is just using one private key to generate a small image. However, of course this could scale up. One could generate a large 1MB image and then break this down into thousands of private keys. These could be used in transactions and spam the blockchain. This is likely to be considered as spam, while just generating one image as a private key and using it to process “financial transactions”, may not be considered as spam by anyone, even the most extreme pro-filter people, even though it involves an image.

Weak Signatures

The above method of “putting images” onchain isn’t particularly effective. For starters, when making Bitcoin transactions, private keys are supposed to be secret, when the spammers want to have the images publicly viewable. However, one can generate an insecure signature, such that the private key can be calculated from the onchain data. If the image data can be determined from the data available on the blockchain, that is basically putting images on the blockchain.

In order to sign a message with ECDSA, one needs to perform various calculations as part of the process of generating a signature. One of the calculations requires a randomly generated value, K. There have been various security issues in Bitcoin’s history where bad randomness was used to generate K, for example an issue with the Blockchain.info wallet in August 2013. As a result of a security failing, the same K value was used to sign multiple transactions. This vulnerability resulted in the theft of user funds. Another example of using the same K values for different messages was Sony’s Playstation 3 console, which used the same K value for each game. This vulnerability was revealed at the 2010 Chaos Computer Congress in Germany. Legendary hacker George Hotz then published the private Playstation 3 keys a few days later. It is therefore critical that the K value is both secret and that a different K value is used for each message, otherwise anyone can calculate the private key.

We developed a basic scheme using these weak K values, to put a JPG image in our private keys, such that these private keys can be calculated by anyone with access to the blockchain. We then put a JPG image on the blockchain using this system, by broadcasting our transaction. We believe this is the first significant/meaningful image stored in vulnerable private keys in Bitcoin’s history. We created a 15 of 15 P2SH multisignature input, in a one input one output transaction. The total transaction size is 1,690 bytes. As the input is a 15 of 15 multisignature input, there are 15 signatures and 15 public keys on the blockchain. 14 of the 15 associated private keys are a JPG image, which is the image displayed at the top of this article. In homage to the 2011 image, it is the Bitcoin logo, in black and white.

Source: https://mempool.space/tx/700f1b8216d4b28cdbf7fe8abb4061763d51019b2a1007a3d811f50e320db98a

In our structure, for creating weak signatures, we did not use the same K value for multiple messages. We choose a system where:

  • The first K value is a SHA256 hash of the first public key
  • The second K value is a SHA256 hash of the first K value
  • The third K value is SHA256 hash of the second K value
  • And so on…
  • The 15th K value is a genuine securely generated random number

This way the signatures look reasonably secure to a casual observer of the blockchain, but once one knows how we selected the K values and what the K values are, one can calculate the 14 private keys. One can keep altering the scheme, such that if the pro-filter side tries to filter for exposed K values, we can develop a new more secure scheme and always stay one step ahead.

Since all 15 private keys are required to spend the funds at this address and only 14 of the private keys are vulnerable, the funds are still secure and an attacker cannot sweep the funds away before the transaction gets confirmed. Therefore, we achieve our objective of having secure funds and also having the private keys (which are also images) enter the public domain.

The formula, from Wikipedia, to calculate the private key is as follows:

It should be noted that the S and R values are available in the signature, while Z is the message hash. Therefore the private keys can easily be calculated if one knows the K values. Why used a Python script to do the maths for us.

The private keys for our transaction are in the table below:

1b7010000ffd8ffe000104a46494600010101004800480000ffdb004300432e32
23a322a433a363a4b47434f64a66c645c5c64cc929a79a6f1d4fefaedd4e9e5ff
3 ffffffffffffffe5e9ffffffffffffffffffffffffffffffffffffffffffc000
4 0b08002b002b01011100ffc40019000002030100000000000000000000000004
50500020301ffc400251000020202010305010101000000000000010200030411
6 122122611331415171a13281ffda0008010100003f0036cb16a42ee740459767
75961210f05f1ef072ccdd4927ccbd7916d67b5cfe1ea231c5cb5bfb5bb5febee
8131567dc6cb8a03da9d3fec1d38f31cf6577d75192e3d4943147e22d0002df13
90cda0af17441e985036208ac558329d11ec639a6d16d4afd06c44cc49624fb93
10222f37551f27519e5ad6ca9535a2bf91d272c031b04a6cbec6b7fb164d52c655
110013a9cc9acd77baf9d8fc9b615952baab5659cb746fa84e45156439736f1e3d
12a7e84adf6555627a48e1ceb43aee2e8cb1f114d085fdc8dcbe6637aebb5ff63d
13bcc59df53fcab2ff00258dced5942760b723fb338561e21b583b8d20fec6924c
14eda6bb477a03e62ab5155f4074dc370e8a8af22809f30c927fffd90000000000
15 Not disclosed

Once you have all the private keys, all one needs to do is concatenate them together and remove a few bytes at either end, which results in the following string.

ffd8ffe000104a46494600010101004800480000ffdb004300432e323a322a433a363a4b47434f64a66c645c5c64cc929a79a6f1d4fefaedd4e9e5ffffffffffffffffe5e9ffffffffffffffffffffffffffffffffffffffffffc0000b08002b002b01011100ffc400190000020301000000000000000000000000040500020301ffc400251000020202010305010101000000000000010200030411122122611331415171a13281ffda0008010100003f0036cb16a42ee7404597675961210f05f1ef072ccdd4927ccbd7916d67b5cfe1ea231c5cb5bfb5bb5febee131567dc6cb8a03da9d3fec1d38f31cf6577d75192e3d4943147e22d0002df130cda0af17441e985036208ac558329d11ec639a6d16d4afd06c44cc49624fb93222f37551f27519e5ad6ca9535a2bf91d272c031b04a6cbec6b7fb164d52c6550013a9cc9acd77baf9d8fc9b615952baab5659cb746fa84e45156439736f1e3da7e84adf6555627a48e1ceb43aee2e8cb1f114d085fdc8dcbe6637aebb5ff63dbcc59df53fcab2ff00258dced5942760b723fb338561e21b583b8d20fec6924ceda6bb477a03e62ab5155f4074dc370e8a8af22809f30c927fffd9

This 439 bytes of hexadecimal data can then be converted into a JPG. This results in the following unstoppable image:

 

The post The Unstoppable JPG In Private Keys appeared first on BitMEX Blog.

​BitMEX Blog 

Weiterlesen 

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert