Betrachten von RIPEMD-160-Bitcoin-Adressen zum Spaß und ohne Gewinn

Manchmal stöbere ich zum Spaß in diesem wunderbaren, unordentlichen Datenpool, der Bitcoin-Blockchain. Es steckt voller interessanter Transaktionen, Daten und seltsamer, eigenartiger Ereignisse. Heute veröffentliche ich diesen Artikel, in dem seltsame, sich wiederholende Bitcoin-Adressen und ihre Bedeutung behandelt werden.

Eine große Anzahl von Bitcoin-Adressen wird aus 160-Bit-Zeichenfolgen abgeleitet, die sehr seltsam und ausgesprochen zufällig aussehen. Ich bin zunächst zu dem Schluss gekommen, dass viele wahrscheinlich auf Codierungsfehler zurückzuführen sind. Die Adressen mit dem höchsten Wert haben jedoch Ausgabetransaktionen, was darauf hindeutet, dass es sich um Eitelkeitsadressen handelt.

Ich habe festgestellt, dass t ungefähr 89,2 BTC aufgrund von Codierungsfehlern verloren gegangen sind, was beim heutigen Wechselkurs ungefähr einer halben Million Dollar entspricht.

Die Frage bleibt weiterhin: Warum sollte jemand Bitcoin-Adressen erstellen wollen, die mit vielen Einsen beginnen?

Das Computercodebit

Letzte Nacht habe ich mich gefragt: “Wie viele Bitcoin-Adressen haben einen Kontostand?”, also habe ich nach Github gesucht und natürlich fast sofort ein ordentliches Python-Skript gefunden, das die Bitcoin-Chainstate-Datenbank durchsucht und eine generiert Datei mit genau diesen Daten. Es ist unter https://github.com/graymauser/btcposbal2csv verfügbar.

Extrahieren der Transaktionen

Zunächst benötigen Sie eine aktuelle Kopie der Bitcoin-Chainstate-Datenbank. Diese befindet sich im Chainstate-Ordner Ihres Bitcoin-Kerndatenverzeichnisses.

Ich habe ungefähr 20 Minuten gebraucht, um alle Installationsprobleme für die Abhängigkeiten zu lösen, die in graymausers Skript benötigt werden. Daher habe ich mir die Zeit genommen, https://github.com/kf106/btcposbal2csv zu erstellen, das alles mit einem einzigen Problem löst Installationsskript:

Es stellt sich heraus, dass die am 9. Mai generierte Datei 24.157.834 Zeilen lang ist und etwa 1,2 GB Speicherplatz beansprucht. Jede Zeile zeigt eine Bitcoin-Adresse, den Kontostand in Satoshis und den letzten Block, in dem für diese Adresse eine Aktivität stattgefunden hat. Sehr ordentlich.

Die Dateigröße bedeutet, dass Sie eine Tabelle nicht wirklich verwenden können, um den Dateninhalt zu analysieren. Es ist Zeit, sed-, awk- und andere Linux-Befehlszeilenskripte auszubrechen, die diese Art von Datenmenge verarbeiten können…

Erster Schritt: Addieren wir die Gesamtzahl der vom Skript aufgezeichneten Satoshis:

Wenn ich das mache, bekomme ich 1.571.401.006.662.989 Satoshis, das sind 15,7 Millionen Bitcoins. Hmm, das Skript hat gewarnt, dass es nicht alle Transaktionen verarbeiten kann. Während ich dies schreibe, wurden ungefähr 17,7 Millionen ausgegeben, sodass 2 Millionen fehlen. Egal – es ist nah genug.

Einführung in RIPEMD-160

Es gibt auch ein Skript, das die RIPEMD-160-Adresse zu der durch Kommas getrennten Datei hinzufügt. Wenn Sie zu https://gobittest.appspot.com/Address gehen, wird eine nützliche Seite angezeigt, auf der alle Schritte zum Generieren einer Bitcoin-Adresse aus einem privaten ECDSA-Schlüssel aufgeführt sind (Hinweis: Geben Sie aus Sicherheitsgründen keinen eigenen privaten Schlüssel ein Geben Sie diese oder eine andere Webseite ein. Die RIPEMD-160-Adresse befindet sich auf halber Strecke und wird verwendet, um den öffentlichen ECDSA-Schlüssel zu verschleiern, bis Sie Ihre Bitcoin-Adresse verwenden, um das Risiko einer Adresskompromittierung zu verringern. Es wird normalerweise in base58 mit einer Prüfsumme codiert, um Tippfehler zu vermeiden und das System besser lesbar zu machen.

