Debian GNU/Linux
/meta
Posted on 2006-12-11 by ivo :: /meta :: link
Debian GNU/Linux is a Linux distribution.
Worldwide, about one thousand people work together to make a
high-quality free operating
system. I have been a developer since about october 2000. My work
there is mainly maintaining packages, and sometimes I translate some
Debian-specific things. Read more
about my work for Debian.
python-gnutls
The GnuTLS project is
developing a library that provides an interface to TLS or SSL sockets. python-gnutls
provides a set of bindings so that the GnuTLS library can be used from
your python
programs.
tinc
tinc is a Virtual Private Network daemon that
uses the linux tun device, and runs completely in userspace. Now the
development is mostly done by Guus
Sliepen.
pokey
Pokey is a graphical
interface to tinc. It shows a graphical representation of the network
that has been built up with tinc. It doesn't work with the latest
version of tinc, because the protocol has changed a few times since
the last release of pokey. Development will probably be picked up
again when tinc splits the protocol handling into a library. Here's a
screenshot.
Translating software
http://vertaling.nl.linux.org/
Translating open source software to Dutch. More information about the
GNU Translation Project's website.
Doflijn
Doflijn is a
windowmanager for the X Window System. It is based on aewm, and aimed at
providing as little functionality as possible while still being about
as useful as for example sawfish.
Sheep
Sheep (officially
called "Sheep Asleep") is a script for EPIC (which is an IRC
client). It was originally based on SplitFire, but now it has been
rewritten from scratch. This script (or rather, this collection of
scripts) is now obsolete, since irssi is so much more suited for the
level of scriptability required for sheep. Not only that, irssi is
also scriptable in Perl (actually any language, but Perl seems to be
the most common) instead of EPIC's horrible Tcl-like language. I have
a small collection of scripts for irssi on my IrssiScripts
page.
BLURT
BLURT stands for
Bloody Lame Useless Redundant Terminal. It is a terminal emulator for
X, intended to use less
resources than xterm or rxvt. It also offers far less
features; in fact it was designed to be as small as possible, but
still provide a fully functional terminal emulator.
Useless Code
UselessCode: A collection of completely useless code. Do not expect
too much of it, it's just a compilation of some of my more embarassing
little projects. A lot of this code is also scattered throughout this
site and the wiki.
CVS
Some of my code is available from CVS, and can be browsed through online via
ViewCVS.
Style guides
I wrote a few Coding
style guides. They basically document the style that I like to
program in, in four languages (C, C++, Perl, Python). This will
differ from other people's styles. They are certainly not
prescriptive, only indicative of what I think yields readable source
code for any project.
Blosxom
I wrote a few plugins and themes for Blosxom, a simple but powerful
weblogging system.
Plugins
Themes
About lychnis.net/meta
Posted on 2006-12-11 by ivo :: /meta :: link
License and copyright
Most material on this site is copyright © 2003-2004 Ivo Timmermans. Material on this
site by other copyright holders is clearly indicated.
Unless otherwise specified, all material on this website
(including any images, sound files, and other original works) that
has been published by me has been licensed for distribution under
a Creative
Commons License.
Comments to the articles are not covered by this license, they
should be considered normal copyrighted works. Always contact their
authors for more information.
All released code archives, downloadable scripts, etc. should
always be accompanied with a license that indicates if and under
which conditions they can be redistributed.
Layout
The original idea for the old layout of this site (which is still
used in the image pages for
example) is copied from a design on OSWD, called libra.
Among other things I changed it to be XHTML 1.1 compliant and to
make more use of CSS.
Code
The site uses blosxom as if
it were some kind of content management system (CMS). I know it's
not intended to be, but it interacts nicely with my weblog, which is running another instance of
blosxom. They share the content, but for reading older articles
the weblog is more suited. This instance is using some plugins to
generate the content: better_title, gzip, headlines, hide, sitelinks,
theme, writeback, xhtml. All these plugins can be downloaded from
the blosxom website. The theme file is not yet finished, but when
it is I will publish it.
Lychnis
Lychnis is the name of a genus of flowers that are common in
Europe. The image at the top left of the old layout and in the
shortcut icon is a processed image of a lychnis
flos-cuculi L. (ragged robin).
Stats
Website
statistics.
Links

