Index: includes/theme.inc
===================================================================
RCS file: /cvs/drupal/drupal/includes/theme.inc,v
retrieving revision 1.608
diff -u -p -r1.608 theme.inc
--- includes/theme.inc	3 Sep 2010 19:49:55 -0000	1.608
+++ includes/theme.inc	4 Sep 2010 14:53:14 -0000
@@ -604,9 +604,7 @@ function list_themes($refresh = FALSE) {
         }
       }
       foreach ($theme->info['scripts'] as $script => $path) {
-        if (file_exists($path)) {
-          $theme->scripts[$script] = $path;
-        }
+        $theme->scripts[$script] = $path;
       }
       if (isset($theme->info['engine'])) {
         $theme->engine = $theme->info['engine'];
@@ -2274,6 +2272,7 @@ function template_preprocess_page(&$vari
     $variables['theme_hook_suggestions'] = $suggestions;
   }
 }
+
 /**
  * Process variables for html.tpl.php
  *
Index: modules/aggregator/aggregator.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/aggregator/aggregator.info,v
retrieving revision 1.13
diff -u -p -r1.13 aggregator.info
--- modules/aggregator/aggregator.info	17 Nov 2009 21:24:18 -0000	1.13
+++ modules/aggregator/aggregator.info	4 Sep 2010 14:48:39 -0000
@@ -13,3 +13,4 @@ files[] = aggregator.processor.inc
 files[] = aggregator.install
 files[] = aggregator.test
 configure = admin/config/services/aggregator/settings
+stylesheets[all][] = aggregator.css
Index: modules/aggregator/aggregator.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/aggregator/aggregator.module,v
retrieving revision 1.442
diff -u -p -r1.442 aggregator.module
--- modules/aggregator/aggregator.module	4 Aug 2010 03:54:54 -0000	1.442
+++ modules/aggregator/aggregator.module	4 Sep 2010 14:48:39 -0000
@@ -283,13 +283,6 @@ function _aggregator_category_title($cat
 }
 
 /**
- * Implements hook_init().
- */
-function aggregator_init() {
-  drupal_add_css(drupal_get_path('module', 'aggregator') . '/aggregator.css', array('preprocess' => TRUE));
-}
-
-/**
  * Find out whether there are any aggregator categories.
  *
  * @return
Index: modules/book/book.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/book/book.info,v
retrieving revision 1.13
diff -u -p -r1.13 book.info
--- modules/book/book.info	17 Nov 2009 21:24:18 -0000	1.13
+++ modules/book/book.info	4 Sep 2010 14:48:39 -0000
@@ -10,3 +10,4 @@ files[] = book.pages.inc
 files[] = book.install
 files[] = book.test
 configure = admin/content/book/settings
+stylesheets[all][] = book.css
Index: modules/book/book.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/book/book.module,v
retrieving revision 1.550
diff -u -p -r1.550 book.module
--- modules/book/book.module	30 Aug 2010 05:58:46 -0000	1.550
+++ modules/book/book.module	4 Sep 2010 14:48:39 -0000
@@ -215,13 +215,6 @@ function book_admin_paths() {
 }
 
 /**
- * Implements hook_init().
- */
-function book_init() {
-  drupal_add_css(drupal_get_path('module', 'book') . '/book.css', array('preprocess' => TRUE));
-}
-
-/**
  * Implements hook_entity_info_alter().
  */
 function book_entity_info_alter(&$info) {
Index: modules/comment/comment.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/comment/comment.info,v
retrieving revision 1.13
diff -u -p -r1.13 comment.info
--- modules/comment/comment.info	16 Aug 2010 20:57:22 -0000	1.13
+++ modules/comment/comment.info	4 Sep 2010 14:48:39 -0000
@@ -12,3 +12,4 @@ files[] = comment.install
 files[] = comment.test
 files[] = comment.tokens.inc
 configure = admin/content/comment
+stylesheets[all][] = comment.css
Index: modules/comment/comment.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/comment/comment.module,v
retrieving revision 1.893
diff -u -p -r1.893 comment.module
--- modules/comment/comment.module	30 Aug 2010 05:58:46 -0000	1.893
+++ modules/comment/comment.module	4 Sep 2010 14:48:39 -0000
@@ -290,13 +290,6 @@ function comment_menu() {
 }
 
 /**
- * Implements hook_init().
- */
-function comment_init() {
-  drupal_add_css(drupal_get_path('module', 'comment') . '/comment.css', array('preprocess' => TRUE));
-}
-
-/**
  * Implements hook_menu_alter().
  */
 function comment_menu_alter(&$items) {
Index: modules/field/field.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/field/field.info,v
retrieving revision 1.8
diff -u -p -r1.8 field.info
--- modules/field/field.info	21 Jun 2010 02:27:47 -0000	1.8
+++ modules/field/field.info	4 Sep 2010 14:48:39 -0000
@@ -15,3 +15,4 @@ files[] = field.form.inc
 files[] = tests/field.test
 dependencies[] = field_sql_storage
 required = TRUE
+stylesheets[all][] = theme/field.css
Index: modules/field/field.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/field/field.module,v
retrieving revision 1.83
diff -u -p -r1.83 field.module
--- modules/field/field.module	2 Sep 2010 20:59:11 -0000	1.83
+++ modules/field/field.module	4 Sep 2010 14:48:39 -0000
@@ -169,13 +169,6 @@ function field_theme() {
 }
 
 /**
- * Implements hook_init().
- */
-function field_init() {
-  drupal_add_css(drupal_get_path('module', 'field') . '/theme/field.css', array('preprocess' => TRUE));
-}
-
-/**
  * Implements hook_cron().
  *
  * Purges some deleted Field API data, if any exists.
Index: modules/forum/forum.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/forum/forum.info,v
retrieving revision 1.13
diff -u -p -r1.13 forum.info
--- modules/forum/forum.info	17 Nov 2009 21:24:18 -0000	1.13
+++ modules/forum/forum.info	4 Sep 2010 14:48:39 -0000
@@ -12,3 +12,4 @@ files[] = forum.pages.inc
 files[] = forum.install
 files[] = forum.test
 configure = admin/structure/forum
+stylesheets[all][] = forum.css
Index: modules/forum/forum.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/forum/forum.module,v
retrieving revision 1.573
diff -u -p -r1.573 forum.module
--- modules/forum/forum.module	17 Aug 2010 16:20:07 -0000	1.573
+++ modules/forum/forum.module	4 Sep 2010 14:48:39 -0000
@@ -218,13 +218,6 @@ function forum_menu_local_tasks_alter(&$
 }
 
 /**
- * Implements hook_init().
- */
-function forum_init() {
-  drupal_add_css(drupal_get_path('module', 'forum') . '/forum.css', array('preprocess' => TRUE));
-}
-
-/**
  * Implements hook_entity_info_alter().
  */
 function forum_entity_info_alter(&$info) {
Index: modules/node/node.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/node/node.info,v
retrieving revision 1.13
diff -u -p -r1.13 node.info
--- modules/node/node.info	17 Nov 2009 21:24:18 -0000	1.13
+++ modules/node/node.info	4 Sep 2010 14:48:39 -0000
@@ -13,3 +13,4 @@ files[] = node.test
 files[] = node.tokens.inc
 required = TRUE
 configure = admin/structure/types
+stylesheets[all][] = node.css
Index: modules/node/node.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/node/node.module,v
retrieving revision 1.1295
diff -u -p -r1.1295 node.module
--- modules/node/node.module	3 Sep 2010 19:56:51 -0000	1.1295
+++ modules/node/node.module	4 Sep 2010 14:48:39 -0000
@@ -2012,13 +2012,6 @@ function _node_custom_theme() {
   }
 }
 
-/**
- * Implements hook_init().
- */
-function node_init() {
-  drupal_add_css(drupal_get_path('module', 'node') . '/node.css', array('preprocess' => TRUE));
-}
-
 function node_last_changed($nid) {
   return db_query('SELECT changed FROM {node} WHERE nid = :nid', array(':nid' => $nid))->fetch()->changed;
 }
Index: modules/poll/poll.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/poll/poll.info,v
retrieving revision 1.10
diff -u -p -r1.10 poll.info
--- modules/poll/poll.info	19 Aug 2009 20:19:36 -0000	1.10
+++ modules/poll/poll.info	4 Sep 2010 14:48:39 -0000
@@ -9,3 +9,4 @@ files[] = poll.pages.inc
 files[] = poll.install
 files[] = poll.test
 files[] = poll.tokens.inc
+stylesheets[all][] = poll.css
Index: modules/poll/poll.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/poll/poll.module,v
retrieving revision 1.354
diff -u -p -r1.354 poll.module
--- modules/poll/poll.module	30 Jul 2010 02:47:28 -0000	1.354
+++ modules/poll/poll.module	4 Sep 2010 14:48:39 -0000
@@ -28,13 +28,6 @@ function poll_help($path, $arg) {
 }
 
 /**
- * Implements hook_init().
- */
-function poll_init() {
-  drupal_add_css(drupal_get_path('module', 'poll') . '/poll.css', array('preprocess' => TRUE));
-}
-
-/**
  * Implements hook_theme().
  */
 function poll_theme() {
Index: modules/search/search.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/search/search.info,v
retrieving revision 1.11
diff -u -p -r1.11 search.info
--- modules/search/search.info	17 Nov 2009 21:24:18 -0000	1.11
+++ modules/search/search.info	4 Sep 2010 14:48:39 -0000
@@ -11,3 +11,4 @@ files[] = search.install
 files[] = search.test
 files[] = search.extender.inc
 configure = admin/config/search/settings
+stylesheets[all][] = search.css
Index: modules/search/search.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/search/search.module,v
retrieving revision 1.358
diff -u -p -r1.358 search.module
--- modules/search/search.module	18 Aug 2010 18:40:50 -0000	1.358
+++ modules/search/search.module	4 Sep 2010 14:48:39 -0000
@@ -98,13 +98,6 @@ function search_help($path, $arg) {
 }
 
 /**
- * Implements hook_init().
- */
-function search_init() {
-  drupal_add_css(drupal_get_path('module', 'search') . '/search.css', array('preprocess' => TRUE));
-}
-
-/**
  * Implements hook_theme().
  */
 function search_theme() {
Index: modules/simpletest/tests/common.test
===================================================================
RCS file: /cvs/drupal/drupal/modules/simpletest/tests/common.test,v
retrieving revision 1.122
diff -u -p -r1.122 common.test
--- modules/simpletest/tests/common.test	17 Aug 2010 21:31:13 -0000	1.122
+++ modules/simpletest/tests/common.test	4 Sep 2010 14:48:39 -0000
@@ -576,6 +576,27 @@ class CascadingStylesheetsTestCase exten
   }
 
   /**
+   * Test that stylesheets in module .info files are loaded.
+   */
+  function testModuleInfo() {
+    $this->drupalGet('');
+
+    // Verify common_test.css in a STYLE media="all" tag.
+    $elements = $this->xpath('//style[@media=:media and contains(text(), :filename)]', array(
+      ':media' => 'all',
+      ':filename' => 'tests/common_test.css',
+    ));
+    $this->assertTrue(count($elements), "Stylesheet with media 'all' in module .info file found.");
+
+    // Verify common_test.print.css in a STYLE media="print" tag.
+    $elements = $this->xpath('//style[@media=:media and contains(text(), :filename)]', array(
+      ':media' => 'print',
+      ':filename' => 'tests/common_test.print.css',
+    ));
+    $this->assertTrue(count($elements), "Stylesheet with media 'print' in module .info file found.");
+  }
+
+  /**
    * Tests adding a file stylesheet.
    */
   function testAddFile() {
Index: modules/simpletest/tests/common_test.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/simpletest/tests/common_test.info,v
retrieving revision 1.1
diff -u -p -r1.1 common_test.info
--- modules/simpletest/tests/common_test.info	2 Jul 2009 04:27:23 -0000	1.1
+++ modules/simpletest/tests/common_test.info	4 Sep 2010 14:48:39 -0000
@@ -5,4 +5,6 @@ package = Testing
 version = VERSION
 core = 7.x
 files[] = common_test.module
+stylesheets[all][] = common_test.css
+stylesheets[print][] = common_test.print.css
 hidden = TRUE
Index: modules/system/system.api.php
===================================================================
RCS file: /cvs/drupal/drupal/modules/system/system.api.php,v
retrieving revision 1.189
diff -u -p -r1.189 system.api.php
--- modules/system/system.api.php	1 Sep 2010 02:39:58 -0000	1.189
+++ modules/system/system.api.php	4 Sep 2010 14:48:39 -0000
@@ -1441,9 +1441,10 @@ function hook_boot() {
  * used to set up global parameters which are needed later in the request.
  * when this hook is called, all modules are already loaded in memory.
  *
- * For example, this hook is a typical place for modules to add CSS or JS
- * that should be present on every page. This hook is not run on cached
- * pages - though CSS or JS added this way will be present on a cached page.
+ * This hook is not run on cached pages.
+ *
+ * To add CSS or JS that should be present on all pages, modules should not
+ * implement this hook, but declare these files in their .info file.
  */
 function hook_init() {
   drupal_add_css(drupal_get_path('module', 'book') . '/book.css');
@@ -3955,7 +3956,7 @@ function hook_filetransfer_backends() {
 /**
  * Control site status before menu dispatching.
  *
- * The hook is called after checking whether the site is offline but before 
+ * The hook is called after checking whether the site is offline but before
  * the current router item is retrieved and executed by
  * menu_execute_active_handler(). If the site is in offline mode,
  * $menu_site_status is set to MENU_SITE_OFFLINE.
Index: modules/system/system.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/system/system.module,v
retrieving revision 1.958
diff -u -p -r1.958 system.module
--- modules/system/system.module	3 Sep 2010 19:49:56 -0000	1.958
+++ modules/system/system.module	4 Sep 2010 14:55:04 -0000
@@ -1837,7 +1837,6 @@ function system_init() {
   drupal_add_css($path . '/system-menus.css', array('weight' => CSS_SYSTEM, 'preprocess' => TRUE));
   drupal_add_css($path . '/system-messages.css', array('weight' => CSS_SYSTEM, 'preprocess' => TRUE));
 
-
   // Ignore slave database servers for this request.
   //
   // In Drupal's distributed database structure, new data is written to the master
@@ -1859,6 +1858,29 @@ function system_init() {
       unset($_SESSION['ignore_slave_server']);
     }
   }
+
+  // Add CSS/JS files from module .info files.
+  system_add_module_assets();
+}
+
+/**
+ * Adds CSS and JavaScript files declared in module .info files.
+ */
+function system_add_module_assets() {
+  foreach (system_get_info('module') as $module => $info) {
+    if (!empty($info['stylesheets'])) {
+      foreach ($info['stylesheets'] as $media => $stylesheets) {
+        foreach ($stylesheets as $stylesheet) {
+          drupal_add_css($stylesheet, array('media' => $media, 'preprocess' => TRUE));
+        }
+      }
+    }
+    if (!empty($info['scripts'])) {
+      foreach ($info['scripts'] as $script) {
+        drupal_add_js($script, array('preprocess' => TRUE));
+      }
+    }
+  }
 }
 
 /**
@@ -2305,6 +2327,15 @@ function _system_rebuild_module_data() {
     // Merge in defaults and save.
     $modules[$key]->info = $module->info + $defaults;
 
+    // Prefix stylesheets and scripts with module path.
+    $path = dirname($module->uri);
+    if (isset($module->info['stylesheets'])) {
+      $module->info['stylesheets'] = system_info_add_path($module->info['stylesheets'], $path);
+    }
+    if (isset($module->info['scripts'])) {
+      $module->info['scripts'] = system_info_add_path($module->info['scripts'], $path);
+    }
+
     // Install profiles are hidden by default, unless explicitly specified
     // otherwise in the .info file.
     if ($key == $profile && !isset($modules[$key]->info['hidden'])) {
@@ -2396,6 +2427,8 @@ function _system_rebuild_theme_data() {
     'features' => _system_default_theme_features(),
     'screenshot' => 'screenshot.png',
     'php' => DRUPAL_MINIMUM_PHP,
+    'stylesheets' => array(),
+    'scripts' => array(),
   );
 
   $sub_themes = array();
@@ -2428,28 +2461,14 @@ function _system_rebuild_theme_data() {
       }
     }
 
-    // Give the stylesheets proper path information.
-    $pathed_stylesheets = array();
-    if (isset($themes[$key]->info['stylesheets'])) {
-      foreach ($themes[$key]->info['stylesheets'] as $media => $stylesheets) {
-        foreach ($stylesheets as $stylesheet) {
-          $pathed_stylesheets[$media][$stylesheet] = dirname($themes[$key]->uri) . '/' . $stylesheet;
-        }
-      }
-    }
-    $themes[$key]->info['stylesheets'] = $pathed_stylesheets;
+    // Prefix stylesheets and scripts with module path.
+    $path = dirname($theme->uri);
+    $theme->info['stylesheets'] = system_info_add_path($theme->info['stylesheets'], $path);
+    $theme->info['scripts'] = system_info_add_path($theme->info['scripts'], $path);
 
-    // Give the scripts proper path information.
-    $scripts = array();
-    if (isset($themes[$key]->info['scripts'])) {
-      foreach ($themes[$key]->info['scripts'] as $script) {
-        $scripts[$script] = dirname($themes[$key]->uri) . '/' . $script;
-      }
-    }
-    $themes[$key]->info['scripts'] = $scripts;
     // Give the screenshot proper path information.
     if (!empty($themes[$key]->info['screenshot'])) {
-      $themes[$key]->info['screenshot'] = dirname($themes[$key]->uri) . '/' . $themes[$key]->info['screenshot'];
+      $themes[$key]->info['screenshot'] = $path . '/' . $themes[$key]->info['screenshot'];
     }
   }
 
@@ -2497,6 +2516,27 @@ function system_rebuild_theme_data() {
 }
 
 /**
+ * Prefixes .info file array values with a given path.
+ *
+ * @param $info
+ *   A nested array of data of an .info file to be processed.
+ * @param $path
+ *   A file path to prepend to each value in $info.
+ */
+function system_info_add_path($info, $path) {
+  foreach ($info as $key => $value) {
+    if (is_array($value)) {
+      $info[$key] = system_info_add_path($info[$key], $path);
+    }
+    else {
+      unset($info[$key]);
+      $info[$value] = $path . '/' . $value;
+    }
+  }
+  return $info;
+}
+
+/**
  * Returns an array of default theme features.
  */
 function _system_default_theme_features() {
Index: modules/user/user.info
===================================================================
RCS file: /cvs/drupal/drupal/modules/user/user.info,v
retrieving revision 1.13
diff -u -p -r1.13 user.info
--- modules/user/user.info	17 Nov 2009 21:24:19 -0000	1.13
+++ modules/user/user.info	4 Sep 2010 14:48:39 -0000
@@ -12,3 +12,4 @@ files[] = user.test
 files[] = user.tokens.inc
 required = TRUE
 configure = admin/config/people
+stylesheets[all][] = user.css
Index: modules/user/user.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/user/user.module,v
retrieving revision 1.1197
diff -u -p -r1.1197 user.module
--- modules/user/user.module	1 Sep 2010 20:08:17 -0000	1.1197
+++ modules/user/user.module	4 Sep 2010 14:48:39 -0000
@@ -1799,13 +1799,6 @@ function user_admin_paths() {
 }
 
 /**
- * Implements hook_init().
- */
-function user_init() {
-  drupal_add_css(drupal_get_path('module', 'user') . '/user.css', array('preprocess' => TRUE));
-}
-
-/**
  * Load either a specified or the current user account.
  *
  * @param $uid
Index: themes/bartik/bartik.info
===================================================================
RCS file: /cvs/drupal/drupal/themes/bartik/bartik.info,v
retrieving revision 1.3
diff -u -p -r1.3 bartik.info
--- themes/bartik/bartik.info	28 Jul 2010 01:40:39 -0000	1.3
+++ themes/bartik/bartik.info	4 Sep 2010 14:48:39 -0000
@@ -12,8 +12,6 @@ stylesheets[all][] = css/style.css
 stylesheets[all][] = css/colors.css
 stylesheets[print][] = css/print.css
 
-scripts[] = scripts/search.js
-
 regions[header] = Header
 regions[help] = Help
 regions[page_top] = Page top
