[CRIU,2/2] p.haul: create Virtuozzo specific dump images during final dump

Submitted by Nikita Spiridonov on May 14, 2016, 2:48 p.m.

Details

Message ID 1463237313-347740-3-git-send-email-nspiridonov@virtuozzo.com
State New
Series "p.haul: create Virtuozzo specific dump images during final dump"
Headers show

Commit Message

Nikita Spiridonov May 14, 2016, 2:48 p.m.
For Virtuozzo containers vzctl create addtional images during local
dump of the container - vz_clock_bootbased.img,
vz_clock_monotonic.img, vz_aio_max_nr.img and vz_core_pattern.img.
Need to duplicate this logic in vz module of phaul since we use
"vzctl restore" for final restore and it rely on this additional
images.

Signed-off-by: Nikita Spiridonov <nspiridonov@virtuozzo.com>
---
 phaul/p_haul_vz.py |   48 ++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 48 insertions(+), 0 deletions(-)

Patch hide | download patch | download mbox

diff --git a/phaul/p_haul_vz.py b/phaul/p_haul_vz.py
index 602bd57..3609f14 100644
--- a/phaul/p_haul_vz.py
+++ b/phaul/p_haul_vz.py
@@ -15,6 +15,8 @@  import pycriu.rpc
 vz_global_conf = "/etc/vz/vz.conf"
 vz_conf_dir = "/etc/vz/conf/"
 vzctl_bin = "vzctl"