Wenn Sie das RIPEMD-160-Skript bei der ersten Ausgabe ausführen, erhalten Sie eine 2,2-GB-Datei, wobei jede Zeile die Bitcoin-Adresse, den Kontostand, den letzten Block, in dem sie aktiv war, und die RIPEMD-160-Adresse enthält . Ich habe diese Datei ripe.csv genannt. Wenn Sie die Anzahl der Zeilen selbst überprüfen möchten, führen Sie einfach Folgendes aus:

Als nächstes habe ich beschlossen, die Bitcoin-Adressen, Salden und Blockgrößen zu entfernen, um nur die RIPEMD-160-Adressen zu betrachten. Ich habe auch beschlossen, sie zu sortieren. Ich bin mir nicht sicher, warum ich das getan habe, aber die folgenden Befehle tun genau das:

Und jetzt das sehr interessante Stück. Mit dem Befehl head oder tail können Sie die ersten neun Zeilen oder die letzten neun Zeilen einer Datei anzeigen. Schauen Sie sich also diese Ausgabe von head an:

Und hier ist die Ausgabe von tail:

Diese sehen nicht wie zufällige Adressen aus!

Faul sein ist viel weniger Arbeit

Nun könnte ich viele Berechnungen durchführen, um die Wahrscheinlichkeit zu bestimmen, dass viele wiederholte Ziffern in einer RIPEMD-160-Adresse erscheinen, aber das klingt nach viel Arbeit. Offensichtlich sind einige wiederholte Ziffern zu erwarten. Aber an welchem ​​Punkt können wir schließen, dass eine Adresse nicht das Produkt eines pseudozufälligen Zufalls ist, sondern auf einen Programmiererfehler zurückzuführen ist? (Und was ist in der Endausgabe mit dieser “db004301” -String, die immer wieder auftaucht?)

Ein kurzes Tutorial: RIPEMD-160 verwendet eine beliebige Zeichenfolge als Eingabe und gibt eine 160-Bit-Zahl zurück, die hexadezimal 40 Oktette beträgt, d. h. vierzig Zeichen, die aus 0–9 oder A-F bestehen. Das sind ungefähr 1,5 * 10⁴⁸ mögliche Ausgaben.

Mein erster Gedanke war also, eine Datei mit 24.157.834 Zeilen und wirklich zufälligen RIPEMD-160-Ausgaben zu erstellen. Zeit, ein Bash-Skript zusammenzuschustern! Ein erster Versuch, Zufallszahlen zu generieren und diese durch die Hash-Funktion zu leiten, schlug aufgrund von Speicherproblemen fehl (trotz 16 GB RAM in meinem Computer). Wie wäre es stattdessen mit der Verwendung der tatsächlichen Adressliste als Eingabe, um eine zufällige RIPEMD-160-Liste zu generieren:

Dazu habe ich jede der RIPEMD-160-Adressen erneut gehasht und in eine neue Datei eingefügt. Die Hash-Funktion RIPEMD-160 soll eine kryptografische Hash-Funktion sein, daher sollte ihre Ausgabe pseudozufällig sein.

Okay, das dauert ein bisschen. Tatsächlich 12 Stunden – manchmal dauert es lange, faul zu sein. Es ist also gut, dass die Lieferpizza angekommen ist und es Zeit ist, die Kinder zu füttern und sie dann ins Bett zu bringen, fernzusehen und dann selbst ins Bett zu gehen.

In einem gegebenen RIPEMD-160-Hash, der hexadezimal dargestellt wird, beträgt die Wahrscheinlichkeit, dass einer bestimmten Ziffer neun weitere folgen, 1 / (16⁹), wenn eine Ziffer (z. B. ‘F’) gegeben ist von der nächsten Ziffer, die gleich ist, ist 1/16 und die darauf folgende 1/16 und so weiter neunmal. Das ist 1 / 68,719,476,736.

In einer 40-stelligen Zeichenfolge gibt es 31 Möglichkeiten, eine Ziffer noch neun Mal abzugleichen, und es gibt 24.157.834 Adressen. Eine grobe Schätzung der Wahrscheinlichkeit einer Adresse mit zehn wiederholten Ziffern lautet also (31 * 24.157.834) ) / 68,719,476,736, was ungefähr 0,0105 entspricht. Oder einfach ausgedrückt, es besteht eine Wahrscheinlichkeit von 1%, dass dies auf natürliche Weise geschieht.

Im Allgemeinen beträgt die Wahrscheinlichkeit, dass sich N Ziffern irgendwo wiederholen,

((41-N) * 24157834) / (16 ^ N)

