mirror of
https://github.com/checkpoint-restore/criu
synced 2025-08-30 05:48:05 +00:00
test: A simple test for criu_restore_sub call v2
Which is at the same time the demonstration of how to do the trick. v2: * remove stupid sleep 1 synchronization * run internal version of child, not the external script Signed-off-by: Pavel Emelyanov <xemul@parallels.com> Acked-by: Andrew Vagin <avagin@parallels.com>
This commit is contained in:
parent
24d2f56fad
commit
a137d9fd58
@ -1,9 +1,15 @@
|
||||
all: build/test
|
||||
all: build/test test_sub
|
||||
.PHONY: all
|
||||
|
||||
run: all
|
||||
./run.sh
|
||||
|
||||
test_sub: test_sub.o
|
||||
gcc $^ -L ../../lib -lcriu -o $@
|
||||
|
||||
test_sub.o: test_sub.c
|
||||
gcc -c $^ -I ../../lib -o $@
|
||||
|
||||
build/test: build/test.o
|
||||
gcc $^ -L ../../lib -lcriu -o $@
|
||||
|
||||
@ -11,5 +17,5 @@ build/test.o: test.c
|
||||
gcc -c $^ -I ../../lib -o $@
|
||||
|
||||
clean:
|
||||
rm -rf build
|
||||
rm -rf build test_sub test_sub.o
|
||||
.PHONY: clean
|
||||
|
27
test/libcriu/run_sub.sh
Normal file
27
test/libcriu/run_sub.sh
Normal file
@ -0,0 +1,27 @@
|
||||
#!/bin/bash
|
||||
|
||||
source ../env.sh || exit 1
|
||||
|
||||
LOOP_PID=0
|
||||
|
||||
echo "== Clean"
|
||||
make clean
|
||||
rm -rf wdir
|
||||
rm -f ./libcriu.so.1
|
||||
|
||||
echo "== Prepare"
|
||||
make test_sub || { echo "FAIL"; exit 1; }
|
||||
|
||||
mkdir -p wdir/s/
|
||||
mkdir -p wdir/i/
|
||||
echo "== Start service"
|
||||
${CRIU} service -v4 -o service.log --address cs.sk -d --pidfile pidfile -W wdir/s/ || { echo "FAIL"; exit 1; }
|
||||
|
||||
echo "== Run test_sub"
|
||||
ln -s ../../lib/libcriu.so libcriu.so.1
|
||||
export LD_LIBRARY_PATH=.
|
||||
export PATH="`dirname ${BASH_SOURCE[0]}`/../../:$PATH"
|
||||
./test_sub wdir/s/cs.sk wdir/i/
|
||||
|
||||
echo "== Stopping service"
|
||||
kill -TERM $(cat wdir/s/pidfile)
|
140
test/libcriu/test_sub.c
Normal file
140
test/libcriu/test_sub.c
Normal file
@ -0,0 +1,140 @@
|
||||
#include "criu.h"
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <signal.h>
|
||||
|
||||
static void what_err_ret_mean(ret)
|
||||
{
|
||||
/* NOTE: errno is set by libcriu */
|
||||
switch (ret) {
|
||||
case -EBADE:
|
||||
perror("RPC has returned fail");
|
||||
break;
|
||||
case -ECONNREFUSED:
|
||||
perror("Unable to connect to CRIU");
|
||||
break;
|
||||
case -ECOMM:
|
||||
perror("Unable to send/recv msg to/from CRIU");
|
||||
break;
|
||||
case -EINVAL:
|
||||
perror("CRIU doesn't support this type of request."
|
||||
"You should probably update CRIU");
|
||||
break;
|
||||
case -EBADMSG:
|
||||
perror("Unexpected response from CRIU."
|
||||
"You should probably update CRIU");
|
||||
break;
|
||||
default:
|
||||
perror("Unknown error type code."
|
||||
"You should probably update CRIU");
|
||||
}
|
||||
}
|
||||
|
||||
static int stop = 0;
|
||||
static void sh(int sig)
|
||||
{
|
||||
stop = 1;
|
||||
}
|
||||
|
||||
#define SUCC_ECODE 42
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int pid, ret, fd, p[2];
|
||||
|
||||
printf("--- Start loop ---\n");
|
||||
pipe(p);
|
||||
pid = fork();
|
||||
if (pid < 0) {
|
||||
perror("Can't");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!pid) {
|
||||
printf(" `- loop: initializing\n");
|
||||
if (setsid() < 0)
|
||||
exit(1);
|
||||
if (signal(SIGUSR1, sh) == SIG_ERR)
|
||||
exit(1);
|
||||
|
||||
close(0);
|
||||
close(1);
|
||||
close(2);
|
||||
close(p[0]);
|
||||
|
||||
ret = SUCC_ECODE;
|
||||
write(p[1], &ret, sizeof(ret));
|
||||
close(p[1]);
|
||||
|
||||
while (!stop)
|
||||
sleep(1);
|
||||
exit(SUCC_ECODE);
|
||||
}
|
||||
|
||||
close(p[1]);
|
||||
|
||||
/* Wait for kid to start */
|
||||
ret = -1;
|
||||
read(p[0], &ret, sizeof(ret));
|
||||
if (ret != SUCC_ECODE) {
|
||||
printf("Error starting loop\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
/* Wait for pipe to get closed, then dump */
|
||||
read(p[0], &ret, 1);
|
||||
close(p[0]);
|
||||
|
||||
printf("--- Dump loop ---\n");
|
||||
criu_init_opts();
|
||||
criu_set_service_address(argv[1]);
|
||||
criu_set_pid(pid);
|
||||
criu_set_log_file("dump.log");
|
||||
criu_set_log_level(4);
|
||||
fd = open(argv[2], O_DIRECTORY);
|
||||
criu_set_images_dir_fd(fd);
|
||||
|
||||
ret = criu_dump();
|
||||
if (ret < 0) {
|
||||
what_err_ret_mean(ret);
|
||||
kill(pid, SIGKILL);
|
||||
goto err;
|
||||
}
|
||||
|
||||
printf(" `- Dump succeeded\n");
|
||||
wait(pid, NULL, 0);
|
||||
|
||||
printf("--- Restore loop ---\n");
|
||||
criu_init_opts();
|
||||
criu_set_log_level(4);
|
||||
criu_set_log_file("restore.log");
|
||||
criu_set_images_dir_fd(fd);
|
||||
|
||||
pid = criu_restore_child();
|
||||
if (pid <= 0) {
|
||||
what_err_ret_mean(pid);
|
||||
return -1;
|
||||
}
|
||||
|
||||
printf(" `- Restore returned pid %d\n", pid);
|
||||
kill(pid, SIGUSR1);
|
||||
err:
|
||||
if (waitpid(pid, &ret, 0) < 0) {
|
||||
perror(" Can't wait kid");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (WIFEXITED(ret)) {
|
||||
if (WEXITSTATUS(ret) == SUCC_ECODE)
|
||||
printf(" `- Success\n");
|
||||
else
|
||||
printf(" `- FAIL ec is %d\n", WEXITSTATUS(ret));
|
||||
} else if (WIFSIGNALED(ret))
|
||||
printf(" `- FAIL killed %d\n", WTERMSIG(ret));
|
||||
else
|
||||
printf(" `- FAIL bs %#x\n", ret);
|
||||
|
||||
return 0;
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user