Swiftpoint mouse


Today I received a Swiftpoint SM300 in the post … this is a sweet little addition for the laptop, although I find it a little awkward on the desk, and will probably stick to my trackball.

It’s packed full of useful modifications for laptop users; first of all its small! The tiny USB key charges the mouse quickly, talks to it wirelessly and uses an effective magnet to hold it in place when the lid is closed …

And the “parking accessory” sticks over the trackpad, helping to disable it for you … and provides a magnetic docking station to keep the mouse out of the way while you type (although the position they recommend rewards conventional touch-typing — I tend to use the right hand for more of the keyboard than perhaps I should!).

There are lots of nice touches; where in the past a manufacturer might have provided additional features through a driver that would be available only under Windows, this device is a pure USB HID. The “vertical direction” and “smart touch” features are configured through the mouse itself. As a consequence it works perfectly under Linux (well, Ubuntu 10.04 at least) — although when I first plugged it in nothing happened … but that was because the mouse and USB key were not paired, and that’s fixable from the mouse itself as well :-)

[53641.820182] usb 6-1: new full speed USB device using uhci_hcd and address 4
[53641.995500] usb 6-1: configuration #1 chosen from 1 choice
[53642.005439] input: Swiftpoint Limited Swiftpoint Mouse S300 as /devices/pci0000:00/0000:00:1d.1/usb6/6-1/6-1:1.0/input/input22
[53642.005858] generic-usb 0003:214E:0001.000D: input,hidraw0: USB HID v1.11 Mouse [Swiftpoint Limited Swiftpoint Mouse S300] on usb-0000:00:1d.1-1/input0
[53642.010892] input: Swiftpoint Limited Swiftpoint Mouse S300 as /devices/pci0000:00/0000:00:1d.1/usb6/6-1/6-1:1.1/input/input23
[53642.011062] generic-usb 0003:214E:0001.000E: input,hidraw1: USB HID v1.11 Keyboard [Swiftpoint Limited Swiftpoint Mouse S300] on usb-0000:00:1d.1-1/input1

This will be a great travelling mouse too; the only downside perhaps is that the USB key doesn’t have a storage slot inside the mouse body itself, but that’s a minor point. And I still haven’t quite got used to the “SlideScroll” facility, but its only been in use for a couple of hours so far, so I’ll give it a chance!

Tags:

At the sharp end of a DDoS


Recently I was asked to assist a small NZ business, because their ecommerce website was offline due to an HTTP Flood DDoS attack.

These things don’t often get seen by small players, and they are scary and expensive to suffer through. This is the story of what happened, as it happened, and what impact it had. I won’t be identifying any of the people/companies involved unless they ask me to. I’ll be keeping the technical level reasonably high though, so don’t worry if you miss some of the details!

The Players

  • SB - the Small Business who called me for help
  • CMS - The Content Management System company who write & operate SB’s website
  • ISP - The Internet Service Provider who host the CMS servers and provide connectivity

Initial Detection

Early one Friday afternoon, a network system administrator at “ISP” noticed that the load on his firewall was unusually high. Digging into the situation, he saw large volumes of HTTP requests coming through to “CMS’s” webserver, flooding it.

On investigation, he saw only simple requests (”GET /” without identifying which website name was required) coming from many different origins. The CMS webserver in question hosts multiple customer websites, and it wasn’t clear if any of these were a specific target for the attack, or whether it was just the server itself.

The engineer then tried to configure the Intrusion Protection System (IPS) on the firewall to detect and block these requests, which are basically not valid anyway. However, in order to try what he wanted, the IPS software had to be upgraded and then reconfigured, and he was not sure how best to configure the system to be fully effective. The attack continued to keep the CMS webserver effectively offline.

A Change In The Wind

Overnight, the attack changed profile; instead of a simple non-specific request, it had changed to specifically request one of the hosted websites, one belonging to the end-customer “SB”. From the perspective of the ISP and the CMS company, this was great news — they had a chance to isolate the attack and bring their webserver back for the other customers.

