Automated UI testing for Symbian – capturing visual output

Automated UI testing is annoying in general and Symbian doesn’t really provide anything to make it easier. There are many aspects to testing UIs, but one is testing the actual drawing and layout. A necessary conditions for such tests is the ability to exercise drawing code and capture the drawn output in a test.

Symbian programming – automated UI tests shows how to create a fully functioning application environment – CAknEnv (CEikonEnv), CAknAppUi (CEikAppUi) – in your unit test so that you can instantiate a CCoeControl-derived class and how to capture the control’s output to a bitmap and from there into a file.

Posted in Symbian | Comments Off

A Forum Nokia Champion once again

I was one of the very first round of Forum Nokia Champions in 2006. Last year (in the autumn of 2008) I was not re-selected, which is pretty understandable as I had not done anything externally visible since joining Google at that point.

Since then we actually launched Google Latitude and open sourced the Jaiku S60 client which were enough to win membership once again.

Posted in Symbian | 1 Comment

Symbian programming pages updated for 3rd edition

I finally updated the Symbian Programming pages for 3rd edition. The major update is that the source code pointers now point at the Jaiku S60 client (rather than the old ContextPhone sources), which is fully ported to 3rd ed.

After all the griping over the years I have to admit that things have gotten significantly better. Most of the article updates consisted of adding ‘This is now a documented and supported platform feature, see this [Forum Nokia wiki page]‘. Which is neat.

Posted in Symbian | Comments Off

Fighting my way through WINSCW builds

I’ve been trying to set up a reasonable build environment with scons-for-symbian (huge thanks to Jussi Toivola for that) where I can get unit tests running quick enough.

If you ever do something wrong with the builds you are truly on your own. These are the errors from yesterday and today:

-1 on application start after hitting E32Main: wrong uid in exe vs. resource file (I _did_ have the correct uid in the SConstruct but it was not quoted and somehow that dropped the last digit from it – need to see if I can fix that)

-20 on exe start: linked against both openc++ and estlib, both E32Main and main()

Thread c32exe.exe::ESock_IP Panic KERN-EXEC 3: running in CodeWarrior I could see that it was a stack overflow – scons actually sets a stack limit on winscw which is respected when running standalone EXEs and a 20k stack is _not_ enough on WINSCW – the Symbian default is 1MB.

Posted in Symbian | Comments Off

Machinery of Freedom

Read David Friedman’s Machinery of Freedom last week, pretty good stuff.

I think Machinery of Freedom pretty neatly presents some real implementation options for a libertarian society. I especially enjoyed:

  • The calculation that the working class could buy up all the capital goods needed for the US industry by just saving for a couple of years. ‘Put your money where your mouth is.’
  • Speculation on how courts and police could be organized on the market.
  • The discussion on public goods, the difficulty of organizing national defense as something else than a public good.

I think I enjoyed the father’s ‘Capitalism and Freedom’ more – possibly since it was the first of the two I read. My big revelation from it was that by asking for tax money for something you want you are coercing others to pay for your consumption – you are always free to set up a collective to get what you want together with others without coercion.

Weak points:

I think Friedman downplays the threat of sociopaths (see Pinker’s Blank Slate) and authoritarianism (See Altemeyer’s The Authoritarians on the intertubes) to non-coercive security and law enforcement. Groups of people are well known to engage in voluntary violent discrimination: witch-hunts, racist lynchings, continuous wars in primitive societies. Additionally, in several places where he can’t find a market mechanism to solve X he falls back on ‘but most people act decently by default’ which may not be true.

A number of arguments in the book on at least some form of a market equilibrium / efficient market hypothesis. Now since reaching an equilibrium is completely impossible (the amount of time for the necessary information to propagate through actors even in a small state is longer than the remaining lifetie of the universe) such arguments are suspect. Now it could be that a) the arguments don’t really require the hypothesis or b) that they they only require a much weaker form of it – but Friedman never argues for anything like that.

Posted in Economics | Comments Off

Resolving OS-X aliases

My external drive recently started making clicking noises instead of spinning up some of the time so I thought it would be a good time to buy a new one. I keep my photos on the external disk and manipulate them with iPhoto and perl scripts. I dutifully copied the whole disk contents to the new disk and plugged it into the Airport Extreme to run some of my scripts. After a couple of minutes the disk dropped out (WD disks don’t work with Airport disk sharing due to spindown borking the airport, it turns out). No worries, I’ll just plug it in directly – it’ll mount at the same point /Volumes/mika-usb.

Now iPhoto likes to make aliases to files – the files that the library file points to are aliases. I use the MacOSX::Alias perl module to follow them. The problem is that the aliases point both to the afp share and the POSIX path and the API that MacOSX::Alias uses resolves into the afp share – which is not available.

Some searching on the intertubes provided me with enough code examples to write a small command line tool that resolves the path instead. Here it is, in case somebody else runs into the same problem:

#include <CoreServices/CoreServices.h>

