Skip to content


Got to love the open source communities…

Hanging around in #coreboot@irc.freenode.net recently, this just passed by:

15:28  <eikke> is it possible in linux to access partitions in an losetup’ed raw image?
15:29  <carldani>  eikke: yes, I wrote a kernel patch for that
15:29  <eikke> ah, patch :p i did it using –offset now, but thats kinda hackish
15:29  <carldani>  eikke: the easiest way is to use kpartx
15:29  <carldani>  eikke: that was impossible back then
15:30  <eikke> i see
15:30  <carldani>  eikke: kpartx -a /dev/loop0
15:30  <carldani>  eikke: that will give you /dev/mapper/loop0p1 /dev/mapper/loop0p5 etc
15:30  <eikke> cool
15:30  <carldani>  eikke: are you the eikke responsible for ivman?
15:31  <eikke> a long time ago, yes
15:31  <eikke> dont start the flames please :p
15:31  <carldani>  eikke: thanks! I’m still using it on my laptop

A helps out B, B helps out A, A writes something useful for B, B wrote something used by A, etc. Got to love the open source movement.

Posted in Development. Tagged with .

Python gotcha

Don’t ever do this unless it’s really what you want:

import os

def some_func(fd):
    f = os.fdopen(fd, 'w')
    f.write('abc')

fd = get_some_fd()
some_func(fd)
some_other_func(fd)

Here’s what goes wrong: when some_func comes to an end, f (which is a file-like objects) goes out of scope, is destructed, which causes fd to be closed. I think this is pretty weird behavior (an object closing an fd it didn’t open itself), but well.

Here’s a better version, for reference:

def some_func(fd):
    f = os.fdopen(os.dup(fd), 'w')
    #Use f here

Try this on fd 0/1/2 in an (I)Python shell ;-)

Posted in Development. Tagged with .

Scripting your app

Lots of buzz on adding scripting interfaces to applications on Planet GNOME recently, cool. Looks like Alexander Larsson hacked together a wrapper around SpiderMonkey (the Mozilla Engine) to get JavaScript integrated. Related to the jscore-python thing I blogged about before.

Not sure this is the best way to tackle this cool new opportunity though. JavaScript can be pretty hard to “get” for people not used to it, but more familiar with classical languages (wrt object oriented paradigms). I guess lots of current code contributors are not very familiar with JavaScript, but do have an in-depth knowledge of some other scripting language though (not listing any here, you certainly can name some).

So, wouldn’t it be nice if the GScript interface would be abstract for the application developer, who should just create a script context, put some objects in it, and launch a script, after which the GScript runtime figures out which interpreter to use for this script, so scripting languages become plugable?

Reminds me a little of my old OPluginManager work :-)

Posted in Desktop, Development. Tagged with , , .

Embedding JavaScript in Python

Reading some posts about embedding languages/runtimes in applications on Planet GNOME reminded me I still had to announce some really quick and incomplete code blob I created some days after last GUADEC edition (which was insanely cool, thanks guys).

It takes WebKit’s JavaScriptCore and allows you to embed it in some Python program, so you, as a Python developer, can allow consumers to write plugins using JavaScript. Don’t ask me whether it’s useful, maybe it’s not, but anyway.

There’s one catch: currently there is no support to expose custom Python objects to the JavaScript runtime: you’re able to use JavaScript objects and functions etc. from within Python, but not the other way around. I started working on this, but the JSCore API lacked some stuff to be able to implement this cleanly (or I missed a part of it, that’s possible as well), maybe it has changed by now… There is transparent translation of JavaScript base types: unicode strings, booleans, null (which becomes None in Python), undefined (which becomes jscore.UNDEFINED) and floats.

I did not work on the code for quite a long time because of too much real-job-work, maybe it no longer compiles, sorry… Anyway, it’s available in git here, patches welcome etc. I guess this is the best sample code around. It’s using Cython for compilation (never tried with Pyrex, although this might work as well). If anyone can use it, great, if not, too bad, I did learn Cython doing this ;-)

Posted in Development, Linux. Tagged with , , , .

Free Software startups

At GUADEC last days, fun times. One thing I noticed (again) is the growth of the number of small companies, some of them driven by young guys (like, between 25 and 30) doing some really great stuff with Free Software, combining a steady income, whilst still providing valuable contributions to the community.

I’d want to write more about this seen, but here’s a quick idea: how about creating a mailing list for, at one side, these young startups or people interested in starting one, and on the other side people who already got their business running, or already established investors or managers, to discuss issues they encounter, potential business plans, how to get in contact with potential customers, how to combine open communication at one side and dealing with closed environments on the other,…

This could lower the barrier for people to start working full-time on the projects they love, it’d add value to Free Software because larger companies can start using it even more, because more expertise and consultancy is available on the market,…

I guess this is just a shot in the dark, but I think it could be pretty useful. Thoughts?

Posted in Technology.

GUADEC

Leaving for GUADEC ‘08 with RubenV tomorrow. We’re staying in the Golden Horn Sultanahmet hotel. Packing starts in a minute, see you around.

Posted in Various. Tagged with , .

Python ‘all’ odity

[update] Question solved, see bottom of post.

Since Python 2.5 the language got a new built-in method ‘all’ (and it’s nephew ‘any’). I wanted to play around with this a little, combined with generators, so I created a little testcase to test performance.

