#!/usr/bin/env python
-#
-# Copyright (C) 2002 Cluster File Systems, Inc.
-# Author: Robert Read <rread@clusterfs.com>
+# Copyright (C) 2002 Cluster File Systems, Inc.
+# Author: Robert Read <rread@clusterfs.com>
# This file is part of Lustre, http://www.lustre.org.
#
#
"""
-lmc - lustre configurtion data manager
-
- Basic plan for lmc usage:
-# create nodes
-./lmc --output config.xml --node server --net server1 tcp
-./lmc --merge config.xml --node client --net client1 tcp
-
-# configure server
-./lmc --merge config.xml --node server --mds /tmp/mds1
-./lmc --merge config.xml --lov lov1 111 222 333
-./lmc --merge config.xml --node server --lov lov1 --ost /dev/name [size=9999]
+lmc - lustre configuration data manager
-# create client config
-./lmc --merge config.xml --node client --mtpt /mnt/lustre MDC_server lov1
+ See Lustre book (http://www.lustre.org/docs/lustre.pdf) for documentation on lmc.
"""
-import sys, getopt, string
+import sys, os, getopt, string, exceptions, re
import xml.dom.minidom
-from xml.dom.ext import PrettyPrint
-from xml.xpath import Evaluate
-
-DEFAULT_PORT = 888 # XXX What is the right default acceptor port to use?
-
-def usage():
- print """usage: lmc [--node --ost | --mtpt | --lov] args
-Commands:
---node node_name
- Node_name by itself it will create a new node. When used with other
- commands it specifies the node to modify
-
---net hostname nettype [port, recv_buf, send_buf]
- Nettype is either tcp, elan, or gm.
- Requires a node argument
-
---lov lov_name [mdc_name stripe_sz stripe_off pattern]
- Creates a logical volume
- When used with other commands, it specifics the lov to modify
-
---mds device [size]
- Create a MDS using the device
- Requires --node
-
---ost device [size]
- Creates an OBD/OST/OSC configuration triplet for a new device.
- When used on "host", the device will be initialized and the OST
- will be enabled. On client nodes, the OSC will be avaiable.
- Requires --node
- If --lov lov_name is used, this device is added to lov.
-
---mtpt /mnt/point mdc_name lov_name|osc_name
- Creates a client mount point.
- Requires --node
-
-Options:
---merge="xml file" Add the new objects to an existing file
---format Format the partitions if unformated
---reformat Reformat partitions (this should be an lconf arg,
- I think)
+
+def printDoc(doc, stream=sys.stdout):
+ try:
+ from xml.dom.ext import PrettyPrint
+ PrettyPrint(doc, stream)
+ except ImportError:
+ stream.write(doc.toxml())
+ stream.write("\n")
+
+
+PYMOD_DIR = "/usr/lib/lustre/python"
+
+def development_mode():
+ base = os.path.dirname(sys.argv[0])
+ if os.access(base+"/Makefile.am", os.R_OK):
+ return 1
+ return 0
+
+if not development_mode():
+ sys.path.append(PYMOD_DIR)
+
+import Lustre
+
+DEFAULT_PORT = 988
+DEFAULT_STRIPE_SZ = 1048576
+DEFAULT_STRIPE_CNT = 1
+DEFAULT_STRIPE_PATTERN = 0
+UUID_MAX_LENGTH = 31
+
+def reference():
+ print """usage: lmc --add object [object parameters]
+
+Object creation command summary:
+
+--add node
+ --node node_name
+ --timeout num
+ --upcall path
+ --lustre_upcall path
+ --portals_upcall path
+ --ptldebug debug_level
+ --subsystem subsystem_name
+
+--add net
+ --node node_name
+ --nid nid
+ --cluster_id
+ --nettype tcp|elan|gm|scimac
+ --hostaddr addr
+ --port port
+ --tcpbuf size
+ --irq_affinity 0|1
+ --router
+
+--add mds
+ --node node_name
+ --mds mds_name
+ --dev path
+ --fstype extN|ext3
+ --size size
+ --nspath
+ --journal_size size
+ --inode_size size
+
+--add lov
+ --lov lov_name
+ --mds mds_name
+ --stripe_sz num
+ --stripe_cnt num
+ --stripe_pattern num
+
+--add ost
+ --node node_name
+ --ost ost_name
+ --lov lov_name
+ --dev path
+ --size size
+ --fstype extN|ext3
+ --journal_size size
+ --inode_size size
+ --obdtype obdecho|obdfilter
+ --ostuuid uuid
+
+--add mtpt - Mountpoint
+ --node node_name
+ --path /mnt/point
+ --mds mds_name
+ --ost ost_name OR --lov lov_name
+
+--add route
+ --node nodename
+ --gw nid
+ --tgt nid
+ --lo nid
+ --hi nid
+
+--add echo_client
+ --node nodename
+
+--add mgmt - Management/monitoring service
+ --node node_name
+ --mgmt mgmt_service_name
"""
- sys.exit(1)
+
+PARAM = Lustre.Options.PARAM
+lmc_options = [
+ # lmc input/output options
+ ('reference', "Print short reference for commands."),
+ ('verbose,v', "Print system commands as they are run."),
+ ('merge,m', "Append to the specified config file.", PARAM),
+ ('output,o', "Write XML configuration into given output file. Overwrite existing content.", PARAM),
+ ('input,i', "", PARAM),
+ ('batch', "Used to execute lmc commands in batch mode.", PARAM),
+
+ # commands
+ ('add', "", PARAM),
+
+ # node options
+ ('node', "Add a new node in the cluster configuration.", PARAM),
+ ('timeout', "Set timeout to initiate recovery.", PARAM),
+ ('upcall', "Set both lustre and portals upcall scripts.", PARAM),
+ ('lustre_upcall', "Set location of lustre upcall script.", PARAM),
+ ('portals_upcall', "Set location of portals upcall script.", PARAM),
+ ('ptldebug', "Set the portals debug level", PARAM),
+ ('subsystem', "Specify which Lustre subsystems have debug output recorded in the log", PARAM),
+
+ # network
+ ('nettype', "Specify the network type. This can be tcp/elan/gm/scimac.", PARAM),
+ ('nid', "Give the network ID, e.g ElanID/IP Address as used by portals.", PARAM),
+ ('tcpbuf', "Optional argument to specify the TCP buffer size.", PARAM, "0"),
+ ('port', "Optional argument to specify the TCP port number.", PARAM, DEFAULT_PORT),
+ ('irq_affinity', "Optional argument.", PARAM, 0),
+ ('hostaddr', "", PARAM,""),
+ ('cluster_id', "Specify the cluster ID", PARAM, "0"),
+
+ # routes
+ ('route', "Add a new route for the cluster.", PARAM),
+ ('router', "Optional flag to mark a node as router."),
+ ('gw', "Specify the nid of the gateway for a route.", PARAM),
+ ('gateway_cluster_id', "", PARAM, "0"),
+ ('target_cluster_id', "", PARAM, "0"),
+ ('lo', "For a range route, this is the low value nid.", PARAM),
+ ('hi', "For a range route, this is a hi value nid.", PARAM,""),
+
+ # servers: mds and ost
+ ('mds', "Specify MDS name.", PARAM),
+ ('ost', "Specify the OST name.", PARAM,""),
+ ('osdtype', "This could obdfilter or obdecho.", PARAM, "obdfilter"),
+ ('failover', "Enable failover support on OSTs or MDS?"),
+ ('group', "", PARAM),
+ ('dev', "Path of the device on local system.", PARAM,""),
+ ('size', "Specify the size of the device if needed.", PARAM,"0"),
+ ('journal_size', "Specify new journal size for underlying ext3 file system.", PARAM,"0"),
+ ('inode_size', "Specify new inode size for underlying ext3 file system.", PARAM,"0"),
+ ('fstype', "Optional argument to specify the filesystem type.", PARAM, "ext3"),
+ ('mkfsoptions', "Optional argument to mkfs.", PARAM, ""),
+ ('ostuuid', "", PARAM,""),
+ ('nspath', "Local mount point of server namespace.", PARAM,""),
+ ('format', ""),
+
+ # clients: mountpoint and echo
+ ('echo_client', "", PARAM),
+ ('path', "Specify the mountpoint for Lustre.", PARAM),
+ ('filesystem', "Lustre filesystem name", PARAM,""),
+
+ # lov
+ ('lov', "Specify LOV name.", PARAM,""),
+ ('stripe_sz', "Specify the stripe size in bytes.", PARAM),
+ ('stripe_cnt', "Specify the number of OSTs each file should be striped on.", PARAM, 0),
+ ('stripe_pattern', "Specify the stripe pattern. RAID 0 is the only one currently supported.", PARAM, 0),
+
+ # cobd
+ ('real_obd', "", PARAM),
+ ('cache_obd', "", PARAM),
+
+ ('mgmt', "Specify management/monitoring service name.", PARAM, ""),
+ ]
def error(*args):
msg = string.join(map(str,args))
+ raise OptionError("Error: " + msg)
+
+def panic(cmd, msg):
+ print "! " + cmd
print msg
sys.exit(1)
+
+
+def warning(*args):
+ msg = string.join(map(str,args))
+ print "Warning: ", msg
#
# manage names and uuids
names[ret] = 1
return ret
-def get_uuid(name):
- return "%s_UUID" % (name)
+def new_uuid(name):
+ ctr = 2
+ ret = "%s_UUID" % (name)
+ if len(ret) > UUID_MAX_LENGTH:
+ ret = ret[-UUID_MAX_LENGTH:]
+ while uuids.has_key(ret):
+ ret = "%s_UUID_%d" % (name, ctr)
+ ctr = 1 + ctr
+ if len(ret) > UUID_MAX_LENGTH:
+ ret = ret[-UUID_MAX_LENGTH:]
+ uuids[ret] = 1
+ return ret
+
+
+ldlm_name = 'ldlm'
+ldlm_uuid = 'ldlm_UUID'
def new_lustre(dom):
"""Create a new empty lustre document"""
- str = """<lustre> </lustre>"""
+ # adding ldlm here is a bit of a hack, but one is enough.
+ str = """<lustre version="%s">
+ <ldlm name="%s" uuid="%s"/>
+ </lustre>""" % (Lustre.CONFIG_VERSION, ldlm_name, ldlm_uuid)
return dom.parseString(str)
names = {}
uuids = {}
-def init_names(lustre):
+
+def init_names(doc):
"""initialize auto-name generation tables"""
global names, uuids
# get all elements that contain a name attribute
- for n in Evaluate("//@name/..", lustre):
- names[n.getAttribute("name")] = 1
- uuids[n.getAttribute("uuid")] = 1
-
+ for n in doc.childNodes:
+ if n.nodeType == n.ELEMENT_NODE:
+ if getName(n):
+ names[getName(n)] = 1
+ uuids[getUUID(n)] = 1
+ init_names(n)
+
+def get_format_flag(options):
+ if options.format:
+ return 'yes'
+ return 'no'
+
+############################################################
+# Build config objects using DOM
+#
class GenConfig:
doc = None
dom = None
def newService(self, tag, name, uuid):
""" create a new service elmement, which requires name and uuid attributes """
new = self.doc.createElement(tag)
- new.setAttribute("name", name);
new.setAttribute("uuid", uuid);
+ new.setAttribute("name", name);
return new
def addText(self, node, str):
node.appendChild(new)
return new
- def network(self, name, uuid, hostname, net, port=0):
+ def network(self, name, uuid, nid, cluster_id, net, hostaddr="",
+ port=0, tcpbuf=0, irq_aff=0):
"""create <network> node"""
network = self.newService("network", name, uuid)
- network.setAttribute("type", net);
- self.addElement(network, "server", hostname)
+ network.setAttribute("nettype", net);
+ self.addElement(network, "nid", nid)
+ self.addElement(network, "clusterid", cluster_id)
+ if hostaddr:
+ self.addElement(network, "hostaddr", hostaddr)
if port:
self.addElement(network, "port", "%d" %(port))
+ if tcpbuf:
+ self.addElement(network, "sendmem", "%d" %(tcpbuf))
+ self.addElement(network, "recvmem", "%d" %(tcpbuf))
+ if irq_aff:
+ self.addElement(network, "irqaffinity", "%d" %(irq_aff))
+
return network
- def node(self, name, uuid):
+ def routetbl(self, name, uuid):
+ """create <routetbl> node"""
+ rtbl = self.newService("routetbl", name, uuid)
+ return rtbl
+
+ def route(self, gw_net_type, gw, gw_cluster_id, tgt_cluster_id, lo, hi):
+ """ create one entry for the route table """
+ ref = self.doc.createElement('route')
+ ref.setAttribute("type", gw_net_type)
+ ref.setAttribute("gw", gw)
+ ref.setAttribute("gwclusterid", gw_cluster_id)
+ ref.setAttribute("tgtclusterid", tgt_cluster_id)
+ ref.setAttribute("lo", lo)
+ if hi:
+ ref.setAttribute("hi", hi)
+ return ref
+
+ def profile(self, name, uuid):
+ """ create a host """
+ profile = self.newService("profile", name, uuid)
+ return profile
+
+ def node(self, name, uuid, prof_uuid):
""" create a host """
node = self.newService("node", name, uuid)
+ node.appendChild(self.ref("profile", prof_uuid))
return node
- def obd(self, name, uuid, fs, devname, format, dev_size=0):
- obd = self.newService("obd", name, uuid)
- obd.setAttribute('type', 'obdfilter')
- self.addElement(obd, "fstype", fs)
- dev = self.addElement(obd, "device", devname)
- if (dev_size):
- dev.setAttribute("size", "%s" % (dev_size))
- self.addElement(obd, "autoformat", format)
- return obd
-
- def osc(self, name, uuid, obd_uuid, net_uuid):
- osc = self.newService("osc", name, uuid)
- osc.appendChild(self.ref("ost", net_uuid))
- osc.appendChild(self.ref("obd", obd_uuid))
- return osc
-
- def ost(self, name, uuid, obd_uuid, net_uuid):
+ def ldlm(self, name, uuid):
+ """ create a ldlm """
+ ldlm = self.newService("ldlm", name, uuid)
+ return ldlm
+
+ def osd(self, name, uuid, fs, osdtype, devname, format, ost_uuid,
+ node_uuid, dev_size=0, journal_size=0, inode_size=0, nspath="", mkfsoptions=""):
+ osd = self.newService("osd", name, uuid)
+ osd.setAttribute('osdtype', osdtype)
+ osd.appendChild(self.ref("target", ost_uuid))
+ osd.appendChild(self.ref("node", node_uuid))
+ if fs:
+ self.addElement(osd, "fstype", fs)
+ if devname:
+ dev = self.addElement(osd, "devpath", devname)
+ self.addElement(osd, "autoformat", format)
+ if dev_size:
+ self.addElement(osd, "devsize", "%s" % (dev_size))
+ if journal_size:
+ self.addElement(osd, "journalsize", "%s" % (journal_size))
+ if inode_size:
+ self.addElement(osd, "inodesize", "%s" % (inode_size))
+ if mkfsoptions:
+ self.addElement(osd, "mkfsoptions", mkfsoptions)
+ if nspath:
+ self.addElement(osd, "nspath", nspath)
+ return osd
+
+ def cobd(self, name, uuid, real_uuid, cache_uuid):
+ cobd = self.newService("cobd", name, uuid)
+ cobd.appendChild(self.ref("realobd",real_uuid))
+ cobd.appendChild(self.ref("cacheobd",cache_uuid))
+ return cobd
+
+ def ost(self, name, uuid, osd_uuid, group=""):
ost = self.newService("ost", name, uuid)
- ost.appendChild(self.ref("network", net_uuid))
- ost.appendChild(self.ref("obd", obd_uuid))
+ ost.appendChild(self.ref("active", osd_uuid))
+ if group:
+ self.addElement(ost, "group", group)
return ost
- def lov(self, name, uuid, stripe_sz, stripe_off, pattern):
+ def oss(self, name, uuid):
+ oss = self.newService("oss", name, uuid)
+ return oss
+
+ def lov(self, name, uuid, mds_uuid, stripe_sz, stripe_cnt, pattern):
lov = self.newService("lov", name, uuid)
- devs = self.addElement(lov, "devices" )
- devs.setAttribute("stripesize", stripe_sz)
- devs.setAttribute("stripeoffset", stripe_off)
- devs.setAttribute("pattern", pattern)
+ lov.appendChild(self.ref("mds", mds_uuid))
+ lov.setAttribute("stripesize", str(stripe_sz))
+ lov.setAttribute("stripecount", str(stripe_cnt))
+ lov.setAttribute("stripepattern", str(pattern))
return lov
- def mds(self, name, uuid, fs, devname, format, net_uuid, failover_uuid = "", dev_size=0 ):
+ def lovconfig(self, name, uuid, lov_uuid):
+ lovconfig = self.newService("lovconfig", name, uuid)
+ lovconfig.appendChild(self.ref("lov", lov_uuid))
+ return lovconfig
+
+ def mds(self, name, uuid, mdd_uuid, group=""):
mds = self.newService("mds", name, uuid)
- self.addElement(mds, "fstype", fs)
- dev = self.addElement(mds, "device", devname)
- if dev_size:
- dev.setAttribute("size", "%s" % (dev_size))
- self.addElement(mds, "autoformat", format)
- mds.appendChild(self.ref("network", net_uuid))
- if failover_uuid:
- mds.appendChild(self.ref("failover", failover_uuid))
+ mds.appendChild(self.ref("active",mdd_uuid))
+ if group:
+ self.addElement(mds, "group", group)
return mds
- def mdc(self, name, uuid, mds_uuid):
- mdc = self.newService("mdc", name, uuid)
- mdc.appendChild(self.ref("mds", mds_uuid))
- return mdc
-
- def mountpoint(self, name, uuid, mdc_uuid, osc_uuid, path):
- mtpt = self.newService("mtpt", name, uuid)
- mtpt.appendChild(self.ref("mdc", mdc_uuid))
- mtpt.appendChild(self.ref("osc", osc_uuid))
+ def mdsdev(self, name, uuid, fs, devname, format, node_uuid,
+ mds_uuid, dev_size=0, journal_size=0, inode_size=256,
+ nspath="", mkfsoptions=""):
+ mdd = self.newService("mdsdev", name, uuid)
+ self.addElement(mdd, "fstype", fs)
+ dev = self.addElement(mdd, "devpath", devname)
+ self.addElement(mdd, "autoformat", format)
+ if dev_size:
+ self.addElement(mdd, "devsize", "%s" % (dev_size))
+ if journal_size:
+ self.addElement(mdd, "journalsize", "%s" % (journal_size))
+ if inode_size:
+ self.addElement(mdd, "inodesize", "%s" % (inode_size))
+ if nspath:
+ self.addElement(mdd, "nspath", nspath)
+ if mkfsoptions:
+ self.addElement(mdd, "mkfsoptions", mkfsoptions)
+ mdd.appendChild(self.ref("node", node_uuid))
+ mdd.appendChild(self.ref("target", mds_uuid))
+ return mdd
+
+ def mgmt(self, mgmt_name, mgmt_uuid, node_uuid):
+ mgmt = self.newService("mgmt", mgmt_name, mgmt_uuid)
+ mgmt.appendChild(self.ref("node", node_uuid))
+ # Placeholder until mgmt-service failover.
+ mgmt.appendChild(self.ref("active", mgmt_uuid))
+ return mgmt
+
+ def mountpoint(self, name, uuid, fs_uuid, path):
+ mtpt = self.newService("mountpoint", name, uuid)
+ mtpt.appendChild(self.ref("filesystem", fs_uuid))
self.addElement(mtpt, "path", path)
return mtpt
-def findByName(lustre, name, tag = "*"):
- path = '//%s[@name="%s"]' % (tag, name)
- ret = Evaluate(path, lustre)
- if ret:
- return ret[0]
+ def filesystem(self, name, uuid, mds_uuid, obd_uuid, mgmt_uuid):
+ fs = self.newService("filesystem", name, uuid)
+ fs.appendChild(self.ref("mds", mds_uuid))
+ fs.appendChild(self.ref("obd", obd_uuid))
+ if mgmt_uuid:
+ fs.appendChild(self.ref("mgmt", mgmt_uuid))
+ return fs
+
+ def echo_client(self, name, uuid, osc_uuid):
+ ec = self.newService("echoclient", name, uuid)
+ ec.appendChild(self.ref("obd", osc_uuid))
+ return ec
+
+############################################################
+# Utilities to query a DOM tree
+# Using this functions we can treat use config information
+# directly as a database.
+def getName(n):
+ return n.getAttribute('name')
+
+def getUUID(node):
+ return node.getAttribute('uuid')
+
+
+def findByName(lustre, name, tag = ""):
+ for n in lustre.childNodes:
+ if n.nodeType == n.ELEMENT_NODE:
+ if tag and n.nodeName != tag:
+ continue
+ if getName(n) == name:
+ return n
+ else:
+ n = findByName(n, name)
+ if n: return n
+ return None
+
+
+def lookup(node, uuid):
+ for n in node.childNodes:
+ if n.nodeType == n.ELEMENT_NODE:
+ if getUUID(n) == uuid:
+ return n
+ else:
+ n = lookup(n, uuid)
+ if n: return n
return None
+
+
+def name2uuid(lustre, name, tag="", fatal=1):
+ ret = findByName(lustre, name, tag)
+ if not ret:
+ if fatal:
+ error('name2uuid:', '"'+name+'"', tag, 'element not found.')
+ else:
+ return ""
+ return getUUID(ret)
+def lookup_filesystem(lustre, mds_uuid, ost_uuid):
+ for n in lustre.childNodes:
+ if n.nodeType == n.ELEMENT_NODE and n.nodeName == 'filesystem':
+ if ref_exists(n, mds_uuid) and ref_exists(n, ost_uuid):
+ return getUUID(n)
+ return None
+
# XXX: assumes only one network element per node. will fix this
# as soon as support for routers is added
def get_net_uuid(lustre, node_name):
""" get a network uuid for a node_name """
node = findByName(lustre, node_name, "node")
if not node:
- error ("node not found:", node_name)
- net = Evaluate("./network", node)
+ error ('get_net_uuid:', '"'+node_name+'"', "node element not found.")
+ net = node.getElementsByTagName('network')
if net:
- return net[0].getAttribute("uuid")
+ return getUUID(net[0])
return None
-def lov_add_osc(gen, lov, osc_uuid):
- devs = Evaluate("devices", lov)
- if len(devs) == 1:
- devs[0].appendChild(gen.ref("osc", osc_uuid))
- else:
- error("No devices element found for LOV:", lov)
-
-def node_add_mnt(gen, node, mnt_uuid):
- node.appendChild(gen.ref("mountpoint", mnt_uuid))
-
-def node_add_mds(gen, node, mds_uuid):
- node.appendChild(gen.ref("mds", mds_uuid))
+
+def lov_add_obd(gen, lov, osc_uuid):
+ lov.appendChild(gen.ref("obd", osc_uuid))
+def ref_exists(profile, uuid):
+ elist = profile.childNodes
+ for e in elist:
+ if e.nodeType == e.ELEMENT_NODE:
+ ref = e.getAttribute('uuidref')
+ if ref == uuid:
+ return 1
+ return 0
+
+# ensure that uuid is not already in the profile
+# return true if uuid is added
+def node_add_profile(gen, node, ref, uuid):
+ refname = "%s_ref" % "profile"
+ ret = node.getElementsByTagName(refname)
+ if not ret:
+ error('node has no profile ref:', node)
+ prof_uuid = ret[0].getAttribute('uuidref')
+ profile = lookup(node.parentNode, prof_uuid)
+ if not profile:
+ error("no profile found:", prof_uuid)
+ if ref_exists(profile, uuid):
+ return 0
+ profile.appendChild(gen.ref(ref, uuid))
+ return 1
+def get_attr(dom_node, attr, default=""):
+ v = dom_node.getAttribute(attr)
+ if v:
+ return v
+ return default
+
+############################################################
+# Top level commands
#
-# Create a new obd, osc, and ost. Add them to the DOM.
-#
-def add_ost(gen, lustre, options, args):
- if len(args) < 1:
- usage()
-
- if options.has_key('node'):
- node_name = options['node']
- else:
- error("--ost requires a --node argument")
-
- if options.has_key('lov'):
- lovname = options['lov']
- else:
- lovname = ''
-
- devname = args[0]
- if len(args) > 1:
- size = args[1]
+def set_node_options(gen, node, options):
+ if options.router:
+ node.setAttribute('router', '1')
+ if options.timeout:
+ gen.addElement(node, "timeout", get_option(options, 'timeout'))
+ if options.upcall:
+ default_upcall = get_option(options, 'upcall')
else:
- size = 0
+ default_upcall = ''
+ if default_upcall or options.lustre_upcall:
+ if options.lustre_upcall:
+ gen.addElement(node, 'lustreUpcall', options.lustre_upcall)
+ else:
+ gen.addElement(node, 'lustreUpcall', default_upcall)
+ if default_upcall or options.portals_upcall:
+ if options.portals_upcall:
+ gen.addElement(node, 'portalsUpcall', options.portals_upcall)
+ else:
+ gen.addElement(node, 'portalsUpcall', default_upcall)
+ if options.ptldebug:
+ gen.addElement(node, "ptldebug", get_option(options, 'ptldebug'))
+ if options.subsystem:
+ gen.addElement(node, "subsystem", get_option(options, 'subsystem'))
+ return node
+
+def do_add_node(gen, lustre, options, node_name):
+ uuid = new_uuid(node_name)
+ prof_name = new_name("PROFILE_" + node_name)
+ prof_uuid = new_uuid(prof_name)
+ profile = gen.profile(prof_name, prof_uuid)
+ node = gen.node(node_name, uuid, prof_uuid)
+ lustre.appendChild(node)
+ lustre.appendChild(profile)
- obdname = new_name('OBD_'+ node_name)
- oscname = new_name('OSC_'+ node_name)
- ostname = new_name('OST_'+ node_name)
- obd_uuid = get_uuid(obdname)
- ost_uuid = get_uuid(ostname)
- osc_uuid = get_uuid(oscname)
+ node_add_profile(gen, node, 'ldlm', ldlm_uuid)
+ set_node_options(gen, node, options)
+ return node
- net_uuid = get_net_uuid(lustre, node_name)
- if not net_uuid:
- error("NODE: ", node_name, "not found")
- obd = gen.obd(obdname, obd_uuid, "extN", devname, "no", size)
- ost = gen.ost(ostname, ost_uuid, obd_uuid, net_uuid)
- osc = gen.osc(oscname, osc_uuid, obd_uuid, ost_uuid)
-
- if lovname:
- lov = findByName(lustre, lovname, "lov")
- if not lov:
- error("LOV:", lovname, "not found.")
- lov_add_osc(gen, lov, osc_uuid)
-
- lustre.appendChild(obd)
- lustre.appendChild(osc)
- lustre.appendChild(ost)
-
-def add_net(gen, lustre, options, args):
+def add_node(gen, lustre, options):
""" create a node with a network config """
- if len(args) < 2:
- usage()
- node_name = options['node']
- nid = args[0]
- net_type = args[1]
+ node_name = get_option(options, 'node')
+ ret = findByName(lustre, node_name, "node")
+ if ret:
+ print "Node:", node_name, "exists."
+ return
+ do_add_node(gen, lustre, options, node_name)
- if net_type == 'tcp':
- if len(args) > 2:
- port = int(args[2])
- else:
- port = DEFAULT_PORT
- # add send, recv buffer size here
- elif net_type in ('elan', 'gm'):
+
+def add_net(gen, lustre, options):
+ """ create a node with a network config """
+
+ node_name = get_option(options, 'node')
+ nid = get_option(options, 'nid')
+ cluster_id = get_option(options, 'cluster_id')
+ hostaddr = get_option(options, 'hostaddr')
+ net_type = get_option(options, 'nettype')
+
+ if net_type in ('tcp',):
+ port = get_option_int(options, 'port')
+ tcpbuf = get_option_int(options, 'tcpbuf')
+ irq_aff = get_option_int(options, 'irq_affinity')
+ elif net_type in ('elan', 'gm', 'scimac'):
port = 0
+ tcpbuf = 0
+ irq_aff = 0
else:
print "Unknown net_type: ", net_type
sys.exit(2)
ret = findByName(lustre, node_name, "node")
if not ret:
- uuid = get_uuid(node_name)
- node = gen.node(node_name, uuid)
+ node = do_add_node(gen, lustre, options, node_name)
else:
node = ret
+ set_node_options(gen, node, options)
+
net_name = new_name('NET_'+ node_name +'_'+ net_type)
- net_uuid = get_uuid(net_name)
- node.appendChild(gen.network(net_name, net_uuid, nid, net_type, port))
- lustre.appendChild(node)
+ net_uuid = new_uuid(net_name)
+ node.appendChild(gen.network(net_name, net_uuid, nid, cluster_id, net_type,
+ hostaddr, port, tcpbuf, irq_aff))
+ node_add_profile(gen, node, "network", net_uuid)
+
-def add_node(gen, lustre, options, args):
+def add_route(gen, lustre, options):
""" create a node with a network config """
- if len(args) > 1:
- usage()
- node_name = options['node']
+ node_name = get_option(options, 'node')
+ gw_net_type = get_option(options, 'nettype')
+ gw = get_option(options, 'gw')
+ gw_cluster_id = get_option(options, 'gateway_cluster_id')
+ tgt_cluster_id = get_option(options, 'target_cluster_id')
+ lo = get_option(options, 'lo')
+ hi = get_option(options, 'hi')
+ if not hi:
+ hi = lo
- ret = findByName(lustre, node_name, "node")
- if ret:
- print "Node:", node_name, "exists."
- return
- uuid = get_uuid(node_name)
- node = gen.node(node_name, uuid)
- lustre.appendChild(node)
+ node = findByName(lustre, node_name, "node")
+ if not node:
+ error (node_name, " not found.")
+
+ rlist = node.getElementsByTagName('routetbl')
+ if len(rlist) > 0:
+ rtbl = rlist[0]
+ else:
+ rtbl_name = new_name("RTBL_" + node_name)
+ rtbl_uuid = new_uuid(rtbl_name)
+ rtbl = gen.routetbl(rtbl_name, rtbl_uuid)
+ node.appendChild(rtbl)
+ node_add_profile(gen, node, "routetbl", rtbl_uuid)
+ rtbl.appendChild(gen.route(gw_net_type, gw, gw_cluster_id, tgt_cluster_id,
+ lo, hi))
+
+
+def add_mds(gen, lustre, options):
+ node_name = get_option(options, 'node')
+ mds_name = get_option(options, 'mds')
+ mdd_name = new_name("MDD_" + mds_name +"_" + node_name)
+ mdd_uuid = new_uuid(mdd_name)
+
+ mds_uuid = name2uuid(lustre, mds_name, 'mds', fatal=0)
+ if not mds_uuid:
+ mds_uuid = new_uuid(mds_name)
+ mds = gen.mds(mds_name, mds_uuid, mdd_uuid, options.group)
+ lustre.appendChild(mds)
+ else:
+ mds = lookup(lustre, mds_uuid)
+ if options.failover:
+ mds.setAttribute('failover', "1")
+ devname = get_option(options, 'dev')
+ size = get_option(options, 'size')
+ fstype = get_option(options, 'fstype')
+ journal_size = get_option(options, 'journal_size')
+ inode_size = get_option(options, 'inode_size')
+ nspath = get_option(options, 'nspath')
+ mkfsoptions = get_option(options, 'mkfsoptions')
-def add_lov(gen, lustre, options, args):
- """ create a lov """
- if len(args) < 3:
- usage()
+ node_uuid = name2uuid(lustre, node_name, 'node')
- name = options['lov']
- stripe_sz = args[0]
- stripe_off = args[1]
- pattern = args[2]
+ node = findByName(lustre, node_name, "node")
+ node_add_profile(gen, node, "mdsdev", mdd_uuid)
+ net_uuid = get_net_uuid(lustre, node_name)
+ if not net_uuid:
+ error("NODE: ", node_name, "not found")
- ret = findByName(lustre, name, "lov")
- if ret:
- error("LOV: ", name, " already exists.")
+ mdd = gen.mdsdev(mdd_name, mdd_uuid, fstype, devname,
+ get_format_flag(options), node_uuid, mds_uuid,
+ size, journal_size, inode_size, nspath, mkfsoptions)
+ lustre.appendChild(mdd)
+
- uuid = get_uuid(name)
- lov = gen.lov(name,uuid,stripe_sz, stripe_off, pattern)
- lustre.appendChild(lov)
+def add_mgmt(gen, lustre, options):
+ node_name = get_option(options, 'node')
+ node_uuid = name2uuid(lustre, node_name, 'node')
+ mgmt_name = get_option(options, 'mgmt')
+ if not mgmt_name:
+ mgmt_name = new_name('MGMT_' + node_name)
+ mgmt_uuid = name2uuid(lustre, mgmt_name, 'mgmt', fatal=0)
+ if not mgmt_uuid:
+ mgmt_uuid = new_uuid(mgmt_name)
+ mgmt = gen.mgmt(mgmt_name, mgmt_uuid, node_uuid)
+ lustre.appendChild(mgmt)
+ else:
+ mgmt = lookup(lustre, mgmt_uuid)
-def add_mtpt(gen, lustre, options, args):
- """ create mtpt on a node """
- if len(args) < 3:
- usage()
+ node = findByName(lustre, node_name, "node")
+ node_add_profile(gen, node, 'mgmt', mgmt_uuid)
- if options.has_key('node'):
- node_name = options['node']
+def add_ost(gen, lustre, options):
+ node_name = get_option(options, 'node')
+ lovname = get_option(options, 'lov')
+ osdtype = get_option(options, 'osdtype')
+
+ node_uuid = name2uuid(lustre, node_name, 'node')
+
+ if osdtype == 'obdecho':
+ fstype = ''
+ devname = ''
+ size = 0
+ fstype = ''
+ journal_size = ''
+ inode_size = ''
+ mkfsoptions = ''
else:
- error("--mtpt requires a --node argument")
+ devname = get_option(options, 'dev') # can be unset for bluearcs
+ size = get_option(options, 'size')
+ fstype = get_option(options, 'fstype')
+ journal_size = get_option(options, 'journal_size')
+ inode_size = get_option(options, 'inode_size')
+ mkfsoptions = get_option(options, 'mkfsoptions')
+
+ nspath = get_option(options, 'nspath')
- path = args[0]
- mdc_name = args[1]
- lov_name = args[2]
+ ostname = get_option(options, 'ost')
+ if not ostname:
+ ostname = new_name('OST_'+ node_name)
- name = new_name('MNT_'+ node_name)
+ osdname = new_name("OSD_" + ostname + "_" + node_name)
+ osd_uuid = new_uuid(osdname)
- ret = findByName(lustre, name, "mountpoint")
- if ret:
- error("MOUNTPOINT: ", name, " already exists.")
+ ost_uuid = name2uuid(lustre, ostname, 'ost', fatal=0)
+ if not ost_uuid:
+ ost_uuid = get_option(options, 'ostuuid')
+ if ost_uuid:
+ if lookup(lustre, ost_uuid):
+ error("Duplicate OST UUID:", ost_uuid)
+ else:
+ ost_uuid = new_uuid(ostname)
+
+ ost = gen.ost(ostname, ost_uuid, osd_uuid, options.group)
+ lustre.appendChild(ost)
+ if lovname:
+ lov = findByName(lustre, lovname, "lov")
+ if not lov:
+ error('add_ost:', '"'+lovname+'"', "lov element not found.")
+ lov_add_obd(gen, lov, ost_uuid)
+ else:
+ ost = lookup(lustre, ost_uuid)
- ret = findByName(lustre, lov_name, "lov")
- if not ret:
- ret = findByName(lustre, lov_name, "osc")
- if not ret:
- error(lov_name, "not found.")
-
- lov_uuid = ret.getAttribute("uuid")
+ if options.failover:
+ ost.setAttribute('failover', "1")
+
- ret = findByName(lustre, mdc_name, "mdc")
- if not ret:
- error("MDC: ", mdc_name, "not found.")
- mdc_uuid = ret.getAttribute("uuid")
+ osd = gen.osd(osdname, osd_uuid, fstype, osdtype, devname,
+ get_format_flag(options), ost_uuid, node_uuid, size,
+ journal_size, inode_size, nspath, mkfsoptions)
- uuid = get_uuid(name)
- mtpt = gen.mountpoint(name, uuid, mdc_uuid, lov_uuid, path)
node = findByName(lustre, node_name, "node")
- if not node:
- error('node:', node_name, "not found.")
- node_add_mnt(gen, node, uuid)
- lustre.appendChild(mtpt)
+## if node_add_profile(gen, node, 'oss', oss_uuid):
+## ossname = 'OSS'
+## oss_uuid = new_uuid(ossname)
+## oss = gen.oss(ossname, oss_uuid)
+## lustre.appendChild(oss)
-def add_mds(gen, lustre, options, args):
- if len(args) < 1:
- usage()
+ node_add_profile(gen, node, 'osd', osd_uuid)
+ lustre.appendChild(osd)
- if options.has_key('node'):
- node_name = options['node']
- else:
- error("--mds requires a --node argument")
+
+def add_cobd(gen, lustre, options):
+ node_name = get_option(options, 'node')
+ name = new_name('COBD_' + node_name)
+ uuid = new_uuid(name)
+
+ real_name = get_option(options, 'real_obd')
+ cache_name = get_option(options, 'cache_obd')
+
+ real_uuid = name2uuid(lustre, real_name, tag='obd')
+ cache_uuid = name2uuid(lustre, cache_name, tag='obd')
+
+ node = findByName(lustre, node_name, "node")
+ node_add_profile(gen, node, "cobd", uuid)
+ cobd = gen.cobd(name, uuid, real_uuid, cache_uuid)
+ lustre.appendChild(cobd)
+
+
+def add_echo_client(gen, lustre, options):
+ """ add an echo client to the profile for this node. """
+ node_name = get_option(options, 'node')
+ lov_name = get_option(options, 'ost')
+
+ node = findByName(lustre, node_name, 'node')
+
+ echoname = new_name('ECHO_'+ node_name)
+ echo_uuid = new_uuid(echoname)
+ node_add_profile(gen, node, 'echoclient', echo_uuid)
+
+ lov_uuid = name2uuid(lustre, lov_name, tag='lov', fatal=0)
+ if not lov_uuid:
+ lov_uuid = name2uuid(lustre, lov_name, tag='ost', fatal=1)
+
+ echo = gen.echo_client(echoname, echo_uuid, lov_uuid)
+ lustre.appendChild(echo)
+
+
+def add_lov(gen, lustre, options):
+ """ create a lov """
+
+ lov_orig = get_option(options, 'lov')
+ name = new_name(lov_orig)
+ if name != lov_orig:
+ warning("name:", lov_orig, "already used. using:", name)
+
+ mds_name = get_option(options, 'mds')
+ stripe_sz = get_option_int(options, 'stripe_sz')
+ stripe_cnt = get_option_int(options, 'stripe_cnt')
+ pattern = get_option_int(options, 'stripe_pattern')
+ uuid = new_uuid(name)
+
+ ret = findByName(lustre, name, "lov")
+ if ret:
+ error("LOV: ", name, " already exists.")
- devname = args[0]
- if len(args) > 1:
- size = args[1]
+ mds_uuid = name2uuid(lustre, mds_name, 'mds')
+ lov = gen.lov(name, uuid, mds_uuid, stripe_sz, stripe_cnt, pattern)
+ lustre.appendChild(lov)
+
+ # add an lovconfig entry to the active mdsdev profile
+ lovconfig_name = new_name('LVCFG_' + name)
+ lovconfig_uuid = new_uuid(lovconfig_name)
+ mds = findByName(lustre, mds_name, "mds")
+ mds.appendChild(gen.ref("lovconfig", lovconfig_uuid))
+ lovconfig = gen.lovconfig(lovconfig_name, lovconfig_uuid, uuid)
+ lustre.appendChild(lovconfig)
+
+def add_default_lov(gen, lustre, mds_name, lov_name):
+ """ create a default lov """
+
+ stripe_sz = DEFAULT_STRIPE_SZ
+ stripe_cnt = DEFAULT_STRIPE_CNT
+ pattern = DEFAULT_STRIPE_PATTERN
+ uuid = new_uuid(lov_name)
+
+ ret = findByName(lustre, lov_name, "lov")
+ if ret:
+ error("LOV: ", lov_name, " already exists.")
+
+ mds_uuid = name2uuid(lustre, mds_name, 'mds')
+ lov = gen.lov(lov_name, uuid, mds_uuid, stripe_sz, stripe_cnt, pattern)
+ lustre.appendChild(lov)
+
+ # add an lovconfig entry to the active mdsdev profile
+ lovconfig_name = new_name('LVCFG_' + lov_name)
+ lovconfig_uuid = new_uuid(lovconfig_name)
+ mds = findByName(lustre, mds_name)
+ mds.appendChild(gen.ref("lovconfig", lovconfig_uuid))
+ lovconfig = gen.lovconfig(lovconfig_name, lovconfig_uuid, uuid)
+ lustre.appendChild(lovconfig)
+
+def new_filesystem(gen, lustre, mds_uuid, obd_uuid, mgmt_uuid):
+ fs_name = new_name("FS_fsname")
+ fs_uuid = new_uuid(fs_name)
+ mds = lookup(lustre, mds_uuid)
+ mds.appendChild(gen.ref("filesystem", fs_uuid))
+ fs = gen.filesystem(fs_name, fs_uuid, mds_uuid, obd_uuid, mgmt_uuid)
+ lustre.appendChild(fs)
+ return fs_uuid
+
+def get_fs_uuid(gen, lustre, mds_name, obd_name, mgmt_name):
+ mds_uuid = name2uuid(lustre, mds_name, tag='mds')
+ obd_uuid = name2uuid(lustre, obd_name, tag='lov', fatal=0)
+ if mgmt_name:
+ mgmt_uuid = name2uuid(lustre, mgmt_name, tag='mgmt', fatal=1)
else:
- size = 0
+ mgmt_uuid = ''
+ fs_uuid = lookup_filesystem(lustre, mds_uuid, obd_uuid)
+ if not fs_uuid:
+ fs_uuid = new_filesystem(gen, lustre, mds_uuid, obd_uuid, mgmt_uuid)
+ return fs_uuid
+
+def add_mtpt(gen, lustre, options):
+ """ create mtpt on a node """
+ node_name = get_option(options, 'node')
- mds_name = new_name('MDS_'+ node_name)
- mdc_name = new_name('MDC_'+ node_name)
- mds_uuid = get_uuid(mds_name)
- mdc_uuid = get_uuid(mdc_name)
+ path = get_option(options, 'path')
+ fs_name = get_option(options, 'filesystem')
- node = findByName(lustre, node_name, "node")
- if not node:
- error('node:', node_name, 'not found')
- node_add_mds(gen, node, mds_uuid)
+ lov_name = get_option(options, 'lov')
+ ost_name = get_option(options, 'ost')
+ mds_name = get_option(options, 'mds')
+ if lov_name == '':
+ if ost_name == '':
+ error("--add mtpt requires --lov lov_name or --ost ost_name")
+ else:
+ warning("use default value for lov, due no --lov lov_name provided")
+ lov_name = new_name("lov_default")
+ add_default_lov(gen, lustre, mds_name, lov_name)
+ ost_uuid = name2uuid(lustre, ost_name, 'ost', fatal=0)
+ if not ost_uuid:
+ error('add_mtpt:', '"'+ost_name+'"', "ost element not found.")
+ lov = findByName(lustre, lov_name, "lov")
+ lov_add_obd(gen, lov, ost_uuid)
+
+ if fs_name == '':
+ mgmt_name = get_option(options, 'mgmt')
+ fs_uuid = get_fs_uuid(gen, lustre, mds_name, lov_name, mgmt_name)
+ else:
+ fs_uuid = name2uuid(lustre, fs_name, tag='filesystem')
- net_uuid = get_net_uuid(lustre, node_name)
- if not net_uuid:
- error("NODE: ", node_name, "not found")
+ name = new_name('MNT_'+ node_name)
+ ret = findByName(lustre, name, "mountpoint")
+ if ret:
+ # this can't happen, because new_name creates unique names
+ error("MOUNTPOINT: ", name, " already exists.")
- mds = gen.mds(mds_name, mds_uuid, "extN", devname, "no", net_uuid, dev_size=size)
- mdc = gen.mdc(mdc_name, mdc_uuid, mds_uuid)
- lustre.appendChild(mds)
- lustre.appendChild(mdc)
-
+ uuid = new_uuid(name)
+ mtpt = gen.mountpoint(name, uuid, fs_uuid, path)
+ node = findByName(lustre, node_name, "node")
+ if not node:
+ error('node:', node_name, "not found.")
+ node_add_profile(gen, node, "mountpoint", uuid)
+ lustre.appendChild(mtpt)
-#
+############################################################
# Command line processing
#
+class OptionError (exceptions.Exception):
+ def __init__(self, args):
+ self.args = args
+
+def get_option(options, tag):
+ """Look for tag in options hash and return the value if set. If not
+ set, then if return default it is set, otherwise exception."""
+ if options.__getattr__(tag) != None:
+ return options.__getattr__(tag)
+ else:
+ raise OptionError("--add %s requires --%s <value>" % (options.add, tag))
-def parse_cmdline(argv):
- short_opts = "ho:i:m:"
- long_opts = ["ost", "mtpt", "lov=", "node=", "mds", "net",
- "merge=", "format", "reformat", "output=",
- "in=", "help"]
- opts = []
- args = []
- options = {}
+def get_option_int(options, tag):
+ """Return an integer option. Raise exception if the value is not an int"""
+ val = get_option(options, tag)
try:
- opts, args = getopt.getopt(argv, short_opts, long_opts)
- except getopt.GetoptError:
- print "invalid opt"
- usage()
-
- for o, a in opts:
- if o in ("-h", "--help"):
- usage()
- if o in ("-o", "--output"):
- options['output'] = a
- if o == "--ost":
- options['ost'] = 1
- if o == "--mds":
- options['mds'] = 1
- if o == "--net":
- options['net'] = 1
- if o == "--mtpt":
- options['mtpt'] = 1
- if o == "--node":
- options['node'] = a
- if o == "--lov":
- options['lov'] = a
- if o in ("-m", "--merge"):
- options['merge'] = a
- if o == "--format":
- options['format'] = 1
- if o == "--reformat":
- options['reformat'] = 1
- if o in ("--in" , "-i"):
- options['in'] = a
-
- return options, args
+ n = int(val)
+ except ValueError:
+ raise OptionError("--%s <num> (value must be integer)" % (tag))
+ return n
+
+# simple class for profiling
+import time
+class chrono:
+ def __init__(self):
+ self._start = 0
+ def start(self):
+ self._stop = 0
+ self._start = time.time()
+ def stop(self, msg=''):
+ self._stop = time.time()
+ if msg:
+ self.display(msg)
+ def dur(self):
+ return self._stop - self._start
+ def display(self, msg):
+ d = self.dur()
+ str = '%s: %g secs' % (msg, d)
+ print str
+
+#################################################################
+# function cmdlinesplit used to split cmd line from batch file
+#
+def cmdlinesplit(cmdline):
+
+ double_quote = re.compile(r'"(([^"\\]|\\.)*)"')
+ single_quote = re.compile(r"'(.*?)'")
+ escaped = re.compile(r'\\(.)')
+ esc_quote = re.compile(r'\\([\\"])')
+ outside = re.compile(r"""([^\s\\'"]+)""")
+
+ arg_list = []
+ i = 0; arg = None
+ while i < len(cmdline):
+ c = cmdline[i]
+ if c == '"':
+ match = double_quote.match(cmdline, i)
+ if not match:
+ print "Unmatched double quote:", cmdline
+ sys.exit(1)
+ i = match.end()
+ if arg is None: arg = esc_quote.sub(r'\1', match.group(1))
+ else: arg = arg + esc_quote.sub(r'\1', match.group(1))
+
+ elif c == "'":
+ match = single_quote.match(cmdline, i)
+ if not match:
+ print "Unmatched single quote:", cmdline
+ sys.exit(1)
+ i = match.end()
+ if arg is None: arg = match.group(1)
+ else: arg = arg + match.group(1)
+
+ elif c == "\\":
+ match = escaped.match(cmdline, i)
+ if not match:
+ print "Unmatched backslash", cmdline
+ sys.exit(1)
+ i = match.end()
+ if arg is None: arg = match.group(1)
+ else: arg = arg + match.group(1)
+
+ elif c in string.whitespace:
+ if arg != None:
+ arg_list.append(str(arg))
+ arg = None
+ while i < len(cmdline) and cmdline[i] in string.whitespace:
+ i = i + 1
+ else:
+ match = outside.match(cmdline, i)
+ assert match
+ i = match.end()
+ if arg is None: arg = match.group()
+ else: arg = arg + match.group()
+
+ if arg != None: arg_list.append(str(arg))
+
+ return arg_list
+
+############################################################
+# Main
+#
+
+def add(devtype, gen, lustre, options):
+ if devtype == 'net':
+ add_net(gen, lustre, options)
+ elif devtype == 'mtpt':
+ add_mtpt(gen, lustre, options)
+ elif devtype == 'mds':
+ add_mds(gen, lustre, options)
+ elif devtype == 'ost':
+ add_ost(gen, lustre, options)
+ elif devtype == 'lov':
+ add_lov(gen, lustre, options)
+ elif devtype == 'route':
+ add_route(gen, lustre, options)
+ elif devtype == 'node':
+ add_node(gen, lustre, options)
+ elif devtype == 'echo_client':
+ add_echo_client(gen, lustre, options)
+ elif devtype == 'cobd':
+ add_cobd(gen, lustre, options)
+ elif devtype == 'mgmt':
+ add_mgmt(gen, lustre, options)
+ else:
+ error("unknown device type:", devtype)
+
+def do_command(gen, lustre, options, args):
+ if options.add:
+ add(options.add, gen, lustre, options)
+ else:
+ error("Missing command")
def main():
- options, args = parse_cmdline(sys.argv[1:])
+ cl = Lustre.Options("lmc", "", lmc_options)
+ try:
+ options, args = cl.parse(sys.argv[1:])
+ except Lustre.OptionError, e:
+ panic("lmc", e)
+
+ if len(args) > 0:
+ panic(string.join(sys.argv), "Unexpected extra arguments on command line: " + string.join(args))
+
+ if options.reference:
+ reference()
+ sys.exit(0)
+
outFile = '-'
- if options.has_key('merge'):
- outFile = options['merge']
- doc = xml.dom.minidom.parse(outFile)
- elif options.has_key('in'):
- doc = xml.dom.minidom.parse(options['in'])
+ if options.merge:
+ outFile = options.merge
+ if os.access(outFile, os.R_OK):
+ doc = xml.dom.minidom.parse(outFile)
+ else:
+ doc = new_lustre(xml.dom.minidom)
+ elif options.input:
+ doc = xml.dom.minidom.parse(options.input)
else:
doc = new_lustre(xml.dom.minidom)
- if options.has_key('output'):
- outFile = options['output']
+ if options.output:
+ outFile = options.output
lustre = doc.documentElement
init_names(lustre)
- lustre = doc.documentElement
if lustre.tagName != "lustre":
print "Existing config not valid."
sys.exit(1)
gen = GenConfig(doc)
- if options.has_key('ost'):
- add_ost(gen, lustre, options, args)
- elif options.has_key('mtpt'):
- add_mtpt(gen, lustre, options, args)
- elif options.has_key('mds'):
- add_mds(gen, lustre, options, args)
- elif options.has_key('net'):
- add_net(gen, lustre, options, args)
- elif options.has_key('lov'):
- add_lov(gen, lustre, options, args)
- elif options.has_key('node'):
- add_node(gen, lustre, options, args)
+
+ if options.batch:
+ fp = open(options.batch)
+ batchCommands = fp.readlines()
+ fp.close()
+ for cmd in batchCommands:
+ try:
+ options, args = cl.parse(cmdlinesplit(cmd))
+ if options.merge or options.input or options.output:
+ print "The batchfile should not contain --merge, --input or --output."
+ sys.exit(1)
+ do_command(gen, lustre, options, args)
+ except OptionError, e:
+ panic(cmd, e)
+ except Lustre.OptionError, e:
+ panic(cmd, e)
else:
- print "Missing command"
- usage()
+ try:
+ do_command(gen, lustre, options, args)
+ except OptionError, e:
+ panic(string.join(sys.argv),e)
+ except Lustre.OptionError, e:
+ panic("lmc", e)
if outFile == '-':
- PrettyPrint(doc)
+ printDoc(doc)
else:
- PrettyPrint(doc, open(outFile,"w"))
+ printDoc(doc, open(outFile,"w"))
+
if __name__ == "__main__":
main()
-
-