UDPXD - A general purpose UDP relay/port forwarder/proxy - Updated 26.04.2015 14:04

There are cases, when you need to change the source ip address of a client, but can't do it in the kernel. Either because you don't have a firewall running or because it doesn't work, or because there's no firewall available.

In such cases the usual aproach is to use a port forwarder. This is a small piece of software, which opens a port on the inside, visible to the client and establishes a new connection to the intended destination, which is otherwise unreachable for the client. In fact, a port forwarder implements hiding nat or masquerading in userspace. Tools like this are also usefull for testing things, to simulate requests when the tool you need to use for the test are unable to set their source ip address (binding address).

For TCP there are LOTs of solutions available, e.g. tcpxd. Unfortunately there are not so many solutions available if you want to do port forwarding with UDP. One tool I found was udp-redirect. But it is just a dirty hack and didn't work for me. Also it doesn't track clients and is therefore not able to handle multiple clients simultaneusly.

So I decided to enhance it. The - current - result is udpxd, a "general purpose UDP relay/port forwarder/proxy". It supports multiple concurrent clients, it is able to bind to a specific source ip address and it is small and simple. Just check out the repository, enter "make" and "sudo make install" and you're done.

How does it work: I'll explain it on a concrete example. On the server where this website is running there are multiple ip addresses configured on the outside interface, because I'm using jails to separate services. One of those jail ip addresses is 78.47.130.33. Now if I want to send a DNS query to the Hetzner nameserver 213.133.98.98 from the root system (not inside the jail with the .33 ip address!), then the packet will go out with the first interface address of the system. Let's say I don't want that (either for testing or because the remote end does only allow me to use the .33 address). In this szenario I could use udpxd like this:

udpxd -l 172.16.0.3:53 -b 78.47.130.33 -t 213.133.98.98:53

The ip address 172.16.0.3 is configured on the loopback interface lo0. Now I can use dig to send a dns query to 172.16.0.3:53:

dig +nocmd +noall +answer google.de a @172.16.0.3
google.de.              135     IN      A       173.194.116.151
google.de.              135     IN      A       173.194.116.152
google.de.              135     IN      A       173.194.116.159
google.de.              135     IN      A       173.194.116.143

When we look with tcpdump on our external interface, we see:

IP 78.47.130.33.24239 > 213.133.98.98.53: 4552+ A? google.de. (27)
IP 213.133.98.98.53 > 78.47.130.33.24239: 4552 4/0/0 A 173.194.116.152,
              A 173.194.116.159, A 173.194.116.143, A 173.194.116.151 (91)

And this is how the same request looks on the loopback interface:

IP 172.16.0.3.24239 > 172.16.0.3.53: 4552+ A? google.de. (27)
IP 172.16.0.3.53 > 172.16.0.3.24239: 4552 4/0/0 A 173.194.116.152,
              A 173.194.116.159, A 173.194.116.143, A 173.194.116.151 (91)

As you can see, dig sent the packet to 172.16.0.3:53, udpxd took it, opened a new outgoing socket, bound to 78.47.130.33 and sent the packet with that source ip address to the hetzner nameserver. It also remembered which socket the particular client (source ip and source port) has used. Then the response came back from hetzner, udpxd took it, looked up its internal cache for the matching internal client and sent it back to it with the source ip on the loopback interface.

As I already said, udpxd is a general purpose udp port forwarder, so you can use it with almost any udp protocol. Here's another example using ntp: now I set up a tunnel between two systems, because udpxd cannot bind to any interface with port 123 while ntpd is running (ntpd binds to *.123). So on system A I have 3 udpxd's running:

udpxd -l 172.17.0.1:123 -b 78.47.130.33 -t 178.23.124.2:123
udpxd -l 172.17.0.2:123 -b 78.47.130.33 -t 5.9.29.107:123
udpxd -l 172.17.0.3:123 -b 78.47.130.33 -t 217.79.179.106:123

Here I forward ntp queries on 172.16.0.1-3:123 to the real ntp pool servers and I'm using the .33 source ip to bind for outgoing packets again. On the other system B, which is able to reach 172.17.0.0/24 via the tunnel, I reconfigured the ntpd like so:

server 172.17.0.1 iburst dynamic
server 172.17.0.2 iburst dynamic
server 172.17.0.3 iburst dynamic

After restarting, let's look how it works:

ntpq> peers
     remote           refid      st t when poll reach   delay   offset  jitter
==============================================================================
*172.17.0.1      131.188.3.221    2 u   12   64    1   18.999    2.296   1.395
 172.17.0.2      192.53.103.104   2 u   11   64    1    0.710    1.979   0.136
 172.17.0.3      130.149.17.8     2 u   10   64    1   12.073    5.836   0.089

Seems to work :), here's what we see in the tunnel interface:

14:13:32.534832 IP 10.10.10.1.123 > 172.17.0.1.123: NTPv4, Client, length 48
14:13:32.556627 IP 172.17.0.1.123 > 10.10.10.1.123: NTPv4, Server, length 48
14:13:33.535081 IP 10.10.10.1.123 > 172.17.0.2.123: NTPv4, Client, length 48
14:13:33.535530 IP 172.17.0.2.123 > 10.10.10.1.123: NTPv4, Server, length 48
14:13:34.535166 IP 10.10.10.1.123 > 172.17.0.1.123: NTPv4, Client, length 48
14:13:34.535278 IP 10.10.10.1.123 > 172.17.0.3.123: NTPv4, Client, length 48
14:13:34.544585 IP 172.17.0.3.123 > 10.10.10.1.123: NTPv4, Server, length 48
14:13:34.556956 IP 172.17.0.1.123 > 10.10.10.1.123: NTPv4, Server, length 48
14:13:35.535308 IP 10.10.10.1.123 > 172.17.0.2.123: NTPv4, Client, length 48
14:13:35.535742 IP 172.17.0.2.123 > 10.10.10.1.123: NTPv4, Server, length 48
14:13:36.535363 IP 10.10.10.1.123 > 172.17.0.1.123: NTPv4, Client, length 48
...

And the forwarded traffic on the public interface:

14:13:32.534944 IP 78.47.130.33.63956 > 178.23.124.2.123: NTPv4, Client, length 48
14:13:32.556586 IP 178.23.124.2.123 > 78.47.130.33.63956: NTPv4, Server, length 48
14:13:33.535188 IP 78.47.130.33.48131 > 5.9.29.107.123: NTPv4, Client, length 48
14:13:33.535500 IP 5.9.29.107.123 > 78.47.130.33.48131: NTPv4, Server, length 48
14:13:34.535255 IP 78.47.130.33.56807 > 178.23.124.2.123: NTPv4, Client, length 48
14:13:34.535337 IP 78.47.130.33.56554 > 217.79.179.106.123: NTPv4, Client, length 48
14:13:34.544543 IP 217.79.179.106.123 > 78.47.130.33.56554: NTPv4, Server, length 48
14:13:34.556932 IP 178.23.124.2.123 > 78.47.130.33.56807: NTPv4, Server, length 48
14:13:35.535379 IP 78.47.130.33.22968 > 5.9.29.107.123: NTPv4, Client, length 48
14:13:35.535717 IP 5.9.29.107.123 > 78.47.130.33.22968: NTPv4, Server, length 48
14:13:36.535442 IP 78.47.130.33.24583 > 178.23.124.2.123: NTPv4, Client, length 48
...

You see, the ntp server gets the time via the tunnel via udpxd which in turn forwards it to real ntp servers.

Note, if you left the parameter -b out, then the first ip address of the outgoing interface will be used.

udpxd source code and documentation is on github.


Update 26.04.2015 14:04:

I made a couple of enhancements to udpxd:

  • added ipv6 support (see below)
  • udpxd now forks and logs to syslog if -d (-v) is specified

So the most important change is ip version 6 support. udpxd can now listen on an ipv6 address and forward to an ipv4 address (or vice versa), or listen and forward on ipv6. Examples:

Listen on ipv6 loopback and forward to ipv6 google:

udpxd -l [::1]:53 -t [2001:4860:4860::8888]:53
Listen on ipv6 loopback and forward to ipv4 google:
udpxd -l [::1]:53 -t 8.8.8.8:53
Listen on ipv4 loopback and forward to ipv6 google:
udpxd -l 127.0.0.1:53 -t [2001:4860:4860::8888]:53

