Index: modules/block/block.admin.inc
===================================================================
RCS file: /cvs/drupal/drupal/modules/block/block.admin.inc,v
retrieving revision 1.90
diff -u -p -r1.90 block.admin.inc
--- modules/block/block.admin.inc	10 Oct 2010 20:11:21 -0000	1.90
+++ modules/block/block.admin.inc	1 Nov 2010 02:13:37 -0000
@@ -286,7 +286,7 @@ function block_admin_configure($form, &$
     '#type' => 'fieldset',
     '#title' => t('Region settings'),
     '#collapsible' => FALSE,
-    '#description' => t('Specify in which themes and regions this block is displayed.'),
+    '#description' => t('Specify the regions in which this block is displayed.'),
     '#tree' => TRUE,
   );
 
Index: modules/block/block.test
===================================================================
RCS file: /cvs/drupal/drupal/modules/block/block.test,v
retrieving revision 1.60
diff -u -p -r1.60 block.test
--- modules/block/block.test	25 Oct 2010 15:51:21 -0000	1.60
+++ modules/block/block.test	1 Nov 2010 02:13:37 -0000
@@ -321,18 +321,13 @@ class NewDefaultThemeBlocks extends Drup
     $admin_user = $this->drupalCreateUser(array('administer themes'));
     $this->drupalLogin($admin_user);
 
-    // Ensure no other theme's blocks are in the block table yet.
-    $themes = array();
-    $themes['default'] = variable_get('theme_default', 'bartik');
-    if ($admin_theme = variable_get('admin_theme')) {
-      $themes['admin'] = $admin_theme;
-    }
-    $count = db_query_range('SELECT 1 FROM {block} WHERE theme NOT IN (:themes)', 0, 1, array(':themes' => $themes))->fetchField();
-    $this->assertFalse($count, t('Only the default theme and the admin theme have blocks.'));
+    // Ensure the Stark theme's blocks are not in the block table yet.
+    $count = db_query_range('SELECT 1 FROM {block} WHERE theme = :theme', 0, 1, array(':theme' => 'stark'))->fetchField();
+    $this->assertFalse($count, t('The Stark theme does not start off with any blocks.'));
 
     // Populate list of all blocks for matching against new theme.
     $blocks = array();
-    $result = db_query('SELECT * FROM {block} WHERE theme = :theme', array(':theme' => $themes['default']));
+    $result = db_query('SELECT * FROM {block} WHERE theme = :theme', array(':theme' => variable_get('theme_default', 'bartik')));
     foreach ($result as $block) {
       // $block->theme and $block->bid will not match, so remove them.
       unset($block->theme, $block->bid);
Index: modules/dashboard/dashboard.install
===================================================================
RCS file: modules/dashboard/dashboard.install
diff -N modules/dashboard/dashboard.install
--- modules/dashboard/dashboard.install	1 Nov 2010 00:44:31 -0000	1.1
+++ /dev/null	1 Jan 1970 00:00:00 -0000
@@ -1,79 +0,0 @@
-<?php
-// $Id: dashboard.install,v 1.1 2010/11/01 00:44:31 webchick Exp $
-
-/**
- * @file
- * Install, update and uninstall functions for the dashboard module.
- */
-
-/**
- * Implements hook_disable().
- *
- * Stash a list of blocks enabled on the dashboard, so they can be re-enabled
- * if the dashboard is re-enabled. Then disable those blocks, since the
- * dashboard regions will no longer be defined.
- */
-function dashboard_disable() {
-  // Stash a list of currently enabled blocks.
-  $stashed_blocks = array();
-
-  $result = db_select('block', 'b')
-    ->fields('b', array('module', 'delta', 'region'))
-    ->condition('b.region', dashboard_regions(), 'IN')
-    ->execute();
-
-  foreach ($result as $block) {
-    $stashed_blocks[] = array(
-      'module' => $block->module,
-      'delta' => $block->delta,
-      'region' => $block->region,
-    );
-  }
-  variable_set('dashboard_stashed_blocks', $stashed_blocks);
-
-  // Disable the dashboard blocks.
-  db_update('block')
-    ->fields(array(
-      'status' => 0,
-      'region' => BLOCK_REGION_NONE,
-    ))
-    ->condition('region', dashboard_regions(), 'IN')
-    ->execute();
-}
-
-/**
- * Implements hook_enable().
- *
- * Restores blocks to the dashboard that were there when the dashboard module
- * was disabled.
- */
-function dashboard_enable() {
-  global $theme_key;
-  if (!$stashed_blocks = variable_get('dashboard_stashed_blocks')) {
-    return;
-  }
-  if (!$admin_theme = variable_get('admin_theme')) {
-    drupal_theme_initialize();
-    $admin_theme = $theme_key;
-  }
-  foreach ($stashed_blocks as $block) {
-    db_update('block')
-      ->fields(array(
-        'status' => 1,
-        'region' => $block['region']
-      ))
-      ->condition('module', $block['module'])
-      ->condition('delta', $block['delta'])
-      ->condition('theme', $admin_theme)
-      ->condition('status', 0)
-      ->execute();
-  }
-  variable_del('dashboard_stashed_blocks');
-}
-
-/**
- * Implements hook_uninstall().
- */
-function dashboard_uninstall() {
-  variable_del('dashboard_stashed_blocks');
-}
Index: modules/dashboard/dashboard.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/dashboard/dashboard.module,v
retrieving revision 1.40
diff -u -p -r1.40 dashboard.module
--- modules/dashboard/dashboard.module	21 Oct 2010 11:55:08 -0000	1.40
+++ modules/dashboard/dashboard.module	1 Nov 2010 02:13:37 -0000
@@ -20,9 +20,7 @@ function dashboard_help($path, $arg) {
       return $output;
 
     case 'admin/dashboard/configure':
-      // @todo This assumes the current page is being displayed using the same
-      //   theme that the dashboard is displayed in.
-      $output = '<p>' . t('Rearrange blocks for display on the <a href="@dashboard-url">dashboard</a>. Disabling a block makes it available on the main <a href="@blocks-url">blocks administration page</a>.', array('@dashboard-url' => url('admin/dashboard'), '@blocks-url' => url("admin/structure/block/list/{$GLOBALS['theme_key']}"))) . '</p>';
+      $output = '<p>' . t('Rearrange blocks for display on the <a href="@dashboard-url">dashboard</a>.', array('@dashboard-url' => url('admin/dashboard'))) . '</p>';
       return $output;
   }
 }
