Index: index.php
===================================================================
RCS file: /cvs/drupal/drupal/index.php,v
retrieving revision 1.87
diff -u -r1.87 index.php
--- index.php	28 Aug 2005 18:26:20 -0000	1.87
+++ index.php	7 Oct 2005 16:08:30 -0000
@@ -20,6 +20,9 @@
   case MENU_ACCESS_DENIED:
     drupal_access_denied();
     break;
+  case MENU_SITE_OFFLINE:
+    drupal_site_offline();
+    break;
   default:
     if (!empty($return)) {
       print theme('page', $return);
Index: includes/menu.inc
===================================================================
RCS file: /cvs/drupal/drupal/includes/menu.inc,v
retrieving revision 1.85
diff -u -r1.85 menu.inc
--- includes/menu.inc	18 Sep 2005 17:03:26 -0000	1.85
+++ includes/menu.inc	7 Oct 2005 16:08:31 -0000
@@ -164,6 +164,7 @@
 define('MENU_FOUND', 1);
 define('MENU_NOT_FOUND', 2);
 define('MENU_ACCESS_DENIED', 3);
+define('MENU_SITE_OFFLINE', 4);
 
 /**
  * @} End of "Menu status codes".
@@ -324,6 +325,10 @@
  * act as if the user were in a different location on the site.
  */
 function menu_execute_active_handler() {
+  if (_menu_check_if_offline()) {
+    return MENU_SITE_OFFLINE;
+  }
+
   $menu = menu_get_menu();
 
   // Determine the menu item containing the callback.
@@ -1040,3 +1045,17 @@
   return $forked;
 }
 
+
+function _menu_check_if_offline() {
+  // Check if site is set to offline mode
+  if (variable_get('site_offline', 0)) {
+    // Check if the user has administration privileges
+    if (!user_access('administer site configuration')) {
+      // Check if this is an attempt to login
+      if (drupal_get_normal_path($_GET['q']) != 'user/login') {
+        return TRUE;
+      }
+    }
+  }
+  return FALSE;
+}
Index: includes/common.inc
===================================================================
RCS file: /cvs/drupal/drupal/includes/common.inc,v
retrieving revision 1.483
diff -u -r1.483 common.inc
--- includes/common.inc	7 Oct 2005 06:51:16 -0000	1.483
+++ includes/common.inc	7 Oct 2005 16:08:32 -0000
@@ -252,6 +252,17 @@
   exit();
 }
 
+
+/**
+ * Generates a site offline message
+ */
+function drupal_site_offline() {
+  header('HTTP/1.0 503 Service unavailable');
+  drupal_set_title(t('Site offline'));
+  print theme('maintenance_page', variable_get('site_offline_message', 
+    t('%site is currently under maintenance. We should be back shortly. Thank you for your patience.', array('%site' => variable_get('site_name', t('This drupal site'))))));
+}
+
 /**
  * Generates a 404 error if the request can not be handled.
  */
Index: modules/system.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/system.module,v
retrieving revision 1.236
diff -u -r1.236 system.module
--- modules/system.module	7 Oct 2005 06:09:13 -0000	1.236
+++ modules/system.module	7 Oct 2005 16:08:33 -0000
@@ -412,6 +412,29 @@
   );
 
 
+  // Site Offline/Maintenance settings
+  $form['site_status'] = array(
+    type => 'fieldset',
+    title => t('Site Status'),
+    collapsible => TRUE,
+    collapsed => TRUE);
+
+  $form['site_status']['site_offline'] = array(
+    type => 'radios',
+    title => t('Site status'),
+    default_value => variable_get('site_offline', 0),
+    options => array(t('Online'), t('Offline')),
+    description => t('When set to "Online", all visitors will be able to browse your site normally. When set to "Offline", only users with "administer site configuration" permission will be able to access your site to perform maintenance, all other visitors will see the site offline message configured below.')
+  );
+ 
+  $form['site_status']['site_offline_message'] = array(
+    type => 'textarea',
+    rows => 5,
+    title => t('Site offline message'),
+    default_value => variable_get('site_offline_message', t('%site is currently under maintenance. We should be back shortly. Thank you for your patience.', array('%site' => variable_get('site_name', t('This drupal site'))))),
+    description => t('Message to show visitors when site is offline.')
+  );
+  
   // String handling: report status and errors.
   $form['strings'] = array(type => 'fieldset', title => t('String handling'), collapsible => TRUE, collapsed => TRUE);
   $form['strings'] = array_merge($form['strings'], unicode_settings());
