zoukankan      html  css  js  c++  java
  • 终端

    在UNIX系统中,用户通过终端登录系统后得到一个Shell进程,这个终端成为Shell进程的控制终端(Controlling Terminal),控制终端是保存在PCB中的信息,而我们知道fork会复制PCB中的信息,因此由Shell进程启动的其它进程的控制终端也是这个终端。默认情况下(没有重定向),每个进程的标准输入、标准输出和标准错误输出都指向控制终端,进程从标准输入读也就是读用户的键盘输入,进程往标准输出或标准错误输出写也就是输出到显示器上。,在控制终端输入一些特殊的控制键可以给前台进程发信号,例如Ctrl-C表示SIGINT,Ctrl-表示SIGQUIT。

    init–>fork–>exec–>getty–>用户输入帐号–>login–>输入密码–>exec–>shell

    每个进程都可以通过一个特殊的设备文件/dev/tty访问它的控制终端。事实上每个终端设备都对应一个不同的设备文件,/dev/tty提供了一个通用的接口,一个进程要访问它的控制终端既可以通过/dev/tty也可以通过该终端设备所对应的设备文件来访问ttyname函数可以由文件描述符查出对应的文件名,该文件描述符必须指向一个终端设备而不能是任意文件。下面我们通过实验看一下各种不同的终端所对应的设备文件名。

    #include <unistd.h>
    #include <stdio.h>
    int main()
    {
        printf("fd 0: %s
    ", ttyname(0));  //标准输入文件描述符 0
        printf("fd 1: %s
    ", ttyname(1));  //标准输出文件描述符 1
        printf("fd 2: %s
    ", ttyname(2));  //标准错误文件描述符 2
        return 0;
    }
    
    
    输出结果:
    fd 0: /dev/pts/0
    fd 1: /dev/pts/0
    fd 2: /dev/pts/0

    硬件驱动程序负责读写实际的硬件设备,比如从键盘读入字符和把字符输出到显示器,线路规程像一个过滤器,对于某些特殊字符并不是让它直接通过,而是做特殊处理,比如在键盘上按下Ctrl-Z,对应的字符并不会被用户程序的read读到,而是被线路规程截获,解释成SIGTSTP信号发给前台进程,通常会使该进程停止。线路规程应该过滤哪些字符和做哪些特殊处理是可以配置的。 

    网络终端:

      虚拟终端或串口终端的数目是有限的,虚拟终端(字符控制终端)一般就是/dev/tty1∼/dev/tty6六个,串口终端的数目也不超过串口的数目。然而网络终端或图形终端窗口的数目却是不受限制的,这是通过伪终端(Pseudo TTY)实现的。一套伪终端由一个主设备(PTYMaster)和一个从设备(PTY Slave)组成。主设备在概念上相当于键盘和显示器,只不过它不是真正的硬件而是一个内核模块,操作它的也不是用户而是另外一个进程。从设备和上面介绍的/dev/tty1这样的终端设备模块类似,只不过它的底层驱动程序不是访问硬件而是访问主设备。网络终端或图形终端窗口的Shell进程以及它启动的其它进程都会认为自己的控制终端是伪终端从设备,例如/dev/pts/0、/dev/pts/1等。下面以telnet为例说明网络登录和使用伪终端的过程。 

     

    1. 用户通过telnet客户端连接服务器。如果服务器配置为独立(Standalone)模式,则在服务器监听连接请求是一个telnetd进程,它fork出一个telnetd子进程来服务客户端,父进程仍监听其它连接请求。

    2. telnetd子进程打开一个伪终端设备,然后再经过fork一分为二:父进程操作伪终端主设备,
    子进程将伪终端从设备作为它的控制终端,并且将文件描述符0、1、2指向控制终端,二者通过伪终端通信,父进程还负责和telnet客户端通信,而子进程负责用户的登录过程,提示输入帐号,然后调用exec变成login进程,提示输入密码,然后调用exec变成Shell进程。这个Shell进程认为自己的控制终端是伪终端从设备,伪终端主设备可以看作键盘显示器等硬件,而操作这个伪终端的“用户”就是父进程telnetd。

    3. 当用户输入命令时,telnet客户端将用户输入的字符通过网络发给telnetd服务器,由telnetd服务器代表用户将这些字符输入伪终端。Shell进程并不知道自己连接的是伪终端而不是真正的键盘显示器,也不知道操作终端的“用户”其实是telnetd服务器而不是真正的用户。Shell仍然解释执行命令,将标准输出和标准错误输出写到终端设备,这些数据最终由telnetd服务器发回给telnet客户端,然后显示给用户看。

    如果telnet客户端和服务器之间的网络延迟较大,我们会观察到按下一个键之后要过几秒钟才能回显到屏幕上。这说明我们每按一个键telnet客户端都会立刻把该字符发送给服务器,然后这个字符经过伪终端主设备和从设备之后被Shell进程读取,同时回显到伪终端从设备,回显的字符再经过伪终端主设备、telnetd服务器和网络发回给telnet客户端,显示给用户看。也许你会觉得吃惊,但真的是这样:每按一个键都要在网络上走个来回!

  • 相关阅读:
    4、[重点]Mybatis配置解析
    3、Mybatis的CRUD实现
    mybatis程序容易出错的地方
    1、初识Mybatis
    容易忽略的基础
    读取.properties配置文件的几种方式:
    格式化数字显示
    安装ipa文件
    保活一个线程
    地图经纬度的问题
  • 原文地址:https://www.cnblogs.com/13224ACMer/p/6412912.html
Copyright © 2011-2022 走看看