Posts on tag: source

Table of contents

PDF Seiten extrahieren und neu anordnen

Gestern hatte ich folgendes Problem: ich habe ein 4-seitiges Dokument eingescannt und der Scanner hat das PDF File falsch herum ausgespuckt, d.h. es fing mit Seite 4 an und hörte mit Seite 1 auf. Ich hätte es neu scannen können, aber dafür war es zu spät (ich war schon daheim). Was tun?

Nach ein wenig Googelei habe ich pdfjam gefunden. Es war gleich installiert, Latex hatte ich eh schon drauf, aber: es crashte mit meinem PDF File (Segmentation Fault). Nicht pdfjam crashte, sondern pdftex. Ich stand also erheblich auf dem Schlauch. Irgendwann fand ich heraus, dass man das gleiche auch mit Ghostscript tun kann und das Ergebnis wird sogar besser als das von pdfjam (weil Ghostscript die PDF Seiten nicht verändert).

Da die Commandline von Ghostscript nicht der Burner ist und ich das wie üblich gerne flexibel hätte, habe ich kurzerhand ein Wrapperscript geschrieben: pdfjamgs. Das ist im Prinzip ein Ersatz für pdfjam, nur mit Ghostscript als Backend und es unterstützt auch nicht alle Features von pdfjam. Zumindest einzelne Seiten aus einem oder mehreren Dokumenten kann man aber extrahieren und in ein neues PDF schreiben.

So sieht das zum Beispiel aus:

% pdfjamgs -i source.pdf:3,4,7-9 -o destination.pdf

Ich denke, das muss man nicht extra erklären. Und natürlich kann man -i mehrmals angeben.

↷ 04.12.2013 🠶 #source

Status C++ API for Pretty Curved Privacy

While I'm waiting for Frank to fix the AIX libsodium issue I thought it would be a good idea to start with a C++ API for Pretty Curved Privacy. And I've to admit, that it is really fun to do that. Working with the C++ API makes the whole thing a LOT easier. Here's an example of how to generate some keys and encrypt some data:

#include <pcp++.h>
#include <string>
#include <iostream>

using namespace pcp; using namespace std;

int main() { try { /* generate 2 secret keys */ Key A = Key("a", "alicia", "alicia@local"); Key B = Key("b", "bobby", "bobby@local");

/* extract the public parts of them */ PubKey PA = A.get_public(); PubKey PB = B.get_public();

/* decrypt the secret keys */ A.decrypt("a"); B.decrypt("b");

/* create crypto objects (1st for the sender, 2nd for the recipient) */ Crypto A2B(A, PB); Crypto B2A(B, PA);

/* actually encrypt something (alicia to bobby) */ string cipher = A2B.encrypt("Hallo");

/* and decrypt it (bobby from alicia) */ ResultSet res = B2A.decrypt(cipher);

/* see if it worked as expected */ if(res.String == "Hallo") cout << "ok" << endl; else throw pcp::exception("wtf - decryption failed (uncatched as well)"); } catch (pcp::exception &E) { cerr << "Catched exception: " << E.what() << endl; } return 0; }

Now, that's easy, isn't it? At least I like it. The API is not ready though, signing and derived keys are not done yet. More example code can be seen in the C++ unittest.

↷ 02.12.2013 🠶 #source

PCP Vorstellung

Mittlerweile bin ich mit meinem Projekt Pretty Curved Privacy recht weit vorangekommen, daher dachte ich wird es an der Zeit, das hier mal ausführlicher vorzustellen.

Angefangen hat das alles, als ich - im Zuge der NSA Affäre nach Alternativen suchend - auf Curve25519 gestossen bin. Kryptographie mit eliptischen Kurven ist überaus faszinierend. Das gibt es schon länger, auch OpenSSL bietet entsprechende Algorithmen an, allerdings sind das alles NIST Standards. Und da wir mittlerweile wissen, dass das NIST von der NSA kompormittiert worden ist, muss etwas anderes her. Jedenfalls wenn man paranoid ist so wie ich. Curve25519 ist so etwas. Entwickelt von D.J.Bernstein und verfügbar in der nacl Bibliothek. Da nacl aber nicht so richtig portabel ist, gibt es eine portable Implementierung namens libsodium.

