diff --git a/core/lib/Drupal/Core/Access/CsrfTokenGenerator.php b/core/lib/Drupal/Core/Access/CsrfTokenGenerator.php
index 2e4e44d..81ea2c6 100644
--- a/core/lib/Drupal/Core/Access/CsrfTokenGenerator.php
+++ b/core/lib/Drupal/Core/Access/CsrfTokenGenerator.php
@@ -72,7 +72,7 @@ public function setCurrentUser(AccountInterface $current_user = NULL) {
    * @see \Drupal\Core\Session\SessionManager::start()
    */
   public function get($value = '') {
-    return Crypt::hmacBase64($value, session_id() . $this->privateKey->get() . drupal_get_hash_salt());
+    return Crypt::hmacBase64($value, $this->getTokenSeed() . $this->privateKey->get() . drupal_get_hash_salt());
   }
 
   /**
@@ -93,4 +93,18 @@ public function validate($token, $value = '', $skip_anonymous = FALSE) {
     return ($skip_anonymous && $this->currentUser->isAnonymous()) || ($token === $this->get($value));
   }
 
+  /**
+   * Return the token seed bound to the current user session.
+   *
+   * @return string
+   *   base64 encoded string of a 32 random bytes.
+   */
+  protected function getTokenSeed() {
+    if (empty($_SESSION['csrf_token_seed'])) {
+      $_SESSION['csrf_token_seed'] = Crypt::randomBytesBase64();
+    }
+
+    return $_SESSION['csrf_token_seed'];
+  }
+
 }
diff --git a/core/lib/Drupal/Core/Session/SessionManager.php b/core/lib/Drupal/Core/Session/SessionManager.php
index 30ca61b..8c5667b 100644
--- a/core/lib/Drupal/Core/Session/SessionManager.php
+++ b/core/lib/Drupal/Core/Session/SessionManager.php
@@ -83,7 +83,7 @@ public function initialize() {
       // anonymous users not use a session cookie unless something is stored in
       // $_SESSION. This allows HTTP proxies to cache anonymous pageviews.
       $this->start();
-      if ($user->isAuthenticated() || !empty($_SESSION)) {
+      if ($user->isAuthenticated() || !$this->isEmptySession()) {
         drupal_page_is_cacheable(FALSE);
       }
     }
@@ -138,7 +138,7 @@ public function save() {
       return;
     }
 
-    if ($user->isAnonymous() && empty($_SESSION)) {
+    if ($user->isAnonymous() && $this->isEmptySession()) {
       // There is no session data to store, destroy the session if it was
       // previously started.
       if ($this->isStarted()) {
@@ -289,4 +289,27 @@ protected function isCli() {
     return PHP_SAPI === 'cli';
   }
 
+  /**
+   * Test whether the session is empty.
+   *
+   * @return bool
+   *   TRUE when the session does not contain any values.
+   */
+  protected function isEmptySession(array $session = NULL) {
+    if (isset($_SESSION) && !isset($session)) {
+      $session = $_SESSION;
+    }
+
+    // Ignore the CSRF token seed.
+    //
+    // @todo: As soon as https://drupal.org/node/2238087 lands, the token seed
+    // can be moved onto Drupal\Core\Session\MetadataBag. This will result in
+    // the CSRF token to be ignored automatically.
+    unset($session['csrf_token_seed']);
+
+    if (empty($session)) {
+      return TRUE;
+    }
+  }
+
 }
