diff --git a/core/modules/node/lib/Drupal/node/Tests/NodeRevisionPermissionsTest.php b/core/modules/node/lib/Drupal/node/Tests/NodeRevisionPermissionsTest.php
index 7af3429..53b9d94 100644
--- a/core/modules/node/lib/Drupal/node/Tests/NodeRevisionPermissionsTest.php
+++ b/core/modules/node/lib/Drupal/node/Tests/NodeRevisionPermissionsTest.php
@@ -16,9 +16,16 @@ class NodeRevisionPermissionsTest extends NodeTestBase {
 
   // Map revision permission names to node revision access ops.
   protected $map = array(
-    'view' => 'view revisions',
-    'update' => 'revert revisions',
-    'delete' => 'delete revisions',
+    'view' => 'view all revisions',
+    'update' => 'revert all revisions',
+    'delete' => 'delete all revisions',
+  );
+
+  // Map revision permission names to node type revision access ops.
+  protected $type_map = array(
+    'view' => 'view page revisions',
+    'update' => 'revert page revisions',
+    'delete' => 'delete page revisions',
   );
 
   public static function getInfo() {
@@ -32,19 +39,28 @@ public static function getInfo() {
   function setUp() {
     parent::setUp();
 
-    // Create a node with several revisions.
-    $node = $this->drupalCreateNode();
-    $this->node_revisions[] = $node;
-
-    for ($i = 0; $i < 3; $i++) {
-      // Create a revision for the same nid and settings with a random log.
-      $revision = clone $node;
-      $revision->setNewRevision();
-      $revision->log = $this->randomName(32);
-      node_save($revision);
-      $this->node_revisions[] = $revision;
+    $types = array('page', 'article');
+
+    foreach ($types as $type) {
+      // Create a node with several revisions.
+      $nodes[$type] = $this->drupalCreateNode(array('type' => $type));
+      $this->node_revisions[$type][] = $nodes[$type];
+
+      for ($i = 0; $i < 3; $i++) {
+        // Create a revision for the same nid and settings with a random log.
+        $revision = clone $nodes[$type];
+        $revision->revision = 1;
+        $revision->log = $this->randomName(32);
+        node_save($revision);
+        $this->node_revisions[$type][] = $revision;
+      }
     }
+  }
 
+  /**
+   * Tests general revision access permissions.
+   */
+  function testNodeRevisionAccessAnyType() {
     // Create three users, one with each revision permission.
     foreach ($this->map as $op => $permission) {
       // Create the user.
@@ -64,18 +80,14 @@ function setUp() {
     $admin_account = $this->drupalCreateUser(array('access content', 'administer nodes'));
     $admin_account->is_admin = TRUE;
     $this->accounts['admin'] = $admin_account;
+    $accounts['admin'] = $admin_account;
 
     // Create a normal account (returns FALSE for all revision permissions).
     $normal_account = $this->drupalCreateUser();
     $normal_account->op = FALSE;
     $this->accounts[] = $normal_account;
-  }
-
-  /**
-   * Tests the _node_revision_access() function.
-   */
-  function testNodeRevisionAccess() {
-    $revision = node_revision_load($this->node_revisions[1]->vid);
+    $accounts[] = $normal_account;
+    $revision = $this->node_revisions['page'][1];
 
     $parameters = array(
       'op' => array_keys($this->map),
@@ -83,24 +95,70 @@ function testNodeRevisionAccess() {
     );
 
     $permutations = $this->generatePermutations($parameters);
+
     foreach ($permutations as $case) {
-      if (!empty($case['account']->is_admin) || $case['op'] == $case['account']->op) {
-        $this->assertTrue(_node_revision_access($revision, $case['op'], $case['account']), "{$this->map[$case['op']]} granted.");
-      }
-      else {
-        $this->assertFalse(_node_revision_access($revision, $case['op'], $case['account']), "{$this->map[$case['op']]} not granted.");
+      // Skip this test if there are no revisions for the node.
+      if (!($revision->isDefaultRevision() && (db_query('SELECT COUNT(vid) FROM {node_revision} WHERE nid = :nid', array(':nid' => $revision->nid))->fetchField() == 1 || $case['op'] == 'update' || $case['op'] == 'delete'))) {
+        if (!empty($case['account']->is_admin) || user_access($this->map[$case['op']], $case['account'])) {
+          $this->assertTrue(_node_revision_access($revision, $case['op'], $case['account']), "{$this->map[$case['op']]} granted.");
+        }
+        else {
+          $this->assertFalse(_node_revision_access($revision, $case['op'], $case['account']), "{$this->map[$case['op']]} not granted.");
+        }
       }
     }
 
     // Test that access is FALSE for a node administrator with an invalid $node
     // or $op parameters.
-    $admin_account = $this->accounts['admin'];
+    $admin_account = $accounts['admin'];
     $this->assertFalse(_node_revision_access($revision, 'invalid-op', $admin_account), '_node_revision_access() returns FALSE with an invalid op.');
+  }
+
+  /**
+   * Tests revision access permissions for a specific content type.
+   */
+  function testNodeRevisionAccessPerType() {
+    // Create three users, one with each revision permission.
+    foreach ($this->type_map as $op => $permission) {
+      // Create the user.
+      $account = $this->drupalCreateUser(
+        array(
+          'access content',
+          'edit any page content',
+          'delete any page content',
+          $permission,
+        )
+      );
+      $account->op = $op;
+      $accounts[] = $account;
+    }
 
-    // Test that the $account parameter defaults to the "logged in" user.
-    $original_user = $GLOBALS['user'];
-    $GLOBALS['user'] = $admin_account;
-    $this->assertTrue(_node_revision_access($revision, 'view'), '_node_revision_access() returns TRUE when used with global user.');
-    $GLOBALS['user'] = $original_user;
+    $parameters = array(
+      'op' => array_keys($this->type_map),
+      'account' => $accounts,
+    );
+
+    // Test that the accounts have access to the correspoding page revision permissions.
+    $revision = $this->node_revisions['page'][1];
+
+    $permutations = $this->generatePermutations($parameters);
+    foreach ($permutations as $case) {
+      // Skip this test if there are no revisions for the node.
+      if (!($revision->isDefaultRevision() && (db_query('SELECT COUNT(vid) FROM {node_revision} WHERE nid = :nid', array(':nid' => $revision->nid))->fetchField() == 1 || $case['op'] == 'update' || $case['op'] == 'delete'))) {
+        if (!empty($case['account']->is_admin) || user_access($this->type_map[$case['op']], $case['account'])) {
+          $this->assertTrue(_node_revision_access($revision, $case['op'], $case['account']), "{$this->type_map[$case['op']]} granted.");
+        }
+        else {
+          $this->assertFalse(_node_revision_access($revision, $case['op'], $case['account']), "{$this->type_map[$case['op']]} not granted.");
+        }
+      }
+    }
+
+    // Test that the accounts have no access to the article revisions.
+    $revision = $this->node_revisions['article'][1];
+
+    foreach ($permutations as $case) {
+      $this->assertFalse(_node_revision_access($revision, $case['op'], $case['account']), "{$this->type_map[$case['op']]} did not grant revision permission for articles.");
+    }
   }
 }
diff --git a/core/modules/node/lib/Drupal/node/Tests/NodeRevisionsTest.php b/core/modules/node/lib/Drupal/node/Tests/NodeRevisionsTest.php
index 877c003..2ce2abb 100644
--- a/core/modules/node/lib/Drupal/node/Tests/NodeRevisionsTest.php
+++ b/core/modules/node/lib/Drupal/node/Tests/NodeRevisionsTest.php
@@ -16,8 +16,8 @@ class NodeRevisionsTest extends NodeTestBase {
 
   public static function getInfo() {
     return array(
-      'name' => 'Node revisions',
-      'description' => 'Create a node with revisions and test viewing, saving, reverting, and deleting revisions.',
+      'name' => 'Node revisions by type',
+      'description' => 'Create a node with revisions and test viewing, saving, reverting, and deleting revisions for users with access for this content type.',
       'group' => 'Node',
     );
   }
@@ -25,9 +25,17 @@ public static function getInfo() {
   function setUp() {
     parent::setUp();
 
-    // Create and login user.
-    $web_user = $this->drupalCreateUser(array('view revisions', 'revert revisions', 'edit any page content',
-                                               'delete revisions', 'delete any page content', 'administer nodes'));
+    // Create and log in user.
+    $web_user = $this->drupalCreateUser(
+      array(
+        'view page revisions',
+        'revert page revisions',
+        'delete page revisions',
+        'edit any page content',
+        'delete any page content'
+      )
+    );
+
     $this->drupalLogin($web_user);
 
     // Create initial node.
@@ -190,3 +198,144 @@ function testNodeRevisionWithoutLogMessage() {
     $this->assertTrue(empty($node_revision->log), 'After a new node revision is saved with an empty log message, the log message for the node is empty.');
   }
 }
+
+/**
+ * Tests actions against revisions for user with access to all revisions.
+ */
+class NodeRevisionsAllTestCase extends NodeTestBase {
+  protected $nodes;
+  protected $logs;
+  protected $profile = "standard";
+
+  public static function getInfo() {
+    return array(
+      'name' => 'Node revisions all',
+      'description' => 'Create a node with revisions and test viewing, saving, reverting, and deleting revisions for user with access to all.',
+      'group' => 'Node',
+    );
+  }
+
+  function setUp() {
+    parent::setUp();
+
+    // Create and log in user.
+    $web_user = $this->drupalCreateUser(
+      array(
+        'view page revisions',
+        'revert page revisions',
+        'delete page revisions',
+        'edit any page content',
+        'delete any page content'
+      )
+    );
+    $this->drupalLogin($web_user);
+
+    // Create an initial node.
+    $node = $this->drupalCreateNode();
+
+    $settings = get_object_vars($node);
+    $settings['revision'] = 1;
+
+    $nodes = array();
+    $logs = array();
+
+    // Get the original node.
+    $nodes[] = $node;
+
+    // Create three revisions.
+    $revision_count = 3;
+    for ($i = 0; $i < $revision_count; $i++) {
+      $logs[] = $settings['log'] = $this->randomName(32);
+
+      // Create revision with a random title and body and update variables.
+      $this->drupalCreateNode($settings);
+      $node = node_load($node->nid); // Make sure we get revision information.
+      $settings = get_object_vars($node);
+      $nodes[] = $node;
+    }
+
+    $this->nodes = $nodes;
+    $this->logs = $logs;
+  }
+
+  /**
+   * Checks node revision operations.
+   */
+  function testRevisions() {
+    $nodes = $this->nodes;
+    $logs = $this->logs;
+
+    // Get last node for simple checks.
+    $node = $nodes[3];
+
+    // Create and login user.
+    $content_admin = $this->drupalCreateUser(
+      array(
+        'view all revisions',
+        'revert all revisions',
+        'delete all revisions',
+        'edit any page content',
+        'delete any page content'
+      )
+    );
+    $this->drupalLogin($content_admin);
+
+    // Confirm the correct revision text appears on "view revisions" page.
+    $this->drupalGet("node/$node->nid/revisions/$node->vid/view");
+    $this->assertText($node->body[LANGUAGE_NOT_SPECIFIED][0]['value'], t('Correct text displays for version.'));
+
+    // Confirm the correct log message appears on "revisions overview" page.
+    $this->drupalGet("node/$node->nid/revisions");
+    foreach ($logs as $log) {
+      $this->assertText($log, t('Log message found.'));
+    }
+
+    // Confirm that this is the current revision.
+    $this->assertTrue($node->isCurrentRevision(), 'Third node revision is the current one.');
+
+    // Confirm that revisions revert properly.
+    $this->drupalPost("node/$node->nid/revisions/{$nodes[1]->vid}/revert", array(), t('Revert'));
+    $this->assertRaw(t('@type %title has been reverted back to the revision from %revision-date.',
+      array(
+        '@type' => 'Basic page',
+        '%title' => $nodes[1]->title,
+        '%revision-date' => format_date($nodes[1]->revision_timestamp)
+      )),
+      'Revision reverted.');
+    $reverted_node = node_load($node->nid);
+    $this->assertTrue(($nodes[1]->body[LANGUAGE_NOT_SPECIFIED][0]['value'] == $reverted_node->body[LANGUAGE_NOT_SPECIFIED][0]['value']), t('Node reverted correctly.'));
+
+    // Confirm that this is not the current version.
+    $node = node_load($node->nid, $node->vid);
+    $this->assertFalse($node->isCurrentRevision(), 'Third node revision is not the current one.');
+
+    // Confirm revisions delete properly.
+    $this->drupalPost("node/$node->nid/revisions/{$nodes[1]->vid}/delete", array(), t('Delete'));
+    $this->assertRaw(t('Revision from %revision-date of @type %title has been deleted.',
+      array(
+        '%revision-date' => format_date($nodes[1]->revision_timestamp),
+        '@type' => 'Basic page',
+        '%title' => $nodes[1]->title,
+      )),
+      'Revision deleted.');
+    $this->assertTrue(db_query('SELECT COUNT(vid) FROM {node_revision} WHERE nid = :nid and vid = :vid',
+      array(':nid' => $node->nid, ':vid' => $nodes[1]->vid))->fetchField() == 0,
+      'Revision not found.');
+
+    // Set the revision timestamp to an older date to make sure that the
+    // confirmation message correctly displays the stored revision date.
+    $old_revision_date = REQUEST_TIME - 86400;
+    db_update('node_revision')
+      ->condition('vid', $nodes[2]->vid)
+      ->fields(array(
+        'timestamp' => $old_revision_date,
+      ))
+      ->execute();
+    $this->drupalPost("node/$node->nid/revisions/{$nodes[2]->vid}/revert", array(), t('Revert'));
+    $this->assertRaw(t('@type %title has been reverted back to the revision from %revision-date.', array(
+      '@type' => 'Basic page',
+      '%title' => $nodes[2]->title,
+      '%revision-date' => format_date($old_revision_date),
+    )));
+  }
+}
diff --git a/core/modules/node/node.install b/core/modules/node/node.install
index f9c30a5..1fd3860 100644
--- a/core/modules/node/node.install
+++ b/core/modules/node/node.install
@@ -740,6 +740,21 @@ function node_update_8011() {
 }
 
 /**
+ * Renames global revision permissions to use the word 'any'.
+ */
+function node_update_8012() {
+  $actions = array('view', 'delete', 'revert');
+
+  foreach ($actions as $action) {
+    db_update('role_permission')
+      ->fields(array('permission' => "{$action} any revisions"))
+      ->condition('permission', "{$action} revisions")
+      ->condition('module', 'node')
+      ->execute();
+  }
+}
+
+/**
  * @} End of "addtogroup updates-7.x-to-8.x"
  * The next series of updates should start at 9000.
  */
diff --git a/core/modules/node/node.module b/core/modules/node/node.module
index 5415312..e656417 100644
--- a/core/modules/node/node.module
+++ b/core/modules/node/node.module
@@ -1268,14 +1268,16 @@ function node_permission() {
     'view own unpublished content' => array(
       'title' => t('View own unpublished content'),
     ),
-    'view revisions' => array(
-      'title' => t('View content revisions'),
+    'view all revisions' => array(
+      'title' => t('View all revisions'),
     ),
-    'revert revisions' => array(
-      'title' => t('Revert content revisions'),
+    'revert all revisions' => array(
+      'title' => t('Revert all revisions'),
+      'description' => t('Requires <em>view revision</em> and <em>edit rights</em> to nodes in question, or <em>Administer nodes</em>.'),
     ),
-    'delete revisions' => array(
-      'title' => t('Delete content revisions'),
+    'delete all revisions' => array(
+      'title' => t('Delete all revisions'),
+      'description' => t('Requires <em>view revision</em> and <em>delete rights</em> to nodes in question, or <em>Administer nodes</em>.'),
     ),
   );
 
@@ -1588,12 +1590,17 @@ function _node_revision_access(Node $node, $op = 'view', $account = NULL, $langc
   $access = &drupal_static(__FUNCTION__, array());
 
   $map = array(
-    'view' => 'view revisions',
-    'update' => 'revert revisions',
-    'delete' => 'delete revisions',
+    'view' => 'view all revisions',
+    'update' => 'revert all revisions',
+    'delete' => 'delete all revisions',
+  );
+  $type_map = array(
+    'view' => "view $node->type revisions",
+    'update' => "revert $node->type revisions",
+    'delete' => "delete $node->type revisions",
   );
 
-  if (!$node || !isset($map[$op])) {
+  if (!$node || !isset($map[$op]) || !isset($type_map[$op])) {
     // If there was no node to check against, or the $op was not one of the
     // supported ones, we return access denied.
     return FALSE;
@@ -1614,7 +1621,7 @@ function _node_revision_access(Node $node, $op = 'view', $account = NULL, $langc
 
   if (!isset($access[$cid])) {
     // Perform basic permission checks first.
-    if (!user_access($map[$op], $account) && !user_access('administer nodes', $account)) {
+    if (!user_access($map[$op], $account) && !user_access($type_map[$op], $account) && !user_access('administer nodes', $account)) {
       return $access[$cid] = FALSE;
     }
 
@@ -2918,6 +2925,17 @@ function node_list_permissions($type) {
     "delete any $type->type content" => array(
       'title' => t('%type_name: Delete any content', array('%type_name' => $type->name)),
     ),
+    "view $type->type revisions" => array(
+      'title' => t('%type_name: View revisions', array('%type_name' => $type->name)),
+    ),
+    "revert $type->type revisions" => array(
+      'title' => t('%type_name: Revert revisions', array('%type_name' => $type->name)),
+      'description' => t('Requires <em>view revision</em> and <em>edit rights</em> to nodes in question, or <em>Administer nodes</em>.'),
+    ),
+    "delete $type->type revisions" => array(
+      'title' => t('%type_name: Delete revisions', array('%type_name' => $type->name)),
+      'description' => t('Requires <em>view revision</em> and <em>delete rights</em> to nodes in question, or <em>Administer nodes</em>.'),
+    ),
   );
   return $perms;
 }
diff --git a/core/modules/node/node.pages.inc b/core/modules/node/node.pages.inc
index a71f5eb..4be4919 100644
--- a/core/modules/node/node.pages.inc
+++ b/core/modules/node/node.pages.inc
@@ -257,16 +257,19 @@ function node_revision_overview($node) {
   $revisions = node_revision_list($node);
 
   $rows = array();
+  $type = $node->type;
+
   $revert_permission = FALSE;
-  if ((user_access('revert revisions') || user_access('administer nodes')) && node_access('update', $node)) {
+  if (user_access('administer nodes') || (user_access("revert $type revisions") || user_access('revert all revisions') && node_access('update', $node))) {
     $revert_permission = TRUE;
   }
   $delete_permission = FALSE;
-  if ((user_access('delete revisions') || user_access('administer nodes')) && node_access('delete', $node)) {
+  if (user_access('administer nodes') || (user_access("delete $type revisions") || user_access('delete all revisions') && node_access('delete', $node))) {
     $delete_permission = TRUE;
   }
   foreach ($revisions as $revision) {
     $row = array();
+    $type = $node->type;
     if ($revision->current_vid > 0) {
       $row[] = array('data' => t('!date by !username', array('!date' => l(format_date($revision->timestamp, 'short'), "node/$node->nid"), '!username' => theme('username', array('account' => $revision))))
                                . (($revision->log != '') ? '<p class="revision-log">' . filter_xss($revision->log) . '</p>' : ''),
diff --git a/core/modules/rdf/lib/Drupal/rdf/Tests/RdfaMarkupTest.php b/core/modules/rdf/lib/Drupal/rdf/Tests/RdfaMarkupTest.php
index 00e4259..db24097 100644
--- a/core/modules/rdf/lib/Drupal/rdf/Tests/RdfaMarkupTest.php
+++ b/core/modules/rdf/lib/Drupal/rdf/Tests/RdfaMarkupTest.php
@@ -99,7 +99,7 @@ function testDrupalRdfaAttributes() {
    */
   function testAttributesInMarkupFile() {
     // Create a user to post the image.
-    $admin_user = $this->drupalCreateUser(array('edit own article content', 'revert revisions', 'administer content types'));
+    $admin_user = $this->drupalCreateUser(array('edit own article content', 'revert article revisions', 'administer content types'));
     $this->drupalLogin($admin_user);
 
     $langcode = LANGUAGE_NOT_SPECIFIED;