Here’s the test-case: take a list L of X random numbers in a given range [A, B], and check whether

  • all elements in L are >= A
  • all elements in L are >= (A + Z) where Z is a number in [0, (B - A)]

The first test should always result True, the second test could result to False.

Here’s the output of a test-run:

In [1]: import random, sys

In [2]: a = [random.randint(100, sys.maxint) for i in xrange(2000000)]

In [3]: len(a)
Out[3]: 2000000

In [4]: #Check whether all elements are >= 100 

In [5]: %timeit all(i >= 100 for i in a)
10 loops, best of 3: 515 ms per loop

In [6]: %timeit any(i < 100 for i in a)
10 loops, best of 3: 454 ms per loop

In [7]: def f(l):
   ...:     for i in l:
   ...:         if i < 100:
   ...:             return False
   ...:     return True
   ...: 

In [8]: %timeit f(a)
10 loops, best of 3: 292 ms per loop

In [9]: #Same thing for 100000, since now the list shouldn't be completely iterated

In [10]: %timeit all(i >= 100000 for i in a)
100 loops, best of 3: 4.73 ms per loop

In [11]: %timeit any(i < 100000 for i in a)
100 loops, best of 3: 4.29 ms per loop

In [12]: def g(l):
   ....:     for i in l:
   ....:         if i < 100000:
   ....:             return False
   ....:     return True
   ....: 

In [13]: %timeit g(a)
100 loops, best of 3: 2.82 ms per loop

In [14]: #For reference

In [15]: %timeit False in (i >= 100 for i in a)
10 loops, best of 3: 531 ms per loop

In [16]: %timeit False in (i >= 100000 for i in a)
100 loops, best of 3: 5.03 ms per loop

It’s as if ‘all’, ‘any’ or ‘in’ don’t break/return when a first occurence of False (or True, obviously) is found. Is this the desired behaviour, and if it is, why? The calculation time difference between using all/any/in or a custom-made function (which is, unlike all etc, not written in C) which breaks whenever it can, is pretty astonishing.

[update] Question solved. It’s pretty normal the function-based approach performs better, since it combines what ‘all’ and the generator provided to ‘all’ do, taking away the generator function-call overhead. Damn :-)

Posted in Development. Tagged with , .

Python if/else in lambda

Scott, in your “Functional Python” introduction you write:

The one limitation that most disappoints me is that Python lacks is a functional way of writing if/else. Sometimes you just want to do something like this:

lambda x : if_else(x>100, “big number”, “little number”)

(This would return the string “big number” if x was greater than 100, and “little number” otherwise.) Sometimes I get around this by defining my own if_else that I can use in lambda-functions:

def if_else(condition, a, b) :
   if condition : return a
   else         : return b

Actually, you don’t need this helper if_else function at all:

In [1]: f = lambda x: x > 100 and 'big' or 'small'
In [2]: for i in (1, 10, 99, 100, 101, 110):
...:     print i, 'is', f(i)
...:
1 is small
10 is small
99 is small
100 is small
101 is big
110 is big

James, obviously you’re right… Stupid me didn’t think about that. Your version won’t work when a discriminator isn’t known at import time. But even then a function taking *args and **kwargs with a class-like name, returning a correct class instance, would cut the job.

Regarding the module/plugin stuff, I’d rather use setuptools/pkg_resources :-)

Posted in Development. Tagged with , .

Code Review comic

OSNews: WTFs per minute

I just love this comic.

Posted in Development. Tagged with .

Python factory-like type instances

When designing applications or libraries, sometimes you need to be able to create instances of a certain interface (in a liberal sense) at runtime without knowing at write/compile time which specific implementation (class) you’ll need to use, as this could depend on runtime variables.

An example of this is an interface providing some functionality which should be implemented differently on different platforms, eg Linux and Windows.

There are some standard patterns how to achieve this. One of them is the factory pattern, which works somewhat like this Python example (let’s pretend ‘PLATFORM’ is ‘linux2′ or ‘win32′, ie sys.platform):

#Pretend we use sys.platform instead of PLATFORM where we use it
PLATFORM = 'linux2'

class FooBase(object):
    def say_foo(self):
        print 'foo'

class PlatformFoo(FooBase):
    def say_platform_foo(self):
        raise NotImplementedError

    @staticmethod
    def get_class():
        #Several ways to get this (dict, introspection, if-tree,...), pick yours
        klass = {
            'linux2': LinuxFoo,
            'win32': WindowsFoo,
        }.get(PLATFORM, None)
        if not klass:
            raise Exception, 'Platform not supported'
        return klass

class WindowsFoo(PlatformFoo):
    def say_platform_foo(self):
        print 'win32 foo'

class LinuxFoo(PlatformFoo):
    def say_platform_foo(self):
        print 'linux foo'

def main():
    foo_class = PlatformFoo.get_class()
    foo = foo_class()
    foo.say_platform_foo()

if __name__ == '__main__':
    main()

Executing this code will, as expected, write ‘linux foo’ to the console. Obviously we could not return the platform-specific class in a PlatformFoo function, but an actual instance, up to you.

Python allows you to handle this situation somewhat nicer though, without introducing any intermediate functions, by using metaclasses.

Continued…

Posted in Development, Technology. Tagged with , .