Es stellt sich also heraus, dass 9 sich wiederholende Ziffern mit 18% sehr wahrscheinlich in unserer Datei sind. (Bei diesen Berechnungen handelt es sich um Schätzungen. Um dies richtig zu tun, muss ich die Wahrscheinlichkeit eines Laufs berechnen, wie auf dieser Wolfram-Seite gezeigt. Dies ist ein Schmerz im Nacken.)

Der folgende Befehl zählt die Anzahl der Zeilen in einer Datei, in der sich zehn Zeichen wiederholen:

ripesort.csv enthält also 5476 Übereinstimmungen und pseudorandsort.csv enthält erwartungsgemäß 0. Tatsächlich gibt es in pseudorandsort.csv auch keine Wiederholungen mit neun Zeichen und nur drei Wiederholungen mit acht Zeichen. In der Liste der echten Bitcoin-Adressen ist definitiv etwas los. Hier ist ein Beispiel für einige der Übereinstimmungen:

Das sieht doch verdächtig aus, oder?

Addiere die Satoshis

Es ist Zeit, zu ripe.csv zurückzukehren, der Originaldatei mit allen Informationen, und alle in Adressen mit zehn oder mehr wiederholten Ziffern gespeicherten Satoshis zu addieren. Diese beiden Befehle sollten dies tun (der erste extrahiert alle Zeilen mit seltsamen RIPEMD-160-Adressen und der zweite ist wieder unser alter Befehl zum Hinzufügen von Satoshi):

Zuerst teste ich es an einem kleinen Beispiel, um zu überprüfen, ob es funktioniert (tun Sie dies immer, wenn Sie mit vielen Daten zu tun haben), und führe es dann über den gesamten Satz aus. Es dauert ungefähr drei Stunden. Es ist gut, dass ich dies im Hintergrund mache, während ich mich mit anderen Aufgaben beschäftige, aber ich hätte alle Dateioperationen im Speicher und nicht mit tmpfs auf der Festplatte ausführen sollen. Lektion gelernt.

Die Satoshi-Summe beträgt 23734753110. Das sind ungefähr 237 Bitcoins, was bei den heutigen Preisen ungefähr 1,5 Millionen US-Dollar entspricht.

Eitelkeit der Eitelkeiten

Wenn Sie sich jedoch die Adressen ansehen, die zehn führende Nullen enthalten (die diejenigen mit den höchsten Salden waren), stellt sich heraus, dass sie Ausgabetransaktionen haben. Dies bedeutet, dass die privaten Schlüssel für diese Adressen bekannt sind.

Das Sortieren der Datei ripeweird.csv nach der Anzahl der Satoshis und das Anzeigen der Adressen mit dem höchsten Kontostand kann hilfreich sein:

Dies ergibt die folgende Ausgabe:

Bei der vorletzten Adresse mit 67 Bitcoins handelt es sich definitiv um einen Programmiererfehler – es werden nie Ausgaben getätigt, und es ist höchst unwahrscheinlich, dass jemand einen privaten ECDSA-Schlüssel hat oder generieren wird, der mit dieser Bitcoin-Adresse endet.

Die anderen Adressen, die mit zehn Nullen beginnen, scheinen jedoch Eitelkeitsadressen zu sein. Mit einer Eitelkeitsadresse generieren Sie so lange Schlüssel und leiten daraus Bitcoin-Adressen ab, bis Sie eine finden, die mit den gewünschten Zeichen beginnt.

So hat beispielsweise 1111116d87CjjDyP8SF5v1LTvUq22VFg derzeit einen Saldo von 89,5 BTC, hat jedoch im Laufe seiner Lebensdauer fast 400 BTC erhalten.

Zusammenfassung

Ich habe die tatsächlich aktiven Vanity-Adressen manuell entfernt und die Satoshi-Zählung erneut ausgeführt. Diesmal habe ich 8.925.496.933 Satoshis, das sind 89 Bitcoins, und daher einen Wert von etwa einer halben Million Dollar.

Ich habe “Abrufen von Adressen mit Eingaben, aber ohne Ausgaben” in die Liste der Funktionen aufgenommen, die dem Skript “btcposbal2csv” zu einem späteren Zeitpunkt hinzugefügt werden sollen.

Nun, das ist es für dieses Wochenende – ich hoffe, Ihnen hat diese zufällige Erkundung von Bitcoin-Transaktionen gefallen und Sie haben sich inspirieren lassen, sich selbst zu erkunden. Die Bitcoin-Blockchain ist voller interessanter Dinge, sodass Sie problemlos ein schönes Wochenende damit verbringen können, darin herumzustöbern, und hoffentlich hat Ihnen dieser Artikel einige Tools dafür gegeben.