- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我已经为这个问题苦苦挣扎了一段时间。我正在尝试围绕运行子进程编写一个 C++ 类。我正在使用 fork()
、pipe()
、dup2()
和 execv()
启动一个子进程并将其 stdout 和 stderr 重定向到父进程。据我所知,一切正常,直到 dup2()
被调用并且它因 EINVAL
而失败(在 macOS 上,我不认为这是允许的错误类型在 Linux 中)。如果我删除管道周围的所有逻辑,该类将按预期工作。
类声明:
class PosixSubprocess : public Subprocess {
std::string _cmd = {};
std::string _stdout = "";
std::string _stderr = "";
std::vector<std::string> _args = {};
long _pid = -1;
int _status = -1;
public:
void cmd(std::string val) override;
void addArg(std::string val) override;
void run() override;
int status() const override;
std::string out() const override;
std::string err() const override;
};
run()
的定义:
void PosixSubprocess::run() {
std::array<int, 2> stdoutPipe = {};
std::array<int, 2> stderrPipe = {};
if (pipe(stdoutPipe.data()) < 0)
{
throw std::runtime_error("Subprocess: failed to create pipes. Errno: " + std::to_string(errno));
}
if (pipe(stderrPipe.data()) < 0)
{
throw std::runtime_error("Subprocess: failed to create pipes. Errno: " + std::to_string(errno));
}
_pid = fork();
if (_pid == 0) {
if (dup2(stderrPipe[1], STDERR_FILENO)) {
std::cout << "Subprocess: failed to redirect stderr. Errno " << errno << '\n';
exit(errno);
}
if (dup2(stdoutPipe[1], STDOUT_FILENO)) {
std::cout << "Subprocess: failed to redirect stdout. Errno " << errno << '\n';
exit(errno);
}
close(stdoutPipe[0]);
close(stdoutPipe[1]);
close(stderrPipe[0]);
close(stderrPipe[1]);
auto argv = std::make_unique<char*[]>(_args.size() + 1);
argv[_args.size()] = nullptr;
for (size_t i = 0; i < _args.size(); ++i) {
argv[i] = &(_args[i].front());
}
if(execvp(_cmd.c_str(), argv.get())) {
std::cerr << "Subprocess: failed to launch. Errno " << errno << '\n';
exit(errno);
}
} else if (_pid > 0) {
close(stdoutPipe[1]);
close(stderrPipe[1]);
std::array<char, 1024> buf;
auto appendPipe = [&buf](int fd, std::string& str) {
ssize_t nBytes = 0;
do {
nBytes = read(fd, buf.data(), buf.size());
str.append(buf.data(), nBytes);
if (nBytes) std::cout << nBytes << '\n';
} while (nBytes > 0);
};
while(!waitpid(_pid, &_status, WNOHANG)) {
appendPipe(stdoutPipe[0], _stdout);
appendPipe(stdoutPipe[0], _stderr);
}
} else {
close(stdoutPipe[0]);
close(stdoutPipe[1]);
close(stderrPipe[0]);
close(stderrPipe[1]);
throw std::runtime_error("Subprocess: fork failed.");
}
}
对于这里的代码墙,我很抱歉,我不能肯定地说与这个问题无关。
最佳答案
RETURN VALUE
Upon successful completion a non-negative integer, namely the file descriptor, shall be returned; otherwise, -1 shall be returned and errno set to indicate the error.
因为很明显,dup2()
返回原始文件被复制到的文件描述符,并且它是非零的,所以显示的代码认为这是一个错误。
错误条件由负返回值指示。
关于c++ - 重定向标准输出时调用 dup2 失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46919546/
我有一个 excel 文件,我需要进行一些更改。我需要识别重复项,然后将“1st”放在第一个 dup 的系列列中。对于其余的重复需要在系列列中放置“其他重复”。可能吗?我尝试了查找和匹配,但没有任何帮
我是一个C初学者,尝试使用dup(),我写了一个程序来测试这个函数,结果和我预期的有点不同。 代码: // unistd.h, dup() test #include #include #incl
我正在尝试创建两个子进程: 一个子进程从文件中读取输入(该文件作为参数传入),并将输出写入管道。 另一个子进程从管道读取其输出并将其输出写入文件,该文件也作为参数传入。 父级为子级设置一些文件描述符,
当我们使用 dup 将 STDOUT 重定向到我们做的管道时: close(1); dup(fd[1]); close(fd[0]); close(fd[1]); execlp("ls","-al",
因此,我阅读了有关 Linux 中的文件 I/O 的内容,并想尝试一下。然而,我在代码中遇到了两个奇怪的行为,我正在努力寻找它们的原因。 /* * This program shows the us
我想知道为什么 dup 总是在下面的代码中返回零(其中一个文件被打开,而不是连续完成 10 个 dup): #include #include #include #include #inclu
我正在开发一个程序,要求用户输入 s、f 或 0 作为用户输入。 S 向系统打印预定义消息,f 将该预定义消息写入用户作为参数提供的文件。 0 终止程序。 我需要让程序只有一个写入标准输出的写入语句。
我正在在线学习算法类(class),我正在尝试计算数字列表中的最大成对乘积。这个问题之前已经回答过: maximum pairwise product fast solution和 Python fo
我想知道为什么以下字节码中的异常(用于抛出异常)是重复的。 NEW java/lang/IllegalArgumentException DUP INVOKESPECIAL java/lang/Ill
我正在编写代码以将 stdout 重定向到一个文件(例如 ls 返回到一个文件的结果)并且 dup2() 函数不重定向我的输出。这是我的代码: void testDup() { int new
close(fileno(stdout)); int fd = dup(fileno(stdin)); //printf("Hello World\n"); write(fd, "Hell
目前我只是在一个使用 java 字节码的项目中。我通常看到,当创建一个新的类实例并在其上调用一个方法时,字节码将是这样的: NEW DUP INVOKESPECIAL > 这里为什么要做“DUP”?
当涉及到复制文件描述符时,我能得到一个关于 dup() 函数的非常简单的解释吗?我想使用管道,但我还必须让 child 从管道中读取(这是简单的部分),但将数据写回父级。我应该使用另一根管道,还是可以
>> a = 5 => 5 >> b = "hello, world!" => "hello, world!" >> b.dup => "hello, world!" >> a.dup TypeErr
我对这个用于教育目的的小代码有疑问。我不明白它是如何工作的。 #include #include #define FNAME "info.txt" #define STDIN 0 int main
Java字节码指令集提供various forms of dup instruction 。我无法理解这些指令和 swap 指令的用途。哪些 Java 代码在编译时会使用这些指令生成字节码? 最佳答案
鉴于以下信息,我如何在唯一的 params 和 cron_action_id 对上选择最新的订单项(基于 time_entered)还没被处决吗? cron_schedule 例如,id 1、2和4具
int mypipe[2]; pipe(mypipe); int dupstdout=dup2(mypipe[1],1); cout<<"hello";//not printed on termina
我一直想创建一个 fork 两次以创建两个子进程的子进程。随着一个的输出,发送到另一个。我找到了这个示例代码。但我对它的工作原理感到困惑。 我找到了一个 example here .但我对 dup 的
所以我尝试使用 dup() 将标准输出重定向到一个文件。 int save_fd; save_fd=dup(1); //saves the current stdout close(1); //clo
我是一名优秀的程序员,十分优秀!