Error, i woe thee

This bit us. This bit us hard and I blame myself for not catching it. Looking at it after a good night's sleep sets off tons of loud, Star Trek-esque "red alert" klaxons. Why it's bad is left as an exercise for the reader.
################################################################################
# contract: Player, index -> Turn
# let the player take its turn and do validation/contract checking/timeouts
sub give_turn_to_player {
    my ($self, $player, $index) = @_;
 
    my $turn = Game::Turn->new({
        index => $index,
        player => $player,
        admin => $self,
    });
 
    try {
        local $SIG{ALRM} = sub {
            throw Game::Exception::PlayerTimeout(
                'Player timed out after '.PLAYER_TIMEOUT.' seconds' );
        };
        alarm PLAYER_TIMEOUT;
 
        $player->is_taking_turn(1);
        $player->take_turn($turn);
        $player->is_taking_turn(0);
    }
 
    catch Game::Exception::ContractViolation with {
        $self->kick_out_player($player, "You have violated a contract: ".shift);
        return;
    }
 
    catch Game::Exception::PlayerTimeout with {
        $self->kick_out_player($player, "You have timed out after ".PLAYER_TIMEOUT." seconds.");
        return;
    }
 
    otherwise {
        die "asking the player to take a turn failed: ".shift;
    }
 
    finally {
        alarm 0;
    };
 
    unless ($turn->chosen_tile) {
        $self->kick_out_player($player, "You have attempted to place an undefined tile.");
        return;
    }
 
    return $turn;
}
(Still not sure? Here's a hint [PDF]. I swear I remember Matt Sergeant telling me so.)

© Ian Langworth