Während ich so am herumforschen war, wie man das am besten nutzen könnte, bin ich dann auf das Messaging-Framework ZeroMQ gestossen. Abseits kryptographischer Erwägungen ist ZeroMQ eine coole Sache wenn man netzwerkfähige Software schreiben will. Und es unterstützt Curve25519 über das CurveCP Protokoll. Ich spielte also mit dem Zeug so vor mich hin und irgendwann hat mich das bei CZMQ (ein Wrapper für ZeroMQ) mitgelieferte Schlüsselerzeugungstool "makecert" nur noch genervt. Es ist unflexibel und blöd. Wie es sich für einen OpenSource-Anhänger gehört, habe ich mich daher aufgerafft und etwas neues geschrieben: curve-keygen. Um das als Ersatz für makecert in das ZeroMQ Repository zu bekommen, habe ich mit den Entwicklern Kontakt aufgenommen. Die waren (und sind es noch) ohnehin gerade dabei, das Format für Curve25519 Schlüssel zu überarbeiten. Es gab dazu eine rege Diskussion auf der Mailingliste, inzwischen ist da aber Ruhe eingekehrt. Und irgendwann während dieser Diskussion habe ich angefangen, mein curve-keygen Tool neu zu schreiben. Es wurde grösser und grösser und am Ende kam Pretty Curved Privacy (PCP) heraus.

Mit PCP kann man im Grunde all die Sachen machen, die man auch mit PGP (bzw GnuPG) machen kann: Schlüssel erzeugen, verwalten, exportieren, importieren usw., Dateien ver- und entschlüsseln sowie signieren. Nur dass dabei eben keine Algorithmen zum Einsatz kommen, bei deren Entwicklung die NSA ihre Finger im Spiel hatte. Einzige Ausnahme ist SHA256 bzw SHA512, das derzeit noch für Hashes verwendet wird. Das soll aber abgelöst werden, sobald es entsprechenden Ersatz gibt.

Wie Kryptographie mit eliptischen Kurven (ECC) genau funktioniert, werde ich hier nicht erklären. Zum einen weil ich das gar nicht kann, die Mathematik ist mir viel zu heftig, das ist aus meiner Sicht mehr Magie als Mathematik. Und zum anderen wird das woanders bereits gut erklärt. Vereinfacht ist das Grundprinzip folgendes:

Bob erzeugt ein Curve25519 Schlüsselpaar bestehend aus einem öffentlichen und einem privaten Schlüssel. Alice tut das gleiche. Nun gibt Bob seinen öffentlichen Schlüssel Alice und sie tut es umgekehrt mit ihrem. Alice kann nun aus ihrem privaten Schlüssel und Bobs öffentlichen Schlüssel ein sogenanntes "shared secret" erzeugen (im Grunde eine Zahl) und Bob kann ebenfalls mit seinem privaten Schlüssel und Alice's öffentlichen Schlüssel ein "shared secret" erzeugen. Die Magie bei ECC ist nun, dass dieses "shared secret" bei beiden identisch ist! Man kann das also verwenden um Daten zu verschlüsseln, die nur der jeweilige Kommunikationspartner entschlüsseln kann. Wirklich abgefahren. Der dramatische Unterschied zum bei PGP verwendeten RSA ist, dass wenn Alice eine Nachricht für Bob verschlüsselt, dieser die nur unter Verwendung seines privaten UND Alice's öffentlichem Schlüssel entschlüsseln kann. Man kann also nicht einfach den öffentlichen Schlüssel von irgendjemand nehmen und dem dann eine Nachricht schicken. Dieser jemand muss auch einen öffentlichen Schlüssel vom Absender haben, sonst kann er damit nichts anfangen.

