diff --git a/book/security.rst b/book/security.rst
index 9977e7754cc..35d27275ba8 100644
--- a/book/security.rst
+++ b/book/security.rst
@@ -319,7 +319,7 @@ First, enable form login under your firewall:
-
+
@@ -519,6 +519,11 @@ Finally, create the corresponding template:
+.. caution::
+
+ This login form is currently not protected against CSRF attacks. Read
+ :doc:`/cookbook/security/csrf_in_login_form` on how to protect your login form.
+
.. tip::
The ``error`` variable passed into the template is an instance of
diff --git a/book/validation.rst b/book/validation.rst
index 6941d357465..ac4bacfdbd3 100644
--- a/book/validation.rst
+++ b/book/validation.rst
@@ -113,8 +113,9 @@ Next, to actually validate an ``Author`` object, use the ``validate`` method
on the ``validator`` service (class :class:`Symfony\\Component\\Validator\\Validator`).
The job of the ``validator`` is easy: to read the constraints (i.e. rules)
of a class and verify whether or not the data on the object satisfies those
-constraints. If validation fails, an array of errors is returned. Take this
-simple example from inside a controller::
+constraints. If validation fails, a non-empty list of errors
+(class :class:`Symfony\\Component\\Validator\\ConstraintViolationList`) is
+returned. Take this simple example from inside a controller:
// ...
use Symfony\Component\HttpFoundation\Response;
diff --git a/cookbook/map.rst.inc b/cookbook/map.rst.inc
index 9c8260fd929..924d8ece8cc 100644
--- a/cookbook/map.rst.inc
+++ b/cookbook/map.rst.inc
@@ -133,6 +133,7 @@
* :doc:`/cookbook/security/custom_provider`
* :doc:`/cookbook/security/custom_authentication_provider`
* :doc:`/cookbook/security/target_path`
+ * :doc:`/cookbook/security/csrf_in_login_form`
* **Serializer**
diff --git a/cookbook/security/csrf_in_login_form.rst b/cookbook/security/csrf_in_login_form.rst
new file mode 100644
index 00000000000..74a4527af31
--- /dev/null
+++ b/cookbook/security/csrf_in_login_form.rst
@@ -0,0 +1,164 @@
+.. index::
+ single: Security; CSRF in the Login Form
+
+Using CSRF in the Login Form
+============================
+
+When using a login form, you should make sure that you are protected against CSRF
+(`Cross-site request forgery`_). The Security component already has built-in support
+for CSRF. In this article you'll learn how you can use it in your login form.
+
+Configuring CSRF
+----------------
+
+At first, you have to configure the Security component so it can use CSRF protection.
+The Security component needs a CSRF provider. You can set this to use the default
+provider available in the Form component:
+
+.. configuration-block::
+
+ .. code-block:: yaml
+
+ # app/config/security.yml
+ security:
+ firewalls:
+ secured_area:
+ # ...
+ form_login:
+ # ...
+ csrf_provider: form.csrf_provider
+
+ .. code-block:: xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ .. code-block:: php
+
+ // app/config/security.php
+ $container->loadFromExtension('security', array(
+ 'firewalls' => array(
+ 'secured_area' => array(
+ // ...
+ 'form_login' => array(
+ // ...
+ 'csrf_provider' => 'form.csrf_provider',
+ )
+ )
+ )
+ ));
+
+The Security component can be configured further, but this is all information it needs
+to be able to use CSRF in the login form.
+
+Rendering the CSRF field
+------------------------
+
+Now the Security component checks for CSRF tokens, you have to add a *hidden* field
+to the login form containing the CSRF token. By default, this field is named as
+``_csrf_token``. That hidden field has to contain the CSRF token, which can be generated
+by using the ``csrf_token`` function. That function requires a token ID, which must
+be set to ``authenticate`` when using the login form:
+
+.. configuration-block::
+
+ .. code-block:: html+twig
+
+ {# src/Acme/SecurityBundle/Resources/views/Security/login.html.twig #}
+
+ {# ... #}
+
+
+ .. code-block:: html+php
+
+
+
+
+
+
+After this, you have protected your login form against CSRF attacks.
+
+.. tip::
+
+ You can change the name of the field by setting ``csrf_parameter`` and change
+ the token ID by setting ``intention`` in your configuration:
+
+ .. configuration-block::
+
+ .. code-block:: yaml
+
+ # app/config/security.yml
+ security:
+ firewalls:
+ secured_area:
+ # ...
+ form_login:
+ # ...
+ csrf_parameter: _csrf_security_token
+ intention: a_private_string
+
+ .. code-block:: xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ .. code-block:: php
+
+ // app/config/security.php
+ $container->loadFromExtension('security', array(
+ 'firewalls' => array(
+ 'secured_area' => array(
+ // ...
+ 'form_login' => array(
+ // ...
+ 'csrf_parameter' => '_csrf_security_token',
+ 'intention' => 'a_private_string',
+ )
+ )
+ )
+ ));
+
+.. _`Cross-site request forgery`: http://en.wikipedia.org/wiki/Cross-site_request_forgery
diff --git a/cookbook/security/index.rst b/cookbook/security/index.rst
index a8edbdc4317..c2623bcde64 100644
--- a/cookbook/security/index.rst
+++ b/cookbook/security/index.rst
@@ -15,3 +15,4 @@ Security
custom_provider
custom_authentication_provider
target_path
+ csrf_in_login_form