Vulnerability: confirm.php in ATutor 2.2 and earlier allows remote attackers to bypass authentication and gain access as an existing user via the auto_login parameter.
Vulnerability ID: CVE-2014-9753
CWE: CWE-287
Severity score: 6.4
Project: https://github.com/atutor/ATutor
Published: 2020-02-11
File: confirm.php
Commit message: Added a confirmation code to auto_login URL to fix bug where anyone can login as anyone.
Commit author: George Buckingham

Vulnerable version (before fix):
 				require(AT_INCLUDE_PATH.'header.inc.php'); 				echo "<div class=\"input-form\">"; 				require(AT_INCLUDE_PATH.'html/auto_enroll_list_courses.inc.php'); 				echo '<p style="text-align:center"><a href="'. $_SERVER['PHP_SELF'] . '?auto_login=1&member_id='. $id .'">' . _AT("go_to_my_start_page") . '</a></p>'; 				echo "</div>"; 				require(AT_INCLUDE_PATH.'footer.inc.php'); 				exit; 				// enable auto login student into "my start page" 				$_REQUEST["auto_login"] = 1; 				$_REQUEST["member_id"] = $id; 			} 		} else { 			$msg->addError('CONFIRM_BAD'); 	 	$sql = "SELECT M.member_id, M.login, M.preferences, M.language FROM %smembers M WHERE M.member_id=%d"; 	$row = queryDB($sql, array(TABLE_PREFIX, $_REQUEST["member_id"]), TRUE); 	 	if ($row['member_id'] != '')  	{ 		$_SESSION['valid_user'] = true; 		$_SESSION['member_id']	= $_REQUEST["member_id"];

Fixed version (after fix):
 				require(AT_INCLUDE_PATH.'header.inc.php'); 				echo "<div class=\"input-form\">"; 				require(AT_INCLUDE_PATH.'html/auto_enroll_list_courses.inc.php'); 				echo '<p style="text-align:center"><a href="'. $_SERVER['PHP_SELF'] . '?auto_login=1&member_id='. $id .'&code=' . $code .'">' . _AT("go_to_my_start_page") . '</a></p>'; 				echo "</div>"; 				require(AT_INCLUDE_PATH.'footer.inc.php'); 				exit; 				// enable auto login student into "my start page" 				$_REQUEST["auto_login"] = 1; 				$_REQUEST["member_id"] = $id; 				$_REQUEST["code"] = $code; 			} 		} else { 			$msg->addError('CONFIRM_BAD'); 	 	$sql = "SELECT M.member_id, M.login, M.preferences, M.language FROM %smembers M WHERE M.member_id=%d"; 	$row = queryDB($sql, array(TABLE_PREFIX, $_REQUEST["member_id"]), TRUE);  	$code = substr(md5($e . $row['creation_date'] . $id), 0, 10); 	 	if ($row['member_id'] != '' && isset($_REQUEST['code']) && $_REQUEST['code'] == $code)  	{ 		$_SESSION['valid_user'] = true; 		$_SESSION['member_id']	= $_REQUEST["member_id"];

Patch:
patch: @@ -82,7 +82,7 @@
 				require(AT_INCLUDE_PATH.'header.inc.php');
 				echo "<div class=\"input-form\">";
 				require(AT_INCLUDE_PATH.'html/auto_enroll_list_courses.inc.php');
-				echo '<p style="text-align:center"><a href="'. $_SERVER['PHP_SELF'] . '?auto_login=1&member_id='. $id .'">' . _AT("go_to_my_start_page") . '</a></p>';
+				echo '<p style="text-align:center"><a href="'. $_SERVER['PHP_SELF'] . '?auto_login=1&member_id='. $id .'&code=' . $code .'">' . _AT("go_to_my_start_page") . '</a></p>';
 				echo "</div>";
 				require(AT_INCLUDE_PATH.'footer.inc.php');
 				exit;
@@ -94,6 +94,7 @@
 				// enable auto login student into "my start page"
 				$_REQUEST["auto_login"] = 1;
 				$_REQUEST["member_id"] = $id;
+				$_REQUEST["code"] = $code;
 			}
 		} else {
 			$msg->addError('CONFIRM_BAD');
@@ -142,8 +143,10 @@
 	
 	$sql = "SELECT M.member_id, M.login, M.preferences, M.language FROM %smembers M WHERE M.member_id=%d";
 	$row = queryDB($sql, array(TABLE_PREFIX, $_REQUEST["member_id"]), TRUE);
+
+	$code = substr(md5($e . $row['creation_date'] . $id), 0, 10);
 	
-	if ($row['member_id'] != '') 
+	if ($row['member_id'] != '' && isset($_REQUEST['code']) && $_REQUEST['code'] == $code) 
 	{
 		$_SESSION['valid_user'] = true;
 		$_SESSION['member_id']	= $_REQUEST["member_id"];
path: confirm.php