@@ -76,6 +74,20 @@ function dashboard_menu() {
 }
 
 /**
+ * Implements hook_menu_alter().
+ */
+function dashboard_menu_alter(&$items) {
+  // Replace the menu callbacks for adding a new block and configuring an
+  // existing one with a callback that will temporarily enable the dashboard
+  // theme before the form is built.
+  foreach ($items as &$item) {
+    if (isset($item['page callback']) && $item['page callback'] == 'drupal_get_form' && !empty($item['page arguments']) && ($first_argument = reset($item['page arguments'])) && ($first_argument == 'block_admin_configure' || $first_argument == 'block_add_block_form')) {
+      $item['page callback'] = 'dashboard_get_form_dashboard_theme_enabled';
+    }
+  }
+}
+
+/**
  * Implements hook_permission().
  */
 function dashboard_permission() {
@@ -90,23 +102,6 @@ function dashboard_permission() {
 }
 
 /**
- * Implements hook_block_list_alter().
- *
- * Skip rendering dashboard blocks when not on the dashboard page itself. This
- * prevents expensive dashboard blocks from causing performance issues on pages
- * where they will never be displayed.
- */
-function dashboard_block_list_alter(&$blocks) {
-  if (!dashboard_is_visible()) {
-    foreach ($blocks as $key => $block) {
-      if (in_array($block->region, dashboard_regions())) {
-        unset($blocks[$key]);
-      }
-    }
-  }
-}
-
-/**
  * Implements hook_page_build().
  *
  * Display dashboard blocks in the main content region.
@@ -121,14 +116,18 @@ function dashboard_page_build(&$page) {
     // region into it.
     $page['content']['dashboard'] = array('#theme_wrappers' => array('dashboard'));
     foreach (dashboard_regions() as $region) {
-      // Insert regions even when they are empty, so that they will be
-      // displayed when the dashboard is being configured.
-      $page['content']['dashboard'][$region] = !empty($page[$region]) ? $page[$region] : array();
+      // Load the blocks for each dashboard region. Because the output of
+      // block_get_blocks_by_region() depends on the current active theme, we
+      // need to trick the Block module into using the dashboard theme here
+      // instead.
+      $original_theme_key = $theme_key;
+      $theme_key = 'dashboard_theme';
+      $page['content']['dashboard'][$region] = block_get_blocks_by_region($region);
+      $theme_key = $original_theme_key;
       $page['content']['dashboard'][$region]['#dashboard_region'] = $region;
       // Allow each dashboard region to be themed differently, or fall back on
       // the generic theme wrapper function for dashboard regions.
       $page['content']['dashboard'][$region]['#theme_wrappers'][] = array($region, 'dashboard_region');
-      unset($page[$region]);
       $blocks_found = array();
       foreach ($page['content']['dashboard'][$region] as $item) {
         if (isset($item['#theme_wrappers']) && is_array($item['#theme_wrappers']) && in_array('block', $item['#theme_wrappers'])) {
@@ -148,7 +147,7 @@ function dashboard_page_build(&$page) {
       // Find blocks which were not yet displayed on the page (were empty), and
       // add placeholder items in their place for rendering.
       $block_list = db_select('block')
-        ->condition('theme', $theme_key)
+        ->condition('theme', 'dashboard_theme')
         ->condition('status', 1)
         ->condition('region', $region)
         ->fields('block')
@@ -172,20 +171,33 @@ function dashboard_page_build(&$page) {
 
 /**
  * Implements hook_system_info_alter().
- *
- * Add regions to each theme to store the dashboard blocks.
  */
 function dashboard_system_info_alter(&$info, $file, $type) {
   if ($type == 'theme') {
-    $info['regions'] += dashboard_region_descriptions();
-    // Indicate that these regions are intended to be displayed whenever the
-    // dashboard is displayed in an overlay. This information is provided for
-    // any module that might need to use it, not just the core Overlay module.
+    if ($file->name == 'dashboard_theme') {
+      // Add the dashboard regions to the dashboard theme.
+      $info['regions'] = dashboard_region_descriptions();
+    }
+    // Indicate that the dashboard regions are intended to be displayed
+    // whenever the dashboard is displayed in an overlay. We must do this for
+    // all themes, because we do not know what theme will be used to render the
+    // overall page inside the overlay. This information is provided for any
+    // module that might need to use it, not just the core Overlay module.
     $info['overlay_regions'] = !empty($info['overlay_regions']) ? array_merge($info['overlay_regions'], dashboard_regions()) : dashboard_regions();
   }
 }
 
 /**
+ * Implements hook_flush_caches().
+ */
+function dashboard_flush_caches() {
+  // Rehash blocks for the dashboard theme. This is the same as what
+  // block_flush_caches() does for all enabled themes, but since the dashboard
+  // theme is never enabled, we must do it here explicitly.
+  _block_rehash('dashboard_theme');
+}
+
+/**
  * Implements hook_theme().
  */
 function dashboard_theme() {
@@ -276,50 +288,17 @@ function dashboard_admin($launch_customi
  * @see template_preprocess_dashboard_admin_display_form()
  */
 function dashboard_admin_blocks() {
-  global $theme_key;
-  drupal_theme_initialize();
   module_load_include('inc', 'block', 'block.admin');
-
-  // Prepare the blocks for the current theme, and remove those that are
-  // currently displayed in non-dashboard regions.
-  // @todo This assumes the current page is being displayed using the same
-  //   theme that the dashboard is displayed in.
-  $blocks = block_admin_display_prepare_blocks($theme_key);
-  $dashboard_regions = dashboard_region_descriptions();
-  $regions_to_remove = array_diff_key(system_region_list($theme_key, REGIONS_VISIBLE), $dashboard_regions);
+  $blocks = block_admin_display_prepare_blocks('dashboard_theme');
   foreach ($blocks as $id => $block) {
-    if (isset($regions_to_remove[$block['region']])) {
+    // The main system content block cannot be placed in any region, since the
+    // dashboard regions themselves are displayed as part of the main page
+    // content.
+    if ($block['module'] == 'system' && $block['delta'] == 'main') {
       unset($blocks[$id]);
     }
   }
-
-  // Pass in the above blocks and dashboard regions to the form, so that only
-  // dashboard-related regions will be displayed.
-  return drupal_get_form('dashboard_admin_display_form', $blocks, $theme_key, $dashboard_regions);
-}
-
-/**
- * Implements hook_form_FORM_ID_alter().
- */
-function dashboard_form_block_admin_display_form_alter(&$form, &$form_state, $form_id) {
-  // Hide dashboard regions (and any blocks placed within them) from the block
-  // administration form and from the options list on that form. This
-  // function is called for both the dashboard block configuration form and the
-  // standard block configuration form so that both forms can share the same
-  // constructor. As a result the form_id must be checked.
-  if ($form_id != 'dashboard_admin_display_form') {
-    $dashboard_regions = dashboard_region_descriptions();
-    $form['block_regions']['#value'] = array_diff_key($form['block_regions']['#value'], $dashboard_regions);
-    foreach (element_children($form['blocks']) as $i) {
-      $block = &$form['blocks'][$i];
-      if (isset($block['region']['#default_value']) && isset($dashboard_regions[$block['region']['#default_value']])) {
-        $block['#access'] = FALSE;
-      }
-      elseif (isset($block['region']['#options'])) {
-        $block['region']['#options'] = array_diff_key($block['region']['#options'], $dashboard_regions);
-      }
-    }
-  }
+  return drupal_get_form('dashboard_admin_display_form', $blocks, 'dashboard_theme');
 }
 
 /**
@@ -339,37 +318,39 @@ function dashboard_form_dashboard_admin_
 }
 
 /**
- * Implements hook_form_FORM_ID_alter().
+ * Preprocesses variables for block-admin-display-form.tpl.php.
  */
-function dashboard_form_block_admin_configure_alter(&$form, &$form_state) {
-  global $theme_key;
-  drupal_theme_initialize();
-  // Hide the dashboard regions from the region select list on the block
-  // configuration form, for all themes except the current theme (since the
-  // other themes do not display the dashboard).
-  // @todo This assumes the current page is being displayed using the same
-  //   theme that the dashboard is displayed in.
-  $dashboard_regions = dashboard_region_descriptions();
-  foreach (element_children($form['regions']) as $region_name) {
-    $region = &$form['regions'][$region_name];
-    if ($region_name != $theme_key && isset($region['#options'])) {
-      $region['#options'] = array_diff_key($region['#options'], $dashboard_regions);
-    }
-  }
+function template_preprocess_dashboard_admin_display_form(&$variables) {
+  template_preprocess_block_admin_display_form($variables);
 }
 
 /**
- * Implements hook_form_FORM_ID_alter().
- */
-function dashboard_form_block_add_block_form_alter(&$form, &$form_state) {
-  dashboard_form_block_admin_configure_alter($form, $form_state);
-}
+ * Form builder function that treats the dashboard theme as temporarily enabled.
+ *
+ * This function takes the same parameters as drupal_get_form(), but ensures
+ * that while the form is being built, the Dashboard module's hidden theme is
+ * treated as being temporarily enabled on the site. It is used as a menu
+ * callback for cases where the Dashboard module wants to alter Block module
+ * forms to allow blocks to be configured for the Dashboard.
+ */
+function dashboard_get_form_dashboard_theme_enabled() {
+  // Adjust the static variables of list_themes() and system_list() to treat
+  // the dashboard theme as being enabled.
+  $list_themes = &drupal_static('list_themes');
+  $system_list = &drupal_static('system_list');
+  $list_themes['dashboard_theme']->status = 1;
+  $system_list['theme']['dashboard_theme']->status = 1;
+
+  // Build the form using the provided function arguments.
+  $args = func_get_args();
+  $form = call_user_func_array('drupal_get_form', $args);
+
+  // Reset the static variables of list_themes() and system_list() to once
+  // again mark the dashboard theme as being disabled.
+  $list_themes['dashboard_theme']->status = 0;
+  $system_list['theme']['dashboard_theme']->status = 0;
 
-/**
- * Preprocesses variables for block-admin-display-form.tpl.php.
- */
-function template_preprocess_dashboard_admin_display_form(&$variables) {
-  template_preprocess_block_admin_display_form($variables);
+  return $form;
 }
 
 /**
@@ -440,14 +421,10 @@ function dashboard_dashboard_regions() {
  * AJAX callback to show disabled blocks in the dashboard customization mode.
  */
 function dashboard_show_disabled() {
-  global $theme_key;
-
-  // Blocks are not necessarily initialized at this point.
-  $blocks = _block_rehash();
-
-  // Limit the list to disabled blocks for the current theme.
+  // Limit the list to disabled blocks for the dashboard theme.
+  $blocks = _block_rehash('dashboard_theme');
   foreach ($blocks as $key => $block) {
-    if ($block['theme'] != $theme_key || (!empty($block['status']) && !empty($block['region']))) {
+    if (!empty($block['status']) && !empty($block['region'])) {
       unset($blocks[$key]);
     }
   }
@@ -466,12 +443,9 @@ function dashboard_show_disabled() {
  *   The block's delta.
  */
 function dashboard_show_block_content($module, $delta) {
-  drupal_theme_initialize();
-  global $theme_key;
-
   $blocks = array();
   $block_object = db_query("SELECT * FROM {block} WHERE theme = :theme AND module = :module AND delta = :delta", array(
-    ":theme" => $theme_key,
+    ":theme" => 'dashboard_theme',
     ":module" => $module,
     ":delta" => $delta,
     ))
@@ -489,8 +463,6 @@ function dashboard_show_block_content($m
  * Set the new weight of each region according to the drag-and-drop order.
  */
 function dashboard_update() {
-  drupal_theme_initialize();
-  global $theme_key;
   // Check the form token to make sure we have a valid request.
   if (!empty($_REQUEST['form_token']) && drupal_valid_token($_REQUEST['form_token'], 'dashboard-update')) {
     parse_str($_REQUEST['regions'], $regions);
@@ -518,7 +490,7 @@ function dashboard_update() {
           ->key(array(
             'module' => $block->module,
             'delta' => $block->delta,
-            'theme' => $theme_key,
+            'theme' => 'dashboard_theme',
           ))
           ->fields(array(
             'status' => $block->status,
Index: modules/dashboard/dashboard.test
===================================================================
RCS file: /cvs/drupal/drupal/modules/dashboard/dashboard.test,v
retrieving revision 1.7
diff -u -p -r1.7 dashboard.test
--- modules/dashboard/dashboard.test	31 Oct 2010 21:36:24 -0000	1.7
+++ modules/dashboard/dashboard.test	1 Nov 2010 02:13:37 -0000
@@ -42,7 +42,7 @@ class DashboardBlocksTestCase extends Dr
     $custom_block['info'] = $this->randomName(8);
     $custom_block['title'] = $this->randomName(8);
     $custom_block['body[value]'] = $this->randomName(32);
-    $custom_block['regions[stark]'] = 'dashboard_main';
+    $custom_block['regions[dashboard_theme]'] = 'dashboard_main';
     $this->drupalPost('admin/structure/block/add', $custom_block, t('Save block'));
 
     // Ensure admin access.
@@ -90,7 +90,7 @@ class DashboardBlocksTestCase extends Dr
     $custom_block['info'] = $this->randomName(8);
     $custom_block['title'] = $this->randomName(8);
     $custom_block['body[value]'] = $this->randomName(32);
-    $custom_block['regions[stark]'] = 'dashboard_main';
+    $custom_block['regions[dashboard_theme]'] = 'dashboard_main';
     $this->drupalPost('admin/structure/block/add', $custom_block, t('Save block'));
     $this->drupalGet('admin/dashboard');
     $this->assertRaw($custom_block['title'], t('Block appears on the dashboard.'));
Index: profiles/standard/standard.install
===================================================================
RCS file: /cvs/drupal/drupal/profiles/standard/standard.install,v
retrieving revision 1.28
diff -u -p -r1.28 standard.install
--- profiles/standard/standard.install	21 Oct 2010 04:22:34 -0000	1.28
+++ profiles/standard/standard.install	1 Nov 2010 02:13:37 -0000
@@ -90,7 +90,7 @@ function standard_install() {
     array(
       'module' => 'node',
       'delta' => 'recent',
-      'theme' => $admin_theme,
+      'theme' => 'dashboard_theme',
       'status' => 1,
       'weight' => 10,
       'region' => 'dashboard_main',
@@ -170,7 +170,7 @@ function standard_install() {
     array(
       'module' => 'user',
       'delta' => 'new',
-      'theme' => $admin_theme,
+      'theme' => 'dashboard_theme',
       'status' => 1,
       'weight' => 0,
       'region' => 'dashboard_sidebar',
@@ -180,7 +180,7 @@ function standard_install() {
     array(
       'module' => 'search',
       'delta' => 'form',
-      'theme' => $admin_theme,
+      'theme' => 'dashboard_theme',
       'status' => 1,
       'weight' => -10,
       'region' => 'dashboard_sidebar',
Index: themes/dashboard_theme/dashboard_theme.info
===================================================================
RCS file: themes/dashboard_theme/dashboard_theme.info
diff -N themes/dashboard_theme/dashboard_theme.info
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ themes/dashboard_theme/dashboard_theme.info	1 Nov 2010 02:13:37 -0000
@@ -0,0 +1,8 @@
+; $Id$
+name = Dashboard
+description = This is a hidden theme used by the Dashboard module only.
+package = Core
+version = VERSION
+core = 7.x
+engine = phptemplate
+hidden = TRUE
