Stories
Slash Boxes
Comments
NOTE: use Perl; is on undef hiatus. You can read content, but you can't post it. More info will be forthcoming forthcomingly.

All the Perl that's Practical to Extract and Report

use Perl Log In

Log In

[ Create a new account ]

doubi (9222)

doubi
  (email not shown publicly)

Journal of doubi (9222)

Tuesday July 20, 2010
01:04 PM

Thoughts on a Ctypes::Type object API

[ #40454 ]

For the past few days I've been considering and experimenting with the design of simple Ctypes::Type objects. These are objects which, funnily enough, represent C data types for manipulation in Perl.

The reference implementation

Looking at the Python ctypes module, there were various things I didn't like. Python's simple types [0] can be summarized thusly:

>>> i = c_int(42)
>>> print i
c_long(42)
>>> print i.value
42
>>> i.value = -99
>>> print i.value
-99
>>>

Having to specify i.value seemed cumbersome for an object which essentially represents just that value and some rules for what kinds of values it can contain. So I started trying various things with tie'ing and overloading. Indeed, I was about to start a fourth project branch on types [1] before reigning in and having another think about fundamental behaviour.

Metaphor clash

The 'Metaphor Clash' section [2] of perldoc overload made clear the difficulty I was having with my thinking. If you want to be able to say simply,

$int_obj = 42;        # assign new value to Ctypes::Type::c_int object

and not have $int_obj smushed and replaced by a simple IV, you're forced to do something like,

$other_obj = $int_obj->copy();

on those occasions when that's the outcome you really want. That might not be regular for objects in Perl, but I think that this is more suitable in this domain, where as I mentioned before, objects are just there to represent special kinds of values. Particularly, it would let you do this:

$c_int = $c_long;        # Put long value into integer type, with
                         # appropriate checking on STORE

rather than having to say

$c_int->val = $c_long->val;

Normal usage

I think that once you've instantiated a Ctypes::Type object, what you're going to be doing 90% of the time is assigning values to it or assigning its value to other things. The times when you want to squash the object with a different object or value, instead of just creating a new one, will be rare, and there can be special methods for doing those things.

What do you think? Is this a reasonable generalisation to make? How would you like Type objects to work?

Other issues

There are a couple of other issues tangential to this which I'd like to flag up while we're at it...

  • The latter behaviour, while IMO preferable, will I think be harder to implement. I haven't yet found a way using only Perl to hide the process of tie'ing a variable from the user. This is horrible:

    my $int = 5;    # regular scalar
    c_int(\$int);    # make it a Ctypes::Type

    but it's one of the only ways to enable the assignment of new values to the object without using an accessor every time (the other way is returning a reference from c_int() and requiring users to say $$int all the time). I think the desired effect would be possible, but c_int() will have to be written in XS. That's fine, but I want to sound out opinions on whether I'm making the right choices on functionality first.

  • The latter behaviour, while IMO better than that in Python's ctypes, may represent a significant difference from the de facto 'conventional' way of doing things. This raises a bunch of issues to be addressed in a subsequent post.

Please do let me know what you think of the above proposals. I'm highly suggestible.

[0] http://docs.python.org/library/ctypes.html#fundamental-data-types
[1] http://gitorious.org/perl-ctypes/perl-ctypes
[2] http://perldoc.perl.org/overload.html#Metaphor-clash

The Fine Print: The following comments are owned by whoever posted them. We are not responsible for them in any way.
 Full
 Abbreviated
 Hidden
More | Login | Reply
Loading... please wait.