for omf-friendly slices, make sure to umount ssh dir before trying to trash VM (in...
authorThierry Parmentelat <thierry.parmentelat@inria.fr>
Fri, 14 Jun 2013 11:42:40 +0000 (13:42 +0200)
committerThierry Parmentelat <thierry.parmentelat@inria.fr>
Fri, 14 Jun 2013 11:42:40 +0000 (13:42 +0200)
add mounting ssh directory for omf slices on lxc nodes

account.py
sliver_lxc.py
sliver_vs.py

index b15bb67..5cbd21c 100644 (file)
@@ -123,25 +123,43 @@ class Account:
     def stop(self): pass
     def is_running(self): pass
 
-    # bind mount root side dir to sliver side
-    # needs to be done before sliver starts, in the vserver case at least
-    def expose_ssh_dir (self):
+    ### this used to be a plain method but because it needs to be invoked by destroy
+    # which is a static method, they need to become static as well
+    # needs to be done before sliver starts (checked with vs and lxc)
+    @staticmethod
+    def mount_ssh_dir (slicename): return Account._manage_ssh_dir (slicename, do_mount=True)
+    @staticmethod
+    def umount_ssh_dir (slicename): return Account._manage_ssh_dir (slicename, do_mount=False)
+
+    # bind mount / umount root side dir to sliver side
+    @staticmethod
+    def _manage_ssh_dir (slicename, do_mount):
+        logger.log ("_manage_ssh_dir, requested to "+("mount" if do_mount else "umount")+" ssh dir for "+ slicename)
         try:
-            root_ssh="/home/%s/.ssh"%self.name
-            sliver_ssh="/vservers/%s/home/%s/.ssh"%(self.name,self.name)
-            # any of both might not exist yet
-            for path in [root_ssh,sliver_ssh]:
-                if not os.path.exists (path):
-                    os.mkdir(path)
-                if not os.path.isdir (path):
-                    raise Exception
-            mounts=file('/proc/mounts').read()
-            if mounts.find(sliver_ssh)<0:
-                # xxx perform mount
-                subprocess.call("mount --bind -o ro %s %s"%(root_ssh,sliver_ssh),shell=True)
-                logger.log("expose_ssh_dir: %s mounted into slice %s"%(root_ssh,self.name))
+            root_ssh="/home/%s/.ssh"%slicename
+            sliver_ssh="/vservers/%s/home/%s/.ssh"%(slicename,slicename)
+            def is_mounted (root_ssh):
+                for mount_line in file('/proc/mounts').readlines():
+                    if mount_line.find (root_ssh)>=0: return True
+                return False
+            if do_mount:
+                # any of both might not exist yet
+                for path in [root_ssh,sliver_ssh]:
+                    if not os.path.exists (path):
+                        os.mkdir(path)
+                    if not os.path.isdir (path):
+                        raise Exception
+                if not is_mounted(root_ssh):
+                    # xxx perform mount
+                    subprocess.call("mount --bind -o ro %s %s"%(root_ssh,sliver_ssh),shell=True)
+                    logger.log("_manage_ssh_dir: mounted %s into slice %s"%(root_ssh,slicename))
+            else:
+                if is_mounted (root_ssh):
+                    # xxx perform umount
+                    subprocess.call("umount %s"%(root_ssh),shell=True)
+                    logger.log("_manage_ssh_dir: umounted %s"%(root_ssh))
         except:
-            logger.log_exc("expose_ssh_dir with slice %s failed"%self.name)
+            logger.log_exc("_manage_ssh_dir with slice %s failed"%slicename)
 
 class Worker:
 
index 4aa6a21..432f426 100644 (file)
@@ -47,6 +47,9 @@ class Sliver_LXC(Sliver_Libvirt, Initscript):
             return
         # the generic /etc/init.d/vinit script is permanently refreshed, and enabled
         self.install_and_enable_vinit()
+        # expose .ssh for omf_friendly slivers
+        if 'omf_control' in self.rspec['tags']:
+            Account.mount_ssh_dir(self.name)
         Sliver_Libvirt.start (self, delay)
         # if a change has occured in the slice initscript, reflect this in /etc/init.d/vinit.slice
         self.refresh_slice_vinit()
@@ -233,6 +236,8 @@ unset pathmunge
 
     @staticmethod
     def destroy(name):
+        # umount .ssh directory - only if mounted
+        Account.umount_ssh_dir(name)
         logger.verbose ('sliver_lxc: %s destroy'%(name))
         conn = Sliver_Libvirt.getConnection(Sliver_LXC.TYPE)
 
index 1d90f16..432704c 100644 (file)
@@ -134,8 +134,15 @@ class Sliver_VS(vserver.VServer, Account, Initscript):
 
     @staticmethod
     def destroy(name):
+        # need to umount before we trash, otherwise we end up with sequels in 
+        # /vservers/slicename/ (namely in home/ )
+        # also because this is a static method we cannot check for 'omf_control'
+        # but it is no big deal as umount_ssh_dir checks before it umounts..
+        Account.umount_ssh_dir(name)
+        logger.log("sliver_vs: destroying %s"%name)
         logger.log_call(['/bin/bash','-x','/usr/sbin/vuserdel', name, ])
 
+
     def configure(self, rec):
         # in case we update nodemanager..
         self.install_and_enable_vinit()
@@ -153,25 +160,25 @@ class Sliver_VS(vserver.VServer, Account, Initscript):
     def start(self, delay=0):
         if self.rspec['enabled'] <= 0:
             logger.log('sliver_vs: not starting %s, is not enabled'%self.name)
+            return
+        logger.log('sliver_vs: %s: starting in %d seconds' % (self.name, delay))
+        time.sleep(delay)
+        # the generic /etc/init.d/vinit script is permanently refreshed, and enabled
+        self.install_and_enable_vinit()
+        # expose .ssh for omf_friendly slivers
+        if 'omf_control' in self.rspec['tags']:
+            Account.mount_ssh_dir(self.name)
+        # if a change has occured in the slice initscript, reflect this in /etc/init.d/vinit.slice
+        self.refresh_slice_vinit()
+        child_pid = os.fork()
+        if child_pid == 0:
+            # VServer.start calls fork() internally,
+            # so just close the nonstandard fds and fork once to avoid creating zombies
+            tools.close_nonstandard_fds()
+            vserver.VServer.start(self)
+            os._exit(0)
         else:
-            logger.log('sliver_vs: %s: starting in %d seconds' % (self.name, delay))
-            time.sleep(delay)
-            # the generic /etc/init.d/vinit script is permanently refreshed, and enabled
-            self.install_and_enable_vinit()
-            # expose .ssh for omf_friendly slivers
-            if 'omf_control' in self.rspec['tags']:
-                self.expose_ssh_dir()
-            # if a change has occured in the slice initscript, reflect this in /etc/init.d/vinit.slice
-            self.refresh_slice_vinit()
-            child_pid = os.fork()
-            if child_pid == 0:
-                # VServer.start calls fork() internally,
-                # so just close the nonstandard fds and fork once to avoid creating zombies
-                tools.close_nonstandard_fds()
-                vserver.VServer.start(self)
-                os._exit(0)
-            else:
-                os.waitpid(child_pid, 0)
+            os.waitpid(child_pid, 0)
 
     def stop(self):
         logger.log('sliver_vs: %s: stopping' % self.name)