[CRIU] [PATCH 07/13] parasite: Move bootstrap code into parasite-head-x86-64.S

Cyrill Gorcunov gorcunov at openvz.org
Tue Apr 17 17:55:42 EDT 2012


Inline assembly is very convenient if a couple of
instructions is used but when it grows better to
move it out of wrapper C code and write in plain
assembly, after all we need a very precise control
in bootstrap code.

Signed-off-by: Cyrill Gorcunov <gorcunov at openvz.org>
---
 Makefile.pie           |   14 +++++++++++---
 include/linkage.h      |   24 ++++++++++++++++++++++++
 include/parasite.h     |   13 ++++++++-----
 parasite-head-x86-64.S |   24 ++++++++++++++++++++++++
 parasite.c             |   28 +---------------------------
 5 files changed, 68 insertions(+), 35 deletions(-)
 create mode 100644 include/linkage.h
 create mode 100644 parasite-head-x86-64.S

diff --git a/Makefile.pie b/Makefile.pie
index a2885d7..005f0e9 100644
--- a/Makefile.pie
+++ b/Makefile.pie
@@ -1,5 +1,8 @@
 GEN-OFFSETS	:= gen-offsets.sh
 
+PASM-OBJS	+= parasite-head-x86-64.o
+PASM-SRC	+= $(patsubst %.o,%.S,$(PASM-OBJS))
+
 POBJS		+= parasite.o
 PSRCS		+= $(patsubst %.o,%.c,$(POBJS))
 
@@ -21,6 +24,11 @@ DEPS		+= $(patsubst %.o,%.d,$(POBJS))
 DEPS		+= $(patsubst %.o,%.d,$(ROBJS))
 
 PIEFLAGS	:= -fpie
+ASMFLAGS	:= -D__ASSEMBLY__
+
+$(PASM-OBJS): $(PASM-SRC)
+	$(E) "  CC      " $@
+	$(Q) $(CC) -c $(ASMFLAGS) $(CFLAGS) $(PIEFLAGS) $(patsubst %.o,%.S,$@) -o $@
 
 $(POBJS): $(PSRCS) $(PASM-OBJS)
 	$(E) "  CC      " $@
@@ -32,10 +40,10 @@ parasite-util-net.o: util-net.c
 
 POBJS		+= parasite-util-net.o
 
-$(PBLOB-BIN): $(PBLOB-LDS) $(POBJS)
+$(PBLOB-BIN): $(PBLOB-LDS) $(POBJS) $(PASM-OBJS)
 	$(E) "  GEN     " $@
-	$(Q) $(LD) --oformat=binary -T $(PBLOB-LDS) -o $(PBLOB-BIN) $(POBJS)
-	$(Q) $(LD) --oformat=elf64-x86-64 -T $(PBLOB-LDS) -o $(PBLOB-BIN).o $(POBJS)
+	$(Q) $(LD) --oformat=binary -T $(PBLOB-LDS) -o $(PBLOB-BIN) $(POBJS) $(PASM-OBJS)
+	$(Q) $(LD) --oformat=elf64-x86-64 -T $(PBLOB-LDS) -o $(PBLOB-BIN).o $(POBJS) $(PASM-OBJS)
 
 $(PBLOB-HDR): $(PBLOB-BIN) $(GEN-OFFSETS)
 	$(E) "  GEN     " $@
diff --git a/include/linkage.h b/include/linkage.h
new file mode 100644
index 0000000..c50a654
--- /dev/null
+++ b/include/linkage.h
@@ -0,0 +1,24 @@
+#ifndef LINKAGE_H_
+#define LINKAGE_H_
+
+#ifdef __ASSEMBLY__
+
+#define __ALIGN		.align 4, 0x90
+#define __ALIGN_STR	".align 4, 0x90"
+
+#define GLOBAL(name)		\
+	.globl name;		\
+	name:
+
+#define ENTRY(name)		\
+	.globl name;		\
+	.type name, @function;	\
+	__ALIGN;		\
+	name:
+
+#define END(sym)		\
+	.size sym, . - sym
+
+#endif  /* __ASSEMBLY__ */
+
+#endif /* LINKAGE_H_ */
diff --git a/include/parasite.h b/include/parasite.h
index 038fb5c..75eed92 100644
--- a/include/parasite.h
+++ b/include/parasite.h
@@ -1,6 +1,13 @@
 #ifndef CR_PARASITE_H_
 #define CR_PARASITE_H_
 