The change might have come about because the IPS was being successful, or it might have just been the original attacker zeroing in on his original target; we can’t tell.

Utilising a ’spare’ virtual server hosted offshore, the ISP quickly configured a reverse proxy and loaded up some extra software that tries to fight off denial of service atacks. They then changed DNS to send requests for the SB website to that proxy instead of directly to the CMS server; this was successful, and the DDoS attack traffic started arriving at this new location. Unfortunately, the new server was unable to keep up with the size of the attack, and SB’s website was still offline. However, the CMS webserver was no longer being overloaded, and other customer websites came back online.

Stalemate

The ISP had put a lot of resources into fighting off this attack so far, and were reaching the edge of their experience and expertise. They had managed to move the attack away from their core systems, recovering service for the majority of the affected websites. However, they could not “beat” the attack and restore SB’s website. They had been talking to their Upstream provider, who could provide mechanisms to help beat a simple Denial of Service attack, but not a distributed one — at least, not at a cost-effective rate. The ISP did some research online to find companies to help, and identified one possible trustworthy-looking provider who offered a specific DDoS-protection service. They suggested to the CMS company that SB should pay for this extra service.

Second Opinion

It was roughly at this stage that SB got in contact with me; he didn’t fully understand what was happening, and didn’t understand what his real options were. This sort of communication problem is all too common where you have an intensly technical issue affecting the business — trying to explain technical things to non-technical people is very difficult.

My first approach was to talk to the CMS company, and find out what they thought the issues were; after all, they are the one with a financial/contractual relationship with SB. From there, it was easy to track back to the ISP, and they were willing to spend some time talking to me, explaining in their own language what they had seen and what they had done. This enabled me to get back to SB quite quickly, and tell him that there was a real “external” problem, not caused by CMS or ISP, and that they had genuinely been trying to address the issue, and had been acting competantly and in good faith. Maintaining trust between customer and supplier is very important, especially when unusual costs are being experienced, and someone is going to end up paying for it.

One of the questions from SB was about just this, “who should pay?”. The contract trail wasn’t easily available, but I was able to turn up a copy of the original hosting contract that SB entered into before the CMS company took it over; there was a reasonable clause in there indemnifying the host from the effects of virus attacks, and it’s not a long step from there to DDoS. I had used the analogy that a DDoS was like a lightning strike — inherently unpredictable but very destructive — but the next step up from the physical world isn’t directly applicable; if lightning strikes your rented house chimney, your landlord would have to pay to fix it, and would invoke insurance to cover his losses. In the virtual world, the contract with the ‘landlord’ has been able to exclude these things.

Trying To Beat The Attack

The reverse proxy setup that the ISP had deployed was reasonable, but I had a few different ideas. I suggested some experiments and configuration changes that might help, but without hard data to analyse it was unclear whether these would help. Initially, the proxy was trying to simply pass all successful requests back to the CMS webserver; I suggested trying to handle the initial “GET /” request directly from the proxy, therefore reducing load on the CMS — also with the hope that the atackers were not actually listening to the responses, and would therefore never end up sending a redirected request to the CMS. This did appear to be potentially successful, but the attack was still coming in fast enough that the proxy was not able to handle the traffic, and therefore was never able to effectively proxy legitimate requests back to the CMS.

Additionally, the proxy server had very quickly exhausted the bandwidth/data limits set by its contract, which would have made any further attempts increasingly expensive. In order to reduce the cost of traffic to the proxy server, the ISP configured its firewall to reject all HTTP requests. Even so, there was over 2Mbps of traffic trying to get through.

The route to the external “DDoS Protection” service seemed to be the only reasonable short-term business decision, and this was accepted all round as a good choice. I tried to validate this choice by speaking to a large number of experts around the NZ marketplace — security auditors, security equipment vendors, network security technicians and other consultants.

Luck Rather Than Judgement?

Just as I was talking to one last security consultant, we checked the website and things seemed to be working once more! I got hold of the ISP again and this was confirmed; the attack volumes had dropped significantly, and the reverse proxy was now able to handle the load. Luckily the ISP had been constantly monitoring the situation and just before the contract to the external DDoS service had been activated, they noticed that the attack seemed to have mostly abated. Over the next day the attack traffic reduced further; there are still some remnants, and even some attacks still arriving directly on the CMS machine as they have obviously ignored DNS updates. However the levels are well within the capacity of the normal systems to aborb without ill effects. SB is back online.

Conclusions

Painting A Target On Your Back

One question that was difficult to answer, and quite important, was “who was the attack aimed at?”. The initial attack arrived at the CMS webserver with no identifying details, and could have been aimed at the ISP, the CMS company, or any one of the multiple customer sites hosted there. When the attack changed to name the SB website, that would seem to indicate that it was aimed at SB’s business; however SB operates other domain names on the same CMS service, and they were not attacked at all. It is therefore possible that the selection of SB’s domain name was basically only an attempt to overcome the IPS blocking simple requests.

Another possibility is that the attack was aimed at the CMS server, and not the CMS company. One of the observed habits of DDoS attacks is that they are sometimes aimed at each other’s control systems, as part of the cut-throat world they come from. If the CMS server had been infected with some malware that acted as part of the control network for a rival DDoS system, then the server itself would have been the target — the invocation of the SB domain name would effectively been a mistake while trying to work around the early protection provided by the IPS.

If the attack had been aimed at SB specifically, experience from the wider world suggests that there would probably have been some sort of extortion attempts. If a competitor had been trying to shut SB down, they would have targetted all of his domains.

Without any real indication of intelligent decisions behind the targetting, we’re left with the unsavoury possibility that this whole attack was simple mindless vandalism.

A Better Approach?

Throughout this experience, most of the technical people, myself included, focussed on the technical details of the attack, and attempted to beat it despite insufficient experience and resources. However we were losing sight of the business cost; SB has had to hand over extra money, because we were spending it, and possibly suffer a longer downtime.

One piece of advice that I received afterwards was that a good approach for a small company is to just shut down completely for a day or so, and allow the attacker to detect and claim “victory”. While we were unsuccessfully trying to absorb the attack, the website was effectively down from the perspective of real customers, but may have appeared to be “up enough” to encourge the attack to continue. Its an unknown, but perhaps SB would have suffered less total outage if we had taken the site down. Its very hard for technical people to admit defeat while there are still reasonable options to be tried, but at the end of the day a customer’s website is a business tool, not a technical one.

The Losses

The ISP have incurred costs in relation to their time & effort, and the costs of exceeding the traffic quota on their virtual server. On the other hand, they have learned a lot about DDoS attack. The biggest loser is the SB, who have had their main ecommerce offline for a number of days — long enough to affect their search-engine ranking, as well as to lose potential sales. Luckily for this particular SB, I don’t think that would represent an unrecoverable problem, given the nature of their business; but it could be a fatal interruption to cashflow for many companies.

Other Comments

The attack was described as being detected by the ISP; but it should have been detected by the CMS noticing that their webserver was under high load, or perhaps effectively offline. Having an effective system monitoring system can help you to detect problems early on, giving more time to deal with issues.

Tags: ,

Wifi ‘Hole 196′ opens WPA2


It looks like a active attack of an underlying protocol vulnerability in WPA2 has just been announced, by Md. Sohail Ahmad of AirTight Networks. This represents a real risk to people relying on WPA2 (in any flavour) for their data communications security.

This affects WPA2 itself, and although full details won’t be announced for a few days it just serves as a reminder that the security landscape is constantly changing. Vulnerabilities are a fact of life, and upgrades to your security software are essential. If you cannot upgrade, you need to have another layer of protection.

Many people provide their wireless access points from dedicated hardware devices, for example the Linksys WRT54GL or increasingly directly from their ADSL modem. These devices are usually the simplest to configure and support, but they are probably the hardest to upgrade.

In a case such as this, its the whole protocol that has been declared faulty, allowing an attacker to bypass network encryption completely by demanding copies of each device’s PTKs (the transient encryption keys), and the only way around that is for every device on the wireless network to upgrade to a different protocol — and we don’t have one available right now. In practice I’d expect a “WPA3″ to come up, with the specific vulnerability around group keys to be mitigated in some way. This will be delivered to PCs through your operating system updates, but that’s no use if you can’t upgrade your access points; and even though it’s often technically possible to turn up a new firmware for an old device, most hardware vendors would prefer if you just went out and bought a new unit …

So your workaround is to consider your wireless network to be as open as the old hub-based wired networks, or possibly even as dangerous as the raw Internet. Use a firewall to prevent applications on your PC from using the network without your approval, and make sure that every protocol you use with private data is software encrypted; HTTPS (use the EFF’s HTTPS-Everywhere plugin for Firefox as a minimum), IMAPS|POPS for email … or perhaps run a VPN between wireless devices and the access point or server beyond.

In fact, for corporates it may make sense to require the use of a VPN over all wireless networks, after all they are already managing the PCs in question and can keep credentials/keys updated.

This isn’t a new message; this is an old message. The security problems of wireless are not new, and indeed aren’t even specific to wireless technology at all — it’s more an issue of the way that the security software is implemented in firmware, and is therefore difficult to manage by most users. There will be vulnerabilities in the software VPNs; but the fix/upgrade timescales for these will be far faster and more achievable.

Tags: ,

CloudCamp Dunedin


I went to CloudCamp Dunedin yesterday, which I think went very well. Ben Kepes did a great job of encouraging people through the Unconvention structure, and our lightning talk speakers covered a wide range of ideas between them. Just a shame that I had to leave before the wrapup (& pizza!).

There were a lot of different people present, and “the cloud” means some very different things to all of them. I tend to see the system architectural view first, where I worry about how to marshall the resources that go into the cloud, and how software has to be structured to make best use of this different type of environment. But it’s interesting to see how cloud services rather than cloud machines are empowering developers to be able to cut out the middleman of system administrators.

An analogy for that was voiced at the time; currently we’re all like factories running our own power generators, doing our own maintenance and finding our own fuel. But the cloud services move us to just grabbing electricity from the grid. We might still worry about the cost and service level of our power supply, but we don’t employ our own engineers …

(Personal input — my father had a long career as a mechanical engineer for factory power systems, and my father-in-law is a high-voltage electrical engineer)

With a long term background in system administration, I might feel a little threatened by this, but on the whole I can see that its a good thing to be able to move on. With my security hat on, I’m worried about developers exposing their code directly to large-scale on the Internet without the benefit of actually having it evaluated or engineered correctly, but then again that’s part of the free market — if they do a bad job their apps won’t succeed, if they do a good job all will be well.

The economics of cloud services are also interesting; your first hit is free, and for at least one established NZ web-based application provider I know, their entire target market’s usage is low enough to let them run systems with zero infrastructure cost. Think about that for a minute — they can prove their platform in an NZ marketplace, and only have to pay for staff time. That’s a tremendous economic advantage for a small business …

Tags:

Ubuntu’s gnome-panel instability workaround


I’ve been running Ubuntu 10.04 on my desktop since it came out, and about the only real annoyance I have is that occasionally the gnome-panel scrambles the order of my icons and applets. This is possibly because I keep switching the screen layout between a pair of external screens and the laptop screen itself, just using some scripts that invoke xrandr directly … but it still shouldn’t happen.

My workaround for this is to find the files that are modified when the panel attributes are changed, and put the old ones back! So, I sat in a shell finding current files in ~/.gconf using find -mtime 0 until I’d identified the ~/.gconf/apps/panel directory (not ~/.gconf/apps/panel/applets as I initially thought) as being the place to look. I created a bzr repository in that directory and checked in all the files, and in my .bashrc I just run a quick status check to see if anything has been modified … if it has, I can run bzr revert to put it back!

