当前位置: 首页 > 知识库问答 >
问题:

linux - C语言write()函数为何将文件描述符0也视为标准输出?

龚镜
2024-07-23

C语言write()函数文件描述符传0,为什么还是会写入到标准输出(屏幕上)

write的声明如下

ssize_t write(int fd, const void *buf, size_t count);

可以看到第一个参数应该是文件描述符(windows下叫句柄),然后通常情况下,进程会将0初始化为标准输入,将1初始化为标准输出

# define stdin  0
# define stdout 1

但是不知道为什么write这个函数的行为似乎有些诡异,我做了这样一个实验

#include <unistd.h>
#include <string.h>

int main() {
    char *message1 = "Writing to stdout using file descriptor 0\n";
    char *message2 = "Writing to stdout using file descriptor 1\n";

    write(0, message1, strlen(message1));
    write(1, message2, strlen(message2));

    return 0;
}

正常来讲我感觉write函数应该只有message2是可以正常打印的,message1理论上来说会报错,
因为理论上来讲write函数应该是无法写入0(stdin)的, 可是程序编译和运行却完全没有任何问题,这是运行结果

$ gcc test.c
$ ./a.out  
Writing to stdout using file descriptor 0
Writing to stdout using file descriptor 1

所以我想问一下有没有大佬知道为什么write函数文件描述符传0也会写入标准输出(stdout)


备注:我的平台是ubuntu 22.04,gcc版本是gcc (Ubuntu 11.4.0-1ubuntu1~22.04) 11.4.0

共有1个答案

胥诚
2024-07-23

1.write函数属于linux提供的系统调用,这个函数是没有缓冲区的,直接写到fd对应文件在内存中的文件结构体中的缓冲区。
2.文件结构体维护着一个缓冲区,由操作系统决定何时将此缓冲区的内容写到文件在内存的拷贝。
3.键盘也是一个文件,不过大多数情况对于操作系统而言是一个只读文件,我们输入的本质上时字符串,先存在文件结构体的缓冲区,再由操作系统决定何时将这串字符串读到进程里面。
3.stdin=0,当尝试往stdin里面写入字符串时,实际上这个字符串先保存在键盘文件缓冲区,而键盘接收不了字符串,于是这段字符停在缓冲区,而操作系统会认为这是键盘输入的字符,打印在屏幕上。
如下图
image.png
在sleep的10s内,我在键盘上输入字符,命令行也会打印我输入的东西。

 类似资料:
  • 问题内容: 在Python 3中,可以使用以下格式的“整数文件描述符”打开文件对象: 虽然,有趣的是,我发现这也是有效的流。 如果我把它放在文件中: 然后运行该代码,输出为: 看起来就像。然而… 因此看来这实际上不是,而是其他。它似乎也不是: 但是,我确实发现可以使用以下命令重定向输出: 所以我的问题是,到底该怎么办?重定向的“ 0>”流是什么? Python 3.6.5 Bash 3.2 问题答

  • 本文向大家介绍c语言描述回文数的三种算法,包括了c语言描述回文数的三种算法的使用技巧和注意事项,需要的朋友参考一下 题目描述 注意:(这些回文数都没有前导0) 1位的回文数有0,1,2,3,4,5,6,7,8,9 共10个; 2位的回文数有11,22,33,44,55,66,77,88,99 共9个; * 请问:n位的回文数有多少个?请编写一个递归函数来解决此问题!!! 【输入形式】一行一个正整数

  • 文件描述符 Linux很重要的设计思想就是一切皆文件,网络是文件,键盘等外设也是文件,很神奇吧?于是所有资源都有了统一的接口,开发者可以像写文件那样通过网络传输数据,我们也可以通过/proc/的文件看到进程的资源使用情况。 内核给每个访问的文件分配了文件描述符(File Descriptor),它本质是一个非负整数,在打开或新建文件时返回,以后读写文件都要通过这个文件描述符了。 应用 我们想想操作

  • 文件描述符接口 函数 int  fd_new (void)   分配文件描述符   struct dfs_fd *  fd_get (int fd)   获取文件描述结构   void  fd_put (struct dfs_fd *fd)   放置文件描述符   int  fd_is_open (const char *pathname)   判断文件是否已被打开   int  select (

  • 问题内容: 有人告诉我,我的服务器拒绝在特定端口接受客户端网络连接可能是由于缺少文件描述符所致。我查找了所有内容,并在此处阅读了有关内容:http : //www.netadmintools.com/art295.html 所以我测试了我的系统,我得到了: 这是什么意思?我的限制很高,但是我有0个可用的文件描述符?为什么?如何为我的服务器解决此问题? 即使关闭服务器后,第二列实际上仍为0,甚至在引

  • 什么是标准?标准是对重复性事物和概念所做的统一规定,他以科学技术和实践经验的结合成果为基础,经有关方面协商一致,由主管机构批准,以特定形式发布作为共同遵守的准则和依据。 在这个标准概念大行其道的今天,如果大家在生活中稍微注意一下,其实可以很容易发现,我们生活在一个标准化的世界里,每个产品的外包装或者标签上都会注明相应的执行标准。标准贯穿着我们的衣食住行。。总而言之,标准无处不在。 当然标准具有行业

  • 问题内容: 我有一个,是通过致电返回的。我需要从中获取文件描述符,以便对其进行调用。从文件指针获取文件描述符的功能是什么? 问题答案: 适当的功能是。可以在中找到,它是POSIX标准,但不是标准C。

  • 一、字符串操作<string.h> size_t strlen(char const* s); 注意:返回值类型size_t是无符号类型,和int进行运算或比较时需要注意; char* strcpy(char* dst,char const* src); 将src复制到dst,需保证dst有足够容纳src的空间,防止溢出,返回dst。若dst和src重叠,结果未定义 char* strcat(ch