blob: 3c551de06c03ef83c255fe7f20b6d06f0a38005d [file] [log] [blame]
"Robert P. J. Day"63fc1a92006-07-02 19:47:05 +00001/* vi: set sw=4 ts=4: */
Glenn L McGrath5699b852003-11-15 23:19:05 +00002/*
Bernhard Reutner-Fischercfb53df2006-04-02 21:50:01 +00003 * Licensed under GPLv2 or later, see file LICENSE in this tarball for details.
Glenn L McGrath5699b852003-11-15 23:19:05 +00004 */
5
Glenn L McGrath5699b852003-11-15 23:19:05 +00006#include "libbb.h"
Bernhard Reutner-Fischercfb53df2006-04-02 21:50:01 +00007#include "unarchive.h"
8
Glenn L McGrath5699b852003-11-15 23:19:05 +00009/* transformer(), more than meets the eye */
Denis Vlasenko211f7f82007-09-05 11:48:32 +000010/*
Denis Vlasenko059c9172007-11-12 02:13:12 +000011 * On MMU machine, the transform_prog is removed by macro magic
12 * in include/unarchive.h. On NOMMU, transformer is removed.
Denis Vlasenko211f7f82007-09-05 11:48:32 +000013 */
Denis Vlasenko97a8dd32006-10-01 15:55:11 +000014int open_transformer(int src_fd,
Denis Vlasenko211f7f82007-09-05 11:48:32 +000015 USE_DESKTOP(long long) int (*transformer)(int src_fd, int dst_fd),
Denis Vlasenko059c9172007-11-12 02:13:12 +000016 const char *transform_prog)
Glenn L McGrath5699b852003-11-15 23:19:05 +000017{
Denis Vlasenko37188322008-02-16 13:20:56 +000018 struct fd_pair fd_pipe;
Glenn L McGrath5699b852003-11-15 23:19:05 +000019 int pid;
20
Denis Vlasenko37188322008-02-16 13:20:56 +000021 xpiped_pair(fd_pipe);
Glenn L McGrath5699b852003-11-15 23:19:05 +000022
Denis Vlasenko211f7f82007-09-05 11:48:32 +000023#if BB_MMU
Glenn L McGrath5699b852003-11-15 23:19:05 +000024 pid = fork();
Denis Vlasenko211f7f82007-09-05 11:48:32 +000025#else
26 pid = vfork();
27#endif
28 if (pid == -1)
Denis Vlasenkoea620772006-10-14 02:23:43 +000029 bb_perror_msg_and_die("fork failed");
Glenn L McGrath5699b852003-11-15 23:19:05 +000030
31 if (pid == 0) {
32 /* child process */
Denis Vlasenko37188322008-02-16 13:20:56 +000033 close(fd_pipe.rd); /* We don't want to read from the parent */
Denis Vlasenkoea620772006-10-14 02:23:43 +000034 // FIXME: error check?
Denis Vlasenko211f7f82007-09-05 11:48:32 +000035#if BB_MMU
Denis Vlasenko37188322008-02-16 13:20:56 +000036 transformer(src_fd, fd_pipe.wr);
Denis Vlasenko7e0fbf92007-09-04 19:33:22 +000037 if (ENABLE_FEATURE_CLEAN_UP) {
Denis Vlasenko37188322008-02-16 13:20:56 +000038 close(fd_pipe.wr); /* Send EOF */
Denis Vlasenko7e0fbf92007-09-04 19:33:22 +000039 close(src_fd);
40 }
Denis Vlasenkoea620772006-10-14 02:23:43 +000041 exit(0);
Denis Vlasenko211f7f82007-09-05 11:48:32 +000042#else
Denis Vlasenko059c9172007-11-12 02:13:12 +000043 {
44 char *argv[4];
45 xmove_fd(src_fd, 0);
Denis Vlasenko37188322008-02-16 13:20:56 +000046 xmove_fd(fd_pipe.wr, 1);
Denis Vlasenko059c9172007-11-12 02:13:12 +000047 argv[0] = (char*)transform_prog;
48 argv[1] = (char*)"-cf";
49 argv[2] = (char*)"-";
50 argv[3] = NULL;
51 BB_EXECVP(transform_prog, argv);
52 bb_perror_msg_and_die("exec failed");
53 }
Denis Vlasenko211f7f82007-09-05 11:48:32 +000054#endif
Denis Vlasenkoea620772006-10-14 02:23:43 +000055 /* notreached */
Glenn L McGrath5699b852003-11-15 23:19:05 +000056 }
Glenn L McGrath20872be2003-11-18 21:31:19 +000057
Glenn L McGrath5699b852003-11-15 23:19:05 +000058 /* parent process */
Denis Vlasenko37188322008-02-16 13:20:56 +000059 close(fd_pipe.wr); /* Don't want to write to the child */
Glenn L McGrath5699b852003-11-15 23:19:05 +000060
Denis Vlasenko37188322008-02-16 13:20:56 +000061 return fd_pipe.rd;
Glenn L McGrath5699b852003-11-15 23:19:05 +000062}