diff --git a/man/gnt-instance.sgml b/man/gnt-instance.sgml
index d572c64930abd545c7c7389e7261f7775583b0ee..c2a3f5f177ad1426a37449da2a76b31f48081297 100644
--- a/man/gnt-instance.sgml
+++ b/man/gnt-instance.sgml
@@ -424,12 +424,69 @@
         <cmdsynopsis>
           <command>startup</command>
           <arg>--extra=<replaceable>PARAMS</replaceable></arg>
-          <arg choice="req"><replaceable>instance</replaceable></arg>
+          <sbr>
+          <group choice="opt">
+            <arg>--instance</arg>
+            <arg>--node</arg>
+            <arg>--primary</arg>
+            <arg>--secondary</arg>
+            <arg>--all</arg>
+          </group>
+          <sbr>
+          <arg choice="opt"
+          rep="repeat"><replaceable>name</replaceable></arg>
         </cmdsynopsis>
 
         <para>
-          Starts an instance. The node where to start the instance is
-          taken from the configuration.
+          Starts one or more instances, depending on the
+          <option>--by-*</option> mode. The four available modes are:
+          <variablelist>
+            <varlistentry>
+              <term><option>--instance</option></term>
+              <listitem>
+                <simpara>will start the instances given as arguments
+                (at least one argument required); this is the default
+                selection</simpara>
+              </listitem>
+            </varlistentry>
+            <varlistentry>
+              <term>--node</term>
+              <listitem>
+                <simpara>will start the instances who have the given
+                node as either primary or secondary</simpara>
+              </listitem>
+            </varlistentry>
+            <varlistentry>
+              <term><option>--primary</option></term>
+              <listitem>
+                <simpara>will start all instances whose primary node
+                is in the list of nodes passed as arguments (at least
+                one node required)</simpara>
+              </listitem>
+            </varlistentry>
+            <varlistentry>
+              <term><option>--secondary</option></term>
+              <listitem>
+                <simpara>will start all instances whose secondary node
+                is in the list of nodes passed as arguments (at least
+                one node required)</simpara>
+              </listitem>
+            </varlistentry>
+            <varlistentry>
+              <term>--all</term>
+              <listitem>
+                <simpara>will start all instances in the cluster (no
+                arguments accepted)</simpara>
+              </listitem>
+            </varlistentry>
+          </variablelist>
+        </para>
+
+        <para>
+          Note that although you can pass more than one
+          <option>--by-</option> option, the last one wins, so in
+          order to guarantee the desired result, don't pass more than
+          one such option.
         </para>
 
         <para>
@@ -446,6 +503,8 @@
           <screen>
 # gnt-instance start instance1.example.com
 # gnt-instance start --extra single test1.example.com
+# gnt-instance start --by-node node1.example.com node2.example.com
+# gnt-instance start --by-cluster
           </screen>
         </para>
       </refsect3>
@@ -455,20 +514,40 @@
 
         <cmdsynopsis>
           <command>shutdown</command>
-          <arg choice="req"><replaceable>instance</replaceable></arg>
+          <sbr>
+          <group choice="opt">
+            <arg>--instance</arg>
+            <arg>--node</arg>
+            <arg>--primary</arg>
+            <arg>--secondary</arg>
+            <arg>--all</arg>
+          </group>
+          <sbr>
+
+          <arg choice="opt"
+          rep="repeat"><replaceable>name</replaceable></arg>
         </cmdsynopsis>
 
         <para>
-          Stops the instance. If the instance cannot be cleanly
-          stopped during a hardcoded interval (currently 2 minutes),
-          it will forcibly stop the instance (equivalent to switching
-          off the power on a physical machine).
+          Stops one or more instances. If the instance cannot be
+          cleanly stopped during a hardcoded interval (currently 2
+          minutes), it will forcibly stop the instance (equivalent to
+          switching off the power on a physical machine).
+        </para>
+
+        <para>
+          The <option>--instance</option>, <option>--node</option>,
+          <option>--primary</option>, <option>--secondary</option> and
+          <option>--all</option> options are similar as for the
+          <command>startup</command> command and they influence the
+          actual instances being shutodnw.
         </para>
 
         <para>
           Example:
           <screen>
 # gnt-instance shutdown instance1.example.com
