【问题标题】:Setbuf function in CC中的Setbuf函数
【发布时间】:2015-09-22 15:12:01
【问题描述】:

方案一:

    #include<stdio.h>
    void main()
    {
        printf("Hello\n");
    }

输出:

    $strace ./a.out
    ioctl(0, SNDCTL_TMR_TIMEBASE or TCGETS, {B38400 opost isig icanon echo ...}) = 0
    fstat64(0, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 3), ...}) = 0
    .
    .
    .
    .
    write(1, "Hello\n", 6Hello
    )                  = 6
    exit_group(6)                           = ?
    $

方案二:

    #include<stdio.h>
    void main()
    {
        char buf[2];
        setbuf(stdout,buf);
        printf("Hello\n");
    }

输出:

    $ strace ./a.out 
    ioctl(0, SNDCTL_TMR_TIMEBASE or TCGETS, {B38400 opost isig icanon echo ...}) = 0
    fstat64(0, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 3), ...}) = 0
    .
    .
    .
    .
    write(1, "Hello\n", 6Hello
    )                  = 6
    exit_group(6)                           = ?
    $

我的要求是找到setbuf函数的用途。所以,我试验了上面显示的两个程序。在程序 1 中,我没有 将缓冲区设置为标准输出。因此,它使用内置缓冲区。内置缓冲区的大小为 4096(大约)。为此,你好就足够了 单写。因此,write 系统调用只会被调用一次。

但是在程序 2 中,我明确设置了 2 个字符大小的缓冲区。所以, printf 使用这个缓冲区。所以,我的预期输出是 写系统应该被调用 3 到 4 次。但是,两个程序的 strace 输出保持不变。

所以在程序 2 中,printf 函数使用的 buffer(buf) 不是。如果是使用buf,那么write系统调用会被调用4次。 那么,如何检查我的“a.out”程序调用了 write 函数的次数。

【问题讨论】:

  • 同样,void main(){} 应该是 int main(void){}

标签: c linux unix system-calls strace


【解决方案1】:

问题是setbuf()没有指定缓冲区的大小,假设是BUFSIZ,而不是2,因为函数永远不会看到2

而且由于很可能BUFSIZ2 更大,所以你有一个缓冲区溢出!

这很不方便,这就是为什么会有新的setvbuf()

int setvbuf(FILE *stream, char *buf, int mode, size_t size);

这将被用作:

setvbuf(stdout, buf, _IOFBF, sizeof(buf));

PS:你不应该写void main(),改用int main()

【讨论】:

  • 如果我把BUFSIZ宏的值改为2,那么呢?
  • 我假设您必须为此重新编译您的标准库。 BUFSIZ 来自标准库的标头,就库而言,它传达编译时设置。
  • @mohan:不!,BUFSIZ 是一个预定义的宏,它告诉您标准库期望的缓冲区大小。更改宏不会更改库(除非您重新编译 libc,并且您不希望这样)。
  • 那么,如何重新编译stdlib?
  • gnu.org/software/libc/manual/html_node/…。但说真的,这不是一个简单的任务。 assignmant 可能的意思(如果您只能使用 setbuf() 而不能使用 setvbuf())是将缓冲区设置为 null,从而有效地将模式设置为无缓冲。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-11-11
  • 2013-04-21
  • 1970-01-01
  • 2011-01-17
  • 1970-01-01
相关资源
最近更新 更多