diff --git a/shell/modules/help.py.in b/shell/modules/help.py.in
index c6a59ea53a..12cda4d8e7 100644
--- a/shell/modules/help.py.in
+++ b/shell/modules/help.py.in
@@ -1,282 +1,274 @@
 # Copyright (C) 2008 Dejan Muhamedagic <dmuhamedagic@suse.de>
 # 
 # This program is free software; you can redistribute it and/or
 # modify it under the terms of the GNU General Public
 # License as published by the Free Software Foundation; either
 # version 2.1 of the License, or (at your option) any later version.
 # 
 # This software is distributed in the hope that it will be useful,
 # but WITHOUT ANY WARRANTY; without even the implied warranty of
 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 # General Public License for more details.
 # 
 # You should have received a copy of the GNU General Public
 # License along with this library; if not, write to the Free Software
 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 #
 
 import os
 import re
 from cache import WCache
 from utils import odict, page_string
 from msg import *
 
 #
 # help or make users feel less lonely
 #
 def add_shorthelp(topic,shorthelp,topic_help):
     '''
     Join topics ("%s,%s") if they share the same short
     description.
     '''
     for i in range(len(topic_help)):
         if topic_help[i][1] == shorthelp:
             topic_help[i][0] = "%s,%s" % (topic_help[i][0], topic)
             return
     topic_help.append([topic, shorthelp])
 def dump_short_help(help_tab):
     topic_help = []
     for topic in help_tab:
         if topic == '.':
             continue
         # with odict, for whatever reason, python parses differently:
         # help_tab["..."] = ("...","...") and
         # help_tab["..."] = ("...","""
         # ...""")
         # a parser bug?
         if type(help_tab[topic][0]) == type(()):
             shorthelp = help_tab[topic][0][0]
         else:
             shorthelp = help_tab[topic][0]
         add_shorthelp(topic,shorthelp,topic_help)
     for t,d in topic_help:
         print "\t%-16s %s" % (t,d)
 def overview(help_tab):
     print ""
     print help_tab['.'][1]
     print ""
     print "Available commands:"
     print ""
     dump_short_help(help_tab)
     print ""
 def topic_help(help_tab,topic):
     if topic not in help_tab:
         print "There is no help for topic %s" % topic
         return
     if type(help_tab[topic][0]) == type(()):
         shorthelp = help_tab[topic][0][0]
         longhelp = help_tab[topic][0][1]
     else:
         shorthelp = help_tab[topic][0]
         longhelp = help_tab[topic][1]
     if longhelp:
         page_string(longhelp)
     else:
         print shorthelp
 def cmd_help(help_tab,topic = ''):
     "help!"
     # help_tab is an odict (ordered dictionary):
     # help_tab[topic] = (short_help,long_help)
     # topic '.' is a special entry for the top level
     if not help_tab:
         common_info("sorry, help not available")
         return
     if not topic:
         overview(help_tab)
     else:
         topic_help(help_tab,topic)
 
+def is_level(s):
+    return len(s.split("_")) == 2
+
 def help_short(s):
     r = re.search("help_[^,]+,(.*)\]\]", s)
     return r and r.group(1) or ''
 
 class HelpSystem(object):
     '''
     The help system. All help is in the following form in the
     manual:
     [[cmdhelp_<level>_<cmd>,<short help text>]]
     === ...
     Long help text.
     ...
     [[cmdhelp_<level>_<cmd>,<short help text>]]
 
     Help for the level itself is like this:
 
     [[cmdhelp_<level>,<short help text>]]
     '''
     help_text_file = "@datadir@/@PACKAGE@/crm_cli.txt"
     index_file = "%s/%s" % (os.getenv("HOME"),".crm_help_index")
     def __init__(self):
         self.key_pos = {}
-        self.key_list = []
+        self.leveld = {}
         self.no_help_file = False  # don't print repeatedly messages
         self.bad_index = False  # don't print repeatedly warnings for bad index
     def open_file(self,name,mode):
         try:
             f = open(name,mode)
             return f
         except IOError,msg:
             common_err("%s open: %s"%(name,msg))
             common_err("extensive help system is not available")
             self.no_help_file = True
             return None
     def drop_index(self):
         common_info("removing index")
         os.unlink(self.index_file)
         self.key_pos = {}
-        self.key_list = []
+        self.leveld = {}
         self.bad_index = True
     def mk_index(self):
         '''
         Prepare an index file, sorted by topic, with seek positions
         Do we need a hash on content?
         '''
         if self.no_help_file:
             return False
         crm_help_v = os.getenv("CRM_HELP_FILE")
         if crm_help_v:
             self.help_text_file = crm_help_v
         help_f = self.open_file(self.help_text_file,"r")
         if not help_f:
             return False
         idx_f = self.open_file(self.index_file,"w")
         if not idx_f:
             return False
         common_info("building help index")
