=== added file 'modules/menu/menu.install'
--- modules/menu/menu.install	1970-01-01 00:00:00 +0000
+++ modules/menu/menu.install	2007-03-29 05:29:23 +0000
@@ -0,0 +1,45 @@
+<?php
+// $Id$
+
+/**
+ * Implementation of hook_install().
+ */
+function menu_install() {
+  switch ($GLOBALS['db_type']) {
+    case 'mysql':
+    case 'mysqli':
+      db_query("CREATE TABLE {menu_edit} (
+        path varchar(255) NOT NULL default '' ,
+        disabled int NOT NULL default 0,
+        title varchar(255) NOT NULL default '',
+        description varchar(255) NOT NULL default '',
+        weight int NOT NULL default 0 ,
+        type int NOT NULL default 0 ,
+        admin int NOT NULL default 0,
+        parent varchar(255) NOT NULL default '',
+        PRIMARY KEY (path)
+      )");
+      break;
+    case 'pgsql':
+      db_query("CREATE TABLE {menu_edit} (
+        path varchar(255) NOT NULL default '' ,
+        disabled int NOT NULL default 0,
+        title varchar(255) NOT NULL default '',
+        description varchar(255) NOT NULL default '',
+        weight int NOT NULL default 0 ,
+        type int NOT NULL default 0 ,
+        admin int NOT NULL default 0,
+        parent varchar(255) NOT NULL default '',
+        PRIMARY KEY (path)
+      )");
+      break;
+  }
+}
+
+/**
+ * Implementation of hook_uninstall().
+ */
+function menu_uninstall() {
+  db_query('DROP TABLE {menu_edit}');
+  menu_rebuild();
+}

=== modified file 'includes/menu.inc'
--- includes/menu.inc	2007-03-27 05:13:53 +0000
+++ includes/menu.inc	2007-03-29 06:19:05 +0000
@@ -379,7 +379,8 @@ function _menu_translate(&$item, $map, $
         $return = $load_function(isset($path_map[$index]) ? $path_map[$index] : '');
         // If callback returned an error or there is no callback, trigger 404.
         if ($return === FALSE) {
-          return array(FALSE, FALSE, '');
+          $item->access = FALSE;
+          return FALSE;
         }
         $map[$index] = $return;
       }