+# gnt-instance shutdown --by-cluster
           </screen>
         </para>
       </refsect3>
diff --git a/scripts/gnt-instance b/scripts/gnt-instance
index a408d74e320da2676b5f57c75f745bee7d787e6e..0f12d491ca920862067ffdb343ce452ce625bb88 100755
--- a/scripts/gnt-instance
+++ b/scripts/gnt-instance
@@ -21,6 +21,7 @@
 
 import sys
 import os
+import itertools
 from optparse import make_option
 from cStringIO import StringIO
 
@@ -29,6 +30,73 @@ from ganeti import opcodes
 from ganeti import logger
 from ganeti import constants
 from ganeti import utils
+from ganeti import errors
+
+
+_SHUTDOWN_CLUSTER = "cluster"
+_SHUTDOWN_NODES_BOTH = "nodes"
+_SHUTDOWN_NODES_PRI = "nodes-pri"
+_SHUTDOWN_NODES_SEC = "nodes-sec"
+_SHUTDOWN_INSTANCES = "instances"
+
+def _ExpandMultiNames(mode, names):
+  """Expand the given names using the passed mode.
+
+  Args:
+    - mode, which can be one of _SHUTDOWN_CLUSTER, _SHUTDOWN_NODES_BOTH,
+      _SHUTDOWN_NODES_PRI, _SHUTDOWN_NODES_SEC or _SHUTDOWN_INSTANCES
+    - names, which is a list of names; for cluster, it must be empty,
+      and for node and instance it must be a list of valid item
+      names (short names are valid as usual, e.g. node1 instead of
+      node1.example.com)
+
+  For _SHUTDOWN_CLUSTER, all instances will be returned. For
+  _SHUTDOWN_NODES_PRI/SEC, all instances having those nodes as
+  primary/secondary will be shutdown. For _SHUTDOWN_NODES_BOTH, all
+  instances having those nodes as either primary or secondary will be
+  returned. For _SHUTDOWN_INSTANCES, the given instances will be
+  returned.
+
+  """
+  if mode == _SHUTDOWN_CLUSTER:
+    if names:
+      raise errors.OpPrereqError("Cluster filter mode takes no arguments")
+    op = opcodes.OpQueryInstances(output_fields=["name"], names=[])
+    idata = SubmitOpCode(op)
+    inames = [row[0] for row in idata]
+
+  elif mode in (_SHUTDOWN_NODES_BOTH,
+                _SHUTDOWN_NODES_PRI,
+                _SHUTDOWN_NODES_SEC):
+    if not names:
+      raise errors.OpPrereqError("No node names passed")
+    op = opcodes.OpQueryNodes(output_fields=["name", "pinst_list",
+                                             "sinst_list"], names=names)
+    ndata = SubmitOpCode(op)
+    ipri = [row[1] for row in ndata]
+    pri_names = list(itertools.chain(*ipri))
+    isec = [row[2] for row in ndata]
+    sec_names = list(itertools.chain(*isec))
+    if mode == _SHUTDOWN_NODES_BOTH:
+      inames = pri_names + sec_names
+    elif mode == _SHUTDOWN_NODES_PRI:
+      inames = pri_names
+    elif mode == _SHUTDOWN_NODES_SEC:
+      inames = sec_names
+    else:
+      raise errors.ProgrammerError("Unhandled shutdown type")
+
+  elif mode == _SHUTDOWN_INSTANCES:
+    if not names:
+      raise errors.OpPrereqError("No instance names passed")
+    op = opcodes.OpQueryInstances(output_fields=["name"], names=names)
+    idata = SubmitOpCode(op)
+    inames = [row[0] for row in idata]
+
+  else:
+    raise errors.OpPrereqError("Unknown mode '%s'" % mode)
+
+  return inames
 
 
 def ListInstances(opts, args):
