soledad penadés
repeat 4[fd 100 rt 90]

Archive for September, 2008

20080925 mod_rewrite, mod_negotiation and empty $_GET's

I had just added this simple rewrite rule into the .htaccess file

RewriteRule ^section/(\d+)/$ /section.php?id=$1 [L]

and went to section.php expecting to find the id value inside $_GET['id']. Big surprise when it was actually empty. I suspected this could be something to do with that Apache module which tries to guess which file were you referring to when a URL was misspelled, since even if I commented out the rule it still executed section.php when entering /section in the URL. But if the .php file was completely unrelated to the rewrite pattern, (e.g. with RewriteRule ^kkkkkkk/(\d+)$/ /blablabla.php?id=$1) it worked. Very odd!

Since I personally never needed that feature, I didn't know its name (although I have seen it in a couple of servers before). After a while and several google searches, I could confirm the guilty and the one to blame was mod_negotiation, precisely the module which tries to guess which file you really wanted.

I haven't investigated exactly what is going on inside apache, although I guess that basically mod_negotiation is executed before mod_rewrite has a chance to parse the request, and when mod_rewrite is called it receives an overwritten and modified version of $_GET which is completely useless at that point.

So there are two options for getting mod_negotiation out of our way: disabling it altogether or disabling it at .htaccess level.

Disabling mod_negotiation

You can only do this if you control the server, be it a dedicated server, a slice server, or a local computer. This is how I did it with Ubuntu (Hardy Heron):

sudo a2dismod negotiation
sudo /etc/init.d/apache2 force-reload

First line disables the module, second one forces apache to restart (obvious, but just in case someone got lost ;) )

Disabling at .htaccess level

If you're on a shared hosting or you need mod_negotiation for something else, there's still hope!

Just add this

Options -Multiviews

at the top of .htaccess and that's it.

Curious cat strikes back

And out of curiosity… does anybody enable mod_negotiation on purpose? I personally find it more of an annoyance than a feature, specially when one wants to show only certain stuff and discovers that Apache is showing more than it should thanks to this evil module. Anyway, enjoy mod_rewrite ;-)

20080924 Cloud computing is the new social network

I somehow anticipated it when commenting about Techchrnnnnch's views about Google Chrome, but it's now confirmed: Cloud computing is the new social network. Just take a look at this graph that I managed to produce with a couple of clicks and keypresses and the help of Google Trends:

Cloud computing vs Social networks

Here's the entire report.

Unfortunately, the web 2.0 effect is still inducing waves of pleasure amongst the cool-keyword-hunters. If we dare to introduce the term into our cheap market research report generator, it reduces both cloud computing and social networks to an almost statistical nothingness.

Cloud computing vs Social networks vs Web 2.0

Entire report again.

Yet with a bit of luck cloud computing will push our all time favourite term –semantic web– back where it belongs. Disguised as the more glamorous and shiny term Web 3.0, of course.

Meanwhile, you can keep labelling all terms and situations with web 2.0, but do not be afraid of topping your pub chats with a little bit of cloud computing, even more if you're in London. You know weather is a great conversation topic here!

20080917 Damn geeks (and more)

Let's continue the IT fun saga , although it has been suspended for around five months, shame on holidays and all that ;-)

Damn geeks

First, we have a bit of a desperate cry by a certain Solomon Grundy:

Damn geeks. They've screwed up everything. They can't even get something as simple as the Internet right. No wonder 70% of financial application are still coded in COBOL and don't use the Internet as their primary avenue of communications.

from the comments at Adobe yanks speech exposing critical 'clickjacking' vulns. By the way, why do the Register guys have anchors for each individual comment, but do not show them? I had to use the very helpful Web Developer Toolbar once again for revealing anchors in the page (Information — Display anchors, just in case you need it). Damn geeks!

So yes, that's quite serious. It seems there's no way things can be done properly when the internet factor is in the mix. When in doubt, simply blame the Robustness principle: Be liberal in what you accept, and conservative in what you send.

Googleskepticism or just plain common sense?

Following the release of Google's Chrome, one had the immediate feeling that it was going to be a big news — not only appearing at generalist media but even prompting our families to ask us about that new system Google has released for competing against Bill's (literally). I wasn't impressed at all by the G-move neither did feel immediately compelled to download and test it (besides my computer doesn't run Windows anyway), so I just ignored the complete commotion. But it seems Ted Dziuba got a bit more irritated with all the publicity and media fueled bullshit and/or plain lies and simply ended up exploding:

I understand the argument that as web applications proliferate, the desktop operating system becomes less important, and emphasis is placed on the browser. That's all well and good, but let's be realistic here. It's a fucking web browser. It runs JavaScript a bit faster than other web browsers. That doesn't add up to a Windows killer.

[...]

People are calling Chrome a cloud operating system because it is a "platform for running web apps". It renders HTML and interprets Javascript, you know, like every fucking browser made since 1995. It's also got Google Gears built in. Great. I'll alert Tim Berners-Lee.

(emphasis added by me)

He also notes the big amount of nonsense that Michael Arrington managed (once again) to produce for the occasion, with allusions to the new and upcoming hot keyword - cloud computing. I would suggest Ted –and any of you–, only one thing: do not read Techcrunch, for your own mental health.

On confusing people

Only two words: Microsoft SDL.

Why did they have to use an acronym which is so well established is something that I can't understand. Furthermore, Microsoft SDL doesn't stand up for anything remotely related to media or games. Do not even think they are ditching DirectX for the true SDL. In fact, their SDL is the deceptively boring acronym of Secure Development Lifecycle. Which, coming from Microsoft, absolutely deserves a place on the IT fun saga with a special award in the "Irony" category!

20080903 And now PSPLink!

Screenshot from sprite sample

Messing with the memory stick is fine if you're just going to do it a couple of times, but after a while it becomes tedious.

At that point I decided I would try to make psplink work with my computer. It is another utility programmed by the superclever people at pspdev, and enables you to control the psp and even use your computer's hard drive as readable/writable by the console, so you don't need to copy things to the GAME directory anymore.

The building process was quick and easy, although it could have been faster, if I hadn't mistakenly gone into the psplink directory from pspsdk's SVN repository (which is an older version), instead of going directly to the psplinkusb directory, which is the one that lets you do everything via the USB cable. Also, this version's manual is a tad clearer and more explicit, so unless you have any odd interest in using the older version, go for the newest one, at svn://svn.ps2dev.org/psp/trunk/psplinkusb.

Yes! no more messing with the memory stick! You can even reset the console or get an screenshot, like the one from the picture :-)

20080902 PSP joystick & buttons

test output

Following the installation of the toolchain, I decided to make a little program to get some information about the PSP's interface, from the programmers point of view. That is, it would use SDL's joystick functions to find out how many axis and buttons and which codes did they report to the program. Although it might seem useless it is an easy exercise in checking events and it could even be the base for a future game.

I first tested the program on my computer, using a Logitech USB pad that I have for playing emulators. I intended to use it for real games but I still haven't found one which doesn't use the mouse. By the way, the pad works flawlessly in linux, just in case you were looking for a compatible joystick for your linux box.

The pad reported as having six axes, where the axes corresponded to the two analog joysticks and one digital joystick (two axes per joystick: vertical and horizontal), so I was expecting to find a very similar result in the PSP, but with four axes since it only has two joysticks.

Logitech dual action pad

Instead, I got an interesting result: two axes only, and the rest were buttons! PSP is reporting the digital joystick as simply four isolated buttons. This, although being surprising, also makes much easier to program simple stuff where you just need to react when a button has been pressed, instead of having to check the value of the axis which is reporting motions, and deduct the appropriate intended direction from there.

I also noticed that the analog joystick can sometimes have a very erratic behaviour, reporting movements while no one is even touching the console. It might be because it's not a brand new PSP and maybe there's some dirt or something in the controls … or maybe we were experiencing a earthquake and nobody noticed? :)

