zoukankan      html  css  js  c++  java
  • Understanding Unix/Linux Programming-stty指令练习

    先来看一个简单的练习程序:

    1 #include <stdio.h>
    2 
    3 int main()
    4 {
    5     int c  , n = 0 ;
    6     while( (c = getchar() ) != 'Q' )
    7         printf("char %3d is %ccode %d
    " , n++ , c , c  );
    8     return 0 ;
    9 }

    以上是程序编译后运行的效果啦,可以看到在输入hello之后敲击回车后才运行了该程序,也就是说,在终端中输入的字符实际上是被缓冲的。

    另外,回车键本身被识别为换行了,也由该程序识别了,这也与终端的设置有关。

    tty驱动程序包含很多对数据的操作:

    1. 输入:驱动程序如何处理来自终端的字符
    2. 输出:驱动程序如何处理流向终端的字符
    3. 控制:字符如何表示——位的个数,位的奇偶性,停止位等等
    4. 本地:驱动程序如何处理来自驱动程序内部的字符

    编写终端驱动程序:关于系统调用函数:

      改变终端驱动程序的设置就像改变磁盘文件连接的设置一样:

    1. 从驱动程序获得属性
    2. 修改所要修改的属性
    3. 将修改过的属性送回驱动程序

      通常通过tcgetattr和tcsetattr提供对终端驱动程序的访问。这两个函数在termios结构体中交换设置。

      1 /* stty.c
      2  * show the settings of current tty 
      3  */
      4 #include <stdio.h>
      5 #include <stdlib.h>
      6 #include <termios.h>
      7 
      8 struct flaginfo 
      9 {
     10     int fl_value ;
     11     char * fl_name ;
     12 };
     13 
     14 struct flaginfo input_flags[] =
     15 {
     16     IGNBRK , "Ignore break condition" , 
     17     BRKINT , "Signal interrupt on break" , 
     18     IGNPAR , "Ignore chars with parity errors",
     19     PARMRK , "Mark parity errors",
     20     INPCK , "Enable input parity check",
     21     ISTRIP , "Strip character",
     22     INLCR , "Map NL to CR on input",
     23     IGNCR , "Ignore CR",
     24     ICRNL , "Map CR to NL on input",
     25     IXON , "Enable start/stop control",
     26     IXOFF , "Disable start/stop control",
     27     0 , NULL
     28 };
     29 
     30 struct flaginfo local_flags[] = 
     31 {
     32     ISIG , "Enable signals",
     33     ICANON , "Canonical input(erase and kill)",
     34     ECHO , "Enable echo" ,
     35     ECHOE , "Echo REASE as BS-SPACE-BS" ,
     36     ECHOK , "Echo KILL by starting new line",
     37     0 , NULL 
     38 };
     39 
     40 void show_baud(int thespeed);
     41 void show_some_flags(struct termios * ttyp);
     42 void show_flagset(int thevalue , struct flaginfo * thebitnames);
     43 
     44 int main()
     45 {
     46     struct termios ttyinfo ;
     47     // 从文件中获取当前驱动程序的设置
     48     if(tcgetattr(0 , & ttyinfo ) == -1 )
     49     {
     50         perror("cannot get para about stdin");
     51         exit(1);
     52     }
     53     
     54     show_baud( cfgetospeed( &ttyinfo ) );
     55     
     56     printf("The erase character is ascii %d , Ctrl-%c
    ",
     57             ttyinfo.c_cc[VERASE] , ttyinfo.c_cc[VERASE] - 1 + 'A') ;
     58     printf("The line kill character is ascii %d , Ctrl-%c
    ",
     59             ttyinfo.c_cc[VKILL] , ttyinfo.c_cc[VKILL] - 1 + 'A') ;
     60             
     61     show_some_flags(&ttyinfo);
     62     return 0 ;
     63 }
     64 
     65 void show_baud(int thespeed)
     66 {
     67     printf("The baud rate is :");
     68     switch(thespeed)
     69     {
     70         case B300 : printf("300
    "); break ;
     71         case B600 : printf("600
    "); break ;
     72         case B1200 : printf("1200
    "); break ;
     73         case B1800 : printf("1800
    "); break ;
     74         case B2400 : printf("2400
    "); break ;
     75         case B4800 : printf("4800
    "); break ;
     76         case B9600 : printf("9600
    "); break ;
     77         default : printf("Fast!
    ");break ;
     78     }
     79 }
     80 
     81 void show_some_flags(struct termios * ttyp)
     82 {
     83     show_flagset( ttyp -> c_iflag , input_flags ) ;
     84     show_flagset( ttyp -> c_lflag , local_flags ) ;
     85 }
     86 
     87 void show_flagset(int thevalue , struct flaginfo * thebitnames)
     88 {
     89     int i ;
     90     for(i = 0 ; thebitnames[i].fl_name ; i ++ )
     91     {
     92         printf("%s is " , thebitnames[i].fl_name);
     93         if(thevalue & thebitnames[i].fl_value)
     94         {
     95             printf("ON
    ");
     96         }
     97         else
     98         {
     99             printf("OFF
    ");
    100         }
    101     }
    102     
    103 }

    将结构体以及结构体数组的定义提到前面,编译就不会报错了。话说书中例程使用的应该是较老版本的编译器,所以用现在的编译器总是出警告和错误啥的,按照现C++的定义顺序来写就不会有大问题啦。

      

  • 相关阅读:
    微软软件
    绘图软件安装出错解决方法
    Windows平台 Faster-RCNN 制作自己的数据集
    POJ2456 Agressive Cows
    P1030 求先序排列
    Luogu P2015二叉苹果树
    P2234 [HNOI2002]营业额统计
    Luogu P1347排序
    Luogu P1038神经网络
    Luogu P1006传纸条
  • 原文地址:https://www.cnblogs.com/NJdonghao/p/5282703.html
Copyright © 2011-2022 走看看