Of course it is possble to set the bind ip address (-b) using ipv6 as well.

And I added a Travis-CI test, which runs successful. So, udpxd is supported on FreeBSD and Linux. I didn't test other platforms yet.


22.04.2015 15:47 CC0 en opensource udp Source






Travis-CI Review

A couple of days ago I stumbled across Travis-CI, a tool for automated build tetsts of github projects. It sounded like a great idea to me, since I were very lax lately with testing builds of PCP on other platforms, so I gave it a try.

Basically Travis-CI works very simple: you create a .travis.yml file, which contains instructions to configure, build and test your github project, and you create an account on Travis-CI and activate a github project of yours. Then every time you make a commit, Travis-CI creates a fresh VM instance, checks out your latest code and runs the instructions in your .travis.yml file.

However, I had lots of problems making it work. Admittedly some of them were caused by code which either didn't compile or run on linux. This is a fat point on the plus side, because I was totally unaware of those issues. But I had much more trouble getting all the dependencies to work.

According to Travis' documentation each VM contains everything needed like gcc, perl, node.js and whatnot. But in reality you have to denote your project to a specific environment, which is C in my case. The unittests in the PCP source are driven by a perl script which needs a couple of additional modules. Their documentation stated, they use perlbrew, which I know and like a lot since I use it almost every day. Unfortunately perlbrew is not installed in a C VM. And so I had to install the perl modules "manually" (by wgetting them, untar, perl Makefile.PL, make and sudo install).

The good thing is you can do almost anything on the Travis-CI VM including root installs with sudo.  Thanks to this ability I were able to get the unittests to work. But PCP also has a python binding. This was mush more troublesome. Python itself were installed, but no headers, no python-pip, no cffi and so on. First I tried to install a package "python-cffi", which does exist according to google, but not on the Travis-CI VM. Instead I had to install the python headers, python-pip and libffi by downloading and compiling it. There's also an libffi ubuntu package available but it could not be installed because of some unspecified and unresolvable conflict. Such conflicts of binary package management tools are the very reason I left linux behind many years ago.

Well, now, 60 commits later, I've got it working:

Would I recommend Travis-CI? Definitly yes. However, there are some pros and cons I like to point out:

Pros:

  1. Each commit leads to a test build and if that fails you get notified.
  2. Pull requests lead to test builds as well, so you'll see if a patch breaks something or not.
  3. It's a free service, and a recource hungry at that. so - wow!
  4. It just works and every problem can be fixed by yourself, given you know how to do it.
  5. The Travis-CI documentation is outstanding with lots of examples.

Cons:

  1. There's only one platform available for tests: Linux (and only one distribution: Ubuntu). It maybe possible to test on MacOSX, but as of this writing only upon request.
  2. While you can choose between clang and gcc, you cannot test with different versions of the compilers.
  3. Those language specific environments make it difficult to use with a project with multiple language needs.
  4. There's no way to live test your .travis.yml file, like on a VM where you can login temporarily and initiate the test manually multiple times and tune the .travis.yml file til it works. Instead you've got to commit everything you like to try out, wait until Travis-CI tests are done, look on the site for the results and repeat the process. This iterative process comsumes a lot of time.
  5. Travis-CI is a german startup in berlin and as always with german companies they do just not respond to emails. I mailed them because of the mixed language issue outlined above, but noting came back and I had to figure it out myself like a blind one in a foreign country (at least sometimes I felt like this during the process detailed in 3.).
  6. Although they provide a Pro account for which you've to pay, I doubt the business model. Maybe the company will vanish overnight (or, worse, get sold and closed).

20.04.2015 18:36 CC0 en git opensource pcp Source






Willkommen 08/15

Heute wies mich ein Kollege darauf hin, dass wir diese Woche die KW 8 haben, also 08/15 :)


16.02.2015 18:13 CC0 fun Geschwätz






Crypt::PWSafe3 @Fedora

I bumped the version of Crypt::PWSafe3 to 1.16 and re-licensed the code under the Artistic License 2.0. This was required to be license compatible with fedora (and fully ok with me). Now someone made a RPM package of it. So it seems, people are using it, which is quite cool.