For the record, these are the reported SDL button codes, so you can look for an SDL_JOYBUTTONDOWN type of event, and compare event.jbutton.button to the following values to decide what to do:

Left: 7
Right: 9
Up: 8
Down: 6
L: 4
R: 5
Triangle: 0
Square: 3
Circle: 1
Cross: 2
start: 11
select: 10

I didn't manage to read the other buttons, they seem to be out of the reach of SDL. Maybe it's got something to do with kernel/user mode, but it doesn't worry me for the time being.

If you want to try this at home - worry not, it's safe and harmless! Here's the source code. You'll notice I also used the balls and hats functions, but I must confess that while I suspect that balls is referring to trackballs, I have no idea what hats is referring to. If anybody knows, let me know in the comments so that I can stop imagining a little Mexican hat dressing a gamepad :-D

Here's also a possible sample output, using my logitech pad and pressing buttons and moving sticks randomly:

Index: 0
Name: Logitech Logitech Dual Action
Num axes: 6
Num balls: 0
Num hats: 0
Num buttons: 12
// moving the digital stick
Axis motion: j index = 0 axis = 5 value = -32767
Axis motion: j index = 0 axis = 5 value = 0
Axis motion: j index = 0 axis = 5 value = 32767
Axis motion: j index = 0 axis = 5 value = 0
Axis motion: j index = 0 axis = 4 value = -32767
Axis motion: j index = 0 axis = 4 value = 0
Axis motion: j index = 0 axis = 4 value = 32767
Axis motion: j index = 0 axis = 4 value = 0
// moving analog sticks, note the values aren't "all, minus all or nothing" here
// you should get similar values with the psp's analog stick
Axis motion: j index = 0 axis = 0 value = 337
Axis motion: j index = 0 axis = 0 value = 1013
Axis motion: j index = 0 axis = 0 value = 2026
Axis motion: j index = 0 axis = 0 value = 4053
Axis motion: j index = 0 axis = 0 value = 5742
Axis motion: j index = 0 axis = 0 value = 7094
Axis motion: j index = 0 axis = 0 value = 10134
Axis motion: j index = 0 axis = 0 value = 13174
Axis motion: j index = 0 axis = 0 value = 15877
Axis motion: j index = 0 axis = 0 value = 19593
Axis motion: j index = 0 axis = 0 value = 22633
Axis motion: j index = 0 axis = 0 value = 26349
Axis motion: j index = 0 axis = 0 value = 30741
Axis motion: j index = 0 axis = 0 value = 32767
Axis motion: j index = 0 axis = 1 value = -1014
Axis motion: j index = 0 axis = 1 value = -3379
Axis motion: j index = 0 axis = 1 value = -4392
Axis motion: j index = 0 axis = 1 value = -5743
Axis motion: j index = 0 axis = 1 value = -7432
Axis motion: j index = 0 axis = 1 value = -9121
Axis motion: j index = 0 axis = 1 value = -11486
Axis motion: j index = 0 axis = 1 value = -13175
Axis motion: j index = 0 axis = 1 value = -14189
Axis motion: j index = 0 axis = 1 value = -16553
Axis motion: j index = 0 axis = 1 value = -19932
Axis motion: j index = 0 axis = 1 value = -22296
Axis motion: j index = 0 axis = 1 value = -25337
Axis motion: j index = 0 axis = 1 value = -28039
Axis motion: j index = 0 axis = 1 value = -32767
Axis motion: j index = 0 axis = 0 value = 25673
Axis motion: j index = 0 axis = 0 value = 16890
Axis motion: j index = 0 axis = 0 value = 8445
Axis motion: j index = 0 axis = 0 value = 3378
Axis motion: j index = 0 axis = 0 value = 1013
Axis motion: j index = 0 axis = 0 value = 0
Axis motion: j index = 0 axis = 1 value = -31755
Axis motion: j index = 0 axis = 1 value = -27026
Axis motion: j index = 0 axis = 1 value = -22296
Axis motion: j index = 0 axis = 1 value = -13851
Axis motion: j index = 0 axis = 1 value = -3379
Axis motion: j index = 0 axis = 1 value = 0
Axis motion: j index = 0 axis = 2 value = 3040
Axis motion: j index = 0 axis = 2 value = 7769
Axis motion: j index = 0 axis = 2 value = 10472
Axis motion: j index = 0 axis = 3 value = -3041
Axis motion: j index = 0 axis = 2 value = 13512
Axis motion: j index = 0 axis = 3 value = -5068
Axis motion: j index = 0 axis = 2 value = 16215
Axis motion: j index = 0 axis = 3 value = -10473
Axis motion: j index = 0 axis = 2 value = 19593
Axis motion: j index = 0 axis = 3 value = -17229
Axis motion: j index = 0 axis = 2 value = 22971
Axis motion: j index = 0 axis = 3 value = -24661
Axis motion: j index = 0 axis = 2 value = 26011
Axis motion: j index = 0 axis = 3 value = -32767
Axis motion: j index = 0 axis = 2 value = 28038
Axis motion: j index = 0 axis = 2 value = 30741
Axis motion: j index = 0 axis = 2 value = 31078
Axis motion: j index = 0 axis = 2 value = 30065
Axis motion: j index = 0 axis = 2 value = 28038
Axis motion: j index = 0 axis = 2 value = 22295
Axis motion: j index = 0 axis = 2 value = 15539
Axis motion: j index = 0 axis = 2 value = 9458
Axis motion: j index = 0 axis = 2 value = 3040
Axis motion: j index = 0 axis = 2 value = 0
Axis motion: j index = 0 axis = 2 value = -676
Axis motion: j index = 0 axis = 2 value = -2365
Axis motion: j index = 0 axis = 2 value = -3041
Axis motion: j index = 0 axis = 2 value = -3716
Axis motion: j index = 0 axis = 2 value = -4392
Axis motion: j index = 0 axis = 2 value = -5068
Axis motion: j index = 0 axis = 2 value = -7432
Axis motion: j index = 0 axis = 2 value = -11148
Axis motion: j index = 0 axis = 2 value = -13513
Axis motion: j index = 0 axis = 2 value = -16216
Axis motion: j index = 0 axis = 2 value = -18580
Axis motion: j index = 0 axis = 2 value = -19932
Axis motion: j index = 0 axis = 2 value = -21621
Axis motion: j index = 0 axis = 3 value = -31755
Axis motion: j index = 0 axis = 3 value = -27363
Axis motion: j index = 0 axis = 3 value = -22972
Axis motion: j index = 0 axis = 3 value = -19594
Axis motion: j index = 0 axis = 3 value = -16216
Axis motion: j index = 0 axis = 3 value = -15202
Axis motion: j index = 0 axis = 3 value = -11824
Axis motion: j index = 0 axis = 2 value = -19932
Axis motion: j index = 0 axis = 3 value = -10135
Axis motion: j index = 0 axis = 2 value = -18580
Axis motion: j index = 0 axis = 3 value = -8784
Axis motion: j index = 0 axis = 2 value = -14864
Axis motion: j index = 0 axis = 3 value = -6419
Axis motion: j index = 0 axis = 2 value = -8108
Axis motion: j index = 0 axis = 3 value = -3041
Axis motion: j index = 0 axis = 2 value = -676
Axis motion: j index = 0 axis = 3 value = -1014
Axis motion: j index = 0 axis = 2 value = 0
Axis motion: j index = 0 axis = 3 value = 0
// buttons!
Pressed button 0
Pressed button 1
Pressed button 3
Pressed button 2
Pressed button 2
Pressed button 1
Pressed button 7
Pressed button 5
Pressed button 6
Pressed button 4
Pressed button 5
Pressed button 4
Pressed button 6
Pressed button 9
Pressed button 8