@@ -552,8 +553,8 @@ function menu_rebuild() {
   // TODO: split menu and menu links storage.
   db_query('DELETE FROM {menu}');
   $menu = module_invoke_all('menu');
-  drupal_alter('menu', $menu);
-  $mid = 1;
+  drupal_alter('menu', $menu, 0);
+  $mid = 2;
   // First pass: separate callbacks from pathes, making pathes ready for
   // matching. Calculate fitness, and fill some default values.
   foreach ($menu as $path => $item) {
@@ -626,6 +627,7 @@ function menu_rebuild() {
     $menu_path_map[$path] = $new_path;
     $menu[$new_path] = $item;
   }
+  drupal_alter('menu', $menu, 1);
   $menu_path_map[''] = '';
   // Second pass: prepare for sorting and find parents.
   foreach ($menu as $path => $item) {
@@ -634,7 +636,7 @@ function menu_rebuild() {
     if (isset($item['parent'])) {
       $item['parent'] = $menu_path_map[$item['parent']];
       $parent_parts = explode('/', $item['parent'], 6);
-      $slashes = count($parent_parts) - 1;
+      $slashes = count($parent_parts);
     }
     else {
       $parent_parts = $item['_parts'];
@@ -654,11 +656,11 @@ function menu_rebuild() {
         }
       }
     }
-    $parents[] = 0;
+    $parents[] = 1;
     $parents = implode(',', array_reverse($parents));
     // Store variables and set defaults.
     $item += array(
-      '_pid' => 0,
+      '_pid' => 1,
       '_depth' => ($item['_visible'] ? $depth : $number_parts),
       '_parents' => $parents,
       '_parent_parts' => $parent_parts,
@@ -673,7 +675,7 @@ function menu_rebuild() {
   // We are now sorted, so let's build the tree.
   $children = array();
   foreach ($menu as $path => $item) {
-    if ($item['_pid']) {
+    if ($item['_pid'] > 1) {
       $menu[$item['_visible_parent_path']]['_children'][] = $path;
     }
   }
@@ -719,6 +721,9 @@ function menu_rebuild() {
     if (is_bool($item['access callback'])) {
       $item['access callback'] = intval($item['access callback']);
     }
+    if (empty($item['page callback'])) {
+      $item['access callback'] = 0;
+    }
     if ($item['_tab']) {
       if (!isset($item['parent'])) {
         $item['parent'] = implode('/', array_slice($item['_parts'], 0, $item['_number_parts'] - 1));
@@ -764,7 +769,11 @@ function menu_rebuild() {
         break;
       }
     }
-
+    // We remove disabled items here -- this way they will be numbered in the
+    // tree so the menu overview screen can show them.
+    if (!empty($item['disabled'])) {
+      $item['_visible'] = FALSE;
+    }
     db_query("INSERT INTO {menu} (
       mid, pid, path, load_functions, to_arg_functions,
       access_callback, access_arguments, page_callback, page_arguments, fit,
@@ -914,3 +923,13 @@ function menu_get_active_title() {
     }
   }
 }
+
+function menu_get_item_by_mid($mid) {
+  if ($item = db_fetch_object(db_query('SELECT * FROM {menu} WHERE mid = %d', $mid))) {
+    _menu_translate($item, arg(), MENU_RENDER_LINK);
+    if ($item->access) {
+      return $item;
+    }
+  }
+  return FALSE;
+}

=== modified file 'modules/menu/menu.module'
--- modules/menu/menu.module	2007-03-26 00:35:58 +0000
+++ modules/menu/menu.module	2007-03-29 15:48:09 +0000
@@ -32,53 +32,69 @@ Menu administration tabs:
 }
 
 /**
+ * Implementation of hook_perm().
+ */
+function menu_perm() {
+  return array('administer menu');
+}
+
+/**
  * Implementation of hook_menu().
  */
 function menu_menu() {
-  return;
-  $items = array();
-
-  if ($may_cache) {
-    $items[] = array('path' => 'admin/build/menu',
-      'title' => t('Menus'),
-      'description' => t("Control your site's navigation menu, primary links and secondary links. as well as rename and reorganize menu items."),
-      'callback' => 'menu_overview',
-      'access' => user_access('administer menu'));
-    $items[] = array('path' => 'admin/build/menu/list',
-      'title' => t('List'),
-      'type' => MENU_DEFAULT_LOCAL_TASK,
-      'weight' => -10);
-
-    $items[] = array('path' => 'admin/build/menu/item/add',
-      'title' => t('Add menu item'),
-      'callback' => 'drupal_get_form',
-      'callback arguments' => array('menu_edit_item_form', 'add'),
-      'access' => user_access('administer menu'),
-      'type' => MENU_LOCAL_TASK);
-    $items[] = array('path' => 'admin/build/menu/item/edit',
-      'title' => t('Edit menu item'),
-      'callback' => 'drupal_get_form',
-      'callback arguments' => array('menu_edit_item_form', 'edit'),
-      'access' => user_access('administer menu'),
-      'type' => MENU_CALLBACK);
-    $items[] = array('path' => 'admin/build/menu/item/reset',
-      'title' => t('Reset menu item'),
-      'callback' => 'drupal_get_form',
-      'callback arguments' => array('menu_reset_item'),
-      'access' => user_access('administer menu'),
-      'type' => MENU_CALLBACK);
-    $items[] = array('path' => 'admin/build/menu/item/disable',
-      'title' => t('Disable menu item'),
-      'callback' => 'menu_disable_item',
-      'access' => user_access('administer menu'),
-      'type' => MENU_CALLBACK);
-    $items[] = array('path' => 'admin/build/menu/item/delete',
-      'title' => t('Delete menu item'),
-      'callback' => 'drupal_get_form',
-      'callback arguments' => array('menu_item_delete_form'),
-      'access' => user_access('administer menu'),
-      'type' => MENU_CALLBACK);
-
+  $items['admin/build/menu'] = array(
+    'title' => t('Menus'),
+    'description' => t("Control your site's navigation menu, primary links and secondary links. as well as rename and reorganize menu items."),
+    'page callback' => 'menu_overview',
+    'access callback' => 'user_access',
+    'access arguments' => array('administer menu'),
+  );
+  $items['admin/build/menu/list'] = array(
+    'title' => t('List'),
+    'type' => MENU_DEFAULT_LOCAL_TASK,
+    'weight' => -10,
+  );
+  $items['admin/build/menu/item/disable'] = array(
+    'title' => t('Disable menu item'),
+    'page callback' => 'menu_flip_item',
+    'page arguments' => array('0'),
+    'type' => MENU_CALLBACK,
+  );
+  $items['admin/build/menu/item/enable'] = array(
+    'title' => t('Enable menu item'),
+    'page callback' => 'menu_flip_item',
+    'page arguments' => array('1'),
+    'type' => MENU_CALLBACK,
+  );
+  $items['admin/build/menu/item/add'] = array(
+    'title' => t('Add menu item'),
+    'page callback' => 'drupal_get_form',
+    'page arguments' => array('menu_edit_item_form', 'add'),
+    'parent' => 'admin/build/menu',
+    'type' => MENU_LOCAL_TASK);
+  $items['admin/build/menu/item/edit'] = array(
+    'title' => t('Edit menu item'),
+    'page callback' => 'drupal_get_form',
+    'page arguments' => array('menu_edit_item_form', 'edit'),
+    'type' => MENU_CALLBACK);
+  $items['admin/build/menu/item/reset'] = array(
+    'title' => t('Reset menu item'),
+    'page callback' => 'drupal_get_form',
+    'page arguments' => array('menu_reset_item'),
+    'type' => MENU_CALLBACK);
+  $items['admin/build/menu/item/delete'] = array(
+    'title' => t('Delete menu item'),
+    'page callback' => 'drupal_get_form',
+    'page arguments' => array('menu_item_delete_form'),
+    'type' => MENU_CALLBACK);
+  $result = db_query('SELECT * FROM {menu_edit} WHERE admin = 1');
+  while ($item = db_fetch_array($result)) {
+    $item['access callback'] = 1;
+    $item['access inherited'] = TRUE;
+    $items[$item['path']] = $item;
+  }
+  return $items;
+/*
     $items[] = array('path' => 'admin/build/menu/menu/add',
       'title' => t('Add menu'),
       'callback' => 'drupal_get_form',
@@ -105,230 +121,97 @@ function menu_menu() {
       'type' => MENU_LOCAL_TASK,
       'weight' => 5,
     );
-  }
-
-  return $items;
+*/
 }
 
-/**
- * Implementation of hook_block().
- */
-function menu_block($op = 'list', $delta = 0) {
-  if ($op == 'list') {
-    $blocks = array();
-    $root_menus = menu_get_root_menus();
-    foreach ($root_menus as $mid => $title) {
-      // Default "Navigation" block is handled by user.module.
-      if ($mid != 1) {
-        $blocks[$mid]['info'] = $title;
-      }
+function menu_menu_alter(&$menu, $phase) {
+  if ($phase == 1) {
+    $result = db_query('SELECT * FROM {menu_edit} me WHERE admin = 0');
+    while ($item = db_fetch_array($result)) {
+      $menu[$item['path']] = $item + $menu[$item['path']];
     }
-    return $blocks;
-  }
-  else if ($op == 'view') {
-    $item = menu_get_item($delta);
-    $data['subject'] = check_plain($item['title']);
-    $data['content'] = theme('menu_tree', $delta);
-    return $data;
   }
 }
 
-/**
- * Implementation of hook_nodeapi().
- */
-function menu_nodeapi(&$node, $op) {
-
-  if (user_access('administer menu')) {
-    switch ($op) {
-      case 'insert':
-      case 'update':
-        if ($node->menu['delete']) {
-          menu_node_form_delete($node);
-          menu_rebuild();
-        }
-        elseif ($node->menu['title']) {
-          $node->menu['path'] = ($node->menu['path']) ? $node->menu['path'] : "node/$node->nid";
-          menu_edit_item_save($node->menu);
-          menu_rebuild();
-        }
-        break;
-
-      case 'delete':
-        menu_node_form_delete($node);
-        menu_rebuild();
-        break;
+function menu_overview() {
+  $header = array(t('Menu item'), t('Expanded'), array('data' => t('Operations'), 'colspan' => '3'));
+  $result = db_query('SELECT m.*, me.disabled FROM {menu} m LEFT JOIN {menu_edit} me ON m.path = me.path WHERE visible = 1 OR (disabled = 1 AND admin = 0) ORDER BY mleft');
+  $map = arg();
+  while ($item = db_fetch_object($result)) {
+    _menu_translate($item, $map, MENU_RENDER_LINK);
+    if (!$item->access) {
+      continue;
+    }
+    $title = str_repeat('&nbsp;&nbsp;', $item->depth - 1) . ($item->depth > 1 ? '-&nbsp;' : '');
+    $title .= l($item->title, $item->path, (array)$item);
+    // Populate the operations field.
+    $operations = array();
+    // Set the edit column.
+    $operations[] = array('data' => l(t('edit'), 'admin/build/menu/item/edit/'. $item->mid));
+    if ($item->disabled) {
+      $title .= ' ('. t('disabled') .')';
+      $class = 'menu-disabled';
+      $operations[] = array('data' => l(t('enable'), 'admin/build/menu/item/enable/'. $item->mid));
     }
-  }
-}
-
-/**
- * Implementation of hook_perm().
- */
-function menu_perm() {
-  return array('administer menu');
-}
-
-/**
- * Implementation of hook_form_alter().
- * Add menu item fields to the node form.
- */
-function menu_form_alter(&$form, $form_id) {
-  if (isset($form['type']) && $form['type']['#value'] .'_node_form' == $form_id) {
-    $item = array();
-    if ($form['nid']['#value'] > 0) {
-      $item = db_fetch_array(db_query("SELECT * FROM {menu} WHERE path = 'node/%d'", $form['nid']['#value']));
-      if (isset($form['#post']['menu']) && is_array($form['#post']['menu'])) {
-        $item = !is_array($item) ? $form['#post']['menu'] : (($form['#post']['op'] == t('Preview')) ? array_merge($item, $form['#post']['menu']) : array_merge($form['#post']['menu'], $item));
-      }
+    else {
+      $class = 'menu-enabled';
+      $operations[] = array('data' => l(t('disable'), 'admin/build/menu/item/disable/'. $item->mid));
     }
-
-    $form['menu'] = array('#type' => 'fieldset',
-      '#title' => t('Menu settings'),
-      '#access' => user_access('administer menu'),
-      '#collapsible' => TRUE,
-      '#collapsed' => empty($item['title']),
-      '#tree' => TRUE,
-      '#weight' => 30,
-    );
-
-    $form['menu']['title'] = array('#type' => 'textfield',
-      '#title' => t('Title'),
-      '#default_value' => $item['title'],
-      '#description' => t('The name to display for this menu link.'),
-    );
-
-    $form['menu']['description'] = array('#type' => 'textfield',
-      '#title' => t('Description'),
-      '#default_value' => $item['description'],
-      '#description' => t('The description displayed when hovering over a menu item.'),
-    );
-
-    // Generate a list of possible parents.
-    $options = menu_parent_options($item['mid'], variable_get('menu_parent_items', 0));
-
-    $form['menu']['pid'] = array('#type' => 'select',
-      '#title' => t('Parent item'),
-      '#default_value' => $item['pid'],
-      '#options' => $options,
-    );
-
-    $form['menu']['path'] = array('#type' => 'hidden',
-      '#value' => $item['path'],
-    );
-
-    $form['menu']['weight'] = array('#type' => 'weight',
-      '#title' => t('Weight'),
-      '#default_value' => $item['weight'],
-      '#delta' => 10,
-      '#description' => t('Optional. In the menu, the heavier items will sink and the lighter items will be positioned nearer the top.'),
-    );
-
-    $form['menu']['mid'] = array('#type' => 'hidden',
-      '#value' => $item['mid'] ? $item['mid'] : 0,
-    );
-
-    $form['menu']['type'] = array('#type' => 'hidden',
-      '#value' => $item['type'] ? $item['type'] : MENU_CUSTOM_ITEM,
+    // Set the reset column.
+    if ($item->type & MENU_CREATED_BY_ADMIN) {
+      $operations[] = array('data' => l(t('delete'), 'admin/build/menu/item/delete/'. $item->mid));
+    }
+    else if ($item->type & MENU_MODIFIED_BY_ADMIN) {
+      $operations[] = array('data' => l(t('reset'), 'admin/build/menu/item/reset/'. $item->mid));
+    }
+    else {
+      $operations[] = array('data' => '');
+    }
+    $row = array(
+      array('data' => $title, 'class' => $class),
+      array('data' => ($item->has_children ? (($item->type & MENU_EXPANDED) ? t('Yes') : t('No')) : ''), 'class' => $class),
     );
-
-    if ($item['mid'] > 0) {
-      $form['menu']['delete'] = array('#type' => 'checkbox',
-        '#title' => t('Check to delete this menu item.'),
-        '#default_value' => $item['delete'],
-      );
-
-      $form['menu']['advanced'] = array('#type' => 'item',
-        '#value' => t('You may also <a href="@edit">edit the advanced settings</a> for this menu item.', array('@edit' => url("admin/build/menu/item/edit/{$item['mid']}"))),
-      );
+    foreach ($operations as $operation) {
+      $operation['class'] = $class;
+      $row[] = $operation;
     }
+    $rows[] = $row;
   }
+  return theme('table', $header, $rows);
 }
-
-/**
- * Menu callback; presents menu configuration options.
- */
-function menu_configure() {
-  $root_menus = menu_get_root_menus();
-
-  $primary_options = $root_menus;
-  $primary_options[0] = t('No primary links');
-
-  $form['settings_links'] = array('#type' => 'fieldset',
-    '#title' => t('Primary and secondary links settings'),
-  );
-
-  $form['settings_links']['intro'] = array('#type' => 'item',
-    '#value' => t('Primary and secondary links provide a navigational menu system which usually (depending on your theme) appears at the top-right of the browser window. The links displayed can be generated either from a custom list created via the <a href="@menu">menu administration</a> page or from a built-in list of menu items such as the navigation menu links.', array('@menu' => url('admin/build/menu'))),
-  );
-
-  $form['settings_links']['menu_primary_menu'] = array('#type' => 'select',
-    '#title' => t('Menu containing primary links'),
-    '#default_value' => variable_get('menu_primary_menu', 0),
-    '#options' => $primary_options,
-  );
-
-  $secondary_options = $root_menus;
-  $secondary_options[0] = t('No secondary links');
-
-  $form['settings_links']['menu_secondary_menu'] = array('#type' => 'select',
-    '#title' => t('Menu containing secondary links'),
-    '#default_value' => variable_get('menu_secondary_menu', 0),
-    '#options' => $secondary_options,
-    '#description' => t('If you select the same menu as primary links then secondary links will display the appropriate second level of your navigation hierarchy.'),
-  );
-
-  $form['settings_authoring'] = array('#type' => 'fieldset',
-    '#title' => t('Content authoring form settings'),
-  );
-
-  $form['settings_authoring']['intro'] = array('#type' => 'item',
-    '#value' => t('The menu module allows on-the-fly creation of menu links in the content authoring forms. The following option limits the menus in which a new link may be added. E.g., this can be used to force new menu items to be created in the primary links menu or to hide admin menu items.'),
-  );
-
-  $authoring_options = $root_menus;
-  $authoring_options[0] = t('Show all menus');
-
-  $form['settings_authoring']['menu_parent_items'] = array('#type' => 'select',
-    '#title' => t('Restrict parent items to'),
-    '#default_value' => variable_get('menu_parent_items', 0),
-    '#options' => $authoring_options,
-    '#description' => t('Choose the menu to be made available in the content authoring form. Only this menu item and its children will be shown.'),
-   );
-
-  return system_settings_form($form);
-}
-
+  
 /**
- * Menu callback; handle the adding/editing of a new menu.
- */
-function menu_edit_menu_form($type, $mid = 0) {
-  if ($type == 'edit') {
-    if (!($item = db_fetch_array(db_query('SELECT * FROM {menu} WHERE mid = %d', $mid)))) {
-      drupal_not_found();
-      return;
+ * Menu callback; enable/disable a menu item.
+ *
+ * @param $visible
+ *   0 to remove from the menu tree. 1 to make the item and its children
+ *   reappear in menu tree.
+ * @param $mid
+ *    mid of the menu item.
+ * @param $path
+ *    Optional. Path of the menu item. Only considered if mid is NULL.
+ */
+function menu_flip_item($visible, $mid, $path = NULL) {
+  if (isset($mid)) {
+    $parent = menu_get_item_by_mid($mid);
+  }
+  elseif (isset($path)) {
+    $parent = menu_get_item($path);
+  }
+  if (isset($parent) && $parent->access) {
+    $result = db_query('SELECT * FROM {menu} WHERE %d <= mleft AND mright <= %d', $parent->mleft, $parent->mright);
+    while ($item = db_fetch_object($result)) {
+      $update_result = db_query("UPDATE {menu_edit} SET disabled = %d WHERE path = '%s'", !$visible, $item->path);
+      if (!db_affected_rows($update_result)) {
+        db_query("INSERT INTO {menu_edit} (parent, path, title, description, weight, type, admin, disabled) VALUES ('%s', '%s', '%s', '%s', %d, %d, %d, %d)", $item->parent, $item->path, $item->title, $item->description, 0, $item->type, 0, !$visible);
+      }
+    }
+    menu_rebuild();
+    if (isset($mid)) {
+      drupal_set_message($visible ? t('The menu item has been enabled.') : t('The menu item has been disabled.'));
+      drupal_goto('admin/build/menu');
     }
   }
-  else {
-    $item = array('mid' => 0, 'pid' => 0, 'path' => '', 'weight' => 0, 'type' => MENU_CUSTOM_MENU);
-  }
-  $form['title'] = array('#type' => 'textfield',
-    '#title' => t('Title'),
-    '#default_value' => $item['title'],
-    '#description' => t('The name of the menu.'),
-    '#required' => TRUE,
-  );
-  $form['mid'] = array('#type' => 'value', '#value' => $item['mid']);
-  $form['pid'] = array('#type' => 'value', '#value' => $item['pid']);
-  $form['path'] = array('#type' => 'value', '#value' => $item['path']);
-  $form['weight'] = array('#type' => 'value', '#value' => $item['weight']);
-  $form['type'] = array('#type' => 'value', '#value' => $item['type']);
-  $form['submit'] = array('#type' => 'submit', '#value' => t('Submit'));
-  // Reuse the submit function of menu_edit_item_form.
-  $form['#submit']['menu_edit_item_form_submit'] = array();
-  $form['#validate']['menu_edit_item_form_validate'] = array();
-  $form['#theme'] = 'menu_edit_item_form';
-
-  return $form;
 }
 
 /**
@@ -336,7 +219,7 @@ function menu_edit_menu_form($type, $mid
  */
 function menu_edit_item_form($type, $mid = 0) {
   if ($type == 'edit') {
-    if (!($item = db_fetch_array(db_query('SELECT * FROM {menu} WHERE mid = %d', $mid)))) {
+    if (!($item = menu_get_item_by_mid($mid))) {
       drupal_not_found();
       return;
     }
@@ -346,69 +229,89 @@ function menu_edit_item_form($type, $mid
     // The mid argument (if set) will be the default pid to use.
     // Otherwise, we default to the "Navigation" menu (pid #1).
     $default_pid = $mid ? $mid : 1;
-    $item = array('mid' => 0, 'pid' => $default_pid, 'weight' => 0, 'type' => MENU_CUSTOM_ITEM);
+    $item = (object)array('mid' => 0, 'pid' => $default_pid, 'weight' => 0, 'type' => MENU_CUSTOM_ITEM, 'title' => '', 'description' => '', 'path' => '');
   }
 
   $form['title'] = array('#type' => 'textfield',
     '#title' => t('Title'),
-    '#default_value' => $item['title'],
+    '#default_value' => $item->title,
     '#description' => t('The name of the menu item.'),
     '#required' => TRUE,
   );
-  $form['description'] = array('#type' => 'textfield',
+  $form['description'] = array(
+    '#type' => 'textfield',
     '#title' => t('Description'),
-    '#default_value' => $item['description'],
+    '#default_value' => $item->description,
     '#description' => t('The description displayed when hovering over a menu item.'),
   );
 
-  if ($item['type'] & MENU_CREATED_BY_ADMIN) {
-    $form['path'] = array('#type' => 'textfield',
+  if ($item->type & MENU_CREATED_BY_ADMIN) {
+    $form['path'] = array(
+      '#type' => 'textfield',
       '#title' => t('Path'),
-      '#default_value' => $item['path'],
+      '#default_value' => $item->path,
       '#description' => t('The path this menu item links to. This can be an internal Drupal path such as %add-node or an external URL such as %drupal. Enter %front to link to the front page.', array('%front' => '<front>', '%add-node' => 'node/add', '%drupal' => 'http://drupal.org')),
       '#required' => TRUE,
     );
   }
   else {
-    $form['_path'] = array('#type' => 'item',
+    $form['_path'] = array(
+      '#type' => 'item',
       '#title' => t('Path'),
-      '#description' => l($item['path'], $item['path']),
+      '#description' => l($item->path, $item->link_path, (array)$item),
     );
-    $form['path'] = array('#type' => 'value', '#value' => $item['path']);
   }
+  $form['original_path'] = array('#type' => 'value', '#value' => $item->path);
 
-  $expanded = $item['type'] & MENU_EXPANDED ? 1 : 0;
-  $form['expanded'] = array('#type' => 'checkbox',
+  $form['expanded'] = array(
+    '#type' => 'checkbox',
     '#title' => t('Expanded'),
-    '#default_value' => $expanded,
+    '#default_value' => $item->type & MENU_EXPANDED ? 1 : 0,
     '#description' => t('If selected and this menu item has children, the menu will always appear expanded.'),
   );
 
   // Generate a list of possible parents (not including this item or descendants).
-  $options = menu_parent_options($item['mid']);
-  $form['pid'] = array('#type' => 'select',
+  $options = menu_parent_options($item->mid);
+  $form['pid'] = array(
+    '#type' => 'select',
     '#title' => t('Parent item'),
-    '#default_value' => $item['pid'],
+    '#default_value' => $item->pid,
     '#options' => $options,
   );
-  $form['weight'] = array('#type' => 'weight',
+  $form['weight'] = array(
+    '#type' => 'weight',
     '#title' => t('Weight'),
-    '#default_value' => $item['weight'],
+    '#default_value' => isset($item->weight) ? $item->weight : 0,
     '#description' => t('Optional. In the menu, the heavier items will sink and the lighter items will be positioned nearer the top.'),
   );
 
   // Always enable menu items (but not menus) when editing them.
-  if (!($item['type'] & MENU_IS_ROOT)) {
-    $item['type'] |= MENU_VISIBLE_IN_TREE | MENU_VISIBLE_IN_BREADCRUMB;
+  if (!($item->type & MENU_IS_ROOT)) {
+    $item->type |= MENU_VISIBLE_IN_TREE | MENU_VISIBLE_IN_BREADCRUMB;
   }
 
-  $form['type'] = array('#type' => 'value', '#value' => $item['type']);
-  $form['mid'] = array('#type' => 'value', '#value' => $item['mid']);
+  $form['type'] = array('#type' => 'value', '#value' => $item->type);
   $form['submit'] = array('#type' => 'submit', '#value' => t('Submit'));
 
   return $form;
 }
 
+function menu_edit_item_form_validate($form_id, $form_values) {
+  if (isset($form_values['path'])) {
+    // Skip external links.
+    $colonpos = strpos($path, ':');
+    if ($colonpos !== FALSE && !preg_match('![/?#]!', substr($path, 0, $colonpos))) {
+      return;
+    }
+    $item = menu_get_item($form_values['path']);
+    if (!$item || !$item->access) {
+      form_set_error('path', t('This path is either invalid or you do not have access to it'));
+    }
+    elseif ($item->path == $form_values['path']) {
+      form_set_error('path', t('There is already a menu item pointing to this path.'));
+    }
+  }
+}
 /**
  * Process menu and menu item add/edit form submissions.
  */
@@ -418,15 +321,137 @@ function menu_edit_item_form_submit($for
 }
 
 /**
- * Menu callback; delete a single custom item.
- */
-function menu_item_delete_form($mid) {
-  if (!($menu = db_fetch_object(db_query('SELECT type, title FROM {menu} WHERE mid = %d', $mid)))) {
-    drupal_not_found();
+ * Return a list of menu items that are valid possible parents for the
+ * given menu item. The list excludes the given item and its children.
+ *
+ * @param $mid
+ *   The menu item id for which to generate a list of parents.
+ *   If $mid == 0 then the complete tree is returned.
+ * @param $pid
+ *   The menu item id of the menu item at which to start the tree.
+ *   If $pid > 0 then this item will be included in the tree.
+ * @param $depth
+ *   The current depth in the tree - used when recursing to indent the tree.
+ * @return
+ *   An array of menu titles keyed on the mid.
+ */
+function menu_parent_options($mid, $pid = 1, $depth = 0) {
+  $options = array(1 => t('Root'));
+  // Exclude $mid and its children from the list unless $mid is 0.
+  if ($mid && $mid == $pid) {
+    return $options;
+  }
+  $sql = 'SELECT m.*, me.disabled FROM {menu} m LEFT JOIN {menu_edit} me ON m.path = me.path WHERE (m.visible = 1 OR (me.disabled = 1 AND me.admin = 0))';
+  if (!$mid) {
+    $params = array();
+  }
+  elseif ($item = menu_get_item_by_mid($mid)) {
+    $sql .=' AND (mleft < %d OR %d < mright)';
+    $params = array($item->mleft, $item->mright);
+  }
+  else {
+    return $options;
+  }
+  if ($parent_item = menu_get_item_by_mid($pid)) {
+    $sql .= ' AND %d <= mleft AND %d <= mright';
+    $params[] = $parent_item->mleft;
+    $params[] = $parent_item->mright;
+  }
+  $sql .= ' ORDER BY mleft';
+  $result = db_query($sql, $params);
+  $map = arg();
+
+  while ($item = db_fetch_object($result)) {
+    _menu_translate($item, $map, MENU_RENDER_LINK);
+    $title = str_repeat('--', $item->depth) .' '. $item->title;
+    if ($item->disabled) {
+      $title .= ' ('. t('disabled') .')';
+    }
+    $options[$item->mid] = $title;
+  }
+  return $options;
+}
+
+/**
+ * Save changes to a menu item into the database.
+ *
+ * @return mid
+ */
+function menu_edit_item_save($edit) {
+  if (isset($edit['expanded'])) {
+    if ($edit['expanded']) {
+      $edit['type'] |= MENU_EXPANDED;
+    }
+    else {
+      $edit['type'] &= ~MENU_EXPANDED;
+    }
+  }
+
+  $edit['type'] = $edit['type'] | MENU_MODIFIED_BY_ADMIN;
+
+  $parent = $edit['pid'] > 1 ? db_result(db_query('SELECT path FROM {menu} WHERE mid = %d', $edit['pid'])) : '';
+  $t_args = array('%title' => $edit['title']);
+  if (!empty($edit['original_path']) && db_num_rows(db_query("SELECT * FROM {menu_edit} WHERE path='%s'", $edit['original_path']))) {
+    db_query("UPDATE {menu_edit} SET parent = '%s', title = '%s', description = '%s', weight = %d, type = %d WHERE path = '%s'", $parent, $edit['title'], $edit['description'], $edit['weight'], $edit['type'], $edit['original_path']);
+  }
+  else {
+    db_query("INSERT INTO {menu_edit} (parent, path, title, description, weight, type, admin) VALUES ('%s', '%s', '%s', '%s', %d, %d, %d)", $parent, isset($edit['path']) ? $edit['path'] : $edit['original_path'], $edit['title'], $edit['description'], $edit['weight'], $edit['type'], isset($edit['path']));
+  }
+  watchdog('menu', t('Saved menu item %title.', $t_args), WATCHDOG_NOTICE, l(t('view'), 'admin/build/menu'));
+  drupal_set_message(t('The menu item %title has been saved.', $t_args));
+  menu_rebuild();
+}
+
+/**
+ * Remove the menu item.
+ */
+function menu_node_form_delete($node) {
+  menu_delete_item(array('path' => 'node/'. $node->nid));
+}
+
+/**
+ * Menu callback; handle the adding/editing of a new menu.
+ */
+function menu_edit_menu_form($type, $mid = 0) {
+  if ($type == 'edit') {
+    if (!$item = menu_get_item_by_mid($mid)) {
+      drupal_not_found();
+      return;
+    }
+  }
+  else {
+    $item = array('mid' => 0, 'pid' => 0, 'path' => '', 'weight' => 0, 'type' => MENU_CUSTOM_MENU);
+  }
+  $form['title'] = array('#type' => 'textfield',
+    '#title' => t('Title'),
+    '#default_value' => $item['title'],
+    '#description' => t('The name of the menu.'),
+    '#required' => TRUE,
+  );
+  $form['mid'] = array('#type' => 'value', '#value' => $item['mid']);
+  $form['pid'] = array('#type' => 'value', '#value' => $item['pid']);
+  $form['path'] = array('#type' => 'value', '#value' => $item['path']);
+  $form['weight'] = array('#type' => 'value', '#value' => $item['weight']);
+  $form['type'] = array('#type' => 'value', '#value' => $item['type']);
+  $form['submit'] = array('#type' => 'submit', '#value' => t('Submit'));
+  // Reuse the submit function of menu_edit_item_form.
+  $form['#submit']['menu_edit_item_form_submit'] = array();
+  $form['#validate']['menu_edit_item_form_validate'] = array();
+  $form['#theme'] = 'menu_edit_item_form';
+
+  return $form;
+}
+
+/**
+ * Menu callback; delete a single custom item.
+ */
+function menu_item_delete_form($mid) {
+  if (!($menu = db_fetch_object(db_query('SELECT type, path, title FROM {menu} WHERE mid = %d', $mid)))) {
+    drupal_not_found();
     return;
   }
 
-  $form['mid'] = array('#type' => 'value', '#value' => $mid);
+  $form['path'] = array('#type' => 'value', '#value' => $menu->path);
   $form['type'] = array('#type' => 'value', '#value' => $menu->type);
   $form['title'] = array('#type' => 'value', '#value' => $menu->title);
 
@@ -444,7 +469,7 @@ function menu_item_delete_form($mid) {
  * Process menu delete form submissions.
  */
 function menu_item_delete_form_submit($form_id, $form_values) {
-  menu_delete_item($form_values['mid']);
+  menu_delete_item($form_values['path']);
 
   $t_args = array('%title' => $form_values['title']);
   if ($form_values['type'] & MENU_IS_ROOT) {
@@ -463,9 +488,9 @@ function menu_item_delete_form_submit($f
  * Menu callback; reset a single modified item.
  */
 function menu_reset_item($mid) {
-  if (isset($mid) && $title = db_result(db_query('SELECT title FROM {menu} WHERE mid = %d', $mid))) {
-    $form['mid'] = array('#type' => 'value', '#value' => $mid);
-    return confirm_form($form, t('Are you sure you want to reset the item %item to its default values?', array('%item' => $title)), 'admin/build/menu', t('Any customizations will be lost. This action cannot be undone.'), t('Reset'));
+  if (isset($mid) && $item = db_fetch_object(db_query('SELECT path, title FROM {menu} WHERE mid = %d', $mid))) {
+    $form['mid'] = array('#type' => 'value', '#value' => $item->path);
+    return confirm_form($form, t('Are you sure you want to reset the item %item to its default values?', array('%item' => $item->title)), 'admin/build/menu', t('Any customizations will be lost. This action cannot be undone.'), t('Reset'));
   }
   else {
     drupal_not_found();
@@ -483,120 +508,204 @@ function menu_reset_item_submit($form_id
 }
 
 /**
- * Menu callback; hide a menu item.
- */
-function menu_disable_item($mid) {
-  $item = menu_get_item($mid);
-  $type = $item['type'];
-  $type &= ~MENU_VISIBLE_IN_TREE;
-  $type &= ~MENU_VISIBLE_IN_BREADCRUMB;
-  $type |= MENU_MODIFIED_BY_ADMIN;
-  db_query('UPDATE {menu} SET type = %d WHERE mid = %d', $type, $mid);
-  drupal_set_message(t('The menu item has been disabled.'));
-  drupal_goto('admin/build/menu');
-}
-
-/**
- * Menu callback; present the main menu management page.
+ * Delete a menu item from the database. If $item['mid'] is specified, then
+ * this is used to find the existing item; otherwise, $item['path'] is used.
+ *
+ * @param $item
+ *   The path to the menu item to be deleted.
  */
-function menu_overview() {
+function menu_delete_item($path) {
+  db_query("DELETE FROM {menu_edit} WHERE path = '%s'", $path);
   menu_rebuild();
-
-  return menu_overview_tree();
 }
 
+// Conversion ends here.
+
 /**
- * Save changes to a menu item into the database.
- *
- * @return mid
+ * Implementation of hook_block().
  */
-function menu_edit_item_save($edit) {
-  if (isset($edit['expanded'])) {
-    if ($edit['expanded']) {
-      $edit['type'] |= MENU_EXPANDED;
-    }
-    else {
-      $edit['type'] &= ~MENU_EXPANDED;
+function _menu_block($op = 'list', $delta = 0) {
+  if ($op == 'list') {
+    $blocks = array();
+    $root_menus = menu_get_root_menus();
+    foreach ($root_menus as $mid => $title) {
+      // Default "Navigation" block is handled by user.module.
+      if ($mid != 1) {
+        $blocks[$mid]['info'] = $title;
+      }
     }
+    return $blocks;
   }
+  else if ($op == 'view') {
+    $item = menu_get_item($delta);
+    $data['subject'] = check_plain($item['title']);
+    $data['content'] = theme('menu_tree', $delta);
+    return $data;
+  }
+}
 
-  $edit['type'] = $edit['type'] | MENU_MODIFIED_BY_ADMIN;
+/**
+ * Implementation of hook_nodeapi().
+ */
+function _menu_nodeapi(&$node, $op) {
 
-  $status = menu_save_item($edit);
+  if (user_access('administer menu')) {
+    switch ($op) {
+      case 'insert':
+      case 'update':
+        if ($node->menu['delete']) {
+          menu_node_form_delete($node);
+          menu_rebuild();
+        }
+        elseif ($node->menu['title']) {
+          $node->menu['path'] = ($node->menu['path']) ? $node->menu['path'] : "node/$node->nid";
+          menu_edit_item_save($node->menu);
+          menu_rebuild();
+        }
+        break;
 
-  $t_args = array('%title' => $edit['title']);
-  if ($status == SAVED_UPDATED) {
-    drupal_set_message(t('The menu item %title has been updated.', $t_args));
-  }
-  elseif ($status == SAVED_NEW) {
-    drupal_set_message(t('The menu item %title has been added.', $t_args));
-    watchdog('menu', t('Added menu item %title.', $t_args), WATCHDOG_NOTICE, l(t('view'), 'admin/build/menu'));
+      case 'delete':
+        menu_node_form_delete($node);
+        menu_rebuild();
+        break;
+    }
   }
-  return $edit['mid'];
 }
 
 /**
- * Save a menu item to the database.
- *
- * @param $item
- *   The menu item to be saved. This is passed by reference, so that the newly
- *   generated $item['mid'] can be accessed after an insert takes place.
- *
- * @return $status
- *   The operation that was performed in saving. Either SAVED_NEW (if a new
- *   menu item was created), or SAVED_UPDATED (if an existing menu item was
- *   updated).
- */
-function menu_save_item(&$item) {
-  $existing_item = NULL;
-
-  // Check that the item already exists in the menu tree, if $item['mid'] is
-  // specified.
-  if (isset($item['mid'])) {
-    $existing_item = menu_get_item($item['mid']);
-  }
-
-  if ($item['mid'] && !empty($existing_item)) {
-    db_query("UPDATE {menu} SET pid = %d, path = '%s', title = '%s', description = '%s', weight = %d, type = %d WHERE mid = %d", $item['pid'], $item['path'], $item['title'], $item['description'], $item['weight'], $item['type'], $item['mid']);
-    return SAVED_UPDATED;
-  }
-  else {
-    $item['mid'] = db_next_id('{menu}_mid');
-    // Check explicitly for mid <= 2. If the database was improperly prefixed,
-    // this would cause a nasty infinite loop or duplicate mid errors.
-    // TODO: have automatic prefixing through an installer to prevent this.
-    while ($item['mid'] <= 2) {
-      $item['mid'] = db_next_id('{menu}_mid');
+ * Implementation of hook_form_alter().
+ * Add menu item fields to the node form.
+ */
+function _menu_form_alter(&$form, $form_id) {
+  if (isset($form['type']) && $form['type']['#value'] .'_node_form' == $form_id) {
+    $item = array();
+    if ($form['nid']['#value'] > 0) {
+      $item = db_fetch_array(db_query("SELECT * FROM {menu} WHERE path = 'node/%d'", $form['nid']['#value']));
+      if (isset($form['#post']['menu']) && is_array($form['#post']['menu'])) {
+        $item = !is_array($item) ? $form['#post']['menu'] : (($form['#post']['op'] == t('Preview')) ? array_merge($item, $form['#post']['menu']) : array_merge($form['#post']['menu'], $item));
+      }
+    }
+
+    $form['menu'] = array('#type' => 'fieldset',
+      '#title' => t('Menu settings'),
+      '#access' => user_access('administer menu'),
+      '#collapsible' => TRUE,
+      '#collapsed' => empty($item['title']),
+      '#tree' => TRUE,
+      '#weight' => 30,
+    );
+
+    $form['menu']['title'] = array('#type' => 'textfield',
+      '#title' => t('Title'),
+      '#default_value' => $item['title'],
+      '#description' => t('The name to display for this menu link.'),
+    );
+
+    $form['menu']['description'] = array('#type' => 'textfield',
+      '#title' => t('Description'),
+      '#default_value' => $item['description'],
+      '#description' => t('The description displayed when hovering over a menu item.'),
+    );
+
+    // Generate a list of possible parents.
+    $options = menu_parent_options($item['mid'], variable_get('menu_parent_items', 0));
+
+    $form['menu']['pid'] = array('#type' => 'select',
+      '#title' => t('Parent item'),
+      '#default_value' => $item['pid'],
+      '#options' => $options,
+    );
+
+    $form['menu']['path'] = array('#type' => 'hidden',
+      '#value' => $item['path'],
+    );
+
+    $form['menu']['weight'] = array('#type' => 'weight',
+      '#title' => t('Weight'),
+      '#default_value' => $item['weight'],
+      '#delta' => 10,
+      '#description' => t('Optional. In the menu, the heavier items will sink and the lighter items will be positioned nearer the top.'),
+    );
+
+    $form['menu']['mid'] = array('#type' => 'hidden',
+      '#value' => $item['mid'] ? $item['mid'] : 0,
+    );
+
+    $form['menu']['type'] = array('#type' => 'hidden',
+      '#value' => $item['type'] ? $item['type'] : MENU_CUSTOM_ITEM,
+    );
+
+    if ($item['mid'] > 0) {
+      $form['menu']['delete'] = array('#type' => 'checkbox',
+        '#title' => t('Check to delete this menu item.'),
+        '#default_value' => $item['delete'],
+      );
+
+      $form['menu']['advanced'] = array('#type' => 'item',
+        '#value' => t('You may also <a href="@edit">edit the advanced settings</a> for this menu item.', array('@edit' => url("admin/build/menu/item/edit/{$item['mid']}"))),
+      );
     }
-    db_query("INSERT INTO {menu} (mid, pid, path, title, description, weight, type) VALUES (%d, %d, '%s', '%s', '%s', %d, %d)", $item['mid'], $item['pid'], $item['path'], $item['title'], $item['description'], $item['weight'], $item['type']);
-    return SAVED_NEW;
   }
 }
 
 /**
- * Delete a menu item from the database. If $item['mid'] is specified, then
- * this is used to find the existing item; otherwise, $item['path'] is used.
- *
- * @param $item
- *   The menu item to be deleted.
+ * Menu callback; presents menu configuration options.
  */
-function menu_delete_item($item) {
-  if (!is_array($item)) {
-    $item = array('mid' => $item);
-  }
+function menu_configure() {
+  $root_menus = menu_get_root_menus();
 
-  if ($item['mid']) {
-    db_query('DELETE FROM {menu} WHERE mid = %d', $item['mid']);
-  }
-  elseif ($item['path']) {
-    db_query("DELETE FROM {menu} WHERE path = '%s'", $item['path']);
-  }
+  $primary_options = $root_menus;
+  $primary_options[0] = t('No primary links');
+
+  $form['settings_links'] = array('#type' => 'fieldset',
+    '#title' => t('Primary and secondary links settings'),
+  );
+
+  $form['settings_links']['intro'] = array('#type' => 'item',
+    '#value' => t('Primary and secondary links provide a navigational menu system which usually (depending on your theme) appears at the top-right of the browser window. The links displayed can be generated either from a custom list created via the <a href="@menu">menu administration</a> page or from a built-in list of menu items such as the navigation menu links.', array('@menu' => url('admin/build/menu'))),
+  );
+
+  $form['settings_links']['menu_primary_menu'] = array('#type' => 'select',
+    '#title' => t('Menu containing primary links'),
+    '#default_value' => variable_get('menu_primary_menu', 0),
+    '#options' => $primary_options,
+  );
+
+  $secondary_options = $root_menus;
+  $secondary_options[0] = t('No secondary links');
+
+  $form['settings_links']['menu_secondary_menu'] = array('#type' => 'select',
+    '#title' => t('Menu containing secondary links'),
+    '#default_value' => variable_get('menu_secondary_menu', 0),
+    '#options' => $secondary_options,
+    '#description' => t('If you select the same menu as primary links then secondary links will display the appropriate second level of your navigation hierarchy.'),
+  );
+
+  $form['settings_authoring'] = array('#type' => 'fieldset',
+    '#title' => t('Content authoring form settings'),
+  );
+
+  $form['settings_authoring']['intro'] = array('#type' => 'item',
+    '#value' => t('The menu module allows on-the-fly creation of menu links in the content authoring forms. The following option limits the menus in which a new link may be added. E.g., this can be used to force new menu items to be created in the primary links menu or to hide admin menu items.'),
+  );
+
+  $authoring_options = $root_menus;
+  $authoring_options[0] = t('Show all menus');
+
+  $form['settings_authoring']['menu_parent_items'] = array('#type' => 'select',
+    '#title' => t('Restrict parent items to'),
+    '#default_value' => variable_get('menu_parent_items', 0),
+    '#options' => $authoring_options,
+    '#description' => t('Choose the menu to be made available in the content authoring form. Only this menu item and its children will be shown.'),
+   );
+
+  return system_settings_form($form);
 }
 
 /**
  * Present the menu tree, rendered along with links to edit menu items.
  */
-function menu_overview_tree() {
+function _menu_overview_tree() {
   $menu = menu_get_menu();
   $root_menus = menu_get_root_menus();
   $header = array(t('Menu item'), t('Expanded'), array('data' => t('Operations'), 'colspan' => '3'));
@@ -621,152 +730,3 @@ function menu_overview_tree() {
   }
   return $output;
 }
-
-function menu_overview_tree_rows($pid = 0, $depth = 0) {
-  $parent_item = menu_get_item($pid);
-  $rows = array();
-
-  if (isset($parent_item) && isset($parent_item['children'])) {
-    usort($parent_item['children'], '_menu_sort');
-    foreach ($parent_item['children'] as $mid) {
-      $item = menu_get_item($mid);
-      // Populate the title field.
-      $title = '';
-      if ($pid == 0) {
-        // Top-level items are menu names, and don't have an associated path.
-        $title .= check_plain($item['title']);
-      }
-      else {
-        $title .= l($item['title'], $item['path']);
-      }
-      if ($depth > 0) {
-        $title = '-&nbsp;'. $title;
-      }
-      for ($i = 1; $i < $depth; $i++) {
-        $title = '&nbsp;&nbsp;'. $title;
-      }
-
-      // Populate the operations field.
-      $operations = array();
-      if (!($item['type'] & MENU_MODIFIABLE_BY_ADMIN)) {
-        $operations[] = array('data' => t('locked'), 'colspan' => '3', 'align' => 'center');
-      }
-      else {
-        // Set the edit column.
-        if ($item['type'] & (MENU_VISIBLE_IN_TREE | MENU_VISIBLE_IF_HAS_CHILDREN)) {
-          $operations[] = array('data' => l(t('edit'), 'admin/build/menu/item/edit/'. $mid));
-        }
-        else {
-          $operations[] = array('data' => '');
-        }
-
-        // Set the disable column.
-        if ($item['type'] & (MENU_IS_ROOT | MENU_VISIBLE_IF_HAS_CHILDREN)) {
-          // Disabling entire menus is done from block admin page.
-          // MENU_VISIBLE_IF_HAS_CHILDREN menus are always enabled so hide this operation.
-          $operations[] = array('data' => '');
-        }
-        else if ($item['type'] & MENU_VISIBLE_IN_TREE) {
-          $operations[] = array('data' => l(t('disable'), 'admin/build/menu/item/disable/'. $mid));
-        }
-        else {
-          $operations[] = array('data' => l(t('enable'), 'admin/build/menu/item/edit/'. $mid));
-        }
-
-        // Set the reset column.
-        if ($item['type'] & MENU_CREATED_BY_ADMIN) {
-          $operations[] = array('data' => l(t('delete'), 'admin/build/menu/item/delete/'. $mid));
-        }
-        else if ($item['type'] & MENU_MODIFIED_BY_ADMIN) {
-          $operations[] = array('data' => l(t('reset'), 'admin/build/menu/item/reset/'. $mid));
-        }
-        else {
-          $operations[] = array('data' => '');
-        }
-      }
-
-      // Call out disabled items.
-      if ($item['type'] & (MENU_VISIBLE_IN_TREE | MENU_VISIBLE_IF_HAS_CHILDREN)) {
-        $class = 'menu-enabled';
-      }
-      else {
-        $title .= ' ('. t('disabled') .')';
-        $class = 'menu-disabled';
-      }
-
-      if ($item['type'] & (MENU_MODIFIABLE_BY_ADMIN | MENU_VISIBLE_IN_TREE)) {
-        $row = array(array('data' => $title, 'class' => $class), array('data' => ($item['children'] ? (($item['type'] & MENU_EXPANDED) ? t('Yes') : t('No')) : ''), 'class' => $class));
-        foreach ($operations as $operation) {
-          $operation['class'] = $class;
-          $row[] = $operation;
-        }
-        $rows[] = $row;
-        $rows = array_merge($rows, menu_overview_tree_rows($mid, $depth + 1));
-      }
-      else {
-        // Skip items that are hidden and locked; admins will never care about them.
-        $rows = array_merge($rows, menu_overview_tree_rows($mid, $depth));
-      }
-    }
-  }
-
-  return $rows;
-}
-
-/**
- * Return a list of menu items that are valid possible parents for the
- * given menu item. The list excludes the given item and its children.
- *
- * @param $mid
- *   The menu item id for which to generate a list of parents.
- *   If $mid == 0 then the complete tree is returned.
- * @param $pid
- *   The menu item id of the menu item at which to start the tree.
- *   If $pid > 0 then this item will be included in the tree.
- * @param $depth
- *   The current depth in the tree - used when recursing to indent the tree.
- * @return
- *   An array of menu titles keyed on the mid.
- */
-function menu_parent_options($mid, $pid = 0, $depth = 0) {
-  $options = array();
-
-  if (!($parent_item = menu_get_item($pid))) {
-    return $options;
-  }
-
-  // Exclude $mid and its children from the list unless $mid is 0.
-  if ($mid && $mid == $pid) {
-    return $options;
-  }
-
-  // Add the current $pid to the list.
-  if ($pid > 0 && ($parent_item['type'] & (MENU_MODIFIABLE_BY_ADMIN | MENU_IS_ROOT))) {
-    $title = ' '. $parent_item['title'];
-    for ($i = 0; $i < $depth; $i++) {
-      $title = '--'. $title;
-    }
-    if (!($parent_item['type'] & MENU_VISIBLE_IN_TREE)) {
-      $title .= ' ('. t('disabled') .')';
-    }
-    $options[$pid] = $title;
-    $depth ++;
-  }
-
-  // Add children of $pid to the list recursively.
-  if (isset($parent_item['children'])) {
-    usort($parent_item['children'], '_menu_sort');
-    foreach ($parent_item['children'] as $child) {
-      $options += menu_parent_options($mid, $child, $depth);
-    }
-  }
-
-  return $options;
-}
-
-/**
- * Remove the menu item.
- */
-function menu_node_form_delete($node) {
-  menu_delete_item(array('path' => 'node/'. $node->nid));
-}

=== modified file 'modules/node/node.module'
--- modules/node/node.module	2007-03-27 05:13:53 +0000
+++ modules/node/node.module	2007-03-29 15:38:26 +0000
@@ -498,7 +498,7 @@ function node_load($param = array(), $re
   if ($reset) {
     $nodes = array();
   }
-
+  
   $cachable = ($revision == NULL);
   $arguments = array();
   if (is_numeric($param)) {
@@ -527,7 +527,7 @@ function node_load($param = array(), $re
     $node = db_fetch_object(db_query('SELECT n.nid, n.vid, n.type, n.status, n.created, n.changed, n.comment, n.promote, n.sticky, r.timestamp AS revision_timestamp, r.title, r.body, r.teaser, r.log, r.format, u.uid, u.name, u.picture, u.data FROM {node} n INNER JOIN {users} u ON u.uid = n.uid INNER JOIN {node_revisions} r ON r.vid = n.vid WHERE '. $cond, $arguments));
   }
 
-  if ($node->nid) {
+  if ($node && $node->nid) {
     // Call the node specific callback (if any) and piggy-back the
     // results to the node or overwrite some values.
     if ($extra = node_invoke($node, 'load')) {

=== modified file 'modules/system/system.module'
--- modules/system/system.module	2007-03-27 05:13:53 +0000
+++ modules/system/system.module	2007-03-29 05:29:23 +0000
@@ -378,7 +378,7 @@ function system_main_admin_page($arg = N
 function system_admin_menu_block($item) {
   $map = arg(NULL);
   $content = array();
-  $result = db_query('SELECT * FROM {menu} WHERE depth = %d AND %d < mleft AND mright < %d ORDER BY mleft', $item->depth + 1, $item->mleft, $item->mright);
+  $result = db_query('SELECT * FROM {menu} WHERE depth = %d AND %d < mleft AND mright < %d AND visible = 1 ORDER BY mleft', $item->depth + 1, $item->mleft, $item->mright);
   while ($item = db_fetch_object($result)) {
     _menu_translate($item, $map, MENU_RENDER_LINK);
     if (!$item->access) {

