0

After setting up this admin login system I found that I can't access to it with my Sql user/pass, the login page keeps rejecting my details. I've been trying to figure what's the problem here for 2 hours, I'll appreciate your assistance in this one!

function page (admin.php):

<?php

global $pdo;

function dbconnect()
{
global $pdo;
try {
    $pdo = new PDO('mysql:host=localhost;dbname=pong','root','');
} catch (PDOException $e) {
    die('connection failure! ' . $e->getMessage());
    }
}

function attempt($username, $password)
{
global $pdo;

$stmt = $pdo->prepare('
    SELECT id, username
    FROM admin
    WHERE username = :username AND password = :password
    LIMIT 1');

$stmt->execute(array(':username' => $username, 'password' => md5($password)));

if ($data = $stmt->fetch( PDO::FETCH_OBJ )) {
    $_SESSION['username'] = $data->username;
    return true;
} else {
    return false;
}
}

function is_user()
{
if (isset($_SESSION['username']))
    return true;
}

function redirect($url)
{
header('Location: ' .$url);
exit;
}

Sign-in page (signin.php) :

<?php
require('admin.php');
session_start();
if (is_user()) {
    redirect('../tv/game.php');
}
?>
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
    <title>Sign In</title>
    <link rel="stylesheet" type="text/css" href="../css/pure-min.css">
    <link rel="stylesheet" type="text/css" href="../css/style.css">
    </head>
    <body>
    <div class="container">
        <h1>Sign In</h1>

        <?php if (!empty($_GET['error'])): ?>
        <p class="status status-error pure-input-1"><?php echo $_GET['error'] ?></p>
        <?php endif ?>

        <form action="signin_post.php" class="pure-form pure-form-stacked" method="post">
        <fieldset class="pure-group">
            <input type="text" class="pure-input-1" name="username" placeholder="username">
            <input type="password" class="pure-input-1" name="password" placeholder="password">

            <input class="pure-button pure-button-primary pure-input-1" type="submit" value="Sign In">
        </fieldset>
        </form>
    </div>
     </body>
</html>

And signin_post.php :

<?php
require('admin.php');
dbconnect();
session_start();

if ($_SERVER['REQUEST_METHOD'] === 'POST') {

    if (attempt($_POST['username'], $_POST['password'])) {
        header('Location:../tv/game.php');
    }
    else {
        header('Location: signin.php?error=' . urlencode('invalid login details'));
         }
}

Thanks in advance!

Shaya
  • 2,792
  • 3
  • 26
  • 35

2 Answers2

2

Your current attempt() function has password bound improperly. You are missing the colon in front of password in your execute statement. There are much better ways to handle password hashing than MD5, and the PHP crypt() function can help you with this. http://php.net/manual/en/function.crypt.php

  • Thanks for the tip Andrew, I will definitely check it out. still I'd be glad to solve it as-is before I'm moving on. I added the missing colon ,sadly still no improvement! – Shaya Oct 31 '14 at 22:58
  • Can you just run simple queries on the username and password and make sure that they return the objects you are expecting to see? If they are returning the expected objects then maybe try the validation separately? Also, your initial if($_SERVER[...) statement has no way to exit if the conditions required fails, so if the method is GET then there needs to be an else, without an else this is useless logic. Maybe split the if($_SERVER[...) portion into a separate validation check like if(!empty($_POST){..} and then check your objects. – HitMeWithYourBestShot Nov 01 '14 at 00:24
  • Thanks. I checked $_SERVER and it's receiving the $_POST details, which are `array (size=2) 'username' => string '12345' (length=5) 'password' => string '12345' (length=5)`. I'm puzzled – Shaya Nov 01 '14 at 01:18
  • @AndrewHotovy the MD% function in PHP is still no real security issue. MD5 is wiedly well trusted because you couldn't simply backhash it. I know there are duplicates in the md5 output with another input. But it works just well. http://stackoverflow.com/questions/14139727/sha256-or-md5-for-file-integrity MD% is just better I think because it's quicker and not really unsecure. – jankal Nov 01 '14 at 07:56
  • 1
    @xroydot - I made some changes to your attempt function and your signin_post page. See if they work better for you: http://pastebin.com/U6g4SFXd I essentially moved some things around and instead of setting session variables in the function, I moved that to the signin_post page. – HitMeWithYourBestShot Nov 01 '14 at 15:47
0

I think you could start by editing the attempt() function.

function attempt($username, $password) {
    global $pdo;

    $stmt = $pdo->prepare('
        SELECT id, username, password
        FROM admin
        WHERE username = :username
        LIMIT 1');

    $stmt->execute(array(':username' => $username));

    if ($data = $stmt->fetch( PDO::FETCH_OBJ ) AND $data->password == md5($password)) {
        $_SESSION['username'] = $data->username;
        $_SESSION['userid'] = $data->id;
        return true;
    } else {
        return false;
    }
}

OR you could try this:

function attempt($username, $password)
{
global $pdo;

$stmt = $pdo->prepare('
    SELECT id, username
    FROM admin
    WHERE username = :username AND password = :password
    LIMIT 1');

$stmt->execute(array(':username' => $username, ':password' => md5($password)));

if ($data = $stmt->fetch( PDO::FETCH_OBJ )) {
    $_SESSION['username'] = $data->username;
    $_SESSION['userid'] = $data->id;
    return true;
} else {
    return false;
}
}

Hope this works and helps ;)

jankal
  • 1,090
  • 1
  • 11
  • 28
  • Thanks jankal, but still access denied. What could it be? – Shaya Oct 31 '14 at 22:31
  • Could you please post the errors from the error log? I think I found something. I added my ide to the answer. – jankal Oct 31 '14 at 22:43
  • Uhm... I hope you're using the development php.ini. You could try the new code ;) I hope it works but I don't have your interface. – jankal Oct 31 '14 at 22:55
  • The funny thing is that there aren't any errors, even with `error_reporting(E_ALL); ini_set('display_errors', TRUE);` – Shaya Oct 31 '14 at 23:01
  • Yes. I know. But if you're using the productive php.ini, the errors are only in /var/log/apache2/error.log . If there aren't any errors, you should check your database. – jankal Oct 31 '14 at 23:04
  • Thanks. I double checked that I'm in dev mode. I used `var_dump($_POST)` and it showed my login details. I'm using simple Innodb. Going bananas here!! – Shaya Oct 31 '14 at 23:32
  • But do you have your password md5 encrypted in the database? If it's in clean text and you can read it, you should convert it to md5 somewhere in the Internet via HTTPS. – jankal Nov 01 '14 at 07:48