-        key_pos = {}
+        key_pos = odict()
         while 1:
             pos = help_f.tell()
             s = help_f.readline()
             if not s:
                 break
             if s.startswith("[["):
                 r = re.search(r'..([^,]+),', s)
                 if r:
                     key_pos[r.group(1)] = pos
         help_f.close()
-        l = key_pos.keys()
-        l.sort()
-        for key in l:
+        for key in key_pos:
             print >>idx_f, '%s %d' % (key,key_pos[key])
         idx_f.close()
         return True
     def is_index_old(self):
         try:
             t_idx = os.path.getmtime(self.index_file)
         except:
             return True
         try:
             t_help = os.path.getmtime(self.help_text_file)
         except:
             return True
         return t_help > t_idx
     def load_index(self):
         if self.is_index_old():
             self.mk_index()
         self.key_pos = {}
+        self.leveld = {}
         idx_f = self.open_file(self.index_file,"r")
         if not idx_f:
             return False
+        cur_lvl = ''
         for s in idx_f:
             a = s.split()
             if len(a) != 2:
                 if not self.bad_index:
                     common_err("index file corrupt")
                     idx_f.close()
                     self.drop_index()
                     return self.load_index() # this runs only once
                 return False
-            self.key_pos[a[0]] = long(a[1])
+            key = a[0]
+            fpos = long(a[1])
+            if key.startswith("cmdhelp_"):
+                if is_level(key):
+                    if key != cur_lvl:
+                        cur_lvl = key
+                        self.leveld[cur_lvl] = []
+                else:
+                    self.leveld[cur_lvl].append(key)
+            self.key_pos[key] = fpos
         idx_f.close()
-        self.key_list = self.key_pos.keys()
-        self.key_list.sort()
         return True
     def __filter(self,s):
         if '<<' in s:
             return re.sub(r'<<[^,]+,(.+)>>', r'\1', s)
         else:
             return s
-    def __find_key(self,key):
-        low = 0
-        high = len(self.key_list)-1
-        while low <= high:
-            mid = (low + high)/2
-            if self.key_list[mid] > key:
-                high = mid - 1
-            elif self.key_list[mid] < key:
-                low = mid + 1
-            else:
-                return mid
-        return -1
     def __load_help_one(self,key,skip = 2):
         longhelp = ''
         self.help_f.seek(self.key_pos[key])
         shorthelp = help_short(self.help_f.readline())
         for i in range(skip-1):
             self.help_f.readline()
         l = []
         for s in self.help_f:
             if s.startswith("[[") or s.startswith("="):
                 break
             l.append(self.__filter(s))
         if l and l[-1] == '\n':  # drop the last line of empty
             l.pop()
         if l:
             longhelp = ''.join(l)
         if not shorthelp or not longhelp:
             if not self.bad_index:
                 common_warn("help topic %s not found" % key)
                 self.drop_index()
         return shorthelp,longhelp
     def cmdhelp(self,s):
         if not self.key_pos and not self.load_index():
             return None,None
         if not s in self.key_pos:
             if not self.bad_index:
                 common_warn("help topic %s not found" % s)
                 self.drop_index()
             return None,None
         return self.__load_help_one(s)
     def __load_level(self,lvl):
         '''
         For the given level, create a help table.
         '''
         if wcache.is_cached("lvl_help_tab_%s" % lvl):
             return wcache.retrieve("lvl_help_tab_%s" % lvl)
         if not self.key_pos and not self.load_index():
             return None
         self.help_f = self.open_file(self.help_text_file,"r")
         if not self.help_f:
             return None
         lvl_s = "cmdhelp_%s" % lvl
-        if not lvl_s in self.key_pos:
+        if not lvl_s in self.leveld:
             if not self.bad_index:
                 common_warn("help table for level %s not found" % lvl)
                 self.drop_index()
             return None
         common_debug("loading help table for level %s" % lvl)
         help_tab = odict()
         help_tab["."] = self.__load_help_one(lvl_s)
-        lvl_idx = self.__find_key(lvl_s)
-        lvl_idx += 1
-        while lvl_idx < len(self.key_list):
-            key = self.key_list[lvl_idx]
-            if not key.startswith(lvl_s + "_"):
-                break
+        for key in self.leveld[lvl_s]:
             cmd = key[len(lvl_s)+1:]
             help_tab[cmd] = self.__load_help_one(key)
-            lvl_idx += 1
         self.help_f.close()
         help_tab["quit"] = ("exit the program", "")
         help_tab["help"] = ("show help", "")
         help_tab["end"] = ("go back one level", "")
         return help_tab
     def load_level(self,lvl):
         help_tab = self.__load_level(lvl)
         if self.bad_index: # try again
             help_tab = self.__load_level(lvl)
         return wcache.store("lvl_help_tab_%s" % lvl, help_tab)
 
 wcache = WCache.getInstance()
 
 # vim:ts=4:sw=4:et: