# HG changeset patch
# User emellor@xxxxxxxxxxxxxxxxxxxxxx
# Node ID 53cff3f88e45cb5230da39f86d84b6606da0cdbb
# Parent 9558361d8040c2a6830dffba73226c7ed2f57a52
# Parent a8be51efaf46d861042e3af7575ab62a96c4b087
Merged.
diff -r 9558361d8040 -r 53cff3f88e45 tools/examples/network-bridge
--- a/tools/examples/network-bridge Fri Dec 9 11:04:55 2005
+++ b/tools/examples/network-bridge Fri Dec 9 11:05:06 2005
@@ -87,6 +87,31 @@
done
echo "ERROR converting netmask $mask to prefix"
exit 1
+}
+
+parse_kernel_ip() {
+ if egrep 'ip=[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+:' /proc/cmdline; then
+ kip=`sed -e 's!.*ip=\([0-9]\+\.[0-9]\+\.[0-9]\+\.[0-9]\+\):.*!\1!'
/proc/cmdline`
+ kmask=`sed -e 's!.*ip=[^:]*:[^:]*:[^:]*:\([^:]*\):.*!\1!'
/proc/cmdline`
+ kgate=`sed -e 's!.*ip=[^:]*:[^:]*:\([^:]*\):.*!\1!' /proc/cmdline`
+ fi
+}
+
+do_ifup() {
+ if ! ifup $1 ; then
+ if [ ${kip} ] ; then
+ # use the addresses we grocked from /proc/cmdline
+ if [ -z "${kmask}" ]; then
+ PREFIX=32
+ else
+ legacy_mask_to_prefix ${kmask}
+ fi
+ ip addr flush $1
+ ip addr add ${kip}/${PREFIX} dev $1
+ ip link set dev $1 up
+ [ ${kgate} ] && ip route add default via ${kgate}
+ fi
+ fi
}
# Usage: transfer_addrs src dst
@@ -234,14 +259,11 @@
preiftransfer ${netdev}
transfer_addrs ${netdev} ${vdev}
if ! ifdown ${netdev}; then
- # if ifup didn't work, see if we have an ip= on cmd line
- if egrep 'ip=[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+:' /proc/cmdline; then
- kip=`sed -e
's!.*ip=\([0-9]\+\.[0-9]\+\.[0-9]\+\.[0-9]\+\):.*!\1!' /proc/cmdline`
- kmask=`sed -e 's!.*ip=[^:]*:[^:]*:[^:]*:\([^:]*\):.*!\1!'
/proc/cmdline`
- kgate=`sed -e 's!.*ip=[^:]*:[^:]*:\([^:]*\):.*!\1!'
/proc/cmdline`
- ip link set ${netdev} down
- ip addr flush ${netdev}
- fi
+ # If ifdown fails, take the IP details from the kernel command
+ # line.
+ parse_kernel_ip
+ ip link set ${netdev} down
+ ip addr flush ${netdev}
fi
ip link set ${netdev} name ${pdev}
ip link set ${vdev} name ${netdev}
@@ -253,20 +275,8 @@
add_to_bridge ${bridge} ${pdev}
ip link set ${bridge} up
ip link set ${vif0} up
- ip link set ${pdev} up
- if ! ifup ${netdev} ; then
- if [ ${kip} ] ; then
- # use the addresses we grocked from /proc/cmdline
- if [ -z "${kmask}" ]; then
- PREFIX=32;
- else
- legacy_mask_to_prefix ${kmask};
- fi
- ip addr add ${kip}/${PREFIX} dev ${netdev}
- ip link set dev ${netdev} up
- [ ${kgate} ] && ip route add default via ${kgate}
- fi
- fi
+ ip link set ${pdev} up
+ do_ifup ${netdev}
else
# old style without ${vdev}
transfer_addrs ${netdev} ${bridge}
@@ -290,7 +300,9 @@
ip link set dev ${vif0} down
mac=`ip link show ${netdev} | grep 'link\/ether' | sed -e 's/.*ether
\(..:..:..:..:..:..\).*/\1/'`
transfer_addrs ${netdev} ${pdev}
- ifdown ${netdev}
+ if ! ifdown ${netdev}; then
+ parse_kernel_ip
+ fi
ip link set ${netdev} down arp off
ip link set ${netdev} addr fe:ff:ff:ff:ff:ff
ip link set ${pdev} down
@@ -303,8 +315,7 @@
ip link set ${netdev} name ${vdev}
ip link set ${pdev} name ${netdev}
- ifup ${netdev}
-
+ do_ifup ${netdev}
else
transfer_routes ${bridge} ${netdev}
ip link set ${bridge} down
diff -r 9558361d8040 -r 53cff3f88e45 tools/examples/vif-bridge
--- a/tools/examples/vif-bridge Fri Dec 9 11:04:55 2005
+++ b/tools/examples/vif-bridge Fri Dec 9 11:05:06 2005
@@ -61,9 +61,8 @@
;;
offline)
- brctl delif "$bridge" "$vif" ||
- log debug "brctl delif $bridge $vif failed"
- ifconfig "$vif" down || log debug "ifconfig $vif down failed"
+ do_without_error brctl delif "$bridge" "$vif"
+ do_without_error ifconfig "$vif" down
;;
esac
diff -r 9558361d8040 -r 53cff3f88e45 tools/examples/vif-common.sh
--- a/tools/examples/vif-common.sh Fri Dec 9 11:04:55 2005
+++ b/tools/examples/vif-common.sh Fri Dec 9 11:05:06 2005
@@ -113,7 +113,7 @@
#
function ip_of()
{
- ip addr show "$1" | sed -n 's/^.*inet \([0-9.]*\).*$/\1/p'
+ ip addr show "$1" | awk "/^.*inet.*$1\$/{print \$2}" | sed 's,/.*,,'
}
diff -r 9558361d8040 -r 53cff3f88e45 tools/examples/vif-nat
--- a/tools/examples/vif-nat Fri Dec 9 11:04:55 2005
+++ b/tools/examples/vif-nat Fri Dec 9 11:05:06 2005
@@ -155,7 +155,7 @@
;;
offline)
[ "$dhcp" != 'no' ] && dhcp_down
- ifconfig "$vif" down || true
+ do_without_error ifconfig "$vif" down
;;
esac
diff -r 9558361d8040 -r 53cff3f88e45 tools/examples/xen-hotplug-common.sh
--- a/tools/examples/xen-hotplug-common.sh Fri Dec 9 11:04:55 2005
+++ b/tools/examples/xen-hotplug-common.sh Fri Dec 9 11:05:06 2005
@@ -44,6 +44,10 @@
do_or_die() {
"$@" || fatal "$@ failed"
+}
+
+do_without_error() {
+ "$@" 2>/dev/null || log debug "$@ failed"
}
sigerr() {
@@ -121,7 +125,7 @@
while [ $retries -lt $LOCK_RETRIES ]
do
- mkdir "$lockdir" && trap "release_lock $1; sigerr" ERR &&
+ mkdir "$lockdir" 2>/dev/null && trap "release_lock $1; sigerr" ERR &&
_update_lock_info "$lockdir" && return
local new_owner=$(_lock_owner "$lockdir")
diff -r 9558361d8040 -r 53cff3f88e45 tools/python/xen/xend/server/SrvDaemon.py
--- a/tools/python/xen/xend/server/SrvDaemon.py Fri Dec 9 11:04:55 2005
+++ b/tools/python/xen/xend/server/SrvDaemon.py Fri Dec 9 11:05:06 2005
@@ -23,73 +23,37 @@
from params import *
+XEND_PROCESS_NAME = 'xend'
+
+
class Daemon:
"""The xend daemon.
"""
def __init__(self):
- self.shutdown = 0
- self.traceon = 0
+ self.traceon = False
self.tracefile = None
self.traceindent = 0
self.child = 0
-
- def read_pid(self, pidfile):
- """Read process id from a file.
-
- @param pidfile: file to read
- @return pid or 0
- """
- if os.path.isfile(pidfile) and os.path.getsize(pidfile):
- try:
- f = open(pidfile, 'r')
- try:
- return int(f.read())
- finally:
- f.close()
- except:
- return 0
- else:
- return 0
-
- def find_process(self, pid, name):
- """Search for a process.
-
- @param pid: process id
- @param name: process name
- @return: pid if found, 0 otherwise
- """
- running = 0
- if pid:
- lines = os.popen('ps %d 2>/dev/null' % pid).readlines()
- exp = '^ *%d.+%s' % (pid, name)
- for line in lines:
- if re.search(exp, line):
- running = pid
- break
- return running
-
- def cleanup_process(self, pidfile, name, kill):
- """Clean up the pidfile for a process.
+
+
+ def cleanup_xend(self, kill):
+ """Clean up the Xend pidfile.
If a running process is found, kills it if 'kill' is true.
- @param pidfile: pid file
- @param name: process name
@param kill: whether to kill the process
@return running process id or 0
"""
running = 0
- pid = self.read_pid(pidfile)
- if self.find_process(pid, name):
+ pid = read_pid(XEND_PID_FILE)
+ if find_process(pid, XEND_PROCESS_NAME):
if kill:
- os.kill(pid, 1)
+ os.kill(pid, signal.SIGTERM)
else:
running = pid
- if running == 0 and os.path.isfile(pidfile):
- os.remove(pidfile)
+ if running == 0 and os.path.isfile(XEND_PID_FILE):
+ os.remove(XEND_PID_FILE)
return running
- def cleanup_xend(self, kill):
- return self.cleanup_process(XEND_PID_FILE, "xend", kill)
def status(self):
"""Returns the status of the xend daemon.
@@ -97,15 +61,15 @@
0 Running
3 Not running
"""
- if self.cleanup_process(XEND_PID_FILE, "xend", False) == 0:
+ if self.cleanup_xend(False) == 0:
return 3
else:
return 0
- def fork_pid(self, pidfile):
- """Fork and write the pid of the child to 'pidfile'.
-
- @param pidfile: pid file
+
+ def fork_pid(self):
+ """Fork and write the pid of the child to XEND_PID_FILE.
+
@return: pid of child in parent, 0 in child
"""
@@ -113,7 +77,7 @@
if self.child:
# Parent
- pidfile = open(pidfile, 'w')
+ pidfile = open(XEND_PID_FILE, 'w')
try:
pidfile.write(str(self.child))
finally:
@@ -121,10 +85,20 @@
return self.child
+
def daemonize(self):
if not XEND_DAEMONIZE: return
+
# Detach from TTY.
+
+ # Become the group leader (already a child process)
os.setsid()
+
+ # Fork, this allows the group leader to exit,
+ # which means the child can never again regain control of the
+ # terminal
+ if os.fork():
+ os._exit(0)
# Detach from standard file descriptors, and redirect them to
# /dev/null or the log as appropriate.
@@ -164,7 +138,7 @@
# we can avoid a race condition during startup
r,w = os.pipe()
- if self.fork_pid(XEND_PID_FILE):
+ if os.fork():
os.close(w)
r = os.fdopen(r, 'r')
try:
@@ -178,8 +152,43 @@
else:
os.close(r)
# Child
+ self.daemonize()
self.tracing(trace)
- self.run(os.fdopen(w, 'w'))
+
+ # If Xend proper segfaults, then we want to restart it. Thus,
+ # we fork a child for running Xend itself, and if it segfaults
+ # (or exits any way other than cleanly) then we run it again.
+ # The first time through we want the server to write to the (r,w)
+ # pipe created above, so that we do not exit until the server is
+ # ready to receive requests. All subsequent restarts we don't
+ # want this behaviour, or the pipe will eventually fill up, so
+ # we just pass None into run in subsequent cases (by clearing w
+ # in the parent of the first fork).
+ while True:
+ pid = self.fork_pid()
+ if pid:
+ os.close(w)
+ w = False
+
+ (_, status) = os.waitpid(pid, 0)
+
+ if os.WIFEXITED(status):
+ code = os.WEXITSTATUS(status)
+ log.info('Xend exited with status %d.', code)
+ sys.exit(code)
+
+ if os.WIFSIGNALED(status):
+ sig = os.WTERMSIG(status)
+
+ if sig in (signal.SIGINT, signal.SIGTERM):
+ log.info('Xend stopped due to signal %d.', sig)
+ sys.exit(0)
+ else:
+ log.fatal(
+ 'Xend died due to signal %d! Restarting it.',
+ sig)
+ else:
+ self.run(w and os.fdopen(w, 'w') or None)
return ret
@@ -274,25 +283,17 @@
relocate.listenRelocation()
servers = SrvServer.create()
- self.daemonize()
servers.start(status)
except Exception, ex:
print >>sys.stderr, 'Exception starting xend:', ex
if XEND_DEBUG:
traceback.print_exc()
log.exception("Exception starting xend (%s)" % ex)
- status.write('1')
- status.close()
- self.exit(1)
+ if status:
+ status.write('1')
+ status.close()
+ sys.exit(1)
- def exit(self, rc=0):
- # Calling sys.exit() raises a SystemExit exception, which only
- # kills the current thread. Calling os._exit() makes the whole
- # Python process exit immediately. There doesn't seem to be another
- # way to exit a Python with running threads.
- #sys.exit(rc)
- os._exit(rc)
-
def instance():
global inst
try:
@@ -302,10 +303,47 @@
return inst
+def read_pid(pidfile):
+ """Read process id from a file.
+
+ @param pidfile: file to read
+ @return pid or 0
+ """
+ if os.path.isfile(pidfile) and os.path.getsize(pidfile):
+ try:
+ f = open(pidfile, 'r')
+ try:
+ return int(f.read())
+ finally:
+ f.close()
+ except:
+ return 0
+ else:
+ return 0
+
+
+def find_process(pid, name):
+ """Search for a process.
+
+ @param pid: process id
+ @param name: process name
+ @return: pid if found, 0 otherwise
+ """
+ running = 0
+ if pid:
+ lines = os.popen('ps %d 2>/dev/null' % pid).readlines()
+ exp = '^ *%d.+%s' % (pid, name)
+ for line in lines:
+ if re.search(exp, line):
+ running = pid
+ break
+ return running
+
+
def main(argv = None):
global XEND_DAEMONIZE
- XEND_DAEMONIZE = 0
+ XEND_DAEMONIZE = False
if argv is None:
argv = sys.argv
diff -r 9558361d8040 -r 53cff3f88e45 tools/python/xen/xend/server/SrvServer.py
--- a/tools/python/xen/xend/server/SrvServer.py Fri Dec 9 11:04:55 2005
+++ b/tools/python/xen/xend/server/SrvServer.py Fri Dec 9 11:05:06 2005
@@ -68,7 +68,8 @@
# Running the network script will spawn another process, which takes
# the status fd with it unless we set FD_CLOEXEC. Failing to do this
# causes the read in SrvDaemon to hang even when we have written here.
- fcntl.fcntl(status, fcntl.F_SETFD, fcntl.FD_CLOEXEC)
+ if status:
+ fcntl.fcntl(status, fcntl.F_SETFD, fcntl.FD_CLOEXEC)
Vifctl.network('start')
threads = []
@@ -93,8 +94,9 @@
if threads_left:
time.sleep(.5)
- status.write('0')
- status.close()
+ if status:
+ status.write('0')
+ status.close()
for t in threads:
t.join()
_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog
|