Sadly just killing and restarting the gnome-panel doesn’t do enough to reset the session, you’ll have to log out completely to get the panel re-organised. Unless gnome-panel listens to a signal like HUP … and I’m not going to test that today!

Tags: ,

VoIP under pfSense


I used to have a Linksys WRT54GL at the edge of the network, running the Tomato firmware, and things were nice. Then I decided to switch to pfSense on a PC Engines ALIX 2C10 (see my earlier post), and …

Well, VoIP behaves very differently in this new regime, by which I mean SIP and RTP of course. I’ve spent far too long reading pages of badly-stated problems and non-helpful answers, and trying to get my head around just how badly NAT screws things up. And far too long changing settings trying to get improved behaviour …

Ultimately of course pfSense should behave the same way that Linux/Tomato does — things should just work without having to do any specific setup. But the timeout seems to be far more aggressive, and I think that was the real issue that started me down a long road …

I’ve been using a SIP proxy (siproxd), I’ve been NATting RTP & SIP down to a single device, I’ve been using STUN servers … The siproxd seemed to be working perfectly but at the same time there was an upstream problem that prevented me receiving calls on one of my accounts, so that solution got ripped out. The NATting worked fine but was only appropriate for one device at a time, so I started trying to move SIP to a different source port. At one stage I was seeing non-NATted traffic on my firewall’s external interface, which was rumoured to be a specific SIP (UDP port 5060) exclusion in the codebase … but I can’t replicate that any more!

Thanks to a fair bit of handholding from Chris MacGreggor at VentureVoIP, I’ve finished up with a very clean setup — no STUN, no mention of NAT on the phones, anything like that. I have decreased the Registration timeouts to 500 seconds (that’s just over 8 minutes), and put in a couple of rules matching the VoIP destination networks to increase the firewall state timeout to 1800 seconds (30 minutes). This seems to be working well …

For the record, I’ve got a number of SIP devices here :-

  • Snom 300
    • Inode Ltd account at VentureVoIP
    • Home account at VentureVoIP
    • Test account on 2talk
  • Linksys SPA3102 (used as an ATA)
    • Home account at VentureVoIP
  • Grandstream HT486, currently not configured
  • Nokia n900 mobile, currently not working
    • Inode Ltd account at VentureVoIP

So I still have a couple of steps left to take; the n900 thinks everyone is offline when it tries to call them, but then again I’ve never had this working yet so perhaps it’s not my changes that have caused this! And the old HT486 is just plugged backwards into the house phone wiring, but I no longer have any phones connected around the place (just a triplet of DECT phones connected to the Linksys SPA3102) so it’s not much of a priority.

But the basic lesson in migrating from a Linux-based working firewall into a BSD-based one seems to be “check the state table timeouts”!

Tags: ,

Installing pfSense on an ALIX board


The PC Engines ALIX single-board computers don’t have much in the way of interfaces, just ethernet, USB and a serial port, so if you’re not used to dealing with these things it can seem a little daunting to get an OS installed.

Here’s the procedure I use to get the pfSense firewall OS installed on something like an ALIX 2D3. Note that I’m putting the full live distribution on a CF card, which may not be a good choice for you — CF cards have a limited write lifetime. You’ll need the following equipment :-

  • ALIX system board
  • Power Supply of course
  • CF card, I’m using 1GB
  • CF card reader on your desktop machine
  • Null modem 9DB cable
  • A serial port on your desktop (I use a USB/Serial converter)
  • Serial port communications software (minicom works fine; on Ubuntu remember to make sure you have permission to read the /dev file — you may need to join the dialout group)
  • UTP Ethernet cable

Configure the ALIX board

First, check that your ALIX machine is working and do a little setup. Don’t put the board into its case at this stage, as that usually blocks access to the CF card we’ll be using later. Be careful to keep the board on a non-conductive surface. Connect the serial cable to your PC, get the serial port communications software configured for 38400 baud, 8N1. Power on the ALIX machine and you should see this :-

