The MKII Robot Controller

Posted in Crazy Plans, Hardware on 29 January, 2014 by Alec Waters

I thought I’d briefly share the latest gadget I’ve been tinkering with. You may remember the robot I built for HackFu – I always thought I could do better with the packaging of the controller unit. It was in three pieces, namely the camera receiver, the TV, and the control unit itself:

wirelesscontrollerIn a fit of Wii U inspiration, I’ve managed to get all three components into a single, portable enclosure:

botcontrollerfront

There’s a convenient carry handle on the top, handholds left and right, and you operate the sticks with your thumbs. The screen is one of those cheap TVs you get for use in your car.

The AV receiver’s antenna and tuning knob poke out behind one of the hand-holds. It doesn’t get in the way of your fingers, and the tuning knob has fortuitously ended up in a very convenient place:

botcontrollertunerThe antenna will fold through 180 degrees so it won’t catch on anything when you’re not using it. Next to the antenna is the secondary AV input for the display – by changing channels you can switch from the wireless camera feed to an external one. This means you can do things like hook up another Arduino with a Video Game shield and play Tetris:

botcontrollertetrisHere are some action shots showing the telemetry overlay and the bot itself, TempEx One:

botcontrollerscreen

botcontrollerandbotWith the lid off you can see the XBee for communicating with TempEx and the arrangement of the AV receiver and Arduino:

botcontrollertopoffThere’s a single 12v DC input jack in the bottom left that powers everything.

Things still on the TODO list include:

  • Swap the XBee for one that supports an external antenna. This will be mounted in the left hand hold, flipping up and down like the AV antenna does
  • Addition of a speaker for the camera audio
  • Find a compact 12v battery to remove the need for mains power (any suggestions?)
  • Spray it a suitably impressive colour :)


Alec Waters is responsible for all things security at Dataline Software, and can be emailed at alec.waters@dataline.co.uk

I love it when a plan comes together

Posted in General Security, NSM on 9 January, 2014 by Alec Waters

As defenders, we have many reasons to do our jobs. We want to comply with regulations, protect our employers (and protect our pay cheques!), and just maybe we enjoy the challenge despite the certain knowledge that someday an exploit with our name on it is going to smack us between the eyes.

The “why we do it” is therefore straightforward; what about the “how”? How do we defend? I don’t mean from a technical perspective – at a generic level, what are we trying to achieve?

There are certainly many answers to that question, but I quite like the idea that there are three mutually supporting objectives for defenders. The idea I’m presenting below is probably a little monitoring-centric, but then so am I!

At the top tier, there’s the “Defenders’ Utopia”, namely Prevent-It:

planaIt doesn’t matter what “It” is – if we can prevent all badness, we’ve won! Let’s patch stuff, pentest stuff, educate our users, harden our deployments, use SDL principles and products X, Y and Z to prevent all the badness, guaranteeing us “corporate security hero” status.

Prevent-It is therefore our “Plan A”. Sadly, it’s not enough because Prevention Eventually Fails – we need a Plan B.

preventioneventuallyfailsIf we can’t Prevent-It, Plan B should be to “Detect-It” in a timely fashion:

planabAnd no, third-party breach notification doesn’t count as “timely”! As well as responding to obvious indicators such as AV or IDS hits, we need to be proactive in detection by hunting through all of the instrumentation at our disposal looking for indicators like uncommon or never-before-seen events, unusual volumes of network traffic or event types, Bob logging in from Antigua when you know he’s in Scotland, etc. A solid ability to Detect-It will help you invoke the Intruder’s Dilemma.

“Detect-It” is bigger than “Prevent-It” in the diagram because prevention is hard, and we are more likely to be able to detect things than we are to prevent them if we try hard enough. Attackers have more tactics at their disposal than defenders have preventative measures so you need to be as thorough and as business-tailored as you can be in your monitoring. Know your infrastructure in as much detail as possible in terms of the platform (e.g., MVC app on IIS8 behind a Cisco ASA) and make certain it’s behaving as expected. For a self-contained security team, this latter part might be hard – I’d possibly venture the opinion that an app’s functional spec might be a useful thing for the security team to have. Should app X be sending emails? Doing FTP transfers? Talking to SkyDrive? If the security team don’t understand these details, they may miss things.

Eventually, you’ll likely run up against an attacker who slips past detection and conjures up the defenders’ nightmare of third-party breach notification – you’ve been compromised, you didn’t notice it happen, and now you’re front page news. Plan B has failed – your final recourse is Plan C:

planabc

If we can’t Prevent-It, and we didn’t Detect-It then we have to maintain the ability to Investigate-It. This bit’s biggest because it represents your gathering of logs, network traffic data and other indicators – your monumental programme of “hay collection” (the Detect-It part can be thought of as a “hay removal” process whose output is needles, if you follow my metaphor).

Even boring, routine logs may be worth their weight in gold when Investigating-It – collect as much as is feasible and legal. Even if we don’t have the resource to actually look at all the collected logs as a matter of course, at least we’ve got a huge pool of evidence to trawl through as part of the Incident Response process.

We can also use Investigate-It for retrospective analysis. If a new set of IOCs (Indicators of Compromise) comes to light, we can check them against what we’ve collected so far. Investigate-It also supports your corporate forensic readiness plan – knowing what information you need as part of IR, where to get it, and what you can get quickly without outside help is key.

Stairway to Heaven

If our org has sufficient resources we can move back up the stack, leveraging each tier to improve the one above. If we have an excellent capability to Investigate-It, it means we can improve our ability to Detect-It by hunting through the collected logs in different ways, producing more insightful reports/alerts/dashboards that pull together many disparate log sources. Lessons learned as part of Investigate-It can be incorporated into Detect-It – make sure that the indicators that were missed this time won’t be missed next time.

Moving up again, improving our ability to Detect-It can improve our ability to Prevent-It because we may discover things we don’t like that we can put a stop to before they become a problem (e.g. people emailing confidential docs to their personal email account so they can “work on them from home”, people logging in as local admin, people running apps you don’t like, why is there an active Bluetooth serial port on the CEO’s MacBook, etc) or we may even discover Existing Badness that we can zap.

So now we’re back at the top of the diagram, hopefully in better stead than before we started. Like I say, it’s a monitoring-centric way of looking at things, but if you’re in the game hopefully it’s an interesting perspective!


Alec Waters is responsible for all things security at Dataline Software, and can be emailed at alec.waters@dataline.co.uk

When Worlds Collide

Posted in NSM on 8 November, 2013 by Alec Waters

ELSA is a powerful component of SecurityOnion; one can waste productively use many hours drilling through your logs. The more parsers and dashboards you write for your own specific log sources the more insightful it becomes and pretty soon you’ll be asking yourself questions you never knew you had.

Take the session below as an example:

elsa1This is Bro accounting for a TCP session, showing a local IP address (redacted) sending over 8MB of data to 92.232.36.19 on TCP port 25289. Something like this should raise an eyebrow or two and is certainly worthy of further investigation – why is a local machine having this kind of conversation? Can we rule out foul play? Or is there an innocent explanation? Deerstalkers on, sleuths…

The first thing we can do is find out some more about the remote IP address. You can’t trust rDNS and whois to be totally accurate (or truthful), but a quick whois and dig -x tells us that we’re dealing with what looks like a residential broadband IP address rather than a business (the rDNS lookup is cpc25-newt29-2-0-cust18.19-3.cable.virginm.net). If it were a business with whom we have a relationship there may be an easier answer, but at the moment it looks like our local IP address is talking with a computer in someone’s living room. We still don’t know what the traffic was, though. Exfiltration of Top Secret business plans, maybe?

Maybe we can get some answers by pivoting from ELSA into capME to get a transcript of the session:

elsa2Drat. The plot thickens! Our local IP address has sent over 8MB of data to a computer apparently in someone’s living room, and we can’t tell what it is because it’s quite possibly encrypted. We still can’t rule out a leak of our Top Secret plans! What if 92.232.36.19 is an innocent machine under the control of The Baddies who are using it to pillage all our stuff? Where’s my tinfoil hat?!

Unanswered questions bug me a great deal. Sometimes even NSM can lead you to a dead end. I can research 92.232.36.19 as much as I like by using ELSA et al to look for other log entries that reference it, or by going OSINT crazy, but in this instance I’m all out of clues. What I’d ideally like to be able to do is work out which process on the local IP address made the connection – perhaps this would solve the mystery.

Marching over to the local machine (EnCase dongle in hand) with the intent of seizing it and carrying out a full host examination probably isn’t the most productive use of time. The user of the machine will hate me for stopping them from working, the process will take a long time, and even then it might not answer my questions fully. Not to mention the fact that I don’t have an EnCase licence in the first place.

Enter Carbon Black. I’ll leave it as an exercise to the reader to peruse their website, but suffice to say running Cb on your systems is akin to running process monitor all the time on all your machines, centrally collecting things like process execution trees, file/registry modification attempts, network connections, etc. It’s basically carrying out host-forensic tasks all the time, capturing very volatile events that you may not be able to recover in retrospect.

Did I just say it collected network connections? I wonder if we can ask it about 92.232.36.19?

ELSA is a wonderfully extensible beast; amongst other things, you can write Plugins that can link to other systems to provide extra information based on ELSA searches. Carbon Black has a REST API and easily accessible search URLs – perhaps we can link ELSA and Cb together?

Happily, yes we can. We’ll get to the nuts and bolts of the plugin in a second, but the net result is something like this. By clicking on the “Info” link by our BRO_CONN log entry, we get a link into Carbon Black that will search on the dstip field:

elsa3

Clicking on the Cb link will perform a search for the suspect IP address – provided our browser is logged in, we’ll see this:

elsa4Aha! It’s Spotify, which has a p2p-style protocol that makes use of “random” ports and encryption. According to the article, most of the music you listen to comes from other users’ machines – our mystery connection is likely the transfer of a song from one (local) Spotify user to another.

What we’re seeing above is a specific execution of Spotify, which means that all the events logged against it are those recorded at a specific time on a specific machine. Drilling down on the process, we can see:

elsa5…the process tree. We can see that explorer.exe started Spotify, and that Spotify itself has child processes. We can see that five other machines have the exact same version of Spotify on them, and that it’s a legitimately signed binary. If this were malware, being able to see at a glance how many other machines it’s executed on is a pretty handy thing. As it is, it’s not malware but we might like to speak to the users of the five machines in question if the use of Spotify represents a policy violation.

Searching the 3502 logged events for our suspect IP address:

elsa6…there it is. Drilling down onto the binary itself, we can see:

elsa7Note the convenient link to VirusTotal, and the Download link which you can use to investigate suspected malware in a sandbox.

To be able to go straight from a network-derived indicator to the process that caused it seems to me to be a pretty powerful ability!

Putting it into practice is fairly straightforward. Step one is to subclass the “Info” Perl class by creating /opt/elsa/web/lib/Info/Cb.pm as follows:

package Info::Cb;
use Moose;
use Data::Dumper;
extends 'Info';

sub BUILD {
    my $self = shift;
    if ($self->conf->get('info/cb/url_templates')){
        foreach my $template (@{ $self->conf->get('info/cb/url_templates') } ){
            push @{ $self->urls }, sprintf($template, $self->data->{dstip});
        }
    }
}

1;

The code above references configuration entries from /etc/elsa_web.conf. Add the following under “info” alongside the entries for “snort”, “url” and “windows”, altering the URL as appropriate for your Cb installation:

"cb": {
   "url_templates": [ "https://carbonblack/#search/cb.urlver=1&q=%s" ]
 }

Finally, we need to tell ELSA which classes to apply the plugin to. Add the following under “plugins”:

"BRO_CONN": "Info::Cb"

That’s the lot. You might need to restart Apache, but once done you should be able to click “Info” on a BRO_CONN result and have a properly populated link into Cb, searching on BRO_CONN.dstip.

This is my first attempt to link ELSA and Cb, and it’s quite a basic one. ELSA also supports transforms to which results can be “piped” – examples that ship with the product include whois, dnsdb and cif. A Cb transform could perform more flexible queries, enriching an ELSA result set with supplementary information from Cb. Stay tuned; I’ll post again if I come up with something useful!


Alec Waters is responsible for all things security at Dataline Software, and can be emailed at alec.waters@dataline.co.uk

HackFu 2013 challenge teardown – Part Two

Posted in Crazy Plans, Packet Challenge on 24 September, 2013 by Alec Waters

Part One of this post is here; this time I’m going to talk about TempEx and its controller:

rover-final

I for one welcome our new robot overlords

wirelesscontroller

TempEx One! You muussst obeeeeeeyyyyy me!

Parts list

From the point of view of the challenge, TempEx is mostly chrome, but we all know that this is the element upon which all coolness is built and we should seek it out with ruthless determination. The core of TempEx is a DFRobotShop rover which is basically a stretched Arduino UNO with tracks and motors. The tracks, wheels and gearboxes are all standard Tamiya model parts, with custom brackets holding the whole lot to the mainboard. It’s a pretty nifty bit of kit, but it needs a bit more than the basic kit to be truly useful.

Firstly, it needs a bit more payload space; this is easily catered for with the expansion plate which sits above the mainboard on standoffs. This gives you considerably more space to work with:

expansionplate

There are plenty of cut outs that you can use to mount equipment, including holes specifically for mounting servos. In terms of payload, TempEx needed to carry an infra-red camera and a rangefinder on a steerable mount like this one from Dagu. Controlling servos with an Arduino is pretty straightforward in concept although surprisingly challenging to execute in an elegant fashion, but we’ll get on to that a bit later on.

The rangefinder is an HC-SR04, which can be had on eBay for a couple of pounds. It’s easy to use (even easier with a decent library) and pretty accurate for the price, although you need to get a good return “bounce” to get a reading – if you’re facing a surface at 45 degrees to the sensor you’re not likely to get a return at all.

I scored a cheap 900Mhz IR camera on eBay:

wirelesscam

The camera can be driven from a 9v battery which gets drained pretty quickly, even more so when it’s dark and all the IR LEDs are turned on. To get around this I used lithium ones which when I tested them gave over five hours of service with no degradation in picture or signal, easily long enough to last through each team’s attempt at the challenge.

At this point, we’ve got enough gear to build a rover that you can drive around tethered via USB – not entirely practical. Two choices for wireless control are Bluetooth and ZigBee/XBee. I wanted to have a controller that worked without a PC so I went for the XBee option because it came with two radios, one for the rover and one to put in the controller.

Conceptually, control of the rover is straightforward. The ‘wasd’ sample is a useful base, reading a character from the serial port and operating the two motors accordingly:

int E1 = 6; //M1 Speed Control
int E2 = 5; //M2 Speed Control
int M1 = 8; //M1 Direction Control
int M2 = 7; //M2 Direction Control

void setup(void)
{
  int i;
  for(i=5;i<=8;i++)
  pinMode(i, OUTPUT);
  Serial.begin(9600);
  Serial.println("setup");
}

void loop(void)
{
  while (Serial.available() < 1) {} // Wait until a character is received
  char val = Serial.read();
  int leftspeed = 120; //255 is maximum speed
  int rightspeed = 120;
  switch(val) // Perform an action depending on the command
  {
    case 'w'://Move Forward
    case 'W':
      forward (leftspeed,rightspeed);
      break;
    case 's'://Move Backwards
    case 'S':
      reverse (leftspeed,rightspeed);
      break;
    case 'a'://Turn Left
    case 'A':
      left (leftspeed,rightspeed);
      break;
    case 'd'://Turn Right
    case 'D':
      right (leftspeed,rightspeed);
      break;
    default:
      stop();
      break;
  }
}

void stop(void) //Stop
{
  digitalWrite(E1,LOW);
  digitalWrite(E2,LOW);
  Serial.println("stop");
}

void forward(char a,char b)
{
  analogWrite (E1,a);
  digitalWrite(M1,LOW);
  analogWrite (E2,b);
  digitalWrite(M2,LOW);
  Serial.println("forward");
}

void reverse (char a,char b)
{
  analogWrite (E1,a);
  digitalWrite(M1,HIGH);
  analogWrite (E2,b);
  digitalWrite(M2,HIGH);
  Serial.println("reverse");
}

void left (char a,char b)
{
  analogWrite (E1,a);
  digitalWrite(M1,HIGH);
  analogWrite (E2,b);
  digitalWrite(M2,LOW);
  Serial.println("left");
}

void right (char a,char b)
{
  analogWrite (E1,a);
  digitalWrite(M1,LOW);
  analogWrite (E2,b);
  digitalWrite(M2,HIGH);
  Serial.println("right");
}

I ended up with a nine-way control of q/w/e, a/s/d, and z/x/c using ‘s’ for stop and q, e, z, and c for large-radius turns running one track at full speed and the other somewhat slower. a and d were for zero-radius turns where the rover spins on the spot.

Moving from a USB tether to wireless via XBee was straightforward. Out of the box the XBee radios act as a kind of cable replacement – whatever one transmits the other receives. Leaving aside the security implications of this default config (and the hacker-rich environment in which TempEx had to operate) moving away from the tether starts by using the XBee to serial board that comes with the rover kit.

dfrobot-xbee-usb-adapter-v2

This appears to a PC as a serial port so you can just attach a terminal app to it and enter characters just like you would in the Arduino serial monitor window. The final step is to ditch the USB port altogether and use the serial TX/RX lines with a second Arduino, again just sending single characters for the rover to interpret.

There were a couple of gotchas along the way. Firstly, the rover would occasionally throw a track when turning, something that could be seen as a result of the sprocket wheels slowly moving outwards on their axles. I was a bit reluctant to glue these in place, but fortunately no tracks were shed during HackFu.

Secondly, I had trouble with power brownouts, especially when doing something like going from full forwards to full reverse. I made three changes to cater for this:

  • Moar axle grease! A tube of this comes with the gearbox for a very good reason.
  • I switched from using the 3.7v LiPo battery to the 4xAA holder. Using rechargeable NiMh AAs gave a voltage of between 5 and 6 volts, about double the nominal voltage of the included motors. The rover went like a rocket with the AAs driving these, but at a cost. Adam Borrell has done some testing with motors like these running under over-voltage conditions. I’m glad I read this before HackFu because the brushes can wear out in a matter of hours – after all of the development hours TempEx had on the clock there was a distinct possibility that the motors would fail during the event. I replaced the 3v motors with 6v ones, and made sure I had spares on the day.
  • Finally, I re-wrote the code to be a little kinder on the drivetrain. Instead of slamming the motors from zero to max revolutions in one hit, I gently ramped the RPMs up so that it took about half a second to get to top speed.

Operating the pan/tilt rig was done in a similar way to the motors, using r/t/y, f/g/h and v/b/n, with t being down, f for left, r for down/left etc. g centred the rig forwards. Similar “kind” code was written for the servos – if slamming a motor from zero to max is unkind, doing the same with a servo is plain brutal! With the mass of the camera to shift as well as the rig itself, it’s important that the servo take its time to reach the desired rotation. For each pass through the Arduino’s loop() the servo would ask “have I rotated far enough yet?” and if not it shifted another couple of degrees towards the goal.

Here is some sample code that moves a servo “kindly” under the command of a Wii Nunchuk to illustrate:

#include <Servo.h> 
#include <Wire.h>
#include <ArduinoNunchuk.h>

#define BAUDRATE 19200

ArduinoNunchuk nunchuk = ArduinoNunchuk();
Servo myservo;  // create servo object to control a servo 
 
int potpin = 0;  // analog pin used to connect the potentiometer
int val;    // variable to read the value from the nunchuck
int servopos; // where the servo is
int threshold = 8; // trigger for movement

void setup()
{
  ///////////////////
  // SERIAL
  Serial.begin(BAUDRATE);
  ///////////////////
  
  ///////////////////
  // NUNCHUK
  nunchuk.init();
  nunchuk.update();
  servopos = map(nunchuk.analogX, 25, 221, 0, 179);     // Get initial value
  ///////////////////
  
  ///////////////////
  // SERVO
  myservo.attach(9);
  myservo.write(servopos);  // initialise position
  ///////////////////  
}
 
 
void loop() 
{ 
  nunchuk.update();

  val = map(nunchuk.analogX, 25, 221, 0, 179);     // scale it to use it with the servo (value between 0 and 180) 


  Serial.print(nunchuk.analogX, DEC);
  Serial.print(' ');
  Serial.print(val);
  Serial.print(' ');
  Serial.print(servopos);
  Serial.print(' ');  

  if( ( servopos < val ) && ( val - servopos > threshold ) )
  {
    // Moving to the right
    servopos += int( threshold / 2 );
    Serial.println('R');
  }
  else if( ( servopos > val ) && ( servopos - val > threshold )  )
  {
    // Moving to the left
    servopos -= int( threshold / 2 );
    Serial.println('L');
  }
  else
  {
    // Not moving!
    Serial.println("STOP");    
  }
  
  if( servopos < 0 )
    servopos = 0;
  else if (servopos > 179 )
    servopos = 179;
    
  myservo.write(servopos);                  // sets the servo position according to the scaled value 
  delay(10);                           // waits for the servo to get there 
} 

It just goes to show, it ain’t what you do, it’s the way that you do it:

Moving swiftly on…

…to the controller. There are four bits to this:

  • An Arduino Uno
  • An XBee radio sitting on the aforementioned USB adapter hooked up to the Arduino’s serial port
  • A pair of two-axis potentiometers, one for controlling the rover and one for steering the pan/tilt rig
  • A Nootropic Design Video Experimenter board, a bundle of awesome if ever there was one. The output of the camera receiver plugs into the video input, with a TV on the video out

The whole lot fit quite nicely into an OKW enclosure that I had left over from the now-defunct PierToPier.net WiFi project (a fully-routed mesh wireless network on Brighton beach for public use – ten years ago!).

The mode of operation is as follows:

  • Read the x and y values from the two sticks and convert them to the wasd-style character
  • Send the character to TempEx by printing it to the serial port, which sends it to the XBee, which sends it to the other XBee on TempEx where the rover’s code takes over
  • TempEx acts on the received character and takes a reading from the rangefinder. This is sent back to the controller via the XBees
  • Back on the controller, read the range from the serial port and use the Video Experimenter board to overlay it on the TV feed from the camera
  • Repeat :)

Step one was an interesting coding challenge – converting a pair of 0-to-255 values to a quadrant in a 3×3 grid in an elegant and efficient manner. I don’t want to blab my method here because I want to use it as a teaching case in the Arduino workshops I’ll be running soon. If you want a hint, contact me via Twitter and I’ll give you a nudge in the right direction.

The VE board displayed a bit more than just the range – I wanted it to look a bit like a heads up display in a military aircraft:

Tower, this is Ghostrider requesting a flyby

The Pan/Tilt markers have indicators that show in which direction you’re steering the camera, the L/R indicator shows which direction the two tracks are moving in, the range is at the bottom, comm errors are shown at the top, and the targeting reticle in the middle is there to make you feel extra-menacing. Here’s a less-than-clear shot of it in action at HackFu:

TempExHUD2

The VE’s overlay was a little light but perfectly legible despite what the picture above looks like. I found that by feeding the camera receiver into a VCR and attaching the VCR to the VE board produced better results, showing that the problem is more likely the output of the camera transmitter rather than the VE board.

I wanted to cater for the case where comms with TempEx were interrupted due to interference or excessive range, so in an attempt to implement reliable control the following steps were taken:

  • If neither joystick is deflected from its home position the controller continually sends ‘s’ (stop) to TempEx. If the controller gets a range in return it knows that TempEx is still there. If we don’t get anything back for two seconds, display NO COMM on the HUD to let the user know.
  • When a joystick is moved, continually send the indicated character to TempEx. This means that, moving or not, TempEx is expecting to receive something from the controller all the time. If TempEx doesn’t hear anything for two seconds it will stop both tracks and centre the pan/tilt rig.

This means that you can never have the case where TempEx runs off out of control if the wireless comm breaks down (it doesn’t stop teams from hitting obstacles at oblique angles and tipping TempEx over, but that’s another story!)

So there you have it, TempEx and its controller. I had a ton of fun putting the challenge together, and I think people had fun playing it. As I’ve said, HackFu is beyond awesome – keep your ear to the ground sometime next Spring here, here and here for a chance to win a ticket for HackFu 2014. Maybe see you there!


Alec Waters is responsible for all things security at Dataline Software, and can be emailed at alec.waters@dataline.co.uk

HackFu 2013 challenge teardown – Part One

Posted in Crazy Plans, Packet Challenge on 9 July, 2013 by Alec Waters

Words have not yet been invented to describe the utter awesomeness of HackFu. Run by MWR Infosecurity, it’s two extremely intense days of team-based hacking, puzzling and pwning, tackled by meanshackfu of skill, luck and sometimes even outright cash bribery (Facebook photo albums here and here). Many thanks to the RAF Air Defence Radar Museum for providing the venue – it’s a great place to visit, go check it out!.

As with last year, I supplied a challenge for the event. I’m going to document it here, because it was a little, errm, “different”, and I learned an awful lot whilst I was screwing it together. HackFu is all about learning stuff, and there’s no point in learning without sharing the knowledge, right?

tl;dr

Booby trapped Aztec temple. Violent kinetic defences. Golden Idols for the taking. Robots with night vision and sonar. Four distinct forms of wireless comms.

Enter the Maze…

All HackFu events are themed, and this year’s theme was The Crystal Maze. My challenge was for the Aztec zone, and had quite a straightforward aim – retrieve the Golden Idol from the altar in the temple and discover its full name. It’s not going to be as easy as walking in there and picking it up – as this journal entry shows, we could be entering a high-threat environment. How to minimise the risk? In “The Phantom Menace,” Rune Haako was faced with a similar situation: “Are you brain-dead? I’m not going in dere with two Jedi. Send a droid.”

Send a droid, you say? Enter TempEx One, the remotely operated temple explorer:

rover-finalTempEx allows the players to reconnoitre the temple, detect traps, discover clues, and ultimately permits them to formulate a plan to safely enter and retrieve the Golden Idol from the altar. TempEx is equipped with an ultrasonic range finder and a wireless infra-red camera, both mounted on a steerable pan/tilt mount.

TempEx is remotely controlled by means of a two-stick controller, shown here with its lid off:

wirelesscontrollerThe left stick drives TempEx; the right one operates the pan/tilt rig. The camera receiver is shown in the background, and its output is pumped through a TV overlay board. This means I can draw a nice heads-up-display over the camera feed that shows command inputs from the sticks, telemetry received from TempEx, and a cool targeting reticle to make the user feel extra-menacing. With the lid on, only the sticks poke out:

controllersmallAnd the altar? It’s equipped with:

  • A light sensor – keep it dark in there, or face the consequences!
  • A pressure pad – remember what happened to Indy when he tried to swipe the Idol in Raiders of the Lost Ark!
  • Tripwires – careful where you step!
  • Active defences – eye protection mandatory!

Finally, we have the gameplay element of the challenge. It’s got to be fun, it’s got to be do-able, it’s got to have scoring in order to rank the teams, and it has to involve some hacking (otherwise the event would just be called “Fu”)

Hopefully…

…I’m keeping your attention. I built and coded all of the hardware above, and I’m going to document it one piece at a time. It’s a journey of discovery in which I struggle to remember which end of a soldering iron to hold and am forced to deploy several “Plan B’s” in pursuit of realising my ideas.

The Altar

The altar is basically an Arduino Mega 2560 mounted inside an appropriately decorated biscuit tub with one of my kids’ toys on top to give the Golden Idol somewhere to sit. It’s a pretty squat assembly, but from TempEx’s point of view seven or eight inches off the ground it looks pretty tall, especially with the idol sat on the top:

altar

The Golden Idol is definitely made of gold, honest:

goldenidol

I’d never touched an Arduino before embarking on this challenge, but when you take a look at the ingredients in an Arduino Boffin Kit things like tripwires and light sensors suddenly don’t seem impossible to implement. Books like Beginning Arduino confirm the suspicion – it’s all possible, and even relatively straightforward.

For the hardware side of the Altar, I wanted four tripwires, some kind of pressure pad, and a light sensor. I also wanted to have some kind of visual indication that the pressure pad was being read, so that people could time some kind of Indy-style switchout, taking the Golden Idol and replacing it with something else. The idea was that players would start with a given points score which would be deducted from when they trip the traps. Tripping the light sensor and pressure pad were considered major sins when compared to tripping the wires – I wanted to guard against people just turning on the lights and swiping the Idol without “playing the game”.

Let’s start with the tripwires. They’re basically switches, and that’s what I used for my first prototype. From the Arduino’s perspective, they were normally-open switches attached to digital pins configured as INPUT_PULLUP – this means that they will read high until they are dragged low, in this case by my switches being closed.

The pressure pad and light sensor were implemented as a force-sensitive resistor and a light-dependant resistor. Both were configured in series with a fixed-value resistor, forming a voltage divider. This means that by attaching the voltage divider’s Vout to an Arduino analogue pin I can determine “how much weight is on the pad” and “how light it is in the room”.

The first prototype for the Altar looked like this, built in the traditional fashion on breadboard with jumper wires:

altarprototypemarkedupThe light-dependant resistor is highlighted blue; red shows two switches pretending to be tripwires (there were four in the final version), green is the force sensitive resistor and cyan shows an LED that flashes when the FSR is being read. The LED highlighted white was used as a debugging aid to show me when all the traps were tripped. The Arduino sketch for all of this was reasonably straightforward (final version is shown later on).

Great! It’s the Altar done! Check it off the list!

Orrrrr, not. What we have here is strictly a prototype, knocked up over the course of an evening. This isn’t a deployable solution – we’ve got to “make” something, based upon the breadboarded proof of concept.

The tripwires were the easiest bit. On the breadboard above, the switches were normally-open (causing the INPUT_PULLUP pins to read high) until they were closed (causing the pin to read low). To replicate this, I took some clothespegs and drilled holes in the pads and ran wires through them:

tripwire-closeThe idea is that when the peg closes the two wires touch, making the circuit and pulling the Arduino pin low. To (perhaps unnecessarily) aid conduction, I wrapped the ends in foil, resulting in this:

tripwiresOK, now we’ve replicated the switches on the breadboard. How to make these into practical tripwires? To keep the pegs “open”, I used strips of plastic cut from a drinks bottle. Next, I tied some fishing line to the strip and anchored the other end to a fixed point. The net result is a working tripwire – if you knock the fishing line, you’ll pull the plastic strip out of the peg, which will make the circuit and cause the Arduino pin to read low, telling it that the wire has been tripped. Boom!

The FSR, LDR and flashing LED were a slightly different proposition – I had to get out the soldering iron and fabricate a circuit on stripboard. I wanted to take a modular approach, so I soldered some stackable pin headers onto the stripboard so that I could run removable wires from it back to the Arduino. More stackable headers were used as “sockets” for the tripwires. The finished stripboard is the rectangular affair that can be seen standing proud of the rim of the Altar in the picture below:

altarprototype4I mounted the Arduino in a case I had lying around; the case was eventually mounted in the decorated biscuit tub that you can see sitting under the Altar in the first picture of it above.

I have got an LCD display attached to the Arduino, from a dirt-cheap “lucky bag” from Maplin. This was originally intended to be part of the challenge, showing several lines of clues for the players. I got caught up in the fun of hooking up the display and I had it all working nicely before I realised the obvious – TempEx’s camera is an active IR one. This means that it has an IR-sensitive camera surrounded by a ring of IR LEDs – basically infra-red torches. This means that, when viewed on the camera, the LCD display is completely obscured by the reflection of the IR LEDs and you can’t read a single thing on it… Cue Plan ‘B’, which involves having the clues on a piece of paper hidden somewhere in the temple. Crude and low tech, but gets the job done!

We’re nearly there with the Altar. It can detect intrusions with all its various sensors – all it needs to be able to do is ward people off. My eldest son was suggesting things we could do when the traps were tripped, and his least lethal suggestion was to shoot them with a Nerf gun. Fortunately, MWR have a Nerf Vulcan in the corporate toybox – all I had to do was hook it up.

I wasn’t keen on destructively modding the Vulcan. Instead, I put a strip of plastic in the battery compartment between one of the spring terminals and the adjacent battery, with long wires snaking out of the compartment from each side of the strip. By turning on the Vulcan’s power and taping the trigger shut it can now be fired by touching the ends of the wires together. Satisfied that it’s working like this, we can put the ends of the wires into a relay that we can control from the Arduino – at this point, we have an Arduino-controlled Nerf gun, which is extremely cool in itself. I used a convenient relay board for this, having the relay energise for two seconds when one of the tripwires was pulled – this was sufficient to unleash a volley of about 6-7 darts.

relayboard

As interesting as the Altar hopefully is, it doesn’t pose much of a hacking challenge – something else is needed. Time to put the soldering iron away and think about the “gameplay” element of things.

The idea was that the altar would have a “remote management” interface which, when discovered and activated, would allow players to:

  • See the status of the traps
  • Decrease the polling interval of the FSR (to make it physically possible to swap the golden idol for a stone one)
  • Increase the trip threshold of the light sensor (so that you can send someone in with a glowstick so they can see where they’re going).

The altar management interface was implemented as a simple set of web pages on a small PC attached to the Arduino in the altar via USB. Communication was by means of a simple serial protocol over the emulated serial port that appears when you connect the two together (/dev/ttyACM0 in my case).

Here’s where a slight oddity of the Arduino platform threw a spanner in the works. By default, when you open a serial port the DTR line goes low for a short period of time. This “DTR waggle” is seen by the Arduino, which then performs an auto-reset (reboot) and starts running the sketch from scratch. This is somewhat problematic if you’re trying to keep track of someone’s score!

There’s a page on the Arduino site devoted to disabling this feature. I wasn’t keen on physically altering my Mega, nor could I make any of the software solutions work. I found another solution here – by executing “tail -f /dev/ttyACM0″ on the PC, the serial connection is kept open and my scripts could talk to the Arduino without resetting it.

So now the traps are set, the remote management interface is deployed, and the Altar can be controlled via a PC. Here is how the challenge was intended to be played:

  1. From the safety of a room outside the temple, read the journal entry and TempEx manual.
  2. Cautiously open the door to the darkened temple. This will trip the tripwire controlling the Vulcan, causing the player to get a bunch of Nerf darts in the head. Aside from being for the amusement of the challenge creator, this step is designed to put players on edge and make them more cautious than they need to be. But mostly it was for the amusement of the challenge creator.
  3. Send in TempEx and have a look around. Things it will see include the Golden Idol sitting on the Altar at the far end of the room (with a light that’s flashing really fast), the tripwires, a stone Idol, and if you look hard enough, some clues written on the wall (these were the clues that I intended to show on the LCD).
  4. The clues list some “control codes” to turn “remote management” on and off. There is also the statement that something is “listening on: xx:xx:xx:xx:xx:x”.
  5. The xx:xx.. thing looks a bit like a MAC address, but it’s not – it’s one nybble short in the last byte. It’s actually a phone number, and you can turn remote management on and off by sending the command codes to it via SMS. The codes are received by a GPRS modem (below) attached to the PC, and are parsed by a script run by gsmsmsd.
    gprsmodemThe script checks the content of the message, and will communicate with the Arduino if an appropriate message is present. A response message is then sent to the sender informing them of the result. I implemented a couple of commands for my own purposes, including retrieving the current trap status and score, and resetting all the trap statuses.
  6. If remote management has been turned on, the player receives the following message: “Probing for – 4zt3c : Listening on – 192.168.99.100:80 – Access Token – Sallah : Password – Kobayashii”. Oddly enough, gsmsmsd seemed to duplicate the last character when sending the reply, hence the two i’s when only one is in the script.
  7. Hopefully, the word “probing” will make the players think of wifi and set up an access point serving up an SSID of “4zt3c” (hostapd or airbase-ng could be used for this).
  8. Once the Altar has connected to your wireless network, we dutifully connect a web browser to http://192.168.99.100, as directed by the SMS. A login screen appears:
  9. management…but the supplied Access Token and Password don’t work. Whoops. Investigation of the page source shows some client-side validation JavaScript that attempts to prevent the use of several characters including <, > and ‘
  10. Knowing that most of the players will be skilled pentesters, I was hoping that they would see this as a potential indicator of a SQL Injection vulnerability. Sure enough, bypassing the JavaScript and supplying values with single quotes in them causes a MySQL error to be displayed…
  11. …but there isn’t a MySQL database, let alone a SQLi hole. The entire site is fake, designed to make people waste their time. Nothing you can enter into the form will log you in, because there’s nothing to log in to. Deception is a completely valid defensive technique!
  12. Examination of the HTTP host headers sent by the server shows that there’s one called “nazcaTrail” whose value is “clupea_harengus_russus_0120-bona_fide_0177322″. “Clupea Harengus Russus” roughly translates as “red herring”, and 0120 is 80 in Octal. The message I was trying to send was that the red herring is on port 80, and the “bona fide” site is on port 65234 (decimal representation of the octal 0177322).
  13. Finally, we have a site we can log in to at http://192.168.99.100:65234. Sure enough, it shows the state of all the traps and offers a facility to tweak the pressure pad polling interval and light sensor trip threshold. There is also a schematic of the altar showing how it all hangs together.
  14. After tweaking the pad’s polling interval, TempEx’s camera will show the Altar’s light flashing much more slowly. A brave adventurer will go in, pick up the stone idol, negotiate the tripwires, and will attempt to swap the stone idol for the golden one on the Altar in between light flashes. Except they can’t see the flashes because the LED is an infra-red one, and can only be seen on TempEx’s camera feed. To solve this problem some teams resorted to banging on the wall, others installed metronome apps on their phones and synced them up to the flashing of the LED.
  15. However they approached the LED problem, eventually the adventurer would emerge from the temple clutching the golden idol. Underneath the idol was written its name – the answer to the challenge! But…
  16. …the challenge asks for the idol’s full  name. Closer examination of the remote management website shows that the idol is running at 13.56MHz, which is an RFID frequency. Scanning the idol with an NFC-capable phone will tell you the idol’s surname.

Job done! Another successful quest for the Man In The Hat!

Here’s the Arduino sketch running the altar. I’m using the Metro library as a pseudo-timer to control the FSR polling interval and the update frequency of the (redundant) LCD display:

// Pseudo-timer library
#include <Metro.h>

// LCD driver code
#include <LiquidCrystal.h>

// RW,EN,RS on the LCD
int lcdRW = 42;
int lcdEN = 45;
int lcdRS = 44;

// The LEDs on the LCD
int lcdLED1 = 43;
int lcdLED2 = 40;

// The button on the LCD
int lcdButton = 35;

// initialize the library with the numbers of the interface pins
LiquidCrystal lcd(lcdRS, lcdRW, lcdEN, 48, 49, 46, 47);

// LDR to ensure darkness in the room
int LDR = 0;
int ldrLowThreshold = 200;
int ldrHighThreshold = 590;
int LDRThreshold = ldrLowThreshold;
bool ldrIsThresholdLow = true;

// FSR to check for presence of Golden Idol
int FSR = 1;
int FSRThreshold = 600;

// Tripwires - normally open, read high when untripped
#define numTripWires 4
int tripWireOne = 12;
int tripWireTwo = 11;
int tripWireThree = 6;
int tripWireFour = 7;

// Relay board - Nerf gun is attached to this
int relay = 8;

// Lights up when you trip all the traps
int alarmIndicator = lcdLED2;

// Lights up when the FSR is being polled
int fsrIndicator = 10;

// Polling speeds in milliseconds
int fsrFastPoll = 100;
int fsrSlowPoll = 1000;
Metro fsrMetro = Metro(fsrFastPoll);
bool fsrFastPolling = true;

// Health counter - your "score", deducted from when you trip traps
int health = 1400;

// Sensor penalties and tripped flags
int LDRPenalty = 300;
bool LDRTripped = false;
int FSRPenalty = 300;
bool FSRTripped = false;
int tripWirePenalty[numTripWires] = { 200, 200, 200, 200 };
bool tripWireTripped[numTripWires] = { false, false, false, false };
int tripWirePins[numTripWires]	= { tripWireOne, tripWireTwo, tripWireThree, tripWireFour };

// Display modes
const int dispModeListeningOnText = 0;
const int dispModeListeningOnValue = 1;
const int dispModeControlCodeOneText = 2;
const int dispModeControlCodeOne = 3;
const int dispModeControlCodeTwoText = 4;
const int dispModeControlCodeTwo = 5;
const int dispModeRemote = 6;
const int dispModeProbingFor = 7;
// How many modes?
const int dispModesRemoteOff = 7;
const int dispModesRemoteOn = 8;
int numModesActive = dispModesRemoteOff;

// Set inital display mode
int dispMode = dispModeListeningOnText;

// Set pseudoTimer for display
Metro dispMetro = Metro(2000);

// Holds data received on serial port
String serialInput = "";
// Is the message complete, terminated by # ?
bool serialInputMessageComplete = false;	

// Is remote management on on the PC?
bool remoteManagementActive = false;

// Phone number to listen on
String listeningOn = "07:xx:xx:xx:xx:x";

void setup()
{
	// Set up serial port for debugging
	Serial.begin(9600);

	// reserve 200 bytes for serialInput:
	serialInput.reserve(200);
	
	// Set up pinmodes
	pinMode( alarmIndicator, OUTPUT );
	pinMode( fsrIndicator, OUTPUT );	
	pinMode( lcdLED1, OUTPUT );
	pinMode( lcdLED2, OUTPUT );	
	pinMode( lcdButton, INPUT );		
	for( int tripWire = 0; tripWire < numTripWires; tripWire++ )
		pinMode( tripWirePins[tripWire], INPUT_PULLUP );	
	pinMode( LDR, INPUT );
	pinMode( FSR, INPUT );
	pinMode( relay, OUTPUT );		

	// Turn off alarmIndicator and fsrIndicator
	digitalWrite( alarmIndicator, LOW );
	digitalWrite( fsrIndicator, LOW );	

	// Turn off the LEDs on the LCD
	digitalWrite( lcdLED1, LOW );	
	digitalWrite( lcdLED2, LOW );	 
	
	// set up the LCD's number of columns and rows: 
	lcd.begin(16, 2);
	
	// Turn off relay
	digitalWrite( relay, LOW );
}

void loop()
{ 
	checkLCDButton();
	health -= checkLDR();
	health -= checkFSR();
	health -= checkTripwires();
	if( health <= 0 )
		digitalWrite( alarmIndicator, HIGH );

	updateDisplay(); 
	
	if( serialInputMessageComplete )
		processSerialInput( serialInput );
}

///////////////////////////////////////////////////////////////
// Updates the LCD
///////////////////////////////////////////////////////////////
void updateDisplay()
{
	if( dispMetro.check() == 1 )
	{	
		switch( dispMode )
		{
			case dispModeListeningOnText:
				lcd.clear();
				lcd.print( "Listening on:" );						
				break;
			case dispModeListeningOnValue:
				lcd.clear();
				lcd.print( listeningOn );									
				break;
			case dispModeControlCodeOneText:
				lcd.clear();
				lcd.print( "Control code 1:" );									
				break;
			case dispModeControlCodeOne:
				lcd.clear();
				lcd.print( "QZ = rmtmgmt on" );												
				break;
			case dispModeControlCodeTwoText:
				lcd.clear();
				lcd.print( "Control code 2:" );												
				break;
			case dispModeControlCodeTwo:
				lcd.clear();
				lcd.print( "JV = rmtmgmt off" );															
				break;
			case dispModeRemote:
				lcd.clear();
				lcd.print( "Remote mgmt: " );			
				lcd.setCursor( 13, 0 );
				lcd.print( remoteManagementActive ? "Y" : "N" );				
				break;
			case dispModeProbingFor:
				lcd.clear();
				lcd.print( "Probe for: 4zt3c" );						
				break;
			default:
				dispMode = 0;
		}
		
		// Cycle display
		if( ++dispMode >= numModesActive )
			dispMode = 0;
	}
}

///////////////////////////////////////////////////////////////
// Checks the LDR against the threshold
// Returns penalty
///////////////////////////////////////////////////////////////
int checkLDR()
{	
	int penalty = 0;
	
	if( !LDRTripped )
	{
		// Read LDR
		int val = analogRead( LDR );
 
		if( val > LDRThreshold )
		{
			penalty += LDRPenalty;
			LDRTripped = true;
		}
	}

	return( penalty );
}

///////////////////////////////////////////////////////////////
// Checks all tripwires
// Returns accumulated penalty
///////////////////////////////////////////////////////////////
int checkTripwires()
{
	int penalty = 0;

	for( int tripWire = 0; tripWire < numTripWires; tripWire++ )
	{
		if( !tripWireTripped[tripWire] )
		{
			if( digitalRead( tripWirePins[tripWire] ) == LOW )
			{
				penalty += tripWirePenalty[tripWire];
				tripWireTripped[tripWire] = true;
				
				if( tripWire == 3 )
				{
					// Fire the Nerf gun! Ahahahhahahaaaaaa!
					digitalWrite( relay, HIGH );		
					delay( 2000 );
					// Cease fire!
					digitalWrite( relay, LOW );
				}
			}
		}
	}

	return( penalty );
}

///////////////////////////////////////////////////////////////
// Checks the FSR
// Returns penalty
///////////////////////////////////////////////////////////////
int checkFSR()
{	
	int penalty = 0;
	
	if( fsrMetro.check() == 1 )
	{	
		// Turn on LED
		digitalWrite( fsrIndicator, HIGH );			
	
		if( !FSRTripped )
		{
			// Read FSR
			int val = analogRead( FSR );
			
			if( val < FSRThreshold )
			{
				penalty += FSRPenalty;
				FSRTripped = true;
			}
		}
	
		// Delay to blip the LED
		delay( 10 );
		// Turn LED off
		digitalWrite( fsrIndicator, LOW );			
	}
	
	return( penalty );
}

///////////////////////////////////////////////////////////////
// Checks status of button
// Resets sensors when pressed
///////////////////////////////////////////////////////////////
void checkLCDButton()
{
	if( digitalRead( lcdButton ) == HIGH )
	{
		resetTraps();
		digitalWrite( lcdLED1, HIGH );	
	}
	else
		digitalWrite( lcdLED1, LOW );	 
}

///////////////////////////////////////////////////////////////
// Resets everything for the next team!
///////////////////////////////////////////////////////////////
void resetTraps()
{
		// Reset health
		health = 1400;
		FSRTripped = false;
		fsrMetro.interval( fsrFastPoll );
		fsrFastPolling = true;				
		for( int tripWire = 0; tripWire < numTripWires; tripWire++ )
			tripWireTripped[tripWire] = false;
		LDRTripped = false;
		LDRThreshold = ldrLowThreshold;
		ldrIsThresholdLow = true;	
		numModesActive = dispModesRemoteOff;
		remoteManagementActive = false;		
		digitalWrite( lcdLED2, LOW );	 
}	

///////////////////////////////////////////////////////////////
// SerialEvent occurs whenever a new data comes in the
// hardware serial RX.	This routine is run between each
// time loop() runs, so using delay inside loop can delay
// response.	Multiple bytes of data may be available.
///////////////////////////////////////////////////////////////
void serialEvent() 
{
	while( Serial.available() ) 
	{
		// get the new byte:
		char inChar = (char)Serial.read(); 
		// add it to the inputString:
		serialInput += inChar;
		// if the incoming character is a #, set a flag
		// so the main loop can do something about it:
		if (inChar == '#') 
			serialInputMessageComplete = true;
	}
}

