[TASK] Mitigate argon2i hash issues
[Packages/TYPO3.CMS.git] / typo3 / sysext / install / Classes / Authentication / AuthenticationService.php
1 <?php
2 declare(strict_types = 1);
3 namespace TYPO3\CMS\Install\Authentication;
4
5 /*
6 * This file is part of the TYPO3 CMS project.
7 *
8 * It is free software; you can redistribute it and/or modify it under
9 * the terms of the GNU General Public License, either version 2
10 * of the License, or any later version.
11 *
12 * For the full copyright and license information, please read the
13 * LICENSE.txt file that was distributed with this source code.
14 *
15 * The TYPO3 project - inspiring people to share!
16 */
17
18 use TYPO3\CMS\Core\Configuration\ConfigurationManager;
19 use TYPO3\CMS\Core\Crypto\PasswordHashing\InvalidPasswordHashException;
20 use TYPO3\CMS\Core\Crypto\PasswordHashing\PasswordHashFactory;
21 use TYPO3\CMS\Core\Mail\MailMessage;
22 use TYPO3\CMS\Core\Utility\GeneralUtility;
23 use TYPO3\CMS\Install\Service\SessionService;
24
25 /**
26 * Authenticates a user (currently comparing it through the install tool password, but could be extended)
27 */
28 class AuthenticationService
29 {
30 /**
31 * @var SessionService
32 */
33 protected $sessionService;
34
35 /**
36 * @param SessionService $sessionService
37 */
38 public function __construct(SessionService $sessionService)
39 {
40 $this->sessionService = $sessionService;
41 }
42
43 /**
44 * Checks against a given password
45 *
46 * @param string $password
47 * @return bool if authentication was successful, otherwise false
48 */
49 public function loginWithPassword($password = null): bool
50 {
51 $validPassword = false;
52 if ($password !== null && $password !== '') {
53 $installToolPassword = $GLOBALS['TYPO3_CONF_VARS']['BE']['installToolPassword'];
54 $hashFactory = GeneralUtility::makeInstance(PasswordHashFactory::class);
55 try {
56 $hashInstance = $hashFactory->get($installToolPassword, 'BE');
57 $validPassword = $hashInstance->checkPassword($password, $installToolPassword);
58 } catch (InvalidPasswordHashException $invalidPasswordHashException) {
59 // Given hash in global configuration is not a valid salted password
60 if (md5($password) === $installToolPassword) {
61 // Update configured install tool hash if it is still "MD5" and password matches
62 // @todo: This should be removed in v10 with a dedicated breaking patch
63 // @todo: Additionally, this code should check required hash updates and update the hash if needed
64 $hashInstance = $hashFactory->getDefaultHashInstance('BE');
65 $configurationManager = GeneralUtility::makeInstance(ConfigurationManager::class);
66 $configurationManager->setLocalConfigurationValueByPath(
67 'BE/installToolPassword',
68 $hashInstance->getHashedPassword($password)
69 );
70 $validPassword = true;
71 } else {
72 // Still no valid hash instance could be found. Probably the stored hash used a mechanism
73 // that is not available on current system. We throw the previous exception again to be
74 // handled on a higher level. The install tool will render an according exception message
75 // that links to the wiki.
76 throw $invalidPasswordHashException;
77 }
78 }
79 }
80 if ($validPassword) {
81 $this->sessionService->setAuthorized();
82 $this->sendLoginSuccessfulMail();
83 return true;
84 }
85 $this->sendLoginFailedMail();
86 return false;
87 }
88
89 /**
90 * If install tool login mail is set, send a mail for a successful login.
91 */
92 protected function sendLoginSuccessfulMail()
93 {
94 $warningEmailAddress = $GLOBALS['TYPO3_CONF_VARS']['BE']['warning_email_addr'];
95 if ($warningEmailAddress) {
96 $mailMessage = GeneralUtility::makeInstance(MailMessage::class);
97 $mailMessage
98 ->addTo($warningEmailAddress)
99 ->setSubject('Install Tool Login at \'' . $GLOBALS['TYPO3_CONF_VARS']['SYS']['sitename'] . '\'')
100 ->addFrom($this->getSenderEmailAddress(), $this->getSenderEmailName())
101 ->setBody('There has been an Install Tool login at TYPO3 site'
102 . ' \'' . $GLOBALS['TYPO3_CONF_VARS']['SYS']['sitename'] . '\''
103 . ' (' . GeneralUtility::getIndpEnv('HTTP_HOST') . ')'
104 . ' from remote address \'' . GeneralUtility::getIndpEnv('REMOTE_ADDR') . '\'')
105 ->send();
106 }
107 }
108
109 /**
110 * If install tool login mail is set, send a mail for a failed login.
111 */
112 protected function sendLoginFailedMail()
113 {
114 $formValues = GeneralUtility::_GP('install');
115 $warningEmailAddress = $GLOBALS['TYPO3_CONF_VARS']['BE']['warning_email_addr'];
116 if ($warningEmailAddress) {
117 $mailMessage = GeneralUtility::makeInstance(MailMessage::class);
118 $mailMessage
119 ->addTo($warningEmailAddress)
120 ->setSubject('Install Tool Login ATTEMPT at \'' . $GLOBALS['TYPO3_CONF_VARS']['SYS']['sitename'] . '\'')
121 ->addFrom($this->getSenderEmailAddress(), $this->getSenderEmailName())
122 ->setBody('There has been an Install Tool login attempt at TYPO3 site'
123 . ' \'' . $GLOBALS['TYPO3_CONF_VARS']['SYS']['sitename'] . '\''
124 . ' (' . GeneralUtility::getIndpEnv('HTTP_HOST') . ')'
125 . ' The last 5 characters of the MD5 hash of the password tried was \'' . substr(md5($formValues['password']), -5) . '\''
126 . ' remote address was \'' . GeneralUtility::getIndpEnv('REMOTE_ADDR') . '\'')
127 ->send();
128 }
129 }
130
131 /**
132 * Get sender address from configuration
133 * ['TYPO3_CONF_VARS']['MAIL']['defaultMailFromAddress']
134 * If this setting is empty fall back to 'no-reply@example.com'
135 *
136 * @return string Returns an email address
137 */
138 protected function getSenderEmailAddress()
139 {
140 return !empty($GLOBALS['TYPO3_CONF_VARS']['MAIL']['defaultMailFromAddress'])
141 ? $GLOBALS['TYPO3_CONF_VARS']['MAIL']['defaultMailFromAddress']
142 : 'no-reply@example.com';
143 }
144
145 /**
146 * Gets sender name from configuration
147 * ['TYPO3_CONF_VARS']['MAIL']['defaultMailFromName']
148 * If this setting is empty, it falls back to a default string.
149 *
150 * @return string
151 */
152 protected function getSenderEmailName()
153 {
154 return !empty($GLOBALS['TYPO3_CONF_VARS']['MAIL']['defaultMailFromName'])
155 ? $GLOBALS['TYPO3_CONF_VARS']['MAIL']['defaultMailFromName']
156 : 'TYPO3 CMS install tool';
157 }
158 }