int main (int argc, const char * argv[]) {
  OSErr err = noErr;
  FSRef input_file_ref;
  if (argc < 2) {
    fprintf(stderr, "Usage:\nalias path\n");
    return 2;
  }
  err = FSPathMakeRef(argv[1], &input_file_ref, false);
  if (noErr != err) {
    perror("cannot find file");
    return 1;
  }
  ResFileRefNum resource_ref = FSOpenResFile(&input_file_ref, fsRdPerm);
  AliasHandle alias_handle = (AliasHandle)GetIndResource('alis', 1);
  if (!alias_handle) {
    perror("no alis resource");
    return 1;
  }
  
  FSRef resolved_file_ref;
  Boolean was_changed;
  err = FSResolveAliasWithMountFlags(&input_file_ref, alias_handle,
                                     &resolved_file_ref,
                                     &was_changed, kResolveAliasFileNoUI); 
  CloseResFile(resource_ref);
  if (noErr != err) {
    perror("cannot resolve");
    return 1;
  }
  
  // Convert the file reference into a string
  UInt8 fileNameBuffer[1024];
  OSStatus status = FSRefMakePath(&resolved_file_ref,
                                  fileNameBuffer,
                                  1024);
  printf("resolved to %s\n", &fileNameBuffer);
  return 0;
}
Posted in CS | Comments Off

E32DBMS (Symbian database) performance

(This is a brief overview – I did some measurements at G but never got round to ask permission to publish the data)

Jaiku uses the Symbian databases heavily. All of the posts you see in the overview, by-author and thread views; their idempotence; unread status etc. are managed in one table. This was decided upon based on two factors: we had good experience of read performance on DBMS (in fact it’s excellent, when you scroll the posts in Jaiku the data is read row-by-row from the db) and we were still designing for low-memory phones (can’t hold the data in memory).

However, if you receive a lot of posts on an older phone the interaction sucks. The app pauses randomly for several hundred milliseconds every now and then. (It’s not as bad on more recent phones).

Turns out the major variable in how fast _writes_ to the database are is the number of indices on the table. Jaiku has 7 indices on the main table and 2 on an auxiliary table.

I guess the right way to do this would be to split the indices to separate tables that are updated incrementally at a low priority and making the post visible once all the auxiliary indices have been created. (We already have tuned the transaction size and Compress() interval to get the best interactive performance).

Posted in CS, Symbian | Comments Off

Network fun on Symbian

Been writing some network code for S60, using the HTTP stack for the first time (Jaiku has its own, crappy, stack because it used to run on 6.1). Couple of things that wasted me a day, once again:

I tried to do the simplest possible HTTP request, so I basically ignored all the callbacks except for the ones that indicate completion. Never got the ones for completion. Much swearing about active objects later I found out that this time I _wasn’t_ messing up my event handling – instead there’s a ‘feature’ in the stack: you have to consume the body of the response, otherwise the request never completes. So the minimal HTTP request handling needs to include something like the code below:

case THTTPEvent::EGotResponseBodyData: {
  MHTTPDataSupplier* body = aTransaction.Response().Body();
  body->ReleaseData();
}

The other fun was buggering up my commsdb. I was getting a panic in the ethernet driver when letting the HTTP stack open the connection on its own and decided to go and look at the access points in the Settings app on the emulator. Without thinking I opened the Winsock access point and closed it, which overwrites some of the settings with nonworking things. Now I wasn’t able to manually open any connections either.

So off I go to recreate the commsdb by doing a ceddump on a working SDK and a ced on the non-working one. This doesn’t exactly make things better. After that the emulator would just hang when I opened any application, with no clues as to what whatsoever (other than that I knew it happened after I did ced).

Turns out ced had not completed the commsdb changes, leaving it in a state that would hang the emulator (I think when loading messaging modules and/or networking modules).

The way to get ced to complete is to start it and when its screen gets replaced by the menu, find it in the task switcher and switch to it.

F. U. N. Endless fun.

Posted in Symbian | 197 Comments

Google acquires Jaiku!

Details at the Jaikido blog and Googleblog (and of course on Jaiku).

I’m at least looking forward to meeting some great people and a great backend :-)

Posted in Symbian | Comments Off

Perl lexicals lifetime brokenness with nested anon subs

5.8.8 has a nasty bug in the lifetime of lexicals that are referenced in a closure that is nested within an anon sub (that doesn’t reference those lexicals). The first time the code creating the anon sub is executed the lexicals get an extra reference that never goes away (or at least not before the package goes away or something). On any subsequent runs the refcount is correct.

use strict;
use Devel::Peek;

use Devel::Peek;
use Scalar::Util;
my %ids;

sub create_sub_leaking {
    my $id=shift;
    print "leaking id $id, refcount " . Devel::Peek::SvREFCNT($id) . "\n";
    $ids{$id}=\$id; Scalar::Util::weaken($ids{$id});

    my $sub= sub {
        my $sub2= sub {
            $id;
        };
        return $sub2;
    };
    return $sub;
}

my $s1=create_sub_leaking(1);
my $s2=create_sub_leaking(2);

$s1=undef;
$s2=undef;

print "stashed 1: ";
Dump( $ids{1} );
print "stashed 2: ";
Dump( $ids{2} );

Shows the refcount on the first call being 2 and that the lexical variable doesn’t go away.

Bother.

This means I have to be really careful to reference all the necessary lexicals in all the enclosing subs to make them behave.

This is all fixed in 5.9 since 2003 but will not be backported. And I’m not quite willing to move to 5.9.

Posted in CS | 1 Comment