[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] Fix deadlock in XendDomainInfo when a domain is cleaned up. We are renaming
# HG changeset patch # User emellor@ewan # Node ID 067b9aacb6c2c0920829f925352d66b4783b8f2c # Parent 00a24908057f3b5db5669be346ba41cb10367362 Fix deadlock in XendDomainInfo when a domain is cleaned up. We are renaming the domain, to make it clear that it is a zombie, but this renaming cannot check the uniqueness of the new name, because this causes a deadlock with XendDomain. Instead, we allow the name to be non-unique for the case of zombie domains. Change the locking in waitForShutdown and state_set to be robust in the face of exceptions. Rename the STATE_VM_ constants to STATE_DOM_. Signed-off-by: Ewan Mellor <ewan@xxxxxxxxxxxxx> diff -r 00a24908057f -r 067b9aacb6c2 tools/python/xen/xend/XendDomain.py --- a/tools/python/xen/xend/XendDomain.py Wed Oct 12 09:08:01 2005 +++ b/tools/python/xen/xend/XendDomain.py Wed Oct 12 09:11:35 2005 @@ -57,7 +57,7 @@ # So we stuff the XendDomain instance (self) into xroot's components. xroot.add_component("xen.xend.XendDomain", self) self.domains = {} - self.domains_lock = threading.Condition() + self.domains_lock = threading.RLock() self.watchReleaseDomain() self.domains_lock.acquire() @@ -318,7 +318,7 @@ n = len(matching) if n == 1: return matching[0] - elif n > 1: + elif n > 1 and not d.isTerminated(): log.error('Name uniqueness has been violated for name %s! ' 'Recovering by renaming:', name) for d in matching: diff -r 00a24908057f -r 067b9aacb6c2 tools/python/xen/xend/XendDomainInfo.py --- a/tools/python/xen/xend/XendDomainInfo.py Wed Oct 12 09:08:01 2005 +++ b/tools/python/xen/xend/XendDomainInfo.py Wed Oct 12 09:11:35 2005 @@ -78,8 +78,8 @@ "rename-restart" ] -STATE_VM_OK = "ok" -STATE_VM_TERMINATED = "terminated" +STATE_DOM_OK = 1 +STATE_DOM_SHUTDOWN = 2 """Flag for a block device backend domain.""" SIF_BLK_BE_DOMAIN = (1<<4) @@ -293,7 +293,7 @@ restart = get_cfg('restart') if restart: def handle_restart(event, val): - if not event in result: + if result[event] is None: result[event] = val if restart == "onreboot": @@ -384,7 +384,7 @@ self.console_channel = None self.console_mfn = None - self.state = STATE_VM_OK + self.state = STATE_DOM_OK self.state_updated = threading.Condition() self.refresh_shutdown_lock = threading.Condition() @@ -708,7 +708,7 @@ self.clearRestart() if reason == 'suspend': - self.state_set(STATE_VM_TERMINATED) + self.state_set(STATE_DOM_SHUTDOWN) # Don't destroy the domain. XendCheckpoint will do # this once it has finished. elif reason in ['poweroff', 'reboot']: @@ -821,19 +821,31 @@ def state_set(self, state): self.state_updated.acquire() - if self.state != state: - self.state = state - self.state_updated.notifyAll() - self.state_updated.release() + try: + if self.state != state: + self.state = state + self.state_updated.notifyAll() + finally: + self.state_updated.release() ## public: def waitForShutdown(self): self.state_updated.acquire() - while self.state == STATE_VM_OK: - self.state_updated.wait() - self.state_updated.release() + try: + while self.state == STATE_DOM_OK: + self.state_updated.wait() + finally: + self.state_updated.release() + + + def isShutdown(self): + self.state_updated.acquire() + try: + return self.state == STATE_DOM_SHUTDOWN + finally: + self.state_updated.release() def __str__(self): @@ -1065,11 +1077,11 @@ try: if not self.info['name'].startswith(ZOMBIE_PREFIX): - self.info['name'] = self.generateZombieName() + self.info['name'] = ZOMBIE_PREFIX + self.info['name'] except: log.exception("Renaming Zombie failed.") - self.state_set(STATE_VM_TERMINATED) + self.state_set(STATE_DOM_SHUTDOWN) def cleanupVm(self): @@ -1274,7 +1286,7 @@ log.info("Preserving dead domain %s (%d).", self.info['name'], self.domid) self.storeDom('xend/shutdown_completed', 'True') - self.state_set(STATE_VM_TERMINATED) + self.state_set(STATE_DOM_SHUTDOWN) ## public: @@ -1302,18 +1314,6 @@ return name except VmError: n += 1 - - - def generateZombieName(self): - n = 0 - name = ZOMBIE_PREFIX + self.info['name'] - while True: - try: - self.check_name(name) - return name - except VmError: - n += 1 - name = "%s%d-%s" % (ZOMBIE_PREFIX, n, self.info['name']) def configure_bootloader(self): _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |