As a part of my day job at Amazon, I get to spend time recruiting the brightest and the best of the world’s security professionals – especially those who are willing to move to Seattle, Virginia, Dublin or Bangalore. Every so often, we go out on the road to security conferences, and as well as being able to learn from other security professionals who are presenting, we have a booth whose chief purpose (aside from the usual networking) is to recruit security staff.
If you are interested in security jobs at Amazon, visit http://security.amazon-jobs.com to see what’s available, and email security-ninjas@amazon.com to express your interest and submit your resume.
Black Hat 2011
We’re part way through the first day here at Black Hat in Las Vegas, and already the coding challenge is generating a lot of interest. Every morning, and every afternoon, we put up a piece of code – it’s a small piece of code, to make it readable and to make solving the challenge relatively quick and simple. But there’s something wrong with the code.
In my favourite samples, the flaw is a security flaw, but sometimes the flaw is something that, while not directly security related, may still cause a bug to trigger incorrect security behaviour.
Inevitably, we take down the coding challenge before some of the attendees have had a chance to read and work with it. Also, there is no way for non-attendees to get access to the code on the easel.
To fix that, I am uploading the code samples here to my blog. It’s important for readers to know that this is not an indication that anything in this blog is sanctioned or approved by Amazon.com, and it is not an indication that I speak for Amazon.com in any way whatsoever.
Having got that disclaimer out of the way, here’s the code we submitted for today, August 3rd, 2011.
Morning code sample: PerlForm
#!/opt/third-party/bin/perl –w
use strict;
use CGI qw/:standard/;
my $cgi = CGI->new;
my $name = $cgi->param("name");
my $item = $cgi->param("item");
my $count = $cgi->param("count");
print $cgi->header;
print $cgi->start_html('Form test code');
print $cgi->start_form;
print 'Name:',$cgi->textfield("name",$name),$cgi->br;
print 'Item:',$cgi->textfield("item",$item),$cgi->br;
print 'Count:',$cgi->textfield("count", $count),$cgi->br;
if (! $cgi->param) {
# No values - show submit button
print $cgi->submit;
# CSRF protection - submit hidden nonce
my $nonce = rand(100000000); # A bazillionty.
print $cgi->hidden("nonce-value",$nonce);
} else {
# Values - purchase item. Use cookie to identify session
process_values($name, $item, $count);
}
print $cgi->end_form;
print $cgi->end_html;
exit 0;
Afternoon code sample: FixedPoint
bool fixedPoint(int nDecimals, const char *str, int &out)
{
// Converts string representation of decimal numbers
// to fixed-point integer representation, multiplying
// by 10 ^ nDecimals.
// Input has been sanitised and is trusted to be valid.
char *point = 0, *end = 0;
int frac = 0, digits = 0;
out = strtol(str, &point, 10);
if ( *point == '.' )
{
frac = strtol(point+1, &end, 10);
digits = end-point-1;
} else if (point == str)
return false;
while (nDecimals—)
{
out *= 10;
if ( --digits == 0 )
out += frac;
}
return true;
}
Note that the comments here can be relied upon. When we say that the inputs are sanitised and can be trusted to be correct, that means that nDecimals is always greater than or equal to the number of digits past the decimal point. strtol starts at the first parameter converting a representation of an integer from character to integer, and when it finds a character not part of that integer representation, it stops, and stores the pointer to that invalid character in the second parameter. The third parameter is a base, or radix. Here, we use base 10. There is no integer overflow going on here, the numbers being passed in are relatively small.
So what are we doing here?
Obviously, I’m not going to provide answers here for some time, because that would reduce the