+cgget_bin = "cgget"
+cgexec_bin = "cgexec"
 
 
 vz_cgroup_mount_map = {
@@ -150,7 +152,53 @@  class p_haul_type:
 		pass
 
 	def final_dump(self, pid, img, ccon, fs):
+		"""Perform Virtuozzo-specific final dump"""
+		self.__pre_final_dump(img)
 		criu_cr.criu_dump(self, pid, img, ccon, fs)
+		self.__post_final_dump(img)
+
+	def __pre_final_dump(self, img):
+		"""Create extra images before final dump"""
+		extra_images = (
+			("vz_clock_bootbased.img", "ve.clock_bootbased"),
+			("vz_clock_monotonic.img", "ve.clock_monotonic"),
+			("vz_aio_max_nr.img", "ve.aio_max_nr"))
+		for image_name, var_name in extra_images:
+			self.__create_cgget_extra_image(img, image_name, var_name)
+
+	def __post_final_dump(self, img):
+		"""Create extra images after final dump"""
+		extra_images = (
+			("vz_core_pattern.img", ["cat", "/proc/sys/kernel/core_pattern"]),)
+		for image_name, exec_args in extra_images:
+			self.__create_cgexec_extra_image(img, image_name, exec_args)
+
+	def __create_cgget_extra_image(self, img, image_name, var_name):
+		"""Create extra image using cgget output"""
+		proc = subprocess.Popen(
+			[cgget_bin, "-n", "-v", "-r", var_name, self._ctid],
+			stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
+		image_data = proc.communicate()[0]
+		if proc.returncode == 0:
+			self.__create_extra_image(img, image_name, image_data)
+		else:
+			logging.warning("cgget failed to create %s", image_name)
+
+	def __create_cgexec_extra_image(self, img, image_name, exec_args):
+		"""Create extra image using cgexec output"""
+		proc = subprocess.Popen(
+			[cgexec_bin, "-g", "ve:{0}".format(self._ctid)] + exec_args,
+			stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
+		image_data = proc.communicate()[0]
+		if proc.returncode == 0:
+			self.__create_extra_image(img, image_name, image_data)
+		else:
+			logging.warning("cgexec failed to create %s", image_name)
+
+	def __create_extra_image(self, img, image_name, image_data):
+		image_path = os.path.join(img.image_dir(), image_name)
+		with open(image_path, "w") as f:
+			f.write(image_data)
 
 	def final_restore(self, img, connection):
 		"""Perform Virtuozzo-specific final restore"""

Comments

Pavel Emelyanov May 16, 2016, 6:22 p.m.
On 05/14/2016 05:48 PM, Nikita Spiridonov wrote:
> For Virtuozzo containers vzctl create addtional images during local
> dump of the container - vz_clock_bootbased.img,
> vz_clock_monotonic.img, vz_aio_max_nr.img and vz_core_pattern.img.
> Need to duplicate this logic in vz module of phaul since we use
> "vzctl restore" for final restore and it rely on this additional
> images.
> 
> Signed-off-by: Nikita Spiridonov <nspiridonov@virtuozzo.com>
> ---
>  phaul/p_haul_vz.py |   48 ++++++++++++++++++++++++++++++++++++++++++++++++
>  1 files changed, 48 insertions(+), 0 deletions(-)
> 
> diff --git a/phaul/p_haul_vz.py b/phaul/p_haul_vz.py
> index 602bd57..3609f14 100644
> --- a/phaul/p_haul_vz.py
> +++ b/phaul/p_haul_vz.py
> @@ -15,6 +15,8 @@ import pycriu.rpc
>  vz_global_conf = "/etc/vz/vz.conf"
>  vz_conf_dir = "/etc/vz/conf/"
>  vzctl_bin = "vzctl"
> +cgget_bin = "cgget"
> +cgexec_bin = "cgexec"
>  
>  
>  vz_cgroup_mount_map = {
> @@ -150,7 +152,53 @@ class p_haul_type:
>  		pass
>  
>  	def final_dump(self, pid, img, ccon, fs):
> +		"""Perform Virtuozzo-specific final dump"""
> +		self.__pre_final_dump(img)
>  		criu_cr.criu_dump(self, pid, img, ccon, fs)
> +		self.__post_final_dump(img)
> +
> +	def __pre_final_dump(self, img):
> +		"""Create extra images before final dump"""
> +		extra_images = (
> +			("vz_clock_bootbased.img", "ve.clock_bootbased"),
> +			("vz_clock_monotonic.img", "ve.clock_monotonic"),
> +			("vz_aio_max_nr.img", "ve.aio_max_nr"))

Less images is better. Can all this stuff be saved in one file?

> +		for image_name, var_name in extra_images:
> +			self.__create_cgget_extra_image(img, image_name, var_name)
> +
> +	def __post_final_dump(self, img):
> +		"""Create extra images after final dump"""
> +		extra_images = (
> +			("vz_core_pattern.img", ["cat", "/proc/sys/kernel/core_pattern"]),)
> +		for image_name, exec_args in extra_images:
> +			self.__create_cgexec_extra_image(img, image_name, exec_args)
> +
> +	def __create_cgget_extra_image(self, img, image_name, var_name):
> +		"""Create extra image using cgget output"""
> +		proc = subprocess.Popen(
> +			[cgget_bin, "-n", "-v", "-r", var_name, self._ctid],
> +			stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
> +		image_data = proc.communicate()[0]

Less exec-s is better. Can we save this stuff with one call?

> +		if proc.returncode == 0:
> +			self.__create_extra_image(img, image_name, image_data)
> +		else:
> +			logging.warning("cgget failed to create %s", image_name)
> +
> +	def __create_cgexec_extra_image(self, img, image_name, exec_args):
> +		"""Create extra image using cgexec output"""
> +		proc = subprocess.Popen(
> +			[cgexec_bin, "-g", "ve:{0}".format(self._ctid)] + exec_args,
> +			stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
> +		image_data = proc.communicate()[0]
> +		if proc.returncode == 0:
> +			self.__create_extra_image(img, image_name, image_data)
> +		else:
> +			logging.warning("cgexec failed to create %s", image_name)
> +
> +	def __create_extra_image(self, img, image_name, image_data):
> +		image_path = os.path.join(img.image_dir(), image_name)
> +		with open(image_path, "w") as f:
> +			f.write(image_data)
>  
>  	def final_restore(self, img, connection):
>  		"""Perform Virtuozzo-specific final restore"""
>
Cyrill Gorcunov May 16, 2016, 6:32 p.m.
On Mon, May 16, 2016 at 09:22:48PM +0300, Pavel Emelyanov wrote:
> > +
> > +	def __pre_final_dump(self, img):
> > +		"""Create extra images before final dump"""
> > +		extra_images = (
> > +			("vz_clock_bootbased.img", "ve.clock_bootbased"),
> > +			("vz_clock_monotonic.img", "ve.clock_monotonic"),
> > +			("vz_aio_max_nr.img", "ve.aio_max_nr"))
> 
> Less images is better. Can all this stuff be saved in one file?

One per feature is preferred at the moment. Later I hope to merge
all this into CRIU custom cgroups engine, so we won't need to
carry anything.
Nikita Spiridonov May 21, 2016, 10:54 a.m.
On Mon, 2016-05-16 at 21:22 +0300, Pavel Emelyanov wrote:
> On 05/14/2016 05:48 PM, Nikita Spiridonov wrote:
> > For Virtuozzo containers vzctl create addtional images during local
> > dump of the container - vz_clock_bootbased.img,
> > vz_clock_monotonic.img, vz_aio_max_nr.img and vz_core_pattern.img.
> > Need to duplicate this logic in vz module of phaul since we use
> > "vzctl restore" for final restore and it rely on this additional
> > images.
> > 
> > Signed-off-by: Nikita Spiridonov <nspiridonov@virtuozzo.com>
> > ---
> >  phaul/p_haul_vz.py |   48 ++++++++++++++++++++++++++++++++++++++++++++++++
> >  1 files changed, 48 insertions(+), 0 deletions(-)
> > 
> > diff --git a/phaul/p_haul_vz.py b/phaul/p_haul_vz.py
> > index 602bd57..3609f14 100644
> > --- a/phaul/p_haul_vz.py
> > +++ b/phaul/p_haul_vz.py
> > @@ -15,6 +15,8 @@ import pycriu.rpc
> >  vz_global_conf = "/etc/vz/vz.conf"
> >  vz_conf_dir = "/etc/vz/conf/"
> >  vzctl_bin = "vzctl"
> > +cgget_bin = "cgget"
> > +cgexec_bin = "cgexec"
> >  
> >  
> >  vz_cgroup_mount_map = {
> > @@ -150,7 +152,53 @@ class p_haul_type:
> >  		pass
> >  
> >  	def final_dump(self, pid, img, ccon, fs):
> > +		"""Perform Virtuozzo-specific final dump"""
> > +		self.__pre_final_dump(img)
> >  		criu_cr.criu_dump(self, pid, img, ccon, fs)
> > +		self.__post_final_dump(img)
> > +
> > +	def __pre_final_dump(self, img):
> > +		"""Create extra images before final dump"""
> > +		extra_images = (
> > +			("vz_clock_bootbased.img", "ve.clock_bootbased"),
> > +			("vz_clock_monotonic.img", "ve.clock_monotonic"),
> > +			("vz_aio_max_nr.img", "ve.aio_max_nr"))
> 
> Less images is better. Can all this stuff be saved in one file?

We can, but it will complicate logic considerably. Entire patch
duplicates libvzctl logic of local dump/restore actually. I think if
such approach suitable there we can just dup it for now.

> 
> > +		for image_name, var_name in extra_images:
> > +			self.__create_cgget_extra_image(img, image_name, var_name)
> > +
> > +	def __post_final_dump(self, img):
> > +		"""Create extra images after final dump"""
> > +		extra_images = (
> > +			("vz_core_pattern.img", ["cat", "/proc/sys/kernel/core_pattern"]),)
> > +		for image_name, exec_args in extra_images:
> > +			self.__create_cgexec_extra_image(img, image_name, exec_args)
> > +
> > +	def __create_cgget_extra_image(self, img, image_name, var_name):
> > +		"""Create extra image using cgget output"""
> > +		proc = subprocess.Popen(
> > +			[cgget_bin, "-n", "-v", "-r", var_name, self._ctid],
> > +			stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
> > +		image_data = proc.communicate()[0]
> 
> Less exec-s is better. Can we save this stuff with one call?

We can replace cgget with manual reads from cgroup vfs. I don't know
suitable alternative for cgexec. Such change needed?

> 
> > +		if proc.returncode == 0:
> > +			self.__create_extra_image(img, image_name, image_data)
> > +		else:
> > +			logging.warning("cgget failed to create %s", image_name)
> > +
> > +	def __create_cgexec_extra_image(self, img, image_name, exec_args):
> > +		"""Create extra image using cgexec output"""
> > +		proc = subprocess.Popen(
> > +			[cgexec_bin, "-g", "ve:{0}".format(self._ctid)] + exec_args,
> > +			stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
> > +		image_data = proc.communicate()[0]
> > +		if proc.returncode == 0:
> > +			self.__create_extra_image(img, image_name, image_data)
> > +		else:
> > +			logging.warning("cgexec failed to create %s", image_name)
> > +
> > +	def __create_extra_image(self, img, image_name, image_data):
> > +		image_path = os.path.join(img.image_dir(), image_name)
> > +		with open(image_path, "w") as f:
> > +			f.write(image_data)
> >  
> >  	def final_restore(self, img, connection):
> >  		"""Perform Virtuozzo-specific final restore"""
> > 
>