diff options
author | Fabien Potencier <fabien.potencier@gmail.com> | 2016-05-01 06:13:23 +0200 |
---|---|---|
committer | Fabien Potencier <fabien.potencier@gmail.com> | 2016-05-09 13:29:33 -0500 |
commit | 83b345fdf01cb980fb8bd5e15224573d93b8e369 (patch) | |
tree | 955da7a10d029847ebb3fd5e46cb3de14c223c52 | |
parent | a2aa4cdad5949c3bebea89e8aece52a74de4798c (diff) | |
download | symfony-security-83b345fdf01cb980fb8bd5e15224573d93b8e369.zip symfony-security-83b345fdf01cb980fb8bd5e15224573d93b8e369.tar.gz symfony-security-83b345fdf01cb980fb8bd5e15224573d93b8e369.tar.bz2 |
limited the maximum length of a submitted usernamev2.3.42v2.3.41origin/2.3
-rw-r--r-- | Core/SecurityContextInterface.php | 1 | ||||
-rw-r--r-- | Http/Firewall/UsernamePasswordFormAuthenticationListener.php | 5 | ||||
-rw-r--r-- | Tests/Http/Firewall/UsernamePasswordFormAuthenticationListenerTest.php | 78 |
3 files changed, 84 insertions, 0 deletions
diff --git a/Core/SecurityContextInterface.php b/Core/SecurityContextInterface.php index 50c30bb..0253a6a 100644 --- a/Core/SecurityContextInterface.php +++ b/Core/SecurityContextInterface.php @@ -23,6 +23,7 @@ interface SecurityContextInterface const ACCESS_DENIED_ERROR = '_security.403_error'; const AUTHENTICATION_ERROR = '_security.last_error'; const LAST_USERNAME = '_security.last_username'; + const MAX_USERNAME_LENGTH = 4096; /** * Returns the current security token. diff --git a/Http/Firewall/UsernamePasswordFormAuthenticationListener.php b/Http/Firewall/UsernamePasswordFormAuthenticationListener.php index 2147817..26aeb67 100644 --- a/Http/Firewall/UsernamePasswordFormAuthenticationListener.php +++ b/Http/Firewall/UsernamePasswordFormAuthenticationListener.php @@ -20,6 +20,7 @@ use Symfony\Component\Security\Http\Session\SessionAuthenticationStrategyInterfa use Symfony\Component\Security\Http\HttpUtils; use Symfony\Component\Security\Core\Authentication\AuthenticationManagerInterface; use Symfony\Component\Security\Core\Authentication\Token\UsernamePasswordToken; +use Symfony\Component\Security\Core\Exception\BadCredentialsException; use Symfony\Component\Security\Core\Exception\InvalidCsrfTokenException; use Symfony\Component\Security\Core\SecurityContextInterface; use Symfony\Component\EventDispatcher\EventDispatcherInterface; @@ -83,6 +84,10 @@ class UsernamePasswordFormAuthenticationListener extends AbstractAuthenticationL $password = $request->get($this->options['password_parameter'], null, true); } + if (strlen($username) > SecurityContextInterface::MAX_USERNAME_LENGTH) { + throw new BadCredentialsException('Invalid username.'); + } + $request->getSession()->set(SecurityContextInterface::LAST_USERNAME, $username); return $this->authenticationManager->authenticate(new UsernamePasswordToken($username, $password, $this->providerKey)); diff --git a/Tests/Http/Firewall/UsernamePasswordFormAuthenticationListenerTest.php b/Tests/Http/Firewall/UsernamePasswordFormAuthenticationListenerTest.php new file mode 100644 index 0000000..b7c6ab9 --- /dev/null +++ b/Tests/Http/Firewall/UsernamePasswordFormAuthenticationListenerTest.php @@ -0,0 +1,78 @@ +<?php + +/* + * This file is part of the Symfony package. + * + * (c) Fabien Potencier <fabien@symfony.com> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Security\Tests\Http\Firewall; + +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\HttpFoundation\Response; +use Symfony\Component\Security\Http\Firewall\UsernamePasswordFormAuthenticationListener; +use Symfony\Component\Security\Core\SecurityContextInterface; + +class UsernamePasswordFormAuthenticationListenerTest extends \PHPUnit_Framework_TestCase +{ + /** + * @dataProvider getUsernameForLength + */ + public function testHandleWhenUsernameLength($username, $ok) + { + $request = Request::create('/login_check', 'POST', array('_username' => $username)); + $request->setSession($this->getMock('Symfony\Component\HttpFoundation\Session\SessionInterface')); + + $httpUtils = $this->getMock('Symfony\Component\Security\Http\HttpUtils'); + $httpUtils + ->expects($this->any()) + ->method('checkRequestPath') + ->will($this->returnValue(true)) + ; + + $failureHandler = $this->getMock('Symfony\Component\Security\Http\Authentication\AuthenticationFailureHandlerInterface'); + $failureHandler + ->expects($ok ? $this->never() : $this->once()) + ->method('onAuthenticationFailure') + ->will($this->returnValue(new Response())) + ; + + $authenticationManager = $this->getMockBuilder('Symfony\Component\Security\Core\Authentication\AuthenticationProviderManager')->disableOriginalConstructor()->getMock(); + $authenticationManager + ->expects($ok ? $this->once() : $this->never()) + ->method('authenticate') + ->will($this->returnValue(new Response())) + ; + + $listener = new UsernamePasswordFormAuthenticationListener( + $this->getMock('Symfony\Component\Security\Core\SecurityContextInterface'), + $authenticationManager, + $this->getMock('Symfony\Component\Security\Http\Session\SessionAuthenticationStrategyInterface'), + $httpUtils, + 'TheProviderKey', + $this->getMock('Symfony\Component\Security\Http\Authentication\AuthenticationSuccessHandlerInterface'), + $failureHandler, + array('require_previous_session' => false) + ); + + $event = $this->getMock('Symfony\Component\HttpKernel\Event\GetResponseEvent', array(), array(), '', false); + $event + ->expects($this->any()) + ->method('getRequest') + ->will($this->returnValue($request)) + ; + + $listener->handle($event); + } + + public function getUsernameForLength() + { + return array( + array(str_repeat('x', SecurityContextInterface::MAX_USERNAME_LENGTH + 1), false), + array(str_repeat('x', SecurityContextInterface::MAX_USERNAME_LENGTH - 1), true), + ); + } +} |