@@ -209,10 +277,17 @@ def StartupInstance(opts, args):
     args - list containing a single element, the instance name
 
   """
-  instance_name = args[0]
-  op = opcodes.OpStartupInstance(instance_name=instance_name, force=opts.force,
-                                 extra_args=opts.extra_args)
-  SubmitOpCode(op)
+  if opts.multi_mode is None:
+    opts.multi_mode = _SHUTDOWN_INSTANCES
+  inames = _ExpandMultiNames(opts.multi_mode, args)
+  multi_on = len(inames) > 1
+  for name in inames:
+    op = opcodes.OpStartupInstance(instance_name=name,
+                                   force=opts.force,
+                                   extra_args=opts.extra_args)
+    if multi_on:
+      logger.ToStdout("Starting up %s" % name)
+    SubmitOpCode(op)
   return 0
 
 
@@ -224,9 +299,15 @@ def ShutdownInstance(opts, args):
     args - list containing a single element, the instance name
 
   """
-  instance_name = args[0]
-  op = opcodes.OpShutdownInstance(instance_name=instance_name)
-  SubmitOpCode(op)
+  if opts.multi_mode is None:
+    opts.multi_mode = _SHUTDOWN_INSTANCES
+  inames = _ExpandMultiNames(opts.multi_mode, args)
+  multi_on = len(inames) > 1
+  for name in inames:
+    op = opcodes.OpShutdownInstance(instance_name=name)
+    if multi_on:
+      logger.ToStdout("Shutting down %s" % name)
+    SubmitOpCode(op)
   return 0
 
 
@@ -455,6 +536,28 @@ node_opt = make_option("-n", "--node", dest="node", help="Target node",
 os_opt = cli_option("-o", "--os-type", dest="os", help="What OS to run",
                     metavar="<os>")
 
+# multi-instance selection options
+m_pri_node_opt = make_option("--primary", dest="multi_mode",
+                             help="Filter by nodes (primary only)",
+                             const=_SHUTDOWN_NODES_PRI, action="store_const")
+
+m_sec_node_opt = make_option("--secondary", dest="multi_mode",
+                             help="Filter by nodes (secondary only)",
+                             const=_SHUTDOWN_NODES_SEC, action="store_const")
+
+m_node_opt = make_option("--node", dest="multi_mode",
+                         help="Filter by nodes (primary and secondary)",
+                         const=_SHUTDOWN_NODES_BOTH, action="store_const")
+
+m_clust_opt = make_option("--all", dest="multi_mode",
+                          help="Select all instances in the cluster",
+                          const=_SHUTDOWN_CLUSTER, action="store_const")
+
+m_inst_opt = make_option("--instance", dest="multi_mode",
+                         help="Filter by instance name [default]",
+                         const=_SHUTDOWN_INSTANCES, action="store_const")
+
+
 # this is defined separately due to readability only
 add_opts = [
   DEBUG_OPT,
@@ -555,13 +658,17 @@ commands = {
                           default=None, type="string", metavar="<bridge>")
               ],
              "<instance>", "Alters the parameters of an instance"),
-  'shutdown': (ShutdownInstance, ARGS_ONE, [DEBUG_OPT],
+  'shutdown': (ShutdownInstance, ARGS_ANY,
+               [DEBUG_OPT, m_node_opt, m_pri_node_opt, m_sec_node_opt,
+                m_clust_opt, m_inst_opt],
                "<instance>", "Stops an instance"),
-  'startup': (StartupInstance, ARGS_ONE,
+  'startup': (StartupInstance, ARGS_ANY,
               [DEBUG_OPT, FORCE_OPT,
                make_option("-e", "--extra", dest="extra_args",
                            help="Extra arguments for the instance's kernel",
                            default=None, type="string", metavar="<PARAMS>"),
+               m_node_opt, m_pri_node_opt, m_sec_node_opt,
+               m_clust_opt, m_inst_opt,
                ],
             "<instance>", "Starts an instance"),
   'activate-disks': (ActivateDisks, ARGS_ONE, [DEBUG_OPT],