13.02.2015 18:58 CC0 en opensource perl Source






New perl module Data::Interactive::Inspect and dbmdeep

I published a new perl module: Data::Interactive::Inspect, which provides an interactive shell which can be used to inspect and modify a perl data structure. The module is the backend for dbmdeep, a DBM::Deep command line manager.

I made a short video to demonstrate the capabilities of the module:

 

So, basically, you can use the module like a command line database client of some sort, browse the structure and change all aspects of it. There are a couple of scenarios where this capability might help.

Say, you develop a software for systems management at a customer. Your possiblities for debugging are limited, something is awkward and you need to know what the software writes to the DBM::Deep database. With dbmdeep, which uses this module, the customer would be able to look at it himself and he would even be able to remove invalid entries.

Another example: lets say you want to feed a perl software, which uses a DBM::Deep database, with data from the outside and the program you have to use is written in python. Then the python script could just generate a YAML file and use the 'dbmdeep' command line tool to import this into the database.


08.02.2015 16:59 CC0 en opensource perl Source






Eine Tüte Mitleid für Werner Koch - Updated 08.02.2015 12:34

Bei Propublica ist ein Artikel über Werner Koch, dem GNUPG Entwickler erschienen, weil er pleite ist. Dem Artikel ist zu entnehmen, dass der Mann offensichtlich keinen Job hat und nur von den GNUPG Spenden lebt, seine Frau hat auch keine Arbeit.

Ich muss Fefe vollumfänglich Recht geben: mein Mitleid hält sich in Grenzen. Was mich am meisten daran stört ist diese unsägliche Weltanschauung, dass man für so etwas bezahlt werden müsse. Das ist Unsinn. Warum sollte der Mann für GNUPG bezahlt werden? Er hat es als Opensource und kostenlos veröffentlicht und damit hat sich Thema Bezahlung erledigt. Ja, zufälligerweise wird die Software von Hunderttausenden Menschen weltweit verwendet. Aber das ändert nichts an der Tatsache, dass es Opensource ist. Daraus ergibt sich kein "Recht auf Bezahlung".

Ich mache das so, wie Fefe es auch beschreibt: ich habe einen Job, von dem ich gut leben kann. Opensource Entwicklung mache ich in meiner Freizeit und ich WILL dafür kein Geld haben. Was viele nämlich nicht sehen, ist dass ich als Entwickler nämlich derjenige bin, der bezahlt. Ich benutze eine Menge Opensource: FreeBSD, OpenSSH, OpenSSL, Emacs, Bash, GCC, Postfix, Apache, PostgreSQL, Django, Perl, Python, FFmpeg, Xmonad, Firefox und so weiter und so fort. In jedem einzelnen dieser Projekte stecken zum Teil zig Tausende Manntage Entwicklerarbeit. Musste ich dafür was bezahlen? Nein. Aber indem ich ebenfalls Opensource Software veröffentliche, gebe ich etwas zurück. Ich leiste sozusagen meinen Beitrag. Der mag angesichts der erwähnten Giganten bescheiden sein, ja. Aber ich tue das ja primär, weil es mir Spass macht.

Das ist bei Werner Koch auch nicht anders. Er nutzt ebenfalls Opensource Software, sonst könnte er gar nicht an GNUPG arbeiten. Mit seinem Projekt leistet er seinen Beitrag, die Welt zu einem besseren Ort zu machen. Dafür gebührt ihm Dank und Ehre, ohne Zweifel. Aber Geld? Nein, auf keinen Fall.

Hinzu kommt, dass Koch schon diverse Male von hoher Seite unterstützt wurde, unter anderem von der Bundesregierung. Welcher Opensourcler kann das schon von sich behaupten. Aber weil er keinen Job hat, reicht das natürlich nicht. Dass Propublica ihn bei dem Gejammer unterstützt ist eher traurig. Laut dem Artikel hat er inzwischen diverse Sponsoren gefunden: Facebook (von denen würde ich keinen Cent annehmen) und Stripe. Bemerkenswerte Konversation mit Stripe:

Kenn White:
@stripe @gnupg no strings attached? (serious question)


Stripe:
@kennwhite @gnupg Nope.

Klar.

Auf ein Detail in dem Artikel möchte ich noch eingehen, das den zugrundeliegenden Denkfehler sehr schön veranschaulicht:

The fact that so much of the Internet's security software is underfunded is becoming increasingly problematic. Last year, in the wake of the Heartbleed bug, I wrote that while the U.S. spends more than $50 billion per year on spying and intelligence, pennies go to Internet security.

Auch in den Kommentaren zum Artikel gibt es viele Leute, die sich darüber beklagen, dass die US Regierung kaum Geld für Opensource Crypto ausgibt. Liebe Leute, Software wie GNUPG, OpenSSL oder OpenSSH hat vor allem einen Zweck: uns vor der Regierung zu schützen. Wieso sollten wir also von irgendeiner Regierung Geld dafür verlangen, damit wir vor ihr geschützt werden können? Das ist doch absurd.

Opensource ist eine Idee, kein Geschäftsmodell. Die Idee ist, mit den Mitteln, die man hat, zu versuchen die Welt zu verbessern. Seit wann müssen Leute, die die Welt verbessern, dafür bezahlt werden? Wenn man das will, muss man in die Wirtschaft gehen, ein Unternehmen gründen und seine Software verkaufen. Oder eben den Schritt wagen, seine Zeit, Nerven und Resourcen zu opfern für eine grössere Sache. Wovon man während dieser Zeit lebt, ist jedoch eine ganz andere Frage, mit der die Nutzer der Software nichts zu schaffen haben. Ja, die Welt ist hart und gemein. Ja, es wäre schöner, wenn man einfach machen könnte, was man gerne mag und irgendwie automatisch davon leben könnte. Aber so ist die Welt nicht und nicht nur Werner Koch ist davon betroffen, sondern wir alle.

Das heisst: es ist mir scheissegal, wovon Werner Koch's Mittagessen bezahlt wird. Das ist sein eigenes Problem, um das er sich verdammt nochmal selber kümmern muss. Um mein Mittagessen muss ich mich auch selber kümmern. Wie kann man sich nur auf diese Weise selbst erniedrigen, unmöglich.


Update 08.02.2015 12:34:

Es gibt noch einen Nachtrag bei Fefe::

Und dann schmeißt Werner Koch die geschenkten $100k den Patch weg und ich pflege 9 Jahre lang meinen Patch parallel weiter. Und Werner Koch winselt dann herum, dass er nicht versteht, wieso ihm keiner Geld nachwirft.

Das liegt daran, dass Werner Koch das Problem ist, nicht die Lösung. Werner Koch macht mit dem Code keine Wartung, eher eine Geiselnahme. Denn wer will schon gnupg forken. Wir kriegen ja schon ohne Fork die Leute nicht in signifikanter Größenordnung dazu, das zu benutzen. Das wäre noch übler, wenn es da auch noch Marktfragmentierung gäbe. Deshalb hat noch niemand gnupg geforkt. Nötig gewesen wäre es seit Jahren. Ich persönlich hoffe seit Jahren, dass Werner endlich hinwirft, und dann jemand die Wartung übernehmen kann, der auch ein Interesse daran hat, daraus ein ordentliches Projekt zu machen. Aber das wird ja jetzt nicht mehr stattfinden. Jetzt wo nicht mehr nur sein Ego sondern auch sein Lebensunterhalt direkt davon abhängt, dass er weiterhin Diktator von gnupg bleibt.
[..]
Ich sollte der Sicherheit halber dazu sagen, dass das nicht bloß meine Eintschätzung ist, dass Werner Koch das Problem ist, sondern ziemlich breiter Konsens. Ich habe diverse Mails von anderen Leuten gekriegt, die mit Werner vergeblich zu kooperieren versucht haben.








0.2.4 Release Pretty Curved Privacy

Finally I made a new release of Pretty Curved Privacy: 0.2.4. There are no new features,but lots of fixes and enhancements. Also there's a python API available as well (enable with --enable-python-binding).


11.01.2015 17:53 CC0 crypto en pcp Source






Salut

† Georges Wolinski

† Stephane Charbonnier

† Bernard Verlhac

† Jean Cabut

† Bernard Maris

 

 

Defending the Project of Free Inquiry:

A very dangerous principle is now being established as a social right: Thou shalt not hurt others with words. This principle is a menace–and not just to civil liberties. At bottom it threatens liberal inquiry–that is, science itself.

also.


07.01.2015 19:29 CC0 freiheit Gesellschaft






Re: The Perl Jam: Exploiting a 20 Year-old Vulnerability [31c3]

Netanel Rubin held a talk about an alleged 20 year old vulnerability in perl named "The Perl Jam: Exploiting a 20 Year-old Vulnerability" at 31C3 [PDF].

Basically he claims that this is a problem:

my @a = qw(8 foo 666);
my %h = (foo => 100,
	 bar => 333,
	 san => @a);
print Dumper(\%h);

$VAR1 = { 'san' => 8, 'bar' => 333, 'foo' => 666 };

As you can see, the array @a is assigned as a value to the key 'san' of the hash %h. But since it's not assigned as a array reference, the array dissolves into the hash and its values overwrite the keys 'foo' and 'san'.

The "vulnerability" Netanel found, is in the CGI module. The method 'param()' of this module returns an array if a CGI parameter occurs more than once. If the output of that method is being used unchecked in a hash assignment as shown above, then it is possible to overwrite certain values of that hash. This leaded for example to the vulnerability CVE-2014-1572 in Bugzilla.

Netanel's conclusion: perl is broken, horrible, hazardous, bizarre and should not be used anymore.

Wow.

He is wrong on multiple levels. Arrays dissolving into hashes is not a bug and not bad, but intended behavior and very well documented. In fact, I use it alot. I even love it! If you take a look into the function new() of about 80% of all perl modules on CPAN, you'll find, that they support hash arguments, and feed @_ into a hash. Pretty standard for perl people. Others might find it ugly or weird, but hey, it's a free world (mostly), choose another language if you don't like the concept.

Then Netanel has been asked if he knows about references and in response complained about using a backslash in order to assign a reference to a hash (or array) to a variable. He called it "escaping", but that's utter nonsense. \%hash ist pure perl syntax, not escaping.

The talk sounds funny in the first place, but is unsubstancial. Yes there are flaws in perl code which uses CGI.pm in the wrong way. But that's not a perl problem, it's a CGI.pm problem. And it's solved since a long time. Modern web stuff written in perl uses Dancer, Mojolicious or Catalyst and not CGI.pm.


30.12.2014 10:11 CC0 en kritik opensource perl Source






Migrated from Tiddlywiki to Emacs Org-Mode

I am an early adopter of TiddlyWiki, a personal wiki which runs locally in a browser. I used it for many years nearly every day at work and home. I'm so used to it, I'm unable to do my daily work without it. I even wrote a couple of plugins for TiddlyWiki and I ported it to the palm pre mobile platform.

Now that era is over, thanks to the developers of firefox. I used to use an outdated portable firefox instance at work when a couple of weeks ago the NoScript plugin has been updated. From that moment on, firefox didn't work properly anymore, so I had to update firefox as well. I did it and everything looked good. Until I clicked the "save" button in tiddlywiki - it didn't work anymore. Turns out, that the firefox developers disabled the UniversalXPConnect capability, which made it possible for local Javascripts like TiddlyWiki to access the local harddisk.

There's a plugin called TiddlyFox, which aims to close the gap, but there are several reasons why I can't use it. First, it doesn't work with older wikis. Mine was based on version 2.3 and heavily customized. I just couldn't upgrade it (and I don't know, how, anyway). So I had to use the latest TiddlyWiki version, which I don't like. Then there's the problem, that the TiddlyFox plugin just pops up firefox' "Save as..." dialogue, if you click save and the file already exists, you end up with "wiki(1).html", the next time with "wiki(2).html" and so forth, which is really annoying and impractical. Also, the very fact, that a plugin is required to save a wiki, is a no-go for me. What if the admins of my workstation decide to forbid firefox plugins? I would be fucked.

Therefore I decided to make a cut and look for another solution for note taking and organizing. I ended up with org-mode for emacs. I use emacs anyway, primarily for programming, so I'm at home already. I tried org-mode a decade ago and didn't like it. I've got to admit, I still don't really like it, but I get used to it and it'll suffice my requirements. I use org-mode only for note taking, I don't use its agenda-mode or the time and clocking keeping stuff. So, it's ok. The only thing I miss is a feature I regularly used in TiddlyWiki: click on a tag, a popup appears with all tiddlers which also have this tag, from which you can select one to open it (or jump to it, if it's already open). In org-mode you end up in the agenda if you click on a tag, which splits the window. Ok it is possible to click on a tag there which shows all matching entries but if you click on one, it opens it within the same frame as the agenda. So, in the end you've got two frames with org-mode. So far I was unsuccessfull to disable this annoying behavior, therefore I don't use the tags. Maybe some day I've got a working solution for this (e.g. an imenu with matching entries if click on a tag).

Ok, this is the script I used to convert my TiddlyWiki entries to an org-mode file: tiddlers2orgmode.pl. If you want to use it, keep in mind that it is only tested with TiddlyWiki 2.3. You may also tweak it here and there.

Finally here's the org-mode emacs config I've put together so far:

; org mode
(defvar my-home "C:/Cygwin/home/tom")
(defvar my-lisp (concat my-home "/.emacs.d"))
(defvar my-org-file (concat my-home "/notizen.org"))

(setq load-path (cons (concat my-lisp "/org/lisp") load-path))
(setq load-path (cons (concat my-lisp "/org/contrib/lisp") load-path))

(custom-set-variables
 '(org-agenda-files (list my-org-file))
 '(org-default-notes-file (concat "/remember.org"))
 '(org-reverse-note-order t)
 '(org-remember-store-without-prompt t)
 '(org-reverse-note-order t)
 '(org-startup-indented t)
 '(word-wrap t)
 '(org-startup-truncated nil)
 '(org-columns-default-format "%80ITEM %22Timestamp %TODO %TAGS %0PRIORITY")
 '(org-mouse-1-follows-link nil)
 '(org-insert-heading-always-after-current 't) ; new headings below current
 '(org-M-RET-may-split-line nil) ;; dont break heading with enter
 '(org-blank-before-new-entry (
      ; no blank lines after headings
      quote ((heading . auto) (plain-list-item . auto)))
  )
 '(org-agenda-restore-windows-after-quit t)
 '(org-use-speed-commands t) ; see next block for which ones
 '(org-catch-invisible-edits 'error) ; dont edit invisibles
)

(setq org-speed-commands-user (quote (
    ("0" . ignore)
    ("1" . delete-other-windows)
    ("2" . ignore)
    ("3" . ignore)
    ("d" . org-archive-subtree-default-with-confirmation) ; delete, keep track
    ("v" . org-narrow-to-subtree) ; only show current heading ("view")
    ("q" . widen)                 ; close current heading and show all ("quit")
    (":" . org-set-tags-command)  ; add/edit tags
    )))

; ctrl-n for new entry with template
(setq org-capture-templates
      '(("j" "Note" entry (file+datetree my-org-file)
	 "* %? %^g\n %U\n %i\n"))
)

(define-key global-map "\C-n"
  (lambda () (interactive) (org-capture nil "j")))

; use ctrl-arrows to jump between headings
(add-hook 'org-mode-hook ( lambda ()
   ; move heading down
   (local-set-key (kbd "<C-down>") 'outline-next-visible-heading)
   ; move heading up
   (local-set-key (kbd "<C-up>")   'outline-previous-visible-heading)
   ; alt-enter = insert new subheading below current
   (local-set-key (kbd "<kp-enter>") 'org-insert-subheading)
   ; search for tags (ends up in agenda view)
   (local-set-key "\C-f" 'org-tags-view)
))

(setq org-todo-keywords
 '((sequence "TODO" "STARTED" "WAITING" "DONE" "CANCELED")))

;; todo colors
(setq org-todo-keyword-faces '(
   ("TODO"  . (:foreground "#b70101" :weight bold))
   ("STARTED"  . (:foreground "#b70101" :weight bold))
   ("WAITING"  . (:foreground "orange" :weight bold))
   ("DONE"  . (:foreground "forestgreen" :weight bold))
   ("CANCELED"  . shadow)
))

29.12.2014 10:16 CC0 emacs en Emacs