PC Engines ALIX.2 v0.99h
640 KB Base Memory
261120 KB Extended Memory

01F0 - no drive found !
No boot device available, press Enter to continue.

If you don’t get something like that, look for the green lights on the ALIX board and check your comms settings. Once you get that working, it’s time to reboot the ALIX and change the baud rate. Take out the power (remember that PC Engines don’t recommend un/plugging the PSU connector at their end due to the risk of arcing, so do it at the mains end), and this time as the machine reboots press the “s” key while the memory check is counting up.

PC Engines ALIX.2 v0.99h
640 KB Base Memory
261120 KB Extended Memory

01F0 - no drive found !

BIOS setup:

(9) 9600 baud (2) 19200 baud *3* 38400 baud (5) 57600 baud (1) 115200 baud
*C* CHS mode (L) LBA mode (W) HDD wait (V) HDD slave (U) UDMA enable
(M) MFGPT workaround
(P) late PCI init
*R* Serial console enable
(E) PXE boot enable
(X) Xmodem upload
(Q) Quit

Press “9″, then “q”, then “y” to save … at which point you may as well power off again while you change the communication settings on your terminal down to 9600 baud!

*9* 9600 baud (2) 19200 baud (3) 38400 baud (5) 57600 baud (1) 115200 baud
*C* CHS mode (L) LBA mode (W) HDD wait (V) HDD slave (U) UDMA enable
(M) MFGPT workaround
(P) late PCI init
*R* Serial console enable
(E) PXE boot enable
(X) Xmodem upload
(Q) Quit

Save changes Y/N ?
Writing setup to flash... OK
x����x<�������x������x������x���x���x

Confirm you can talk to the device once again, then power off and leave it alone for a little while.

Configure the CF card

Now we’re ready to install pfSense onto the CF card. I don’t want to boot my desktop from the pfSense LiveCD, I’m going to do this via a VM under VirtualBox. First, we need to identify how the CF card shows up in your normal desktop machine, so plug it in. If a filesystem is automounted (most CF cards come with a FAT32 filesystem on them by default) then unmount it. Have a look with dmesg to find out which device it has been connected as — mine comes in as /dev/sdc

$ dmesg|tail
[45748.609374] sd 3:0:0:0: [sdb] Attached SCSI removable disk
[45748.610134] sd 3:0:0:1: [sdc] Write Protect is off
[45748.610141] sd 3:0:0:1: [sdc] Mode Sense: 03 00 00 00
[45748.610146] sd 3:0:0:1: [sdc] Assuming drive cache: write through
[45748.613126] sd 3:0:0:1: [sdc] Assuming drive cache: write through
[45748.613136]  sdc: sdc1
[45748.615125]  sdc1: 
[45748.618619] sd 3:0:0:1: [sdc] Assuming drive cache: write through
[45748.618629] sd 3:0:0:1: [sdc] Attached SCSI removable disk

Now you need to create a passthrough disk that will allow a VM guest machine to talk directly to /dev/sdc. This isn’t well covered through Google searches, but it is out there, and it’s in the VirtualBox documentation too …

$ sudo VboxManage internalcommands createrawvmdk \
-filename passthroughsdc.vmdk -rawdisk /dev/sdc -register

Make sure you create that passthroughsdc.vmdk in the correct directory, ~/.VirtualBox/HardDisks on my setup. You need to be root in order to connect to /dev/sdc, but once the disk file has been created you can chown it back to your ownership.

Now set up a VM guest for FreeBSD, giving it the passthroughsdc.vmdk as the hard drive, and the pfSense LiveCD on the CD drive. Start it up. When pfSense boots, select “i” for the Installer, choose “Easy Install” and let it rip through, copying files onto your CF drive. At the end, choose the “Embedded kernel”, and shutdown normally.

Booting pfSense on the ALIX

Now you can take the CF card and install it into the ALIX, carefully. Switch back to the serial console and power up …

PC Engines ALIX.2 v0.99h
640 KB Base Memory
261120 KB Extended Memory

01F0 Master 044A CF 2GB
Phys C/H/S 3933/16/63 Log C/H/S 983/64/63

F1   FreeBSD

Boot:   F1

pfSense should then boot, leaving you with the serial console options :-

Bootup complete

FreeBSD/i386 (pfSense.local) (console)

*** Welcome to pfSense 1.2.3-RELEASE-pfSense on pfSense ***

  LAN                      ->   vr0     ->      192.168.1.1
  WAN                      ->   vr1     ->      NONE(DHCP)

 pfSense console setup
***************************
 0)  Logout (SSH only)
 1)  Assign Interfaces
 2)  Set LAN IP address
 3)  Reset webConfigurator password
 4)  Reset to factory defaults
 5)  Reboot system
 6)  Halt system
 7)  Ping host
 8)  Shell
 9)  PFtop
10)  Filter Logs
11)  Restart webConfigurator
12)  pfSense Developer Shell
13)  Upgrade from console
14)  Enable Secure Shell (sshd)

Enter an option: 

Now you should be able to connect a UTP Ethernet cable to the LAN interface (vr0 will probably be the interface closest to the power connector) and the other end to your PC — note that this should provide an address (and default route/DNS config — be careful if you thought your PC was supposed to be working via a different interface at the same time) for you automatically. Point your web browser to http://192.168.1.1 and enjoy your pfSense firewall!

By the way, all my PC Engine hardware comes from Nicegear, NZ’s VoIP and Open Source Hardware specialists.

Tags: ,

Running Nagios3 under Nginx & FastCGI


It is quite possible to run Nagios3’s web interface directly from Nginx and a FastCGI server, rather than having to involve a web application server like Apache. This is useful if you want to preserve memory on your machine, for example.

First of all, we ask Nginx to serve the static files for the Nagios web interface. In Debian/Ubuntu, these live in /usr/share/nagios3/htdocs and /usr/share/nagios3/stylesheets, which is a little awkward, but just the sort of thing that the rewrite command is for …

    location / {
        root /usr/share/nagios3/htdocs;
        index index.html;

        rewrite ^/nagios3/stylesheets/(.*)$ /../stylesheets/$1 break;
        rewrite ^/nagios3/(.*)$ /$1 break;
    }

Next, we tell Nginx to send requests for CGI pages down to a FastCGI server :-

    location ~ \.cgi$ {
        root /usr/lib/cgi-bin/nagios3;
        include /etc/nginx/fastcgi_params;

        rewrite ^/cgi-bin/nagios3/(.*)$ /$1;

        auth_basic "Nagios";
        auth_basic_user_file /etc/nagios3/htpasswd.users;

        fastcgi_pass 127.0.1.1:8998;
        fastcgi_param SCRIPT_FILENAME /usr/lib/cgi-bin/nagios3$fastcgi_script_name;
        fastcgi_param AUTH_USER       $remote_user;
        fastcgi_param REMOTE_USER     $remote_user;
    }

We need to make sure that these requests are under authentication, and that we pass the authenticated username to the CGI script properly, hence the auth_basic and fastcgi_param AUTH_USER lines.

That’s Nginx taken care of, but we also need to make sure there’s a generic FastCGI server running on the specified address/port. No configuration is necessary, as we’re passing everything we need, including the script name. fcgiwrap comes recommended on the Nginx wiki.

/usr/bin/spawn-fcgi -a 127.0.1.1 -p 8998 \
-u www-data -g www-data \
-f /usr/local/bin/fcgiwrap -P /var/run/fcgiwrap.pid

And that’s all you need!

Tags: , ,

Testing a FastCGI service


If you have a FastCGI service running, normally you just talk to it through the front-end web server. However, for testing purposes you should send requests directly to the fastcgi server.

Getting this done isn’t terribly obvious, as the FastCGI protocol is not in plain text you can’t just telnet to the server and enter commands, the way you can with HTTP. There is a useful command, cgi-fcgi that comes from the libfcgi package on Debian/Ubuntu (and probably in similar packages in other distros), but the man page assumes you already know a lot more about FastCGI than you probably needed to set something up in the first place!

From http://gist.github.com/mpasternacki comes a short wrapper script to invoke cgi-fcgi to send a simple request - http://gist.github.com/209446. This script sets a bunch of environment variables that the fcgi script may require up front.

Here’s a simpler example. I have a FastCGI server running on 127.0.1.1 port 8998. I used lighttpd’s spawn-fcgi to start up an instance of fcgiwrap, a minimal fcgi processor recommended on the Nginx wiki.

/usr/bin/spawn-fcgi -a 127.0.1.1 -p 8998 \
-u www-data -g www-data \
-f /usr/local/bin/fcgiwrap -P /var/run/fcgiwrap.pid

Then, I use cgi-fcgi to connect to the port, and see what I get back.

$ cgi-fcgi -bind -connect 127.0.1.1:8998
Cannot get script name, are DOCUMENT_ROOT and SCRIPT_NAME (or SCRIPT_FILENAME) set and is the script executable?
Status: 403 Forbidden
Content-type: text/plain

403

This is enough to confirm that fcgiwrap is running OK, but doesn’t tell us if it can actually carry out any work. I’ll ask it to run a Nagios CGI command :-

$ DOCUMENT_ROOT=/var/www \
SCRIPT_FILENAME=/usr/lib/cgi-bin/nagios3/tac.cgi \
cgi-fcgi -bind -connect 127.0.1.1:8998
getcgivars(): Unsupported REQUEST_METHOD -> ''

I'm guessing you're trying to execute the CGI from a command line.
In order to do that, you need to set the REQUEST_METHOD environment
variable to either "GET", "HEAD", or "POST".  When using the
GET and HEAD methods, arguments can be passed to the CGI
by setting the "QUERY_STRING" environment variable.  If you're
using the POST method, data is read from standard input.  Also of
note: if you've enabled authentication in the CGIs, you must set the
"REMOTE_USER" environment variable to be the name of the user you're
"authenticated" as.

Excellent, this error message looks like it has come from the actual CGI command itself. Let’s set a couple more variables to help it work … let’s add REQUEST_METHOD as the error message suggested.

$ REQUEST_METHOD=GET DOCUMENT_ROOT=/var/www \
SCRIPT_FILENAME=/usr/lib/cgi-bin/nagios3/tac.cgi \
cgi-fcgi -bind -connect 127.0.1.1:8998

Cache-Control: no-store
Pragma: no-cache
Refresh: 90
Last-Modified: Wed, 07 Jul 2010 01:27:16 GMT
Expires: Thu, 01 Jan 1970 00:00:00 GMT
Content-type: text/html

...

I’ll spare you the rest of the HTML output. This shows us a way of using a simple command-line test to verify that a FastCGI service is running correctly, without involving any front-end webserver. This is useful if you’re getting stuck setting up the front-end webserver, or if you like to have intelligent service dependency monitoring that can diagnose problems more precisely.

Tags: ,

VirtualBox and an openSUSE 11.2 guest


I had an odd need to run an openSUSE 11.2 machine recently, so I installed one under VirtualBox. It worked very well out of the box, with the screen nicely resizing to the VBox window.

However, when I tried to add a shared folder to copy files from the host machine, things started going wrong … :-(

I have a Shared Folder called “hometmp” that shares my ~/tmp directory. Normally this can be easily added to a guest with

$ sudo mount -t vboxsf hometmp ~/tmp

But for some off reason that was failing with a “Protocol error” every time … so I had to do a little digging. It seems that there’s something wrong with the way “mount -t” operates in this case, I’m not interested in openSUSE enough to dig further, but the workaround is to invoke “mount.vboxsf” directly instead. /sbin isn’t on the user path, BTW …

$ sudo /sbin/mount.vboxsf hometmp ~/tmp

And the strangest bit of all — when I went back to my VBox openSUSE to reproduce the error message in order to write this post … the original normal mount option worked just fine!

Tags: ,