From eb777dc057dc970f4863f21b44a0c5ce9397ad10 Mon Sep 17 00:00:00 2001 From: Michael Jansen Date: Fri, 5 May 2023 10:21:39 +0200 Subject: [PATCH] Assistance: Add alternative approach for link param See: https://mantis.ilias.de/view.php?id=37249 --- .../classes/class.ilPasswordUtils.php | 27 ++++++++++--------- include/inc.pwassist_session_handler.php | 23 +++++++++++++--- 2 files changed, 35 insertions(+), 15 deletions(-) diff --git a/Services/Password/classes/class.ilPasswordUtils.php b/Services/Password/classes/class.ilPasswordUtils.php index 431eb7238a68..a741029fcb07 100644 --- a/Services/Password/classes/class.ilPasswordUtils.php +++ b/Services/Password/classes/class.ilPasswordUtils.php @@ -15,20 +15,23 @@ class ilPasswordUtils */ public static function getBytes(int $length) : string { - if (!defined('PHP_WINDOWS_VERSION_BUILD') && extension_loaded('openssl')) { - $secure = null; - $rand = openssl_random_pseudo_bytes($length, $secure); - if (false !== $rand && $secure === true) { - return $rand; + try { + return random_bytes($length); + } catch (Throwable $ex) { + if (!defined('PHP_WINDOWS_VERSION_BUILD') && extension_loaded('openssl')) { + $secure = null; + $rand = openssl_random_pseudo_bytes($length, $secure); + if (false !== $rand && $secure === true) { + return $rand; + } } - } - // Default random string generation - $rand = ''; - for ($i = 0; $i < $length; $i++) { - $rand .= chr(mt_rand(0, 255)); - } + $rand = ''; + for ($i = 0; $i < $length; ++$i) { + $rand .= chr(random_int(0, 255)); + } - return $rand; + return $rand; + } } } diff --git a/include/inc.pwassist_session_handler.php b/include/inc.pwassist_session_handler.php index 845396d9f366..5363f2a9ae22 100755 --- a/include/inc.pwassist_session_handler.php +++ b/include/inc.pwassist_session_handler.php @@ -64,10 +64,27 @@ function db_pwassist_session_close() * - Only a non-substantial number of bits can be predicted from * previously generated id's. */ -function db_pwassist_create_id() +function db_pwassist_create_id(): string { - // #26009 we use ilSession to duplicate the existing session - return \ilSession::_duplicate(session_id()); + global $DIC; + + $ilDB = $DIC->database(); + + do { + $hash = bin2hex(ilPasswordUtils::getBytes(32)); + + $exists = ( + (int) ($ilDB->fetchAssoc( + $ilDB->query( + "SELECT EXISTS(" . + "SELECT 1 FROM usr_pwassist WHERE pwassist_id = " . $ilDB->quote($hash, ilDBConstants::T_TEXT) . + ") AS hit" + ) + )['hit'] ?? 0) === 1 + ); + } while ($exists); + + return $hash; } /*