+#define PARASITE_STACK_SIZE	2048
+#define PARASITE_ARG_SIZE	8196
+
+#define PARASITE_MAX_SIZE	(64 << 10)
+
+#ifndef __ASSEMBLY__
+
 #include <sys/types.h>
 #include <sys/un.h>
 #include <limits.h>
@@ -13,11 +20,6 @@
 
 #define __head __used __section(.head.text)
 
-#define PARASITE_STACK_SIZE	2048
-#define PARASITE_ARG_SIZE	8196
-
-#define PARASITE_MAX_SIZE	(64 << 10)
-
 enum {
 	PARASITE_CMD_INIT,
 	PARASITE_CMD_SET_LOGFD,
@@ -102,4 +104,5 @@ struct parasite_drain_fd {
 #define PARASITE_HEAD_ADDR(start)				\
 	((start) + parasite_blob_offset____export_parasite_head_start)
 
+#endif /* !__ASSEMBLY__ */
 #endif /* CR_PARASITE_H_ */
diff --git a/parasite-head-x86-64.S b/parasite-head-x86-64.S
new file mode 100644
index 0000000..a2c12dc
--- /dev/null
+++ b/parasite-head-x86-64.S
@@ -0,0 +1,24 @@
+#include "linkage.h"
+#include "parasite.h"
+
+	.section .head.text, "ax"
+ENTRY(__export_parasite_head_start)
+	leaq	__export_parasite_stack(%rip), %rsp
+	subq	$16, %rsp
+	andq	$~15, %rsp
+	pushq	$0
+	movq	%rsp, %rbp
+	movl	__export_parasite_cmd(%rip), %edi
+	leaq	__export_parasite_args(%rip), %rsi
+	call	parasite_service
+	int	$0x03
+	.align 8
+__export_parasite_cmd:
+	.long 0
+__export_parasite_args:
+	.long 0
+	.space PARASITE_ARG_SIZE,0
+	.space PARASITE_STACK_SIZE,0
+__export_parasite_stack:
+	.long 0
+END(__export_parasite_head_start)
diff --git a/parasite.c b/parasite.c
index 2fad936..e34299e 100644
--- a/parasite.c
+++ b/parasite.c
@@ -444,7 +444,7 @@ static int fini(void)
 	return 0;
 }
 
-static int __used parasite_service(unsigned long cmd, void *args)
+int __used parasite_service(unsigned long cmd, void *args)
 {
 	BUILD_BUG_ON(sizeof(struct parasite_dump_pages_args) > PARASITE_ARG_SIZE);
 	BUILD_BUG_ON(sizeof(struct parasite_init_args) > PARASITE_ARG_SIZE);
@@ -487,32 +487,6 @@ static int __used parasite_service(unsigned long cmd, void *args)
 	return -1;
 }
 
-static void __head __export_parasite_head(void)
-{
-	/*
-	 * The linker will handle the stack allocation.
-	 */
-	asm volatile("__export_parasite_head_start:			\n"
-		     "leaq __export_parasite_stack(%rip), %rsp		\n"
-		     "subq $16, %rsp					\n"
-		     "andq $~15, %rsp					\n"
-		     "pushq $0						\n"
-		     "movq %rsp, %rbp					\n"
-		     "movl __export_parasite_cmd(%rip), %edi		\n"
-		     "leaq __export_parasite_args(%rip), %rsi		\n"
-		     "call parasite_service				\n"
-		     "int $0x03						\n"
-		     ".align 8						\n"
-		     "__export_parasite_cmd:				\n"
-		     ".long 0						\n"
-		     "__export_parasite_args:				\n"
-		     ".long 0						\n"
-		     ".space "__stringify(PARASITE_ARG_SIZE)",0		\n"
-		     ".space "__stringify(PARASITE_STACK_SIZE)", 0	\n"
-		     "__export_parasite_stack:				\n"
-		     ".long 0						\n");
-}
-
 #else /* CONFIG_X86_64 */
 # error x86-32 bit mode not yet implemented
 #endif /* CONFIG_X86_64 */
-- 
1.7.7.6



More information about the CRIU mailing list