///////////////////////////////////////////////////////////////
// Processes input from the PC
///////////////////////////////////////////////////////////////
void processSerialInput( String message )
{
	if( message.startsWith( "STATUS" ) )		// Return sensor status
	{
		Serial.print( "STATUS FSR " );
		Serial.print( FSRTripped ? "T " : "N " );
		Serial.print( fsrFastPolling ? "F" : "S" );
		Serial.print( " LDR " );
		Serial.print( LDRTripped ? "T " : "N " );		
		Serial.print( ldrIsThresholdLow ? "L" : "H" );
		for( int tripWire = 0; tripWire < numTripWires; tripWire++ )
		{
			Serial.print( " TRIP " );
			Serial.print( tripWire + 1 );				
			Serial.print( tripWireTripped[tripWire] ? " T" : " N" );
		}
		Serial.print( " RMGMT " );
		Serial.print( remoteManagementActive ? "Y" : "N" );
		Serial.print( " HLTH " );
		Serial.print( health );
		Serial.print( "#" );
	}
	else if( message.startsWith( "LDRLOW" ) )	// Adjust LDR
	{
		LDRThreshold = ldrLowThreshold;
		ldrIsThresholdLow = true;
		Serial.print( "OK#" );
	}
	else if( message.startsWith( "LDRHIGH" ) )	// Adjust LDR
	{
		LDRThreshold = ldrHighThreshold;
		ldrIsThresholdLow = false;
		Serial.print( "OK#" );
	}	
	else if( message.startsWith( "FSRSLOW" ) )	// Adjust FSR
	{
		fsrMetro.interval( fsrSlowPoll );
		fsrFastPolling = false;
		Serial.print( "OK#" );
	}
	else if( message.startsWith( "FSRFAST" ) )	// Adjust FSR
	{
		fsrMetro.interval( fsrFastPoll );
		fsrFastPolling = true;		
		Serial.print( "OK#" );
	}	
	else if( message.startsWith( "REMOTEON" ) )	// Toggle remote management ON
	{
			numModesActive = dispModesRemoteOn;
			remoteManagementActive = true;
			digitalWrite( lcdLED2, HIGH );						
			Serial.print( "OK#" );
	}
	else if( message.startsWith( "REMOTEOFF" ) )	// Toggle remote management OFF
	{
			numModesActive = dispModesRemoteOff;
			remoteManagementActive = false;
			digitalWrite( lcdLED2, LOW );						
			Serial.print( "OK#" );
	}
	else if( message.startsWith( "07:" ) )	// Set phone number
	{
		listeningOn = message;
		Serial.print( "OK#" );
	}		
	else if( message.startsWith( "RESET" ) )	// Resets all the traps
	{
		resetTraps();
		Serial.print( "OK#" );
	}		
	else if( message.startsWith( "HEALTH" ) )	// Outputs health only
	{
		Serial.print( health );
		Serial.print( "#" );
	}			
	else
		Serial.print( "Uknown!" ); 

	// Done with the message now
	serialInput = "";
	serialInputMessageComplete = false;
}

In part two of this post, I’ll delve into TempEx One and its control unit – stay tuned! In the meantime, perhaps you’d like to get yourself an Arduino and start tinkering?


Alec Waters is responsible for all things security at Dataline Software, and can be emailed at alec.waters@dataline.co.uk

The Adventures of Packet Tracy, PI – The Case of the Disappearing Delicacy

Posted in Packet Challenge, Packet Tracy on 15 February, 2013 by Alec Waters

bsideslondon

Welcome to my latest challenge, part of the run-up to BSides London 2013. It’s a bit different this time, both in terms of what you have to do and what you get if you do it. The prizes on offer are tickets to the event, with a special prize of a ticket to Hack In Paris for the best entry! Full rules and T’s&C’s are at the end of this post.

Are you sitting comfortably? Then let’s begin…

packettracy
My name’s Tracy, Packet Tracy. I’m a PI. It says so on my door. Last Tuesday my door was locked because I was out for lunch. Some people only take an hour for lunch, but I do my best work at lunchtime so I take the whole day. As usual I headed for Fat Dex’s Diner on the West Side. Gotta be careful not to confuse it with the oil refinery; the place is covered in a film of grease, and Fat Dex ain’t called Fat Dex for nothing.

I slid in through the front door, tripping over tumbleweeds left and right. I had my choice of tables – the last time this joint was full Kennedy was on the throne and Fat Dex was just called Dex. Even so, lately there are so many tumbleweeds I worry they’re planning some kind of global uprising. Better stock up on weedkiller.

Wendy comes over with something she claims is coffee, but I suspect it’s actually come from the refinery. I ask her for my usual zeppelins in a fog, but when she brings them over it looks like they’ve come from Lakehurst field instead of the kitchen. Oh the humanity.

I can hear Dex crashing about out back. Clearly something is rotten in the state of Dexmark, which is usually my cue to leave before Dex and the Knuckleduster Twins politely ask me to pay my tab. In between tripping over tumbleweeds and slipping on grease he manages to get the jump on me and we sit down for a gentlemanly discussion. He looks stressed and he’s sweating. More than usual. Which is a lot.

Dex says takings are down and the Fatelli brothers are on his back and unless he turns things around soon they’ll be breaking it. He says it’s not his fault, but it never is. According to Dex only San Andreas has faults.

This time he might be right. Some new joint called Iggy’s Eats has opened up on the East Side, and Dex can’t compete. He says they’ve got more money than he has grease, and they’ve got a brand new three-storey R&D facility that’s kicking out some kind of seafood dish that people come from miles around to hook. If that wasn’t bad enough he says they’ve stolen his secret recipe for cheese on toast. 

Before I can tell him that particular recipe ain’t so secret, he says he’s got proof that’ll send Iggy and her Eats down the river to Sing Sing quicker than you can play a song song. Wendy’s culinary talents are below par because she’s tired – she’s been on a nocturnal special op on behalf of Dex. She got close to Iggy’s top guy Jamie and was able to go through his drawers once she was done going through his drawers. She came back with a USB stick with Dex’s stolen cheese on toast recipe on it, enough proof to get Iggy a private room in the State’s finest long-term accommodation facility. But there’s a problem that’s stickier than Dex’s tables – the recipe’s encrypted. According to Wendy the password is in a safe in Iggy’s private office, and not even a team of invisible ninjas is getting in there.

So that’s what Dex is after – he needs me to decrypt the stick and get the proof that Iggy has stolen his recipe. It was a tough case, but you don’t call a PI for the easy ones…

For all you budding PIs out there, the question we need answered is very simple. The crime of corporate espionage has been committed, but who stole the recipe and who will end up in the dock? Iggy? Jamie? Someone else? You’ll need to conduct a thorough investigation and write up your evidence so PT can take it all to the Judge. When you’re done, you can submit it via email here.

Before we give you the USB stick, please take a moment to read the rules:

  1. You cannot enter if you are a volunteer for this event or a member of the BSidesLondon crew
  2. You must submit your answer by April 1st 2013 18:00 (6pm) GMT
  3. The first three people to submit the correct answer showing all the steps taken to determine the guilty party will get a ticket to BSidesLondon13
  4. After the closing deadline the best answer will get a ticket for Hack In Paris 2013, a ticket to BSidesLondon13 (if required) plus a further winner of BSidesLondon13 tickets will be selected from all those who have submitted a correct and complete answer. These winners will be decided on criteria including the thoroughness and completeness of the presented investigation, and/or the use of an appropriate narrative style
  5. Judge’s decision is final and prizes can’t be exchanged for cash or favours ;-)
  6. This challenge will involve you interacting with live systems via the Internet. If the system’s name doesn’t end in wirewatcher.net, you’re in the wrong place and you should stop.
  7. The only tool you need to dish up the dirt is your brain – step away from the BackTrack laptop and use GreyMatter 1.0 instead. Any forceful attempts to “hack” the challenge systems may result in it being taken offline prematurely, which would be a shame. All necessary information is provided for you – all you need to do is find it!
  8. For data protection purposes, names and email addresses of participants will only be used for the challenge, and will be shared with the challenge creator only for the purpose of selecting the best answers. You have Packet Tracy’s cast-iron no-spam guarantee!
  9. All characters, organisations and other such entities featured in the challenge are fictitious. Any resemblance to real persons, living or dead, is purely coincidental.
  10. Play nice and have fun, and please don’t share any answers with anyone!

Ready? You can download the USB stick image here.

If you need any hints, you can try asking PT himself, but he’s pretty tight-lipped, especially in public!


Alec Waters is responsible for all things security at Dataline Software, and can be emailed at alec.waters@dataline.co.uk

Virtual Private Onions

Posted in Crazy Plans, Crypto, NSM, Sguil on 8 October, 2012 by Alec Waters

If you’ve not checked out Security Onion (SO) yet, you really should. It’s a powerhouse Linux distro, running everything an analyst could need to carry out effective Network Security Monitoring (NSM). The latest beta is looking fantastic; watch the video and try it out, you won’t be sorry!

I’m not going to talk about SO itself (Mother Google has plenty of good things to say); instead I’m going to look at the underlying network infrastructure.

A major component of SO is Sguil, a distributed monitoring system that has sensor and server components that are used for monitoring the network and aggregating output from multiple sensors (you can see a Sguil schematic here to understand how it all fits together). The comms between the sensors and the server are protected by SSL, and SO builds on this with autossh tunnels to protect other traffic streams from interception. Ubuntu’s Uncomplicated Firewall (UFW) opens only the necessary ports to allow SO sensors to talk to their server, so all the installations are protected to a high degree.

If all of the connections between the sensors and the server are on your own infrastructure, this is fine (perhaps you have a management VLAN specifically for this purpose, for example). There is however another use case I can think of, where we like to use a slightly different method of sensor-to-server communications.

NSM As A Service?

Let’s say you’re in the business of selling NSM to clients, either short-term (“help me understand what’s on my network”) or long-term (“please be our NSM operators in return for huge bushels of cash”). This will probably involve dropping off SO sensor boxes on customer networks and having them all report in to an SO server back at base. The SO sensors will probably be behind the customer’s NAT and firewalls, but this doesn’t matter, the comms will still work. The network of sensors will look a bit like this:

This particular use case isn’t without issue, though – here is where I think that a slightly different approach to the underlying SO infrastructure has value. Consider the following:

  • The Sguil interface shows you that one of the agents on one of the sensors is down. How do you ssh in to fix it if the sensor is behind someone else’s NAT and firewalls? How do you even know which Internet IP address you should use to try?
  • You suspect one of the sensors is under excessive load. It’d be great to install an snmp agent on the sensor and point Munin at it to try and find the stressed metric. Again, how do we contact the sensor from back at base?
  • You want to implement a custom information flow from the sensor back to the server. You need to think about the security of the new flow – can you implement another autossh tunnel? What if the flow is UDP (e.g., snmp-trap)?
  • One of the sensors is reported lost or stolen. How can you easily stop it from connecting back to base when it’s possibly now in the hands of threat actor du jour?

One possible answer is to build a custom “underlay” network to carry all of the traffic between SO sensors and the server, catering for existing flows and anything else you think of in the future. As a side benefit, the sensors will all have static and known IP addresses, and contacting them from the server will be no problem at all.

Virtual Private Onions

We’ll accomplish this by using OpenVPN to create a secure, privately- and statically-addressed cloud that the sensors and server will use to talk to each other (sorry for using the word “cloud”!). Take our starting point above, showing our distributed sensors at client sites behind client firewalls. By “underlaying” the SO comms with an OpenVPN cloud we’ll end up with is something like this:

The client’s firewalls and NAT are still there, but they’re now hidden by the static, bi-directional comms layer provided by OpenVPN. The sensors all talk over the VPN to the server at 10.0.0.1; the server in turn is free to contact any of the sensors via their static addresses in the 10.0.0.0/24 subnet.

Details

I don’t intend for this to be a HOWTO; I want to wait until people tell me that what I’m proposing isn’t a galactic waste of time and completely unnecessary! Conceptually, it works like this:

The SO Server takes on the additional role of an OpenVPN server. Using OpenVPN’s “easy-rsa” feature, the Server also becomes a Certificate Authority capable of issuing certificates to itself and to the sensors.

OpenVPN gives the SO Server a routed tun0 interface with the IP address 10.0.0.1/24 (note routed - if we wanted to, we can give other subnets back at base that are “behind” the Server access to the SO Sensors via the VPN).

The Sensors become OpenVPN clients, using certificates from the Server to mutually authenticate themselves to it. The Sensors know to point their OpenVPN clients at the static Internet-facing IP address of the server back at base, getting a tun0 interface and a static IP address out of 10.0.0.0/24 in return.

When setting up the SO components on the Sensor boxes, the sosetup script is told that the server is at 10.0.0.1 via tun0, ensuring that all SO comms go over the VPN.

The VPN carries all traffic between Sensors and Server, be it Sguil’s SSL connections, autossh tunnels, SNMP traps or queries, raw syslog forwarding, psychic lottery predictions, anything. The Server is also free to ssh onto the Sensors via their static VPN addresses.

Advantages?

We’ve implemented OpenVPN with SO in this manner, and it works well for us. I hope this approach has some advantages:

  • It makes for easier firewalling at the Server and Sensor ends. You only need to open up one port, which is by default 1194/UDP. All of the VPN traffic is carried over this port.
  • You have deterministic sensor IP addressing, something you wouldn’t otherwise have had when your sensors were deployed on foreign networks behind NAT, firewalls, and dynamic IP addresses on customer DSL routers.
  • You don’t need to worry about setting up additional autossh tunnels when you dream up a new flow of information  between Sensor and Server.
  • You can easily talk to the sensors from the server, for ssh sessions, SNMP polls, or anything else.
  • If a sensor is lost or stolen, all you need to do is revoke its certificate at the Server end and it won’t be able to connect to the VPN (more on sensor security in a moment).

There are of course some disadvantages:

  • Complexity, which as we all know is the enemy of security.
  • Double encryption. OpenVPN is encrypting stuff, including stuff already encrypted by Sguil and autossh.
  • <insert other glaring flaws here>

Security considerations

On the Server side, keep in mind that it is now a Certificate Authority capable of signing certificates that grant access to your SO VPN. Guard the CA key material well – maybe even use a separate system for certificate signing and key generation. Also, once you’ve generated and deployed certificates and private keys for your sensors, remove the private keys from the Server – these belong on each specific sensor and nowhere else.

On the Sensor side, we have a duty of care towards the clients purchasing the “NSM As A Service”. OpenVPN should be configured to prohibit comms between Sensor nodes, so that a compromise of one Sensor machine doesn’t automatically give the attacker a path onto other customer networks.

If a Sensor machine is lost or stolen whilst deployed at a customer site, we can of course revoke its certificate to prevent it from connecting to the VPN. That’s great, but the /nsm directory on it is still going to contain a whole bunch of data that the client wouldn’t want turning up on eBay along with the stolen sensor.

I have a plan for this, but I’ve not implemented it yet (comments welcome!). The plan is to have the /nsm directory encrypted (a TrueCrypt volume? something else?), but to have the decryption key stored on the SO Server rather than on the Sensor. When the Sensor starts up, it builds its OpenVPN connection to the Server before the SO services start. Using the VPN, the Sensor retrieves the decryption key (one unique key per Sensor) from the Server (wget? curl? something else?), taking care never to store it on the Sensor’s local disk. Decryption key in hand, the Sensor can decrypt /nsm and allow the SO services to kick off.

In this way, a stolen Sensor box represents minimal risk to the client as the /nsm directory is encrypted, with the keymat necessary for decryption stored on the Server. Provided that the theft is communicated to the NSMAAS provider in an expedient fashion, that keymat will be out of reach of the thief once the OpenVPN certificate is revoked.

(Other, crazier, plans involve giving the Sensors GPS receivers and 3G comms for covert phone-home-in-an-emergency situations…)

So there you have it…

…Virtual Private Onions. Any comments?


Alec Waters is responsible for all things security at Dataline Software, and can be emailed at alec.waters@dataline.co.uk

Follow

Get every new post delivered to your Inbox.

Join 31 other followers