我在做标题中所说的事情时遇到了很大的麻烦。
基本上,我想要一个程序,例如broadcast.c,它接受用户的输入,然后将该输入发送到两个进程的输入。
因此,如果要运行以下命令:
./broadcast prog1 prog2

它将阻止等待用户的输入,然后将该输入发送到prog1和prog2。

现在,我想使用管道,问题是,我不知道我是否必须使用1个管道或2个管道。

广播

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

    int main(int argc, char* argv[]) {
        int fds1[2], fds2[2];
        char buffer[120];
        pipe(fds1);
        pipe(fds2);

        if (fork() == 0) {
            close(0);
            dup(fds1[0]);
            close(fds1[0]);
            close(fds1[1]);
            execl(argv[1], argv[1], NULL);
        }

        if (fork() == 0) {
            close(0);
            dup(fds2[0]);
            close(fds2[0]);
            close(fds2[1]);
            execl(argv[2], argv[2], NULL);
        }

        while(read(0, buffer, 120) != 0) {
            printf("lido: %s\n", buffer);
            write(fds1[0],buffer,120);
            write(fds2[0],buffer,120);
        }

        close(1);
        dup(fds1[1]);
        dup(fds2[1]);
        exit(0);
    }


我知道这行不通,而且可能会搞砸,所以如果你们可以帮助我,那将是很好的。

现在,我只是想在执行此操作:
./broadcast prog1 prog2
用户输入:您好

输出为:
prog1说:您好!
prog2说:您好!

基本上prog1和prog2只是在fd 0上使用read进行打印。

最佳答案

我想要一个程序,例如broadcast.c,它接受用户的输入,然后将该输入发送到两个进程的输入。因此,如果要运行此命令:./broadcast prog1 prog2


您可以使用broadcast实现bash命令:

$ tee >/dev/null >(prog1) >(prog2)


tee从stdin读取并将其发送到prog1prog2tee默认情况下将stdin复制到stdout,因此使用>/dev/null禁止显示它。

还有来自peemoreutils package命令:

$ pee prog1 prog2


它正是您想要的。它使用popen()运行子进程。实现非常简单,这是完整的源代码(来自pee.cgit://git.kitenet.net/moreutils):

#include <stdlib.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/wait.h>

/* Licensed under the GPL
 * Copyright (c) Miek Gieben, 2006
 */

/* like tee(1), but then connect to other programs using
 * pipes _and_ output to standard output
 */

int
close_pipes(FILE **p, size_t i)
{
    int ret=EXIT_SUCCESS;
    size_t j;
    for (j = 0; j < i; j++) {
        int r = pclose(p[j]);
        if (WIFEXITED(r))
            ret |= WEXITSTATUS(r);
        else
            ret |= 1;
    }
    return ret;
}

int
main(int argc, char **argv) {
    size_t i, r;
    FILE **pipes;
    char buf[BUFSIZ];

    pipes = malloc(((argc - 1) * sizeof *pipes));
    if (!pipes)
        exit(EXIT_FAILURE);

    for (i = 1; i < argc; i++) {
        pipes[i - 1] = popen(argv[i], "w");
        if (!pipes[i - 1]) {
            fprintf(stderr, "Can not open pipe to '%s\'\n", argv[i]);
            close_pipes(pipes, argc);

            exit(EXIT_FAILURE);
        }
    }
    argc--;

    while(!feof(stdin) && (!ferror(stdin))) {
        r = fread(buf, sizeof(char), BUFSIZ, stdin);
        for(i = 0; i < argc; i++) {
            if (fwrite(buf, sizeof(char), r, pipes[i]) != r) {
                fprintf(stderr, "Write error to `%s\'\n", argv[i + 1]);
                close_pipes(pipes, argc);
                exit(EXIT_FAILURE);
            }
        }
    }
    exit(close_pipes(pipes, argc));
}

08-28 01:42