Dieses Szenario kann man mit PCP verwenden, es ist aber nicht die empfohlene Vorgehensweise. Obwohl ein öffentlicher Curve25519 Schlüssel zwar durchaus veröffentlicht werden kann, sollte man das lieber nicht tun. Statt dessen wird z.b. beim CurveCP Protokoll für jede Session ein dynamisches Schlüsselpaar erzeugt. Auf diese Weise kann in der Vergangenheit aufgezeichneter Traffic nicht nachträglich entschlüsselt werden, sollte einmal ein Teil der Schlüssel bekannt werden.

Bei PCP kann ich dieses Vorgehen allerdings nicht umsetzen, weil PCP offline arbeitet. Ich kann da kein Protokoll verwenden um dynamische Schlüssel auszuhandeln. Ich habe mir mit sogenannten "derived keys" abgeholfen: abgeleiteten Schlüsseln. Man sendet einem Partner also nicht den öffentlichen Schlüssel des primären Schlüsselpaars, sondern errechnet aus seinem privaten Schlüssel und einer ID einen dynamischen Schlüssel. Die ID kann die Schlüssel-ID, der Name oder die Emailadresse des Empfängers sein. Davon exportiert man den öffentlichen Schlüssel, schickt das dem Empfänger, der tut das gleiche umgekehrt und dann kann man Nachrichten austauschen. So ein abgeleiteter Schlüssel ist nur von einem bestimmten Kommunikationspartner benutzbar. Sollte er in die falschen Hände geraten, kann maximal die Kommunikation mit dieser einen Person kompromittiert werden - nicht mit allen.

Was gibts noch zu sagen? Nun, PCP ist in C geschrieben und das war eine ausgezeichnete Gelegenheit für mich, wieder da rein zu kommen. War schon eine Weile her inzwischen. Ich habe beim Entwickeln Valgrind entdeckt und lieben gelernt. Man kann gar nicht ermessen, wie sehr mit das geholfen hat, die obskursten Fehler zu finden. Ich habe ausserdem eine Unmenge an Unittests, mit denen ich sämtliche Funktionen prüfen kann. Insbesondere bei Änderungen ist das ungemein hilfreich. Das Framework dazu habe ich in Perl selber geschrieben, basierend auf dem Perlmodul Test::More, weil ich nichts passendes gefunden habe, mit dem man Unittests für command-line Tools schreiben kann. Die Unittests befinden sich im Verzeichnis tests/ im Source.

Einer der drastischsten Fehler, den ich damit gefunden hatte, war der "22-Key-Bug": neben den Unittests gibt es auch einen Stresstest, der eine grosse Menge Schlüssel verarbeitet. Das ging gut bis zum 22ten Schlüssel und dann ist PCP mit einem Segmentation Fault abgestürzt. Da hab ich vielleicht gewühlt, bis ich dem Bug auf die Schliche gekommen bin (es war ein double free, warum auch immer der erst ab dem 23ten Schlüssel anfing habe ich nie herausgefunden). Ohne Valgrind und die Unittests wäre dieser Bug noch immer im Code und ich hätte keine Ahnung davon.

Zum Schluss sei auf die Webseite von PCP hier auf dem Server verwiesen: Pretty Curved Privacy. Dort wird eigentlich alles erklärt (wie üblich auf englisch). Es gibt dort auch die aktuelle Unix Manpage pcp1(1). Den Sourcecode gibt es bei Github. Ich habe es erfolgreich unter FreeBSD, Linux (ein älteres Debian) und unter Windows 7 mit Cygwin compilieren können. Einzige Abhängigkeit ist wie erwähnt libsodium. Es gibt einen ASCII-Cast (eine Art Terminal Video), in dem ich die Verwendung demonstriere: ASCII-Cast PCP.