Wanneer gebruik je -d en wanneer gebruik je -t?/meta
Posted on 2005-07-07 by ivo :: /meta :: link
Wanneer gebruik je -d en wanneer gebruik je -t?
Samenvatting
- Tegenwoordige tijd
- ik: alleen de gecorrigeerde stam.
jij/hij/zij: gecorrigeerde stam + t, ook
als de gecorrigeerde stam op een d eindigt.
Als de stam op een t
eindigt komt er geen extra t bij.
- Verleden tijd
- ik/jij/hij/zij: gecorrigeerde stam + -de/-te,
als de stam
eindigt op een van de medeklinkers in "'t kofschip"
(ch telt als een letter): -te, anders -de.
Hele werkwoord
Het hele werkwoord, ofwel infinitief, is de -en
vorm die de handeling
in zijn geheel aangeeft. Voorbeeld: werken, lopen,
verhuizen, gebeuren, geloven.
Stam
De stam van een werkwoord is de belangrijkste
indicator voor welke letter gebruikt moet worden in de
vervoegingen. De stam wordt verkregen door het
onvervoegde werkwoord
te ontdoen van de uitgang -en.
inf.: werken → stam: werk-
inf.: lopen → stam: lop-
inf.: verhuizen → stam: verhuiz-
inf.: gebeuren → stam: gebeur-
inf.: geloven → stam: gelov-
Soms eindigt de stam van een werkwoord op een
klinker, in dat geval staat er vaak alleen een
-n achter de stam.
inf.: doen → stam: doe-
Gecorrigeerde stam
Vaak is het zo dat de stam op zich niet voldoet aan de nederlandse
spellingsregels en dus niet op zichzelf als een woord gebruikt kan worden.
Voordat dat kan, moet hij eerst gecorrigeerd worden. De stam van
lopen bijvoorbeeld is lop-, waarbij de 'o' een lange klank
heeft. Deze stam wordt dan gecorrigeerd door een 'o' toe te voegen: de
gecorrigeerde stam is loop-.
stam: werk- → gec. stam: werk-
stam: verhuiz- → stam: verhuis-
stam: gebeur- → stam: gebeur-
stam: gelov- → stam: geloof-
Tegenwoordige tijd
In de tegenwoordige tijd geldt altijd de volgende
regel voor werkwoorden waarvan de stam niet eindigt op
een t:
| ik | stam |
| jij | stam-t |
| hij/zij | stam-t |
| wij/jullie/zij | hele werkwoord |
Voor de jij/hij/zij-vervoeging komt er dus altijd een
-t achter de stam, nooit een -d.
| infinitief | werken |
|
infinitief | vinden |
|
infinitief | geloven |
| stam | werk- |
|
stam | vind- |
|
stam | gelov- |
| gec. stam | werk- |
|
gec. stam | vind- |
|
gec. stam | geloof- |
| ik | werk |
|
ik | vind |
|
ik | geloof |
| jij | werkt |
|
jij | vindt |
|
jij | gelooft |
| hij/zij | werkt |
|
hij/zij | vindt |
|
hij/zij | gelooft |
| wij/jullie/zij | werken |
|
wij/jullie/zij | vinden |
|
wij/jullie/zij | geloven |
Het kan nodig zijn de uiteindelijke vorm nog te corrigeren, als hij
bijvoorbeeld eindigt op dubbel t.
Uitzondering: als het zinsdeel jij of je direct volgt op het vervoegde werkwoord, dan is de vervoeging stam zonder -t. Dit geldt alleen als je gebruikt wordt als onderwerp van de zin; in alle andere grammaticale functies van je gaat dit niet op. Dit zal alleen verwarrend werken in de gevallen waar je je kunt gebruiken in plaats van een andere vorm (jou, jezelf, jouw, etc.). Als je je kunt vervangen door jij, dan vervalt de -t.
inf.: werken → stam: werk-
Je werkt hard vandaag.
Werk je hard vandaag?
inf.: vinden → stam: vind-
Jij vindt blauw mooi.
Vind jij blauw mooi?
Jij houdt je op de vlakte. (jezelf) → (je is hierin niet het onderwerp van de zin.)
Hij leest je bestand in. (jouw)
Bij werkwoorden waar de stam eindigt op een t
komt er geen extra -t bij.
inf.: liften → stam: lift-
ik lift, jij lift, hij lift
Lift jij wel eens?
Verleden tijd
Verleden tijd: gec. stam-de of gec. stam-te
Voltooid deelwoord: gegec. stam-d of gegec. stam-t
Om te bepalen of in de verleden tijd een -d of een -t gebruikt moet worden,
kijk je naar de klank voor de -en uitgang in het hele werkwoord.
Als die hard is, moet er een -t uitgang komen in de verleden tijd, en anders
-d. De volgende klanken zijn hard: T K F S CH P.
Uit die klanken komt het kofschip ezelsbruggetje. Dit ezelsbruggetje zegt
dat wanneer de ongecorrigeerde stam op een van de letters uit
'T KoFSCHiP eindigt, de verleden tijd -t krijgt, en anders -d. Let goed op
dat je hiervoor de stam neemt, en niet de gecorrigeerde stam; het gaat immers
om de klank voor -en in het hele werkwoord.
inf.: werken → stam: werk-; eindigt
op een harde klank, dus verleden tijd is -t: werkte.
inf.: verhuizen → stam: verhuiz-; eindigt
op een zachte klank, dus verleden tijd is -d: verhuisde.
inf.: geloven → stam: gelov-; eindigt
op een zachte klank, dus verleden tijd is -d: geloofde.
inf.: gebeuren → stam: gebeur-; eindigt
op een zachte klank, dus verleden tijd is -d: gebeurde.
Dan is er nog het voltooid deelwoord, waar exact dezelfde -d/-t regels
voor gelden. Dit wordt gebruikt in zinnen met een vorm van 'zijn' of 'hebben'
en het voltooid deelwoord begint vaak met ge-.
Ik ben verhuisd.
Het is gebeurd.
Jij hebt gewerkt.
Zo kan het dus voorkomen dat er van 1 werkwoord 2 vormen bestaan waartussen
het enige verschil is dat de laatste letter een d of een t is. Toch is het
altijd helemaal duidelijk omschreven welke vorm er gebruikt moet worden.
Het gebeurt. - Tegenwoordige tijd, dus gec. stam
plus -t.
Het is gebeurd. - Voltooid deelwoord, en een -d
uitgang vanwege de zachte klank in het hele werkwoord, dus gec. stam
plus -d.
Coding style guide - C/meta
Posted on 2004-04-26 by ivo :: /meta :: link
This document is Copyright © 2004 Ivo Timmermans. This document is
licensed for distribution under a Creative
Commons License. It is based on Fruit's Source Code Style,
which was licensed under the artistic
license.
<<
Back to coding style index.
- Source file layout
- Line length
- Copyright and license statement
- Preprocessor directives
- Macros
- Comments
- Documentation
- Function definitions
- Declaration
- Placing braces
- Variables
- Naming
- Declarations
- Initialization
- Function body
- Function length
- Using braces
- How to indent
- Using tabs
- When to indent
- Line continuation
- Complex line continuation
- Control line continuation
- Empty lines
- Parentheses
- Using parentheses
- Placing parentheses
- Using spaces
- Typecasts
- Placing assignments
- Boolean expressions
1. Source file layout
1. Line length
Lines may not exceed 78 characters. Do not write
lines that are longer than 78 characters. It is always possible
to wrap lines, and continue on the next line. It should never be
necessary to indent more than about four levels deep. (This
asserts that tabs count as if they were 8 characters.)
2. Copyright and license statement
At the head of each source file there should be a comment, which
mentions the file name, its function in the program, a copyright
and license statement. Always include at least one email address.
Optional extra information, such as CVS Id tags, should follow the
license. For notes on the layout of multiline comments, see below.
/*
* foo.c - Frobnicate the foobar
* Copyright (C) 2004 Ivo Timmermans <ivo@o2w.nl>
*
* License…
*
* $Id: foo.c,v 1.1 2004/01/10 12:34:56 ivo Exp $
*/
Top-level inline documentation should be in a separate comment,
after this one.
3. Preprocessor directives
Simple statements should be like this:
#include <stdio.h>
#define CONSTANT 3
When nesting statements, such as
#ifdefs, put a tab after the # and the
rest of the line. Put a comment after the accompanying
#else and #endif to indicate which block
is terminated.
#ifdef SOMETHING
# ifdef SOMETHINGELSE
# define CONSTANT 4
# endif /* SOMETHINGELSE */
#endif /* SOMETHING */
4. Macros
There is no reason to make macros longer than 78 characters, they
can be wrapped with a backslash at the end of the previous line.
Creating a macro which uses local variables should be avoided, but
if absolutely necessary, wrap the macro in a do {
… } while (0)-loop. Always wrap macro
arguments in parentheses when the expansion could be
ambiguous.
#define MACRO(x, y) do { \
do_something_with(x); \
(y) = (x) << 4; \
} while (0)
5. Comments
Multiline comments should be formatted as follows, so that the
vertical line of asterisks on the left is a clear indication that
it is a comment.
/*
* First paragraph of a multiline comment.
*
* Second paragraph of the comment.
*/
Simple comments following a statement should be separated from
the statement with two spaces. The length of the entire line
should not be more than 78 characters, put the comment on the
preceding line if necessary (but put an empty line before it to
improve readability).
frob(arguments); /* Frobnicate before it's too late! */
/* This comment is too long to fit on the next line. */
r = functioncall(with, arguments);
/*
* Do not read the code below, it is evil.
*
* Actually that's a lie.
*/
do_evil_stuff();
6. Documentation
Documentation for functions can be placed in a header file, along
with their prototype declarations. This information can be
extracted with tools such as doxygen to make nicely
formatted documents; public functions are usually part of an API.
Static functions will of course have their documentation alongside
their definitions.
Comments on the inner workings of a function—for example
the exact algorithm that is used—should be placed inline in
the code, or above it in the source file.
foo.h:
/* Sort list alphabetically, returns the sorted list */
extern list_t *sort_list(const list_t *list);
foo.c:
/*
* Sort list alphabetically, using the modified bubblesort
* algorithm, which is defined in bubblesort.c.
*/
list_t *sort_list(const list_t *list) {
…
}
2. Function definitions
1. Declaration
Everything in the function declaration should be on one line. If
the argument declaration doesn't fit in 78 characters, they should
be separated at the commas. Precede the continuation line with
two tabs (the continuation must not be on the same indentation
level as the function body).
static struct somestruct *function(struct somestruct **argument,
struct someotherstruct *something, int foo, int blargh) {
Of course, if you need a long declaration such as the one above,
you need to start thinking of using typedefs.
If a function takes no arguments, explicitly declare it with
function(void). If a function returns nothing,
explicitly declare it void function(…).
2. Placing braces
Braces are formatted using what looks like K&R style but is
more regular. In particular, braces are put after a
function declaration, not on a line of their own. So:
int main(int argc, char **argv) {
if (foo) {
bar;
}
return 0;
}
3. Variables
1. Naming
Use lowercase names for everything, using underscores if
something needs multiple words. The only exception are
preprocessor constants, which are all uppercase. Short names
avoid tedious typing but do make the names descriptive of their
content. Don't bother reusing local variables; the compiler will
do that for you.
int i, fd, program_path; /* good */
int aFile, temp; /* bad */
Common sense applies: don't use i for storing the
return value of a function, don't use r as a counter.
Never use one variable for two different things.
2. Declarations
When declaring pointers, the asterisk shall be put next to the
variable name, not next to the type name. This is because the
asterisk is part of what is being declared, not of the type
itself. Example:
char *p; /* good, should be read as “the content of p is a character” */
char* q; /* bad, “q is a character content of” */
The virtue of this becomes apparent when you regard:
char* p, q; /* what is the type of q? */
3. Initialization
The machine internal representation of a NULL-pointer does not
have to be all-zeroes (but the C representation is always false).
Thus, do not initialize structures with memset() or bzero():
memset(p, 0, sizeof *p); /* bad */
struct foo p0 = {0};
*p = p0; /* good */
4. Function body
1. Function length
A function should never have to be longer than about 50 lines
(approximately two screenfuls on a standard terminal), including
empty lines and any extra lines that are caused by wrapping. This
excludes any documentation for the function, which should precede
the function declaration. (Sometimes the documentation can be
placed in header files, accompanying the prototype declaration.)
Any function that requires more than 100 lines is probably badly
designed.
2. Using braces
If possible, braces are omitted, except when either part of an
if (…) … else
… uses braces, then the other part will also use
braces:
if (foo) {
bar;
baz;
} else {
quux;
}
When using nested if statements, always put braces
around the inner code blocks, even if the inner if is
the only statement in that block. This means that possible
else-blocks of the outer if also get
wrapped.
if (foo) {
if (bar)
baz;
else
qux;
} else {
quux;
}
do …
while (…)-loops are formatted with
the while on the same line as the closing brace:
do {
statements;
} while (…);
3. How to indent
Indentation is always done using tabs. It is recommended that
the tab length of your editor be set to something more reasonable
than 8. I personally prefer 4, but the pleasant thing about tabs
is that everyone can use their favourite indentation size.
4. Using tabs
Tabs are used only at the beginning of a line. If you
feel a need to align other bits, use spaces. But rather don't
align them at all, unless there's a very
compelling reason to do so.
5. When to indent
Control statements and their body always have lines of
their own, even if they are very short:
if (x)
y();
6. Line continuation
If a line is more than 78 characters long it should really be
broken into bits. Conversely, if a line is shorter, do write it
on a single line. Every line but the first should be given a
single extra tab. If the line is a formula, then the operator at
which you break the line should be the first character of the new
line. Examples:
x = get_foobar(foo, bar, baz) + get_xyzzy(zxnrbl, quux)
+ get_zoo(bear, monkey, lion, penguin) + get_pets(cat, dog)
+ get_colours(red, green, blue, yellow);
7. Complex line continuation
There are two reasons to deviate from this rule: if the formula
is exeptionally complex it may be better to give some parts an
extra tab to show that they are in fact subordinate clauses to the
main formula:
y = a
+ b
+ c1
* c2
* c3
* c4
+ d;
8. Control line continuation
The other reason is when a broken line is a control statement
that is followed by a body:
if (foo + bar + baz
+ quux + xyzzy) /* an extra tab */
zxnrbl();
9. Empty lines
Use empty lines to indicate blocks of code that pertain to a
specific operation, and to separate those that have different
purposes. Always put an empty line after variable declarations
and indented blocks.
void function(void) {
int a, b = 0;
a = do_something();
if (a) {
b = do_something_with_a();
}
do_something_with_a_and_b(a, b);
}
5. Parentheses
1. Using parentheses
If possible parentheses should be omitted, except when this
evokes a warning from the compiler. In particular,
return and sizeof are not
functions!
int x;
x = sizeof x; /* no parentheses here */
return x; /* nor here */
The only reason why sizeof often needs parentheses
is that it is often used with type expressions, which need
parentheses just like they do in typecasts.
2. Placing parentheses
Parentheses always cuddle up to the function they follow, but
there's a space between a control statement (for,
if and while) and the parenthesis
following it. There are no spaces directly after an opening
parenthesis, or directly before a closing parenthesis:
if (foo) /* one space */
bar(); /* no space here */
qux(a + b); /* no spaces inside the parentheses */
There is a space between a control statement and the opening
parenthesis, but not for function calls.
if (foo) /* a space */
bar(4); /* no space */
for (…) { /* a space */
baz(qux); /* no space */
}
3. Using spaces
In formulas be generous with spaces, they make things more
readable:
return x * (a + b) * y;
When writing comma delimited lists, such as in function
arguments, place a space only after each comma.
foo(a, b); /* good */
bar(a,b); /* bad */
bar( a , b ); /* bad */
4. Typecasts
When doing typecasts, put a space between the type and the object
being cast:
int a = (int) p;
Write complex (pointer) types like you would in a
declaration:
struct something **a;
a = (struct something **) p;
6. Placing assignments
Avoid assignments in truth statements—if only because they
often require extra parentheses to avoid compiler warnings.
r = read(fd, buf, sizeof buf);
if (r == -1)
b0rk();
7. Boolean expressions
Use the fact that boolean expressions in C mean testing for
non-zero-ness. In particular, avoid pointless noise like:
if (p != NULL) …
if (i == 0) …
These should be rewritten as:
if (p) …
if (!i) …
… because C already does such a check internally.
<<
Back to coding style index.
Coding style guides/meta
Posted on 2004-03-25 by ivo :: /meta :: link
Below are four coding style guides. They basically document the
style that I like to program in. These will differ from other
people's. They are certainly not prescriptive, only indicative of
what I think yields readable source code for any project,
regardless of whether it has a small or large code base.
Coding style guide - Perl/meta
Posted on 2004-03-25 by ivo :: /meta :: link
The style I like in perl can probably be best represented by the
following perltidy commandline:
perltidy -sbt=2 -bt=2 -bbt=0 -ci=2 -icp -nicb -ibc -hsc -noll
-msc=2 -nsts -nsfs -pt=2 -syn -w -ce -i=8 -t -nbbc -nbbs -nbbb
-nbl -nsbl -bar -dnl
There is more to it, but this will have to do for now. Most of
the principles from the C style guide will apply here, too.
Resume / curriculum vitae/meta
Posted on 2004-03-20 by ivo :: /meta :: link
Curriculum Vitae
Ivo Timmermans
Personal Details
| name |
Ivo Roald Timmermans |
| gender |
male |
| nationality |
Dutch |
| address |
Derde Werelddreef 83, 2622 HC Delft, NL |
| date of birth |
27 September 1977, Utrecht, NL |
| drivers license |
European, Category B; possess a car |
Education
- 1995-2003
- Applied Mathematics at the Delft University of Technology;
stopped in the bachelor stage.
- 1989-1995
- Secondary school at het Utrechts Stedelijk Gymnasium in
Utrecht; subjects passed in final exams: Dutch, Latin,
English, German, physics, math A, math B, chemistry,
biology.
Career Summary
- February 2002 – present
-
Software engineer at Next Element Solution Provider B.V.:
Programming in PHP, Perl, C, C++, Python, SQL; project
management experience.
- November 2001 – January 2002
-
Software engineer at N2IT B.V.: Developing the
FinalScratch software application; C++, GTK, Linux,
realtime audio.
FinalScratch is an application that allows professional
disk jockeys to play digital music (MP3, wav, Ogg Vorbis,
etc) using their existing analog mixing environment.
- June 2000 – October 2001
-
Software engineer at Cistron Internet Services B.V.:
Perl, CGI, Apache, C, PostgreSQL, Linux system
administration.
Mostly developing custom CGI-based applications for
customers or internal use, for example: a product catalog
and online shop for a comics store; a custom content
management system for students.
- March 1999 – September 2000
-
On detachment from Operator Group Delft as system
administrator for a mixed Windows NT and Novell Netware
network at the Thuiszorg Nieuwe Waterweg-Noord in Schiedam
(institution for home care).
Next to everyday administration activities, I helped
migrating a network of about 150 Windows PCs and eight
Novell NetWare 3 servers to 200 PCs and fifteen Novell
NetWare 5.0 servers.
Publications/talks/competitions
- 2000, 2001, 2002, 2003
- Competed in the local (Delft), the Dutch and the Northwest
European rounds of the Intercollegiate Programming Contests
(ICPC).
- November 2001
- Article GNU Emacs als editor (GNU Emacs as editor),
published in the Dutch Linux Magazine.
- May 2001
- Talk High
Availability VPN solutions during the spring
conference of the NLUUG (Dutch UNIX User Group).
- November 2000
- Article Virtual
Private Networks met tinc (Virtual Private Networks with
tinc), published in the Dutch Linux
Magazine.
- August 2000
- Talk Virtual Private Networks, during the
Networking Event 2000.
Cultural Activities
- January 2003 – present
- Learning Aikidou (a Japanese martial art), currently 6th
kyuu level.
- October 2002 – present
- Playing Go (Chinese/Japanese board game), currently about
11th kyuu level.
- October 2000 – present
- Package maintainer for Debian GNU/Linux (responsible for the
quality of about thirty software packages in Debian, helping
with translations to Dutch).
- November 1998 – present
- Coordinator of the Dutch translation team of the Free
Software Foundation.
- September 1998 – present
- Author (later co-author) of tinc, a userspace VPN daemon for
Linux, *BSD, Solaris, Windows, OSX.
- October 1997 – September 2001
- Network administration commission Delftse
Studentenvereniging Sint Jansbrug (student society).
- August 1997 – August 1999
- Member of the Sponsorship Commission in Sint Jansbrug.
- March 1997 – December 1997
- Lustrum Yearbook Commission for Sint Jansbrug (responsible
for sponsoring and layout).
- October 1995 – present
- Member of the Delftse Studentenvereniging Sint Jansbrug
(student society).
Language proficiency
| Language | Reading | Written | Fluency |
| Dutch | native, very well | native, very well | native, very well |
| English | fluent | fluent | fluent |
| Swedish | x | x | x |
| German | x | | |
| French | x | | |
| Japanese | | | |
References
References available on request.
python-gnutls/meta
Posted on 2004-01-25 by ivo :: /meta :: link
python-gnutls provides a set of bindings so that the GnuTLS
library can be used from your python programs. This enables you
to create secure internet sockets, that can serve on either the
server or client side of a connection.
Announcements regarding python-gnutls—information about
new releases, including change logs—are made in a section
on programming in my weblog: python-gnutls.
See that page for the latest release.
For more about GnuTLS, please see their website.
It's very simple to create a secure client socket, it's just two
more calls after your socket is ready. The following example is a
simple relay between the terminal (stdin/stdout) and a remote
host.
import gnutls
import socket
import select
import os
def main():
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(('some-imap-host', some-port))
c = gnutls.client(s)
c.handshake()
ins = os.fdopen(0, "r", 0)
loop = True
while loop:
readers, writers, errors = select.select([ins, s], [], [])
if len(readers):
for r in readers:
if r == ins:
text = ins.read(1)
if text:
c.send(text)
else:
c.shutdown(gnutls.SHUT_WR)
loop = False
else:
text = c.recv(1000)
if text:
sys.stdout.write(text)
else:
loop = False
del c
s.close()
if __name__ == '__main__':
main()
An example output, when communicating with an IMAPS
server (lines wrapped for display purposes; blue text is typed in stdin):
> python simpleclient.py
* OK [CAPABILITY IMAP4rev1 CHILDREN NAMESPACE THREAD=ORDEREDSUBJECT
THREAD=REFERENCES SORT QUOTA AUTH=PLAIN] Courier-IMAP ready.
Copyright 1998-2003 Double Precision, Inc. See COPYING for
distribution information.
A LOGOUT
* BYE Courier-IMAP server shutting down
A OK LOGOUT completed
Debian GNU/Linux/meta
Posted on 2004-01-19 by ivo :: /meta :: link
Debian GNU/Linux is a Linux
distribution. Worldwide, about one thousand people work together
to make a high-quality free
operating system. Read more about
Debian.
Unofficial Debian packages
My own apt-get-able
repository of unofficial Debian packages. Read
more about its contents, and how to use it.
Planet Debian
The /debian
tree of my weblog is part of Planet Debian, a collection
of the weblogs of several Debian developers.
My work in Debian
I am responsible for the quality of several packages in Debian.
To see which packages they are, have a look at the list of
packages and related info.
To see the state these packages are in, have a look at the outstanding
bugreports against my packages.
Coding style guide - Python/meta
Posted on 2004-01-13 by ivo :: /meta :: link
This document is Copyright © 2004 Ivo Timmermans. This document is
licensed for distribution under a Creative
Commons License. It is based on Style guide for
python code, which was put in the public domain.
Introduction
This document gives coding conventions for the Python code
comprising the standard library for the main Python distribution.
Please see the companion informational PEP describing style
guidelines for the C code in the C implementation of
Python[1].
This document was adapted from Guido's original Python Style
Guide essay[2], with some additions from Barry's style guide[5].
Where there's conflict, Guido's style rules for the purposes of
this PEP. This PEP may still be incomplete (in fact, it may never
be finished <wink>).
A Foolish Consistency is the Hobgoblin of Little Minds
A style guide is about consistency. Consistency with this style
guide is important. Consistency within a project is more
important. Consistency within one module or function is most
important.
But most importantly: know when to be inconsistent —
sometimes the style guide just doesn't apply. When in doubt, use
your best judgement. Look at other examples and decide what looks
best. And don't hesitate to ask!
Two good reasons to break a particular rule:
- When applying the rule would make the code less readable, even
for someone who is used to reading code that follows the
rules.
- To be consistent with surrounding code that also breaks it
(maybe for historic reasons) — although this is also an
opportunity to clean up someone else's mess (in true XP
style).
Code lay-out
Indentation
Use the default of Emacs' Python-mode: 4 spaces for one
indentation level. For really old code that you don't want to
mess up, you can continue to use 8-space tabs. Emacs Python-mode
auto-detects the prevailing indentation level used in a file and
sets its indentation parameters accordingly.
Tabs or Spaces?
Never mix tabs and spaces. The most popular way of indenting
Python is with spaces only. The second-most popular way is with
tabs only. Code indented with a mixture of tabs and spaces should
be converted to using spaces exclusively. (In Emacs, select the
whole buffer and hit ESC-x untabify.) When invoking the python
command line interpreter with the -t option, it issues warnings
about code that illegally mixes tabs and spaces. When using -tt
these warnings become errors. These options are highly
recommended!
For new projects, spaces-only are strongly recommended over tabs.
Most editors have features that make this easy to do. (In Emacs,
make sure indent-tabs-mode is nil).
Maximum Line Length
There are still many devices around that are limited to 80
character lines; plus, limiting windows to 80 characters makes it
possible to have several windows side-by-side. The default
wrapping on such devices looks ugly. Therefore, please limit all
lines to a maximum of 79 characters (Emacs wraps lines that are
exactly 80 characters long). For flowing long blocks of text
(docstrings or comments), limiting the length to 72 characters is
recommended.
The preferred way of wrapping long lines is by using Python's
implied line continuation inside parentheses, brackets and braces.
If necessary, you can add an extra pair of parentheses around an
expression, but sometimes using a backslash looks better. Make
sure to indent the continued line appropriately. Emacs
Python-mode does this right. Some examples:
class Rectangle(Blob):
def __init__(self, width, height,
color='black', emphasis=None, highlight=0):
if width == 0 and height == 0 and \
color == 'red' and emphasis == 'strong' or \
highlight > 100:
raise ValueError, "sorry, you lose"
if width == 0 and height == 0 and (color == 'red' or
emphasis is None):
raise ValueError, "I don't think so"
Blob.__init__(self, width, height,
color, emphasis, highlight)
Blank Lines
Separate top-level function and class definitions with two blank
lines. Method definitions inside a class are separated by a
single blank line. Extra blank lines may be used (sparingly) to
separate groups of related functions. Blank lines may be omitted
between a bunch of related one-liners (e.g. a set of dummy
implementations).
When blank lines are used to separate method definitions, there
is also a blank line between the `class' line and the
first method definition.
Use blank lines in functions, sparingly, to indicate logical
sections.
Python accepts the control-L (i.e. ^L) form feed character as
whitespace; Emacs (and some printing tools) treat these characters
as page separators, so you may use them to separate pages of
related sections of your file.
Encodings (PEP 263)
Code in the core Python distribution should aways use the ASCII
or Latin-1 encoding (a.k.a. ISO-8859-1). Files using ASCII should
not have a coding cookie. Latin-1 should only be used when a
comment or docstring needs to mention an author name that requires
Latin-1; otherwise, using \x escapes is the preferred way to
include non-ASCII data in string literals. An exception is made
for those files that are part of the test suite for the code
implementing PEP 263.
Imports
-
Imports should usually be on separate lines, e.g.:
No: import sys, os
Yes: import sys
import os
it's okay to say this though:
from types import StringType, ListType
-
Imports are always put at the top of the file, just after any
module comments and docstrings, and before module globals and
constants. Imports should be grouped, with the order being
- standard library imports
- related major package imports (i.e. all email package
imports next)
- application specific imports
You should put a blank line between each group of
imports.
-
Relative imports for intra-package imports are highly
discouraged. Always use the absolute package path for all
imports.
-
When importing a class from a class-containing module, it's
usually okay to spell this
from MyClass import MyClass
from foo.bar.YourClass import YourClass
If this spelling causes local name clashes, then spell
them
import MyClass
import foo.bar.YourClass
and use "MyClass.MyClass" and
"foo.bar.YourClass.YourClass"
Whitespace in Expressions and Statements
Pet Peeves
Guido hates whitespace in the following places:
- Immediately inside parentheses, brackets or braces, as in:
"
spam( ham[ 1 ], { eggs: 2 } )". Always write this
as "spam(ham[1], {eggs: 2})".
- Immediately before a comma, semicolon, or colon, as in:
"
if x == 4 : print x , y ; x , y = y , x". Always
write this as "if x == 4: print x, y; x, y = y,
x".
- Immediately before the open parenthesis that starts the
argument list of a function call, as in "
spam (1)".
Always write this as "spam(1)".
- Immediately before the open parenthesis that starts an
indexing or slicing, as in: "
dict ['key'] = list
[index]". Always write this as "dict['key'] =
list[index]".
-
More than one space around an assignment (or other) operator
to align it with another, as in:
x = 1
y = 2
long_variable = 3
Always write this as
x = 1
y = 2
long_variable = 3
(Don't bother to argue with him on any of the above —
Guido's grown accustomed to this style over 20 years.)
Other Recommendations
- Always surround these binary operators with a single space on
either side: assignment (
=), comparisons
(==, <, >,
!=, <>, <=,
>=, in, not in,
is, is not), Booleans
(and, or, not).
-
Use your better judgment for the insertion of spaces around
arithmetic operators. Always be consistent about whitespace
on either side of a binary operator. Some examples:
i = i+1
submitted = submitted + 1
x = x*2 - 1
hypot2 = x*x + y*y
c = (a+b) * (a-b)
c = (a + b) * (a - b)
-
Don't use spaces around the '=' sign when used
to indicate a keyword argument or a default parameter value.
For instance:
def complex(real, imag=0.0):
return magic(r=real, i=imag)
-
Compound statements (multiple statements on the same line)
are generally discouraged.
No: if foo == 'blah': do_blah_thing()
Yes: if foo == 'blah':
do_blah_thing()
No: do_one(); do_two(); do_three()
Yes: do_one()
do_two()
do_three()
Comments
Comments that contradict the code are worse than no comments.
Always make a priority of keeping the comments up-to-date when the
code changes!
Comments should be complete sentences. If a comment is a phrase
or sentence, its first word should be capitalized, unless it is an
identifier that begins with a lower case letter (never alter the
case of identifiers!).
If a comment is short, the period at the end is best omitted.
Block comments generally consist of one or more paragraphs built
out of complete sentences, and each sentence should end in a
period.
You should use two spaces after a sentence-ending period, since
it makes Emacs wrapping and filling work consistenty.
When writing English, Strunk and White apply.
Python coders from non-English speaking countries: please write
your comments in English, unless you are 120% sure that the code
will never be read by people who don't speak your language.
Block Comments
Block comments generally apply to some (or all) code that follows
them, and are indented to the same level as that code. Each line
of a block comment starts with a # and a single space
(unless it is indented text inside the comment). Paragraphs
inside a block comment are separated by a line containing a single
#. Block comments are best surrounded by a blank
line above and below them (or two lines above and a single line
below for a block comment at the start of a a new section of
function definitions).
Inline Comments
An inline comment is a comment on the same line as a statement.
Inline comments should be used sparingly. Inline comments should
be separated by at least two spaces from the statement. They
should start with a # and a single space.
Inline comments are unnecessary and in fact distracting if they
state the obvious. Don't do this:
x = x + 1 # Increment x
But sometimes, this is useful:
x = x + 1 # Compensate for border
Documentation Strings
Conventions for writing good documentation strings
(a.k.a. "docstrings") are immortalized in PEP 257 [3].
- Write docstrings for all public modules, functions, classes,
and methods. Docstrings are not necessary for non-public
methods, but you should have a comment that describes what the
method does. This comment should appear after the
"
def" line.
-
PEP 257 describes good docstring conventions. Note that most
importantly, the """ that ends a multiline
docstring should be on a line by itself, e.g.:
"""Return a foobang
Optional plotz says to frobnicate the bizbaz first.
"""
- For one liner docstrings, it's okay to keep the closing
""" on the same line.
Version Bookkeeping
If you have to have RCS or CVS crud in your source file, do it as
follows.
__version__ = "$Revision: 1.2 $"
# $Source: /home/cvs/ivo/blosxom-content/content/meta/coding-style-python.txt,v $
These lines should be included after the module's docstring,
before any other code, separated by a blank line above and
below.
Naming Conventions
The naming conventions of Python's library are a bit of a mess,
so we'll never get this completely consistent —
nevertheless, here are some guidelines.
Descriptive: Naming Styles
There are a lot of different naming styles. It helps to be able
to recognize what naming style is being used, independently from
what they are used for.
The following naming styles are commonly distinguished:
- x (single lowercase letter)
- X (single uppercase letter)
- lowercase
- lower_case_with_underscores
- UPPERCASE
- UPPER_CASE_WITH_UNDERSCORES
- CapitalizedWords (or CapWords, or CamelCase — so named
because of the bumpy look of its letters[4])
- mixedCase (differs from CapitalizedWords by initial lowercase
character!)
- Capitalized_Words_With_Underscores (ugly!)
There's also the style of using a short unique prefix to group
related names together. This is not used much in Python, but it
is mentioned for completeness. For example, the
os.stat() function returns a tuple whose items
traditionally have names like st_mode,
st_size, st_mtime and so on. The X11
library uses a leading X for all its public functions. (In
Python, this style is generally deemed unnecessary because
attribute and method names are prefixed with an object, and
function names are prefixed with a module name.)
In addition, the following special forms using leading or
trailing underscores are recognized (these can generally be
combined with any case convention):
- _single_leading_underscore: weak "internal use" indicator
(e.g. "
from M import *" does not import objects
whose name starts with an underscore).
- single_trailing_underscore_: used by convention to avoid
conflicts with Python keyword, e.g.
"
Tkinter.Toplevel(master,
class_='ClassName')".
- __double_leading_underscore: class-private names as of Python
1.4.
- __double_leading_and_trailing_underscore__: "magic" objects or
attributes that live in user-controlled namespaces,
e.g.
__init__, __import__ or
__file__. Sometimes these are defined by the user
to trigger certain magic behavior (e.g. operator overloading);
sometimes these are inserted by the infrastructure for its own
use or for debugging purposes. Since the infrastructure
(loosely defined as the Python interpreter and the standard
library) may decide to grow its list of magic attributes in
future versions, user code should generally refrain from using
this convention for its own use. User code that aspires to
become part of the infrastructure could combine this with a
short prefix inside the underscores,
e.g. __bobo_magic_attr__.
Prescriptive: Naming Conventions
Names to Avoid
Never use the characters `l' (lowercase letter el), `O'
(uppercase letter oh), or `I' (uppercase letter eye) as single
character variable names. In some fonts, these characters are
indistinguisable from the numerals one and zero. When tempted to
use `l' use `L' instead.
Module Names
Module names can be either CapWords or lowercase. There is no
unambiguous convention to decide which to use. Modules that
export a single class (or a number of closely related classes,
plus some additional support) are often named in CapWords, with
the module name being the same as the class name (e.g. the
standard StringIO module). Modules that export a bunch of
functions are usually named in all lowercase.
Since module names are mapped to file names, and some file
systems are case insensitive and truncate long names, it is
important that module names be chosen to be fairly short and not
in conflict with other module names that only differ in the case
— this won't be a problem on Unix, but it may be a problem
when the code is transported to Mac or Windows.
There is an emerging convention that when an extension module
written in C or C++ has an accompanying Python module that
provides a higher level (e.g. more object oriented) interface, the
Python module's name CapWords, while the C/C++ module is named in
all lowercase and has a leading underscore (e.g. _socket).
Python packages generally have a short all lowercase name.
Class Names
Almost without exception, class names use the CapWords
convention. Classes for internal use have a leading underscore in
addition.
Exception Names
If a module defines a single exception raised for all sorts of
conditions, it is generally called "error" or
"Error". It seems that built-in (extension) modules
use "error" (e.g. os.error), while
Python modules generally use "Error"
(e.g. xdrlib.Error). The trend seems to be toward
CapWords exception names.
Function Names
Plain functions exported by a module can either use the CapWords
style or lowercase (or lower_case_with_underscores). There is no
strong preference, but it seems that the CapWords style is used
for functions that provide major functionality
(e.g. nstools.WorldOpen()), while lowercase is used more for
"utility" functions (e.g. pathhack.kos_root()).
Global Variable Names
(Let's hope that these variables are meant for use inside one
module only.) The conventions are about the same as those for
exported functions. Modules that are designed for use via
"from M import *" should prefix their globals (and
internal functions and classes) with an underscore to prevent
exporting them.
Method Names
The story is largely the same as for functions. Use lowercase
for methods accessed by other classes or functions that are part
of the implementation of an object type. Use one leading
underscore for "internal" methods and instance variables when
there is no chance of a conflict with subclass or superclass
attributes or when a subclass might actually need access to them.
Use two leading underscores (class-private names, enforced by
Python 1.4) in those cases where it is important that only the
current class accesses an attribute. (But realize that Python
contains enough loopholes so that an insistent user could gain
access nevertheless, e.g. via the __dict__
attribute.)
Designing for inheritance
Always decide whether a class's methods and instance variables
should be public or non-public. In general, never make data
variables public unless you're implementing essentially a record.
It's almost always preferrable to give a functional interface to
your class instead (and some Python 2.2 developments will make
this much nicer).
Also decide whether your attributes should be private or not.
The difference between private and non-public is that the former
will never be useful for a derived class, while the latter might
be. Yes, you should design your classes with inheritence in
mind!
Private attributes should have two leading underscores, no
trailing underscores.
Non-public attributes should have a single leading underscore, no
trailing underscores.
Public attributes should have no leading or trailing underscores,
unless they conflict with reserved words, in which case, a single
trailing underscore is preferrable to a leading one, or a
corrupted spelling, e.g. class_ rather than
klass. (This last point is a bit controversial; if
you prefer klass over class_ then just
be consistent. :).
Programming Recommendations
- Comparisons to singletons like None should always be done with
'
is' or 'is not'. Also, beware of
writing "if x" when you really mean "if x is
not None" — e.g. when testing whether a variable
or argument that defaults to None was set to some other value.
The other value might be a value that's false in a Boolean
context!
-
Class-based exceptions are always preferred over string-based
exceptions. Modules or packages should define their own
domain-specific base exception class, which should be
subclassed from the built-in Exception class. Always include
a class docstring. E.g.:
class MessageError(Exception):
"""Base class for errors in the email package."""
- Use string methods instead of the string module unless
backward-compatibility with versions earlier than Python 2.0 is
important. String methods are always much faster and share the
same API with unicode strings.
-
Avoid slicing strings when checking for prefixes or suffixes.
Use startswith() and endswith()
instead, since they are cleaner and less error prone. For
example:
No: if foo[:3] == 'bar':
Yes: if foo.startswith('bar'):
The exception is if your code must work with Python 1.5.2
(but let's hope not!).
-
Object type comparisons should always use
isinstance() instead of comparing types directly.
E.g.
No: if type(obj) is type(1):
Yes: if isinstance(obj, int):
When checking if an object is a string, keep in mind that it
might be a unicode string too! In Python 2.3, str and unicode
have a common base class, basestring, so you can do:
if isinstance(obj, basestring):
In Python 2.2, the types module has the StringTypes type
defined for that purpose, e.g.:
from types import StringTypes
if isinstance(obj, StringTypes):
In Python 2.0 and 2.1, you should do:
from types import StringType, UnicodeType
if isinstance(obj, StringType) or \
isinstance(obj, UnicodeType) :
- For sequences, (strings, lists, tuples), use the fact that
empty sequences are false, so "
if not seq" or
"if seq" is preferable to "if
len(seq)" or "if not len(seq)".
- Don't write string literals that rely on significant trailing
whitespace. Such trailing whitespace is visually
indistinguishable and some editors (or more recently,
reindent.py) will trim them.
-
Don't compare boolean values to True or
False using == (bool types are new
in Python 2.3):
No: if greeting == True:
Yes: if greeting:
References
[1] PEP 7, Style Guide for C Code, van Rossum
[2] http://www.python.org/doc/essays/styleguide.html
[3] PEP 257, Docstring Conventions, Goodger, van Rossum
[4] http://www.wikipedia.com/wiki/CamelCase
[5] Barry's GNU Mailman/mimelib style guide
http://cvs.sourceforge.net/cgi-bin/viewcvs.cgi/mimelib/mimelib/STYLEGUIDE.txt?rev=1.1&content-type=text/vnd.viewcvs-markup
Debian packages/meta
Posted on 2004-01-11 by ivo :: /meta :: link
This is my personal repository of Debian packages. Some of these
packages have newer versions available in the official Debian
archive. Some of these packages are badly broken. In any case, do
not report bugs about these packages to the BTS, instead, send me
an email (ivo@debian.org) if
you encounter any problems.
The packages in the stable part of the repository are mostly
backports of packages from unstable.
These packages are apt-gettable; just put these lines in your
/etc/apt/sources.list:
Unstable
deb http://home.o2w.net/~ivo/debian unstable/$(ARCH)/
deb http://home.o2w.net/~ivo/debian unstable/all/
deb-src http://home.o2w.net/~ivo/debian unstable/source/
Testing
deb http://home.o2w.net/~ivo/debian testing/$(ARCH)/
deb http://home.o2w.net/~ivo/debian testing/all/
deb-src http://home.o2w.net/~ivo/debian testing/source/
Stable
deb http://home.o2w.net/~ivo/debian stable/$(ARCH)/
deb http://home.o2w.net/~ivo/debian stable/all/
deb-src http://home.o2w.net/~ivo/debian stable/source/
Browse
To browse the directories and download what you need by hand:
Note: Although it says $(ARCH) in the URIs above, only i386 is
really supported, it is my main development platform. Sometimes I
do uploads for other architectures, mainly sparc.