diff --git a/core/includes/tablesort.inc b/core/includes/tablesort.inc
index c42b1f4..53e5fe3 100644
--- a/core/includes/tablesort.inc
+++ b/core/includes/tablesort.inc
@@ -42,7 +42,7 @@ function tablesort_header($cell, $header, $ts) {
   // Special formatting for the currently sorted column header.
   if (is_array($cell) && isset($cell['field'])) {
     $title = t('sort by @s', array('@s' => $cell['data']));
-    if ($cell['data'] == $ts['name']) {
+    if ($cell['field'] == $ts['field']) {
       // aria-sort is a WAI-ARIA property that indicates if items in a table
       // or grid are sorted in ascending or descending order. See
       // http://www.w3.org/TR/wai-aria/states_and_properties#aria-sort
@@ -56,7 +56,7 @@ function tablesort_header($cell, $header, $ts) {
       $ts['sort'] = 'asc';
       $image = '';
     }
-    $cell['data'] = l($cell['data'] . $image, current_path(), array('attributes' => array('title' => $title), 'query' => array_merge($ts['query'], array('sort' => $ts['sort'], 'order' => $cell['data'])), 'html' => TRUE));
+    $cell['data'] = l($cell['data'] . $image, current_path(), array('attributes' => array('title' => $title), 'query' => array_merge($ts['query'], array('sort' => $ts['sort'], 'order' => $cell['field'])), 'html' => TRUE));
 
     unset($cell['field'], $cell['sort']);
   }
@@ -81,7 +81,7 @@ function tablesort_header($cell, $header, $ts) {
  *   A properly formatted cell, ready for _theme_table_cell().
  */
 function tablesort_cell($cell, $header, $ts, $i) {
-  if (isset($header[$i]['data']) && $header[$i]['data'] == $ts['name'] && !empty($header[$i]['field'])) {
+  if (isset($header[$i]['field']) && $header[$i]['field'] == $ts['field']) {
     if (is_array($cell)) {
       $cell['class'][] = 'active';
     }
@@ -118,7 +118,7 @@ function tablesort_get_order($headers) {
   $order = isset($_GET['order']) ? $_GET['order'] : '';
   foreach ($headers as $header) {
     if (is_array($header)) {
-      if (isset($header['data']) && $order == $header['data']) {
+      if (isset($header['field']) && $order == $header['field']) {
         $default = $header;
         break;
       }
@@ -136,8 +136,9 @@ function tablesort_get_order($headers) {
     }
   }
 
-  $default += array('data' => NULL, 'field' => NULL);
-  return array('name' => $default['data'], 'sql' => $default['field']);
+  $default += array('field' => NULL);
+  $default += array('query_field' => $default['field'], 'query_reverse' => FALSE);
+  return array('field' => $default['field'], 'query_field' => $default['query_field'], 'query_reverse' => $default['query_reverse']);
 }
 
 /**
@@ -159,7 +160,7 @@ function tablesort_get_sort($headers) {
     // Find out which header is currently being sorted.
     $ts = tablesort_get_order($headers);
     foreach ($headers as $header) {
-      if (is_array($header) && isset($header['data']) && $header['data'] == $ts['name'] && isset($header['sort'])) {
+      if (is_array($header) && isset($header['field']) && $header['field'] == $ts['field'] && isset($header['sort'])) {
         return $header['sort'];
       }
     }
diff --git a/core/lib/Drupal/Core/Database/Query/TableSortExtender.php b/core/lib/Drupal/Core/Database/Query/TableSortExtender.php
index cf1a042..c324598 100644
--- a/core/lib/Drupal/Core/Database/Query/TableSortExtender.php
+++ b/core/lib/Drupal/Core/Database/Query/TableSortExtender.php
@@ -42,13 +42,17 @@ public function __construct(SelectInterface $query, Connection $connection) {
   public function orderByHeader(array $header) {
     $this->header = $header;
     $ts = $this->init();
-    if (!empty($ts['sql'])) {
+    if (!empty($ts['field'])) {
+      $field = isset($ts['query_field']) ? $ts['query_field'] : $ts['field'];
       // Based on code from db_escape_table(), but this can also contain a dot.
-      $field = preg_replace('/[^A-Za-z0-9_.]+/', '', $ts['sql']);
+      $field = preg_replace('/[^A-Za-z0-9_.]+/', '', $field);
 
       // Sort order can only be ASC or DESC.
       $sort = drupal_strtoupper($ts['sort']);
       $sort = in_array($sort, array('ASC', 'DESC')) ? $sort : '';
+      if (isset($ts['query_reverse']) && $ts['query_reverse'] && strlen($sort) > 0) {
+        $sort = ($sort == 'ASC') ? 'DESC' : 'ASC';
+      }
       $this->orderBy($field, $sort);
     }
     return $this;
diff --git a/core/lib/Drupal/Core/Entity/Query/QueryBase.php b/core/lib/Drupal/Core/Entity/Query/QueryBase.php
index c3c6932..394f91a 100644
--- a/core/lib/Drupal/Core/Entity/Query/QueryBase.php
+++ b/core/lib/Drupal/Core/Entity/Query/QueryBase.php
@@ -268,10 +268,10 @@ public function tableSort(&$headers) {
       }
     }
 
-    $order = tablesort_get_order($headers);
+    $ts = tablesort_get_order($headers);
     $direction = tablesort_get_sort($headers);
     foreach ($headers as $header) {
-      if (is_array($header) && ($header['data'] == $order['name'])) {
+      if (is_array($header) && ($header['field'] == $ts['field'])) {
         $this->sort($header['specifier'], $direction, isset($header['langcode']) ? $header['langcode'] : NULL);
       }
     }