Zu erwähnen wäre noch, dass es sich trotz allen Aufwands, den ich bereits hineingesteckt habe, um experimentelle Software handelt, die man besser nicht für ernstzunehmende produktive Zwecke einsetzen sollte. Die Version ist auch noch unter 1 (aktuell: 0.1.3), daher können sich jederzeit Schlüssel- oder Datenbankformate ändern. Trotz allem würde ich mich natürlich über jede Art Feedback freuen :)

 

Update 2013-11-12:

Telekom kooperiert mit RSA. Mehr als die Überschrift braucht es nicht.

Update 2013-11-11:

Haha: Die IETF vertraut dem NIST auch nicht mehr.

↷ 09.11.2013 🠶 #source

Pretty Curved Privacy Update

Nach relativ viel Arbeit habe ich Pretty Curved Privacy nun in einem recht passablen Zustand. Es compiliert unter FreeBSD, Linux und Cygwin sauber durch und läuft auch auf allen 3 Platformen. MacOSX müsste ich noch probieren, aber mein alter Mac ist auf dem Dachboden. Keine Ahnung ob ich mir das antun will.

↷ 04.11.2013 🠶 #source

Pretty Curved Privacy

Finally, I'm done wit the first working version of "Pretty Curved Privacy". It's late, so for today only an ASCII-Cast about how to use it.

Meanwhile, here are the install instructions, intro and quickstart:

DESCRIPTION

Pretty Curved Privacy (pcp1) is a commandline utility which can be used to encrypt files. pcp1 uses eliptc curve cryptography for encryption (CURVE25519 by Dan J. Bernstein). While CURVE25519 is no worldwide accepted standard it hasn't been compromised by the NSA - which might be better, depending on your point of view.

Caution: since CURVE25519 is no accepted standard, pcp1 has to be considered as experimental software. In fact, I wrote it just to learn about the curve and see how it works.

Beside some differences it works like GNUPG. So, if you already know how to use gpg, you'll feel almost home.

QUICKSTART

Lets say, Alicia and Bobby want to exchange encrypted messages. Here's what the've got to do.

First, both have create a secret key:

 Alicia                             Bobby
 pcp1 -k                            pcp1 -k

After entering their name, email address and a passphrase to protect the key, it will be stored in their vault file (by default ~/.pcpvault).

Now, both of them have to export the public key part of their key:

 Alicia                             Bobby
 pcp1 -p -O alicia.pub              pcp1 -p -O bobby.pub

They've to exchange the public key somehow (which is not my problem at the moment, use ssh, encrypted mail, whatever). Once exchanged, they have to import it:

 Alicia                             Bobby
 pcp1 -P -I bobby.pub               pcp1 -P -I alicia.pub

They will see a response as this when done:

 key 0x29A323A2C295D391 added to .pcpvault.

Now, Alicia finally writes the secret message, encrypts it and sends it to Bobby, who in turn decrypts it:

 Alicia                             Bobby
 echo "Love you, honey" > letter
 pcp1 -e -i 0x29A323A2C295D391 -I letter -O letter.z85
 cat letter.z85 | mail bobby@foo.bar
                                pcp1 -d -I letter.z85 | less</pre>

And that's it.

Please note the big difference to GPG though: both Alicia AND Bobby have to enter the passphrase for their secret key! That's the way CURVE25519 works: you encrypt a message using your secret key and the recipients public key and the recipient does the opposite, he uses his secret key and your public key to actually decrypt the message.

Oh - and if you're wondering why I named them Alicia and Bobby: I was just sick of Alice and Bob. We're running NSA-free, so we're using other sample names as well.

INSTALLATION

There are currently no packages available, so pcp has to be compiled from source. Follow these steps:

First, you will need libsodium:

 git clone git://github.com/jedisct1/libsodium.git
 cd libsodium
 ./autogen.sh
 ./configure && make check
 sudo make install
 sudo ldconfig
 cd ..

Next, pcp:

 git clone git://github.com/tlinden/pcp.git
 cd pcp
 ./configure
 sudo make install
 cd ..

Optionally, you might run the unit tests:

 make test

↷ 28.10.2013 🠶 #source