更好地阅读执行官的文章';d计划';C中的s标准值

更好地阅读执行官的文章';d计划';C中的s标准值,c,memory-management,C,Memory Management,我使用管道读取执行程序的标准输出: int pipes[2]; pipe(pipes); if (fork() == 0) { dup2(pipes[1], 1); close(pipes[1]); execlp("some_prog", ""); } else { char* buf = auto_read(pipes[0]); } 要从标准输出读取数据,我有一个函数auto\u read,可以根据需要自动分配更多内存 char* auto_read(int

我使用管道读取执行程序的标准输出:

int pipes[2];
pipe(pipes);
if (fork() == 0) {
    dup2(pipes[1], 1);
    close(pipes[1]);
    execlp("some_prog", "");
} else {
    char* buf = auto_read(pipes[0]);
}
要从标准输出读取数据,我有一个函数
auto\u read
,可以根据需要自动分配更多内存

char* auto_read(int fp) {
    int bytes = 1000;
    char* buf = (char*)malloc(bytes+1);
    int bytes_read = read(fp, buf, bytes);
    int total_reads = 1;
    while (bytes_read != 0) {
        realloc(buf, total_reads * bytes + 1);
        bytes_read = read(fp, buf + total_reads * bytes, bytes);
        total_reads++;
    }
    buf[(total_reads - 1) * bytes + bytes_read] = 0;
    return buf;
}
我这样做的原因是我不知道程序会提前输出多少文本,我也不想创建一个过大的缓冲区,成为一个内存占用者。我想知道是否有:

  • 写这篇文章的更简洁的方式
  • 一种内存或速度效率更高的方法
  • 如果您只需要从进程中读取数据并且在*NIX平台上,请使用:

    FILE *programStdout = popen("command", "r");
    
    // read from programStdout (fread(), fgets(), etc.)
    char buffer[1024];
    
    while (fgets(buffer, 1024, programStdout))
    {
        puts(buffer);
    }
    
    编辑:您要求提供一种将程序输出映射到文件的方法,因此,请执行以下操作:

    #import <stdio.h>
    #import <unistd.h>
    #import <sys/mman.h>
    
    void *dataWithContentsOfMappedProgram(const char *command,  size_t *len)
    {
        // read the data
        char template[] = "/tmp/tmpfile_XXXXXX";
        int fd = mkstemp(template);
    
        FILE *output = fdopen(fd, "w+");
        FILE *input = popen(command, "r");
    
    #define BUF_SIZ 1024
        char buffer[BUF_SIZ];
        size_t readSize = 0;
        while ((readSize = fread(buffer, 1, BUF_SIZ, input)))
        {
            fwrite(buffer, 1, readSize, output);
        }
        fclose(input);
    
        input = NULL;
    #undef BUF_SIZ
    
        // now we map the file
        long fileLength = ftell(output);
        fseek(output, 0, SEEK_SET);
    
        void *data = mmap(NULL, fileLength, PROT_READ | PROT_WRITE, MAP_FILE | MAP_PRIVATE, fd, 0);
    
        close(fd);
    
        if (data == MAP_FAILED)
            return NULL;
    
        return data;
    }
    
    
    int main()
    {
        size_t fileLen = 0;
        char *mapped = dataWithContentsOfMappedProgram("echo Hello World!", &fileLen);
    
        puts(mapped);
    
        munmap(mapped, fileLen);
    }
    
    #导入
    #进口
    #进口
    void*dataWithContentsOfMappedProgram(const char*命令,size\u t*len)
    {
    //读取数据
    字符模板[]=“/tmp/tmpfile_uuxxxxxx”;
    int fd=mkstemp(模板);
    文件*output=fdopen(fd,“w+”);
    文件*input=popen(命令,“r”);
    #定义基本尺寸1024
    字符缓冲区[BUF_SIZ];
    大小\u t readSize=0;
    而((readSize=fread(缓冲区,1,BUF_SIZ,输入)))
    {
    fwrite(缓冲区,1,读取大小,输出);
    }
    fclose(输入);
    输入=空;
    #未定义BUF_SIZ
    //现在我们映射文件
    long fileLength=ftell(输出);
    fseek(输出,0,寻道设置);
    void*data=mmap(NULL,文件长度,PROT_读取| PROT_写入,MAP_文件| MAP_私有,fd,0);
    关闭(fd);
    如果(数据==映射_失败)
    返回NULL;
    返回数据;
    }
    int main()
    {
    大小文件长度=0;
    char*mapped=dataWithContentsOfMappedProgram(“echo Hello World!”,&fileLen);
    看跌期权(映射);
    munmap(已映射,fileLen);
    }
    
    如果您只需要从进程中读取数据并且在*NIX平台上,请使用:

    FILE *programStdout = popen("command", "r");
    
    // read from programStdout (fread(), fgets(), etc.)
    char buffer[1024];
    
    while (fgets(buffer, 1024, programStdout))
    {
        puts(buffer);
    }
    
    编辑:您要求提供一种将程序输出映射到文件的方法,因此,请执行以下操作:

    #import <stdio.h>
    #import <unistd.h>
    #import <sys/mman.h>
    
    void *dataWithContentsOfMappedProgram(const char *command,  size_t *len)
    {
        // read the data
        char template[] = "/tmp/tmpfile_XXXXXX";
        int fd = mkstemp(template);
    
        FILE *output = fdopen(fd, "w+");
        FILE *input = popen(command, "r");
    
    #define BUF_SIZ 1024
        char buffer[BUF_SIZ];
        size_t readSize = 0;
        while ((readSize = fread(buffer, 1, BUF_SIZ, input)))
        {
            fwrite(buffer, 1, readSize, output);
        }
        fclose(input);
    
        input = NULL;
    #undef BUF_SIZ
    
        // now we map the file
        long fileLength = ftell(output);
        fseek(output, 0, SEEK_SET);
    
        void *data = mmap(NULL, fileLength, PROT_READ | PROT_WRITE, MAP_FILE | MAP_PRIVATE, fd, 0);
    
        close(fd);
    
        if (data == MAP_FAILED)
            return NULL;
    
        return data;
    }
    
    
    int main()
    {
        size_t fileLen = 0;
        char *mapped = dataWithContentsOfMappedProgram("echo Hello World!", &fileLen);
    
        puts(mapped);
    
        munmap(mapped, fileLen);
    }
    
    #导入
    #进口
    #进口
    void*dataWithContentsOfMappedProgram(const char*命令,size\u t*len)
    {
    //读取数据
    字符模板[]=“/tmp/tmpfile_uuxxxxxx”;
    int fd=mkstemp(模板);
    文件*output=fdopen(fd,“w+”);
    文件*input=popen(命令,“r”);
    #定义基本尺寸1024
    字符缓冲区[BUF_SIZ];
    大小\u t readSize=0;
    而((readSize=fread(缓冲区,1,BUF_SIZ,输入)))
    {
    fwrite(缓冲区,1,读取大小,输出);
    }
    fclose(输入);
    输入=空;
    #未定义BUF_SIZ
    //现在我们映射文件
    long fileLength=ftell(输出);
    fseek(输出,0,寻道设置);
    void*data=mmap(NULL,文件长度,PROT_读取| PROT_写入,MAP_文件| MAP_私有,fd,0);
    关闭(fd);
    如果(数据==映射_失败)
    返回NULL;
    返回数据;
    }
    int main()
    {
    大小文件长度=0;
    char*mapped=dataWithContentsOfMappedProgram(“echo Hello World!”,&fileLen);
    看跌期权(映射);
    munmap(已映射,fileLen);
    }
    
    太好了,我会用这个。缓冲区呢?我想我还是应该使用
    auto_read
    ,因为我不知道这个命令会打印多少?@VladtheImpala在
    循环时注意
    。它一直读取,直到程序不再输出,然后
    将其输出到控制台。如果需要内存中输出的全部内容,请考虑将输出写入文件,然后>代码> MMAPP<代码>。如果你想得到一个啧啧,就说,我来写一个。好的,请!那太好了!啊,很好,我会用这个。缓冲区呢?我想我还是应该使用
    auto_read
    ,因为我不知道这个命令会打印多少?@VladtheImpala在
    循环时注意
    。它一直读取,直到程序不再输出,然后
    将其输出到控制台。如果需要内存中输出的全部内容,请考虑将输出写入文件,然后>代码> MMAPP<代码>。如果你想得到一个啧啧,就说,我来写一个。好的,请!那太好了!