#!/usr/bin/php -q // This is purely a proof of concept script, you are free to do what you like with. // Go to http://wiki.cacert.org/wiki/Apache_One_Time_Passwords for more help // Main Configuration // Time in minutes to allow for. $matchperiod = 3; // Shared secret $hash = "1234567812345678"; // User PIN $pin = "0000"; $err = fopen("php://stderr", "w"); $do = `find /var/motp/cookies -type f -cmin +30 | xargs rm 2>/dev/null`; $do = `find /var/motp/cache -type f -cmin +5 | xargs rm 2>/dev/null`; list($crud, $cookie) = explode("=", $_ENV['COOKIE'], 2); $cfile = escapeshellarg("/var/motp/cookies/$cookie"); $cfil = substr($cfile, 1, -1); if(file_exists($cfil)) { $do = `touch $cfile`; fputs($err, "MOTP: Valid Cookie Found\n"); die(0); } $matchperiod *= 6; $fp = fopen("php://stdin", "r"); $user = trim(fgets($fp, 4096)); if($user != "user") { fputs($err, "MOTP: Unknown user '$user'\n"); die(1); } $ufile = escapeshellarg("/var/motp/users/$user"); $fu = fopen($ufile, "r"); $count = intval(trim(fgets($fu, 4096))); fclose($fu); $count++; if($count >= 8) { fputs($err, "MOTP: Too many retries for user='$user'\n"); die(1); } $pass = trim(fgets($fp, 4096)); $file = escapeshellarg("/var/motp/cache/$pass"); $fil = substr($file, 1, -1); if(file_exists($fil)) { fputs($err, "MOTP: OTP token already used\n"); die(1); } fclose($fp); fputs($err, "MOTP: user='$user' pass='$pass'\n"); $time = round(gmdate("U") / 10); for($i = $time - $matchperiod; $i <= $time + $matchperiod * 2; $i++) { $md5 = substr(md5("$i$hash$pin"), 0, 6); // fputs($err, "MOTP: Now trying '$pass'='$md5'\n"); if($pass == $md5) { fputs($err, "MOTP: touch $file\nMOTP: touch $cfile\n"); $do = `touch $file`; $do = `touch $cfile`; unlink(substr($ufile, 1, -1)); fputs($err, "MOTP: Match found!\n"); die(0); } } fputs($err, "MOTP: No Match Found\n"); $fu = fopen($ufile, "w"); fputs($fu, $count); fclose($fu); die(1); ?>