diff --git a/core/core.services.yml b/core/core.services.yml
index b015208..09724bc 100644
--- a/core/core.services.yml
+++ b/core/core.services.yml
@@ -646,7 +646,7 @@ services:
     class: Drupal\Core\Access\AccessArgumentsResolver
   access_manager:
     class: Drupal\Core\Access\AccessManager
-    arguments: ['@router.route_provider', '@url_generator', '@paramconverter_manager', '@access_arguments_resolver', '@request_stack']
+    arguments: ['@router.route_provider', '@url_generator', '@paramconverter_manager', '@access_arguments_resolver', '@request_stack', '@current_user']
     calls:
       - [setContainer, ['@service_container']]
   access_route_subscriber:
diff --git a/core/includes/common.inc b/core/includes/common.inc
index 5a90646..d59c936 100644
--- a/core/includes/common.inc
+++ b/core/includes/common.inc
@@ -2809,6 +2809,17 @@ function drupal_render(&$elements, $is_recursive_call = FALSE) {
     $current->postRenderCache = NestedArray::mergeDeep($current->postRenderCache, $parent->postRenderCache);
     $stack->push($current);
   };
+  /** @var \Drupal\Core\Controller\ControllerResolverInterface $controller_resolver */
+  $controller_resolver = \Drupal::service('controller_resolver');
+  if (isset($elements['#access_callback'])) {
+    if (is_string($elements['#access_callback']) && strpos($elements['#access_callback'], '::') === FALSE) {
+      $callable = $controller_resolver->getControllerFromDefinition($elements['#access_callback']);
+    }
+    else {
+      $callable = $elements['#access_callback'];
+    }
+    $elements['#access'] = call_user_func($callable, $elements);
+  }
 
   // Early-return nothing if user does not have access.
   if (empty($elements) || (isset($elements['#access']) && !$elements['#access'])) {
@@ -2856,8 +2867,6 @@ function drupal_render(&$elements, $is_recursive_call = FALSE) {
   // Make any final changes to the element before it is rendered. This means
   // that the $element or the children can be altered or corrected before the
   // element is rendered into the final text.
-  /** @var \Drupal\Core\Controller\ControllerResolverInterface $controller_resolver */
-  $controller_resolver = \Drupal::service('controller_resolver');
   if (isset($elements['#pre_render'])) {
     foreach ($elements['#pre_render'] as $callable) {
       if (is_string($callable) && strpos($callable, '::') === FALSE) {
diff --git a/core/lib/Drupal/Core/Access/AccessManager.php b/core/lib/Drupal/Core/Access/AccessManager.php
index 54d13de..56ef5f2 100644
--- a/core/lib/Drupal/Core/Access/AccessManager.php
+++ b/core/lib/Drupal/Core/Access/AccessManager.php
@@ -25,8 +25,6 @@
 
 /**
  * Attaches access check services to routes and runs them on request.
- *
- * @see \Drupal\Tests\Core\Access\AccessManagerTest
  */
 class AccessManager implements ContainerAwareInterface, AccessManagerInterface {
 
@@ -103,6 +101,13 @@ class AccessManager implements ContainerAwareInterface, AccessManagerInterface {
   protected $requestStack;
 
   /**
+   * The current user.
+   *
+   * @var \Drupal\Core\Session\AccountInterface
+   */
+  protected $currentUser;
+
+  /**
    * Constructs a AccessManager instance.
    *
    * @param \Drupal\Core\Routing\RouteProviderInterface $route_provider
@@ -115,13 +120,16 @@ class AccessManager implements ContainerAwareInterface, AccessManagerInterface {
    *   The access arguments resolver.
    * @param \Symfony\Component\HttpFoundation\RequestStack $requestStack
    *   The request stack object.
+   * @param \Drupal\Core\Session\AccountInterface $current_user
+   *   The current user.
    */
-  public function __construct(RouteProviderInterface $route_provider, UrlGeneratorInterface $url_generator, ParamConverterManagerInterface $paramconverter_manager, AccessArgumentsResolverInterface $arguments_resolver, RequestStack $requestStack) {
+  public function __construct(RouteProviderInterface $route_provider, UrlGeneratorInterface $url_generator, ParamConverterManagerInterface $paramconverter_manager, AccessArgumentsResolverInterface $arguments_resolver, RequestStack $requestStack, AccountInterface $current_user) {
     $this->routeProvider = $route_provider;
     $this->urlGenerator = $url_generator;
     $this->paramConverterManager = $paramconverter_manager;
     $this->argumentsResolver = $arguments_resolver;
     $this->requestStack = $requestStack;
+    $this->currentUser = $current_user;
   }
 
   /**
@@ -182,7 +190,7 @@ protected function applies(Route $route) {
   /**
    * {@inheritdoc}
    */
-  public function checkNamedRoute($route_name, array $parameters = array(), AccountInterface $account, Request $route_request = NULL) {
+  public function checkNamedRoute($route_name, array $parameters = array(), AccountInterface $account = NULL, Request $route_request = NULL) {
     try {
       $route = $this->routeProvider->getRouteByName($route_name, $parameters);
       if (empty($route_request)) {
@@ -210,7 +218,10 @@ public function checkNamedRoute($route_name, array $parameters = array(), Accoun
   /**
    * {@inheritdoc}
    */
-  public function check(Route $route, Request $request, AccountInterface $account) {
+  public function check(Route $route, Request $request, AccountInterface $account = NULL) {
+    if (!isset($account)) {
+      $account = $this->currentUser;
+    }
     $checks = $route->getOption('_access_checks') ?: array();
     $conjunction = $route->getOption('_access_mode') ?: static::ACCESS_MODE_ALL;
 
diff --git a/core/lib/Drupal/Core/Access/AccessManagerInterface.php b/core/lib/Drupal/Core/Access/AccessManagerInterface.php
index df88ba6..167b6fb 100644
--- a/core/lib/Drupal/Core/Access/AccessManagerInterface.php
+++ b/core/lib/Drupal/Core/Access/AccessManagerInterface.php
@@ -45,7 +45,7 @@
    * @param array $parameters
    *   Optional array of values to substitute into the route path patern.
    * @param \Drupal\Core\Session\AccountInterface $account
-   *   The current user.
+   *   Run access checks for this account. Defaults to the current user.
    * @param \Symfony\Component\HttpFoundation\Request $route_request
    *   Optional incoming request object. If not provided, one will be built
    *   using the route information and the current request from the container.
@@ -53,7 +53,7 @@
    * @return bool
    *   Returns TRUE if the user has access to the route, otherwise FALSE.
    */
-  public function checkNamedRoute($route_name, array $parameters = array(), AccountInterface $account, Request $route_request = NULL);
+  public function checkNamedRoute($route_name, array $parameters = array(), AccountInterface $account = NULL, Request $route_request = NULL);
 
   /**
    * For each route, saves a list of applicable access checks to the route.
@@ -86,11 +86,11 @@ public function addCheckService($service_id, $service_method, array $applies_che
    * @param \Symfony\Component\HttpFoundation\Request $request
    *   The incoming request object.
    * @param \Drupal\Core\Session\AccountInterface $account
-   *   The current account.
+   *   (optional) The user to run checks for, defaults to the current user.
    *
    * @return bool
    *   Returns TRUE if the user has access to the route, otherwise FALSE.
    */
-  public function check(Route $route, Request $request, AccountInterface $account);
+  public function check(Route $route, Request $request, AccountInterface $account = NULL);
 
 }
diff --git a/core/lib/Drupal/Core/Routing/CurrentRouteMatch.php b/core/lib/Drupal/Core/Routing/CurrentRouteMatch.php
index 4b482ea..7971285 100644
--- a/core/lib/Drupal/Core/Routing/CurrentRouteMatch.php
+++ b/core/lib/Drupal/Core/Routing/CurrentRouteMatch.php
@@ -7,6 +7,7 @@
 
 namespace Drupal\Core\Routing;
 
+use Drupal\Core\Session\AccountInterface;
 use Symfony\Component\HttpFoundation\Request;
 use Symfony\Component\HttpFoundation\RequestStack;
 
@@ -92,6 +93,21 @@ public function getCurrentRouteMatch() {
     return $this->getRouteMatch($this->requestStack->getCurrentRequest());
   }
 
+
+  /**
+   * {@inheritdoc}
+   */
+  public function access(AccountInterface $account = NULL) {
+    return $this->getCurrentRouteMatch()->access($account);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function createUrlObject(array $options = array()) {
+    return $this->getCurrentRouteMatch()->createUrlObject($options);
+  }
+
   /**
    * Returns the route match for a passed in request.
    *
diff --git a/core/lib/Drupal/Core/Routing/NullRouteMatch.php b/core/lib/Drupal/Core/Routing/NullRouteMatch.php
index 0ef2c3b..adcf936 100644
--- a/core/lib/Drupal/Core/Routing/NullRouteMatch.php
+++ b/core/lib/Drupal/Core/Routing/NullRouteMatch.php
@@ -7,6 +7,7 @@
 
 namespace Drupal\Core\Routing;
 
+use Drupal\Core\Session\AccountInterface;
 use Symfony\Component\HttpFoundation\ParameterBag;
 
 /**
@@ -56,4 +57,17 @@ public function getRawParameters() {
     return new ParameterBag();
   }
 
+  /**
+   * {@inheritdoc}
+   */
+  public function access(AccountInterface $account = NULL) {
+    return FALSE;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function createUrlObject(array $options = array()) {
+    return NULL;
+  }
 }
diff --git a/core/lib/Drupal/Core/Routing/RouteMatch.php b/core/lib/Drupal/Core/Routing/RouteMatch.php
index eafb184..8b29958 100644
--- a/core/lib/Drupal/Core/Routing/RouteMatch.php
+++ b/core/lib/Drupal/Core/Routing/RouteMatch.php
@@ -7,6 +7,9 @@
 
 namespace Drupal\Core\Routing;
 
+use Drupal\Core\Access\AccessManagerInterface;
+use Drupal\Core\Session\AccountInterface;
+use Drupal\Core\Url;
 use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\ParameterBag;
 use Symfony\Component\HttpFoundation\Request;
@@ -46,6 +49,13 @@ class RouteMatch implements RouteMatchInterface {
   protected $rawParameters;
 
   /**
+   * The access manager.
+   *
+   * @var \Drupal\Core\Access\AccessManagerInterface
+   */
+  protected $accessManager;
+
+  /**
    * Constructs a RouteMatch object.
    *
    * @param string $route_name
@@ -140,6 +150,41 @@ public function getRawParameters() {
   }
 
   /**
+   * {@inheritdoc}
+   */
+  public function createUrlObject(array $options = array()) {
+    return new Url($this->getRouteName(), $this->getRawParameters()->all(), $options);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function access(AccountInterface $account = NULL) {
+    return $this->getAccessManager()->checkNamedRoute($this->getRouteName(), $this->getRawParameters()->all(), $account);
+  }
+
+  /**
+   * Gets the access manager.
+   *
+   * @return \Drupal\Core\Access\AccessManagerInterface
+   */
+  protected function getAccessManager() {
+    if (!isset($this->accessManager)) {
+      $this->accessManager = \Drupal::service('access_manager');
+    }
+    return $this->accessManager;
+  }
+
+  /**
+   * Sets the access manager.
+   *
+   * @param \Drupal\Core\Access\AccessManagerInterface $access_manager
+   */
+  public function setAccessManager(AccessManagerInterface $access_manager) {
+    $this->accessManager = $access_manager;
+  }
+
+  /**
    * Returns the names of all parameters for the currently matched route.
    *
    * @return array
diff --git a/core/lib/Drupal/Core/Routing/RouteMatchInterface.php b/core/lib/Drupal/Core/Routing/RouteMatchInterface.php
index f0d9aa8..35944f8 100644
--- a/core/lib/Drupal/Core/Routing/RouteMatchInterface.php
+++ b/core/lib/Drupal/Core/Routing/RouteMatchInterface.php
@@ -7,6 +7,8 @@
 
 namespace Drupal\Core\Routing;
 
+use Drupal\Core\Session\AccountInterface;
+
 /**
  * Provides an interface for classes representing the result of routing.
  *
@@ -79,4 +81,43 @@ public function getRawParameter($parameter_name);
    */
   public function getRawParameters();
 
+  /**
+   * Checks a route match object with against applicable access check services.
+   *
+   * Determines whether the route is accessible or not.
+   *
+   * @param \Drupal\Core\Session\AccountInterface $account
+   *   Run access checks for this account. Defaults to the current user.
+   *
+   * @return bool
+   *   Returns TRUE if the user has access to the route, otherwise FALSE.
+   */
+  public function access(AccountInterface $account = NULL);
+
+  /**
+   * Creates a Url object from this route match.
+   *
+   * @param array $options
+   *   (optional) An associative array of additional options, with the following
+   *   elements:
+   *   - 'query': An array of query key/value-pairs (without any URL-encoding)
+   *     to append to the URL. Merged with the parameters array.
+   *   - 'fragment': A fragment identifier (named anchor) to append to the URL.
+   *     Do not include the leading '#' character.
+   *   - 'absolute': Defaults to FALSE. Whether to force the output to be an
+   *     absolute link (beginning with http:). Useful for links that will be
+   *     displayed outside the site, such as in an RSS feed.
+   *   - 'language': An optional language object used to look up the alias
+   *     for the URL. If $options['language'] is omitted, it defaults to the
+   *     current language for the language type LanguageInterface::TYPE_URL.
+   *   - 'https': Whether this URL should point to a secure location. If not
+   *     defined, the current scheme is used, so the user stays on HTTP or HTTPS
+   *     respectively. if mixed mode sessions are permitted, TRUE enforces HTTPS
+   *     and FALSE enforces HTTP.
+   *
+   * @return \Drupal\Core\Url|NULL
+   *   The url object. NULL if no route is matched.
+   */
+  public function createUrlObject(array $options = array());
+
 }
diff --git a/core/lib/Drupal/Core/Url.php b/core/lib/Drupal/Core/Url.php
index ea407cc..aae68a6 100644
--- a/core/lib/Drupal/Core/Url.php
+++ b/core/lib/Drupal/Core/Url.php
@@ -8,8 +8,10 @@
 namespace Drupal\Core;
 
 use Drupal\Component\Utility\UrlHelper;
+use Drupal\Core\Access\AccessManagerInterface;
 use Drupal\Core\DependencyInjection\DependencySerializationTrait;
 use Drupal\Core\Routing\UrlGeneratorInterface;
+use Drupal\Core\Session\AccountInterface;
 use Symfony\Cmf\Component\Routing\RouteObjectInterface;
 use Symfony\Component\HttpFoundation\Request;
 
@@ -386,6 +388,7 @@ public function toRenderArray() {
         '#route_name' => $this->getRouteName(),
         '#route_parameters' => $this->getRouteParameters(),
         '#options' => $this->getOptions(),
+        '#access_callback' => array(get_class(), 'renderAccess'),
       );
     }
   }
@@ -412,6 +415,53 @@ public function getInternalPath() {
   }
 
   /**
+   * Checks this Url object against applicable access check services.
+   *
+   * Determines whether the route is accessible or not.
+   *
+   * @param \Drupal\Core\Session\AccountInterface $account
+   *   Run access checks for this account. Defaults to the current user.
+   *
+   * @return bool
+   *   Returns TRUE if the user has access to the url, otherwise FALSE.
+   */
+  public function access(AccountInterface $account = NULL) {
+    return $this->accessManager()->checkNamedRoute($this->getRouteName(), $this->getRouteParameters(), $account);
+  }
+
+  /**
+   * Checks a Url render element against applicable access check services.
+   *
+   * @param array $element
+   *   A render element as returned from \Drupal\Core\Url::toRenderArray().
+   *
+   * @return bool
+   *   Returns TRUE if the current user has access to the url, otherwise FALSE.
+   */
+  public static function renderAccess(array $element) {
+    return (new static($element['#route_name'], $element['#route_parameters'], $element['#options']))->access();
+  }
+
+  /**
+   * @return \Drupal\Core\Access\AccessManagerInterface
+   */
+  protected function accessManager() {
+    if (!isset($this->accessManager)) {
+      $this->accessManager = \Drupal::service('access_manager');
+    }
+    return $this->accessManager;
+  }
+
+  /**
+   * Sets the access manager.
+   *
+   * @param \Drupal\Core\Access\AccessManagerInterface $access_manager
+   */
+  public function setAccessManager(AccessManagerInterface $access_manager) {
+    $this->accessManager = $access_manager;
+  }
+
+  /**
    * Gets the URL generator.
    *
    * @return \Drupal\Core\Routing\UrlGeneratorInterface
diff --git a/core/modules/rdf/src/Tests/Field/TaxonomyTermReferenceRdfaTest.php b/core/modules/rdf/src/Tests/Field/TaxonomyTermReferenceRdfaTest.php
index ed4bbf5..df94280 100644
--- a/core/modules/rdf/src/Tests/Field/TaxonomyTermReferenceRdfaTest.php
+++ b/core/modules/rdf/src/Tests/Field/TaxonomyTermReferenceRdfaTest.php
@@ -7,8 +7,6 @@
 namespace Drupal\rdf\Tests\Field;
 
 use Drupal\Core\Field\FieldStorageDefinitionInterface;
-use Drupal\rdf\Tests\Field\FieldRdfaTestBase;
-use Drupal\Core\Field\FieldDefinitionInterface;
 use Drupal\Core\Language\LanguageInterface;
 
 /**
@@ -100,6 +98,10 @@ protected function setUp() {
   public function testAllFormatters() {
     // Tests the plain formatter.
     $this->assertFormatterRdfa(array('type' => 'taxonomy_term_reference_plain'), 'http://schema.org/about', array('value' => $this->term->getName(), 'type' => 'literal'));
+    // Grant the access content permission to the anonymous user.
+    entity_create('user_role', array('id' => DRUPAL_ANONYMOUS_RID))->save();
+    user_role_grant_permissions(DRUPAL_ANONYMOUS_RID, array('access content'));
+
     // Tests the link formatter.
     $term_uri = $this->getAbsoluteUri($this->term);
     $this->assertFormatterRdfa(array('type'=>'taxonomy_term_reference_link'), 'http://schema.org/about', array('value' => $term_uri, 'type' => 'uri'));
diff --git a/core/modules/system/src/Plugin/Block/SystemBrandingBlock.php b/core/modules/system/src/Plugin/Block/SystemBrandingBlock.php
index 77e63e1..ee65c67 100644
--- a/core/modules/system/src/Plugin/Block/SystemBrandingBlock.php
+++ b/core/modules/system/src/Plugin/Block/SystemBrandingBlock.php
@@ -8,6 +8,7 @@
 namespace Drupal\system\Plugin\Block;
 
 use Drupal\Component\Utility\NestedArray;
+use Drupal\Core\Access\AccessManagerInterface;
 use Drupal\Core\Block\BlockBase;
 use Drupal\Core\Config\ConfigFactoryInterface;
 use Drupal\Core\Form\FormStateInterface;
@@ -15,6 +16,7 @@
 use Drupal\Core\Routing\UrlGeneratorInterface;
 use Drupal\Core\Session\AccountInterface;
 use Drupal\Component\Utility\Xss;
+use Drupal\Core\Url;
 use Symfony\Component\DependencyInjection\ContainerInterface;
 
 /**
@@ -49,6 +51,13 @@ class SystemBrandingBlock extends BlockBase implements ContainerFactoryPluginInt
   protected $currentUser;
 
   /**
+   * The access manager.
+   *
+   * @var \Drupal\Core\Access\AccessManagerInterface
+   */
+  protected $accessManager;
+
+  /**
    * Creates a SystemBrandingBlock instance.
    *
    * @param array $configuration
@@ -64,11 +73,12 @@ class SystemBrandingBlock extends BlockBase implements ContainerFactoryPluginInt
    * @param \Drupal\Core\Session\AccountInterface $current_user
    *   The current user.
    */
-  public function __construct(array $configuration, $plugin_id, $plugin_definition, ConfigFactoryInterface $config_factory, UrlGeneratorInterface $url_generator, AccountInterface $current_user) {
+  public function __construct(array $configuration, $plugin_id, $plugin_definition, ConfigFactoryInterface $config_factory, UrlGeneratorInterface $url_generator, AccountInterface $current_user, AccessManagerInterface $access_manager) {
     parent::__construct($configuration, $plugin_id, $plugin_definition);
     $this->configFactory = $config_factory;
     $this->urlGenerator = $url_generator;
     $this->currentUser = $current_user;
+    $this->accessManager = $access_manager;
   }
 
   /**
@@ -81,7 +91,8 @@ public static function create(ContainerInterface $container, array $configuratio
       $plugin_definition,
       $container->get('config.factory'),
       $container->get('url_generator'),
-      $container->get('current_user')
+      $container->get('current_user'),
+      $container->get('access_manager')
     );
   }
 
@@ -111,26 +122,26 @@ public function blockForm($form, FormStateInterface $form_state) {
     $theme = $form_state['block_theme'];
 
     // Get permissions.
-    $administer_themes_access = $this->currentUser->hasPermission('administer themes');
-    $administer_site_configuration_access = $this->currentUser->hasPermission('administer site configuration');
-
-    if ($administer_themes_access) {
-      // Get paths to theme settings pages.
-      $appearance_settings_url = $this->urlGenerator->generateFromRoute('system.theme_settings');
-      $theme_settings_url = $this->urlGenerator->generateFromRoute('system.theme_settings_theme', array('theme' => $theme));
+    $url_system_theme_settings = new Url('system.theme_settings');
+    $url_system_theme_settings_theme = new Url('system.theme_settings_theme', array('theme' => $theme));
 
+    if ($url_system_theme_settings->access() && $url_system_theme_settings_theme->access()) {
       // Provide links to the Appearance Settings and Theme Settings pages
       // if the user has access to administer themes.
-      $site_logo_description = $this->t('Defined on the <a href="@appearance">Appearance Settings</a> or <a href="@theme">Theme Settings</a> page.', array('@appearance' => $appearance_settings_url, '@theme' => $theme_settings_url));
+      $site_logo_description = $this->t('Defined on the <a href="@appearance">Appearance Settings</a> or <a href="@theme">Theme Settings</a> page.', array(
+        '@appearance' => $url_system_theme_settings->toString(),
+        '@theme' => $url_system_theme_settings_theme->toString(),
+      ));
     }
     else {
       // Explain that the user does not have access to the Appearance and Theme
       // Settings pages.
       $site_logo_description = $this->t('Defined on the Appearance or Theme Settings page. You do not have the appropriate permissions to change the site logo.');
     }
-    if ($administer_site_configuration_access) {
+    $url_system_site_information_settings = new Url('system.site_information_settings');
+    if ($url_system_site_information_settings->access()) {
       // Get paths to settings pages.
-      $site_information_url = $this->urlGenerator->generateFromRoute('system.site_information_settings');
+      $site_information_url = $url_system_site_information_settings->toString();
 
       // Provide link to Site Information page if the user has access to
       // administer site configuration.
diff --git a/core/modules/system/src/Tests/Form/ConfirmFormTest.php b/core/modules/system/src/Tests/Form/ConfirmFormTest.php
index 3ea2820..fcb4e61 100644
--- a/core/modules/system/src/Tests/Form/ConfirmFormTest.php
+++ b/core/modules/system/src/Tests/Form/ConfirmFormTest.php
@@ -33,7 +33,7 @@ function testConfirmForm() {
 
     // Test canelling the form.
     $this->clickLink(t('ConfirmFormTestForm::getCancelText().'));
-    $this->assertUrl('admin', array(), "The form's cancel link was followed.");
+    $this->assertUrl('form-test/autocomplete', array(), "The form's cancel link was followed.");
 
     // Test submitting the form.
     $this->drupalPostForm('form-test/confirm-form', NULL, t('ConfirmFormTestForm::getConfirmText().'));
@@ -47,7 +47,7 @@ function testConfirmForm() {
     // Test cancelling the form with a complex destination.
     $this->drupalGet('form-test/confirm-form-array-path');
     $this->clickLink(t('ConfirmFormArrayPathTestForm::getCancelText().'));
-    $this->assertUrl('admin', array('query' => array('destination' => 'admin/config')), "The form's complex cancel link was followed.");
+    $this->assertUrl('form-test/confirm-form', array('query' => array('destination' => 'admin/config')), "The form's complex cancel link was followed.");
   }
 
 }
diff --git a/core/modules/system/src/Tests/Routing/UrlIntegrationTest.php b/core/modules/system/src/Tests/Routing/UrlIntegrationTest.php
new file mode 100644
index 0000000..66239c9
--- /dev/null
+++ b/core/modules/system/src/Tests/Routing/UrlIntegrationTest.php
@@ -0,0 +1,68 @@
+<?php
+
+/**
+ * @file
+ * Contains \Drupal\system\Tests\Routing\UrlIntegrationTest.
+ */
+
+namespace Drupal\system\Tests\Routing;
+
+use Drupal\Core\Url;
+use Drupal\simpletest\KernelTestBase;
+use Drupal\user\Entity\Role;
+use Drupal\user\Entity\User;
+
+/**
+ * Tests the URL object integration into the access system.
+ *
+ * @group Url
+ */
+class UrlIntegrationTest extends KernelTestBase {
+
+  /**
+   * Modules to enable.
+   *
+   * @var array
+   */
+  public static $modules = array('user', 'router_test', 'system');
+
+  /**
+   * {@inheritdoc}
+   */
+  protected function setUp() {
+    parent::setUp();
+
+    $this->installSchema('system', ['router']);
+  }
+
+  /**
+   * Ensures that the access() method on \Drupal\Core\Url objects works.
+   */
+  public function testAccess() {
+    \Drupal::service('router.builder')->rebuild();
+    /** @var \Drupal\user\RoleInterface $role_with_access */
+    $role_with_access = Role::create(['id' => 'role_with_access']);
+    $role_with_access->grantPermission('administer users');
+    $role_with_access->save();
+
+    /** @var \Drupal\user\RoleInterface $role_without_access */
+    $role_without_access = Role::create(['id' => 'role_without_access']);
+    $role_without_access->save();
+
+    $user_with_access = User::create(['roles' => ['role_with_access']]);
+    $user_without_access = User::create(['roles' => ['role_without_access']]);
+
+    $url_always_access = new Url('router_test.1');
+    $this->assertTrue($url_always_access->access($user_with_access));
+    $this->assertTrue($url_always_access->access($user_without_access));
+
+    $url_none_access = new Url('router_test.15');
+    $this->assertFalse($url_none_access->access($user_with_access));
+    $this->assertFalse($url_none_access->access($user_without_access));
+
+    $url_access = new Url('router_test.16');
+    $this->assertTrue($url_access->access($user_with_access));
+    $this->assertFalse($url_access->access($user_without_access));
+  }
+
+}
diff --git a/core/modules/system/tests/modules/form_test/src/ConfirmFormArrayPathTestForm.php b/core/modules/system/tests/modules/form_test/src/ConfirmFormArrayPathTestForm.php
index c089a26..6cd8c2f 100644
--- a/core/modules/system/tests/modules/form_test/src/ConfirmFormArrayPathTestForm.php
+++ b/core/modules/system/tests/modules/form_test/src/ConfirmFormArrayPathTestForm.php
@@ -25,7 +25,7 @@ public function getFormId() {
    * {@inheritdoc}
    */
   public function getCancelUrl() {
-    return new Url('system.admin', array(), array(
+    return new Url('form_test.route6', array(), array(
       'query' => array(
         'destination' => 'admin/config',
       ),
diff --git a/core/modules/system/tests/modules/form_test/src/ConfirmFormTestForm.php b/core/modules/system/tests/modules/form_test/src/ConfirmFormTestForm.php
index a031747..fd74f3b 100644
--- a/core/modules/system/tests/modules/form_test/src/ConfirmFormTestForm.php
+++ b/core/modules/system/tests/modules/form_test/src/ConfirmFormTestForm.php
@@ -34,7 +34,7 @@ public function getQuestion() {
    * {@inheritdoc}
    */
   public function getCancelUrl() {
-    return new Url('system.admin');
+    return new Url('form_test.route8');
   }
 
   /**
diff --git a/core/modules/system/tests/modules/router_test_directory/router_test.routing.yml b/core/modules/system/tests/modules/router_test_directory/router_test.routing.yml
index 7405d88..5b02a3b 100644
--- a/core/modules/system/tests/modules/router_test_directory/router_test.routing.yml
+++ b/core/modules/system/tests/modules/router_test_directory/router_test.routing.yml
@@ -93,6 +93,20 @@ router_test.14:
   defaults:
     _controller: '\Drupal\router_test\TestControllers::test9'
 
+router_test.15:
+  path: '/router_test/test15'
+  defaults:
+    _controller: '\Drupal\router_test\TestControllers::test1'
+  requirements:
+    _access: 'FALSE'
+
+router_test.16:
+  path: '/router_test/test16'
+  defaults:
+    _controller: '\Drupal\router_test\TestControllers::test1'
+  requirements:
+    _permission: 'administer users'
+
 router_test.hierarchy_parent:
   path: '/menu-test/parent'
   defaults:
diff --git a/core/modules/user/user.module b/core/modules/user/user.module
index 75777bb..21c5615 100644
--- a/core/modules/user/user.module
+++ b/core/modules/user/user.module
@@ -1101,6 +1101,10 @@ function user_user_role_insert(RoleInterface $role) {
   }
 
   $add_id = 'user_add_role_action.' . $role->id();
+
+  if (!\Drupal::entityManager()->hasDefinition('action')) {
+    return;
+  }
   if (!entity_load('action', $add_id)) {
     $action = entity_create('action', array(
       'id' => $add_id,
diff --git a/core/tests/Drupal/Tests/Core/Access/AccessManagerTest.php b/core/tests/Drupal/Tests/Core/Access/AccessManagerTest.php
index 3aa8046..dae6582 100644
--- a/core/tests/Drupal/Tests/Core/Access/AccessManagerTest.php
+++ b/core/tests/Drupal/Tests/Core/Access/AccessManagerTest.php
@@ -12,6 +12,7 @@
 use Drupal\Core\Routing\Access\AccessInterface;
 use Drupal\Core\Access\AccessManager;
 use Drupal\Core\Access\DefaultAccessCheck;
+use Drupal\Core\Session\AccountProxy;
 use Drupal\Tests\UnitTestCase;
 use Drupal\router_test\Access\DefinedTestAccessCheck;
 use Symfony\Cmf\Component\Routing\RouteObjectInterface;
@@ -92,6 +93,11 @@ class AccessManagerTest extends UnitTestCase {
   protected $requestStack;
 
   /**
+   * @var \Drupal\Core\Session\AccountInterface|\PHPUnit_Framework_MockObject_MockObject
+   */
+  protected $currentUser;
+
+  /**
    * {@inheritdoc}
    */
   protected function setUp() {
@@ -129,11 +135,12 @@ protected function setUp() {
     $this->paramConverter = $this->getMock('Drupal\Core\ParamConverter\ParamConverterManagerInterface');
 
     $this->account = $this->getMock('Drupal\Core\Session\AccountInterface');
+    $this->currentUser = $this->getMock('Drupal\Core\Session\AccountInterface');
     $this->argumentsResolver = $this->getMock('Drupal\Core\Access\AccessArgumentsResolverInterface');
 
     $this->requestStack = new RequestStack();
 
-    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack);
+    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack, $this->currentUser);
     $this->accessManager->setContainer($this->container);
   }
 
@@ -162,7 +169,7 @@ public function testSetChecks() {
    */
   public function testSetChecksWithDynamicAccessChecker() {
     // Setup the access manager.
-    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack);
+    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack, $this->currentUser);
     $this->accessManager->setContainer($this->container);
 
     // Setup the dynamic access checker.
@@ -220,6 +227,25 @@ public function testCheck() {
   }
 
   /**
+   * Tests \Drupal\Core\Access\AccessManager::check() with no account specified.
+   *
+   * @covers ::check
+   */
+  public function testCheckWithNullAccount() {
+    $this->setupAccessChecker();
+    $this->accessManager->setChecks($this->routeCollection);
+    $request = new Request;
+    $route = $this->routeCollection->get('test_route_2');
+    $this->argumentsResolver->expects($this->once())
+      ->method('getArguments')
+      ->with(array($this->container->get('test_access_default'), 'access'), $route, $request, $this->currentUser)
+      ->will($this->returnCallback(function ($callable, $route, $request, $account) {
+        return array($route);
+      }));
+    $this->accessManager->check($route, $request);
+  }
+
+  /**
    * Provides data for the conjunction test.
    *
    * @return array
@@ -472,7 +498,7 @@ public function testCheckNamedRouteWithUpcastedValues() {
 
     $subrequest = Request::create('/test-route-1/example');
 
-    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack);
+    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack, $this->currentUser);
     $this->accessManager->setContainer($this->container);
     $this->requestStack->push(new Request());
 
@@ -532,7 +558,7 @@ public function testCheckNamedRouteWithDefaultValue() {
 
     $subrequest = Request::create('/test-route-1/example');
 
-    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack);
+    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack, $this->currentUser);
     $this->accessManager->setContainer($this->container);
     $this->requestStack->push(new Request());
 
@@ -610,7 +636,7 @@ public function testCheckException($return_value, $access_mode) {
       ->will($this->returnValue($return_value));
     $container->set('test_incorrect_value', $access_check);
 
-    $access_manager = new AccessManager($route_provider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack);
+    $access_manager = new AccessManager($route_provider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack, $this->currentUser);
     $access_manager->setContainer($container);
     $access_manager->addCheckService('test_incorrect_value', 'access');
 
@@ -665,7 +691,7 @@ protected static function convertAccessCheckInterfaceToString($constant) {
    * Adds a default access check service to the container and the access manager.
    */
   protected function setupAccessChecker() {
-    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack);
+    $this->accessManager = new AccessManager($this->routeProvider, $this->urlGenerator, $this->paramConverter, $this->argumentsResolver, $this->requestStack, $this->currentUser);
     $this->accessManager->setContainer($this->container);
     $access_check = new DefaultAccessCheck();
     $this->container->register('test_access_default', $access_check);
diff --git a/core/tests/Drupal/Tests/Core/Routing/RouteMatchTest.php b/core/tests/Drupal/Tests/Core/Routing/RouteMatchTest.php
index 6aab6f4..6289409 100644
--- a/core/tests/Drupal/Tests/Core/Routing/RouteMatchTest.php
+++ b/core/tests/Drupal/Tests/Core/Routing/RouteMatchTest.php
@@ -65,4 +65,42 @@ public function testRouteMatchFromRequest() {
     $this->assertSame(array('foo' => '1'), $route_match->getRawParameters()->all());
   }
 
+  /**
+   * Tests the access() method.
+   *
+   * @covers ::access
+   * @covers ::getAccessManager
+   * @covers ::setAccessManager
+   */
+  public function testAccess() {
+    foreach ([TRUE, FALSE] as $access) {
+      $account = $this->getMock('Drupal\Core\Session\AccountInterface');
+
+      $access_manager = $this->getMock('Drupal\Core\Access\AccessManagerInterface');
+      $access_manager->expects($this->once())
+        ->method('checkNamedRoute')
+        ->with('entity.node.canonical', ['node' => 3], $account)
+        ->willReturn($access);
+
+      $route_match = new RouteMatch('entity.node.canonical', new Route('node/{node}'), ['node' => (object) ['nid' => 3]], ['node' => 3]);
+      $route_match->setAccessManager($access_manager);
+
+      $this->assertEquals($access, $route_match->access($account));
+    }
+  }
+
+  /**
+   * Tests the createUrlObject() method.
+   *
+   * @covers ::createUrlObject
+   */
+  public function testCreateUrlObject() {
+    $route_match = new RouteMatch('entity.node.canonical', new Route('node/{node}'), ['node' => (object) ['nid' => 3]], ['node' => 3]);
+
+    $url = $route_match->createUrlObject(['foo' => 'bar']);
+    $this->assertEquals('entity.node.canonical', $url->getRouteName());
+    $this->assertEquals(['node' => 3], $url->getRouteParameters());;
+    $this->assertEquals(['foo' => 'bar'], $url->getOptions());
+  }
+
 }
diff --git a/core/tests/Drupal/Tests/Core/UrlTest.php b/core/tests/Drupal/Tests/Core/UrlTest.php
index 92f429d..9f3850a 100644
--- a/core/tests/Drupal/Tests/Core/UrlTest.php
+++ b/core/tests/Drupal/Tests/Core/UrlTest.php
@@ -318,4 +318,28 @@ public function testGetOptions($urls) {
     }
   }
 
+  /**
+   * Tests the access() method.
+   *
+   * @covers ::access
+   * @covers ::getAccessManager
+   * @covers ::setAccessManager
+   */
+  public function testAccess() {
+    foreach ([FALSE, TRUE] as $access) {
+      $account = $this->getMock('Drupal\Core\Session\AccountInterface');
+
+      $access_manager = $this->getMock('Drupal\Core\Access\AccessManagerInterface');
+      $access_manager->expects($this->once())
+        ->method('checkNamedRoute')
+        ->with('entity.node.canonical', ['node' => 3], $account)
+        ->willReturn($access);
+
+      $url = new Url('entity.node.canonical', ['node' => 3]);
+      $url->setAccessManager($access_manager);
+
+      $this->assertEquals($access, $url->access($account));
+    }
+  }
+
 }
