int main(int argc, char ** argv) { int sock, acc_sock, ret; pid_t pid; uint32_t crc; uint8_t buf[1000]; test_init(argc, argv); sock = setup_srv_sock(); if (sock < 0) exit(1); pid = test_fork(); if (pid < 0) { pr_perror("can't fork"); exit(1); } if (pid == 0) { /* child writes to the unlinked socket and returns */ close(sock); sock = setup_clnt_sock(); if (sock < 0) _exit(1); test_waitsig(); crc = ~0; datagen(buf, sizeof(buf), &crc); if (write(sock, buf, sizeof(buf)) != sizeof(buf)) { pr_perror("can't write to socket"); exit(errno); } close(sock); exit(0); } acc_sock = accept(sock, NULL, NULL); if (acc_sock < 0) { pr_perror("can't accept() the connection on \"%s\"", filename); goto out_kill; } close(sock); sock = acc_sock; if (unlink(filename)) { pr_perror("can't unlink %s", filename); goto out_kill; } test_daemon(); test_waitsig(); if (kill(pid, SIGTERM)) { fail("terminating the child failed: %m\n"); goto out; } if (wait(&ret) != pid) { fail("wait() returned wrong pid %d: %m\n", pid); goto out; } if (WIFEXITED(ret)) { ret = WEXITSTATUS(ret); if (ret) { fail("child exited with nonzero code %d (%s)\n", ret, strerror(ret)); goto out; } } if (WIFSIGNALED(ret)) { fail("child exited on unexpected signal %d\n", WTERMSIG(ret)); goto out; } if (read(sock, buf, sizeof(buf)) != sizeof(buf)) { fail("can't read %s: %m\n", filename); goto out; } crc = ~0; if (datachk(buf, sizeof(buf), &crc)) { fail("CRC mismatch\n"); goto out; } if (close(sock)) { fail("close failed: %m\n"); goto out; } if (unlink(filename) != -1 || errno != ENOENT) { fail("file %s should have been deleted before migration: unlink: %m\n", filename); goto out; } pass(); out_kill: kill(pid, SIGTERM); out: close(sock); return 0; }
int main(int argc, char ** argv) { int sock, acc_sock, ret; char path[256]; pid_t pid; uint32_t crc; uint8_t buf[1000]; test_init(argc, argv); if (snprintf(path, sizeof(path), "%s/foo", dirname) >= sizeof(path)) { err("directory name \"%s\"is too long", dirname); exit(1); } if (mkdir(dirname, 0700)) { err("can't make directory %s: %m\n", dirname); exit(1); } sock = setup_srv_sock(path); if (sock < 0) goto out; pid = fork(); if (pid < 0) { err("can't fork: %m\n"); goto out; } if (pid == 0) { /* child writes to the overmounted socket and returns */ close(sock); sock = setup_clnt_sock(path); if (sock < 0) _exit(1); test_waitsig(); crc = ~0; datagen(buf, sizeof(buf), &crc); if (write(sock, buf, sizeof(buf)) != sizeof(buf)) _exit(errno); close(sock); _exit(0); } acc_sock = accept(sock, NULL, NULL); if (acc_sock < 0) { err("can't accept() the connection on \"%s\": %m", path); goto out_kill; } close(sock); sock = acc_sock; if (mount("rien", dirname, "tmpfs", 0, 0) < 0) { err("can't mount tmpfs over %s: %m", dirname); goto out_kill; } test_daemon(); test_waitsig(); if (kill(pid, SIGTERM)) { fail("terminating the child failed: %m\n"); goto out; } if (wait(&ret) != pid) { fail("wait() returned wrong pid %d: %m\n", pid); goto out; } if (WIFEXITED(ret)) { ret = WEXITSTATUS(ret); if (ret) { fail("child exited with nonzero code %d (%s)\n", ret, strerror(ret)); goto out; } } if (WIFSIGNALED(ret)) { fail("child exited on unexpected signal %d\n", WTERMSIG(ret)); goto out; } if (read(sock, buf, sizeof(buf)) != sizeof(buf)) { fail("can't read %s: %m\n", path); goto out; } crc = ~0; if (datachk(buf, sizeof(buf), &crc)) { fail("CRC mismatch\n"); goto out; } if (umount(dirname) < 0) { fail("can't umount %s: %m", dirname); goto out; } if (close(sock) < 0) { fail("can't close %s: %m", path); goto out; } if (unlink(path) < 0) { fail("can't unlink %s: %m", path); goto out; } pass(); out_kill: kill(pid, SIGKILL); out: close(sock); unlink(path); rmdir(dirname); return 0; }