Generating SSL Cert for Apache

This is mostly just a note to myself, because I have to look it up every time I need to generate one, and the make-ssl-cert script that comes with debian doesn't appear to work.

openssl req -new -x509 -days 365 -nodes -out /tmp/cert.pem -keyout /tmp/cert.pem

Serialization of HTML5 web worker postMessage parameters in webkit

I played around with html5 web workers today. I quickly ran into an issue with chrome. Chrome (and probably also Safari) limit the messages that can be passed around to strings. The spec seems to allow arbitrary objects though, which works in firefox. Luckily Chrome supports native json, so here is a quick workaround.

// in the worker
if(navigator.userAgent.indexOf('WebKit')) {
    var _postMessage = postMessage;
    postMessage = function(data) {
        _postMessage(JSON.stringify(data));
    }
}
// in the page
worker.onmessage = function(e) {
    // assign it to a variable, e.data seems to be read-only
    var data = e.data;
    if(navigator.userAgent.indexOf('WebKit') != -1) {
       data = JSON.parse(data);
    }
// ..

In the worker monkey patching is easily possible. But I'm not aware of a nice way to intercept events so, I just put the decoding in the event handler. If I would need this in a lot of places I would probably write a higher order function the decode the argument.

Flip Images using HTML5 Canvas

You can flip an Image using HTML5 like this:

// flip x axis
ctx.scale(-1, 1);
ctx.drawImage(img, x, y);
// flip it back again
ctx.scale(-1, 1);

You can flip along the y axis in the same way. I'm note sure how fast this transformation is, in practice so you might need to cache it if you are doing realtime graphics.

Hand drawn lines using javascript canvas


For an upcoming game I'm working on I want the lines to look hand drawn. I found a nice paper on the subject. My algorithm is inspired by that paper, but not an exact implementation. But the results look good anyway. I also wrote a method to draw circles, but it needs improvement. Please let me know if you use it anywhere. :)

// randomize a variable
function fuzz(x, f){
    return x + Math.random()*f - f/2;
}

// estimate the movement of the arm
// x0: start
// x1: end
// t: step from 0 to 1
function handDrawMovement(x0, x1, t){
    return x0 + (x0-x1)*(
            15*Math.pow(t, 4) -
            6*Math.pow(t, 5) -
            10*Math.pow(t,3)
    )
}

// hand draw a circle
// ctx: Context2D
// x, y: Coordinates
// r: radius
function handDrawCircle(ctx, x, y, r){
    var steps = Math.ceil(Math.sqrt(r)*3);

    // fuzzyness dependent on radius
    var f = 0.12*r;

    // distortion of the circle
    var xs = 1.0+Math.random()*0.1-0.05;
    var ys = 2.0-xs;

    ctx.moveTo(x+r*xs, y);

    for(var i = 1; i <= steps; i++)
    {
        var t0 = (Math.PI*2/steps)*(i-1);
        var t1 = (Math.PI*2/steps)*i;
        var x0 = x+Math.cos(t0)*r*xs;
        var y0 = y+Math.sin(t0)*r*ys;
        var x1 = x+Math.cos(t1)*r*xs;
        var y1 = y+Math.sin(t1)*r*ys;

        ctx.quadraticCurveTo(fuzz(x0, f), fuzz(y0, f), x1, y1);
        ctx.moveTo(x1, y1);
    }
}

// inspired by this paper http://iwi.eldoc.ub.rug.nl/FILES/root/2008/ProcCAGVIMeraj/2008ProcCAGVIMeraj.pdf
function handDrawLine(ctx, x0, y0, x1, y1){
    ctx.moveTo(x0, y0)

    var d = Math.sqrt((x1-x0)*(x1-x0)+(y1-y0)*(y1-y0))

    var steps = d/25;
    if(steps < 4) {
        steps = 4;
    }

    // fuzzyness
    var f = 8.0;
    for(var i = 1; i <= steps; i++)
    {
        var t1 = i/steps;
        var t0 = t1-1/steps
        var xt0 = handDrawMovement(x0, x1, t0)
        var yt0 = handDrawMovement(y0, y1, t0)
        var xt1 = handDrawMovement(x0, x1, t1)
        var yt1 = handDrawMovement(y0, y1, t1)
        ctx.quadraticCurveTo(fuzz(xt0, f), fuzz(yt0, f), xt1, yt1)
        ctx.moveTo(xt1, yt1)
    }
}

Converting midi2wav using fluidsynth

Converting midi to wav using fluidsynth is not entirely trivial. Here is how I do it:

# convert opensolo.mid to fluidsynth.raw using the soundfont /usr/share/sounds/sf2/FluidR3_GM.sf2 
fluidsynth -l -i -a file -z 2048 /usr/share/sounds/sf2/FluidR3_GM.sf2 opensolo.mid
# convert fluidsynth.raw to fluidsynth.wav using sox
sox -b 16 -c 2 -s -r 44100 fluidsynth.raw fluidsynth.wav

You can use this together with the midi export of tuxguitar to export tuxguitar and guitarpro files to wav files.

m-audio Axiom 61 on Linux (Ubuntu 9.10)

I bought myself a M-Audio Axiom 61 to play around with. It works nicely on Linux, plug & play, literally. I tried it with the demo version of Pianoteq and Fluidsynth. Both worked perfectly on the first try. I'm happy so far.

Trick 37: Sniffing http traffic with tcpdump

Sniffing http traffic can be quite useful to find out what's going wrong on a webserver. Here is a simple way to do it using tcpdump:
tcpdump -X tcp port 80

Installing the nvidia opencl driver on ubuntu 9.10

Yesterday, I messed up my system by trying to install a NVIDIA beta driver in order to use opencl. Today I tried again with more success. Here is how I did it:

  1. Download the driver from the NVIDIA website
  2. Open the hardware driver manager of Ubuntu (Sytem/Administration/Hardware Drivers)
  3. Select the NVIDIA accelerated graphics driver (the active one) and click remove
  4. Log out
  5. Press CTRL+ALT+F1 to get to the console
  6. Login with your username and password
  7. sudo stop gdm
  8. chmod +x ./nvdrivers_*.run
  9. sudo ./nvdrivers_*.run
  10. sudo init 6
  11. Enjoy OpenCL goodness

A WORD OF WARNING don't try this unless you understand all the steps involved and know how to recover your system in case something goes wrong!

Stay tuned for some nice opencl experiment.

Autostart/Autorun with Python

Some time ago I wrote a little python module to automatically start programs when a user logs in. It works on Windows and Linux. On windows it creates registry entries, on linux it creates *.desktop files as defined in the Desktop Application Autostart Specification. You can use it like this:
import os
import autorun
autorun.add("myapp", os.path.abspath(__file__))
So here's the code:
#!/usr/bin/env python
"""A simple crossplatform autostart helper"""
from __future__ import with_statement

import os
import sys

if sys.platform == 'win32':
    import _winreg
    _registry = _winreg.ConnectRegistry(None, _winreg.HKEY_CURRENT_USER)
    def get_runonce():
        return _winreg.OpenKey(_registry,
                r"Software\Microsoft\Windows\CurrentVersion\Run", 0,
        _winreg.KEY_ALL_ACCESS)

    def add(name, application):
        """add a new autostart entry"""
        key = get_runonce()
        _winreg.SetValueEx(key, name, 0, _winreg.REG_SZ, application)
        _winreg.CloseKey(key)

    def exists(name):
        """check if an autostart entry exists"""
        key = get_runonce()
        exists = True
        try:
            _winreg.QueryValueEx(key, name)
        except WindowsError:
            exists = False
        _winreg.CloseKey(key)
        return exists

    def remove(name):
        """delete an autostart entry"""
        key = get_runonce()
        _winreg.DeleteValue(key, name)
        _winreg.CloseKey(key)
else:
    _xdg_config_home = os.environ.get("XDG_CONFIG_HOME", "~/.config")
    _xdg_user_autostart = os.path.join(os.path.expanduser(_xdg_config_home),
            "autostart")

    def getfilename(name):
        """get the filename of an autostart (.desktop) file"""
        return os.path.join(_xdg_user_autostart, name + ".desktop")

    def add(name, application):
        """add a new autostart entry"""
        desktop_entry = "[Desktop Entry]\n"\
            "Name=%s\n"\
            "Exec=%s\n"\
            "Type=Application\n"\
            "Terminal=false\n" % (name, application)
        with open(getfilename(name), "w") as f:
            f.write(desktop_entry)

    def exists(name):
        """check if an autostart entry exists"""
        return os.path.exists(getfilename(name))

    def remove(name):
        """delete an autostart entry"""
        os.unlink(getfilename(name))
def test():
    assert not exists("test_xxx")
    try:
        add("test_xxx", "test")
        assert exists("test_xxx")
    finally:
        remove("test_xxx")
    assert not exists("test_xxx")

if __name__ == "__main__":
    test()
I hope that helps somebody. :)

Getting audio to work on a HP Pavilion dv5 / Ubuntu 9.10

It looks like the problem is still there in Ubuntu 9.10, and it looks like the old fix still works. But it looks gorgeous.