2019年6月22日 星期六

Unix CLI 基本技能-Unix 键盘各种键使用

1.Unix键盘中的修饰键: <Ctrl>键
Unix键盘<Ctrl>键(名称代表Control,即控制)是早期Teletype终端的一个特性。当创建Unix时,Unix开发人员采纳了<Ctrl>键,并将它以若干种方式集成到系统中。
在使用<Ctrl>键时,需要将它按住,然后按另一个键,通常是一个字母键。
根据字母表,这种组合有26种,即从<Ctrl>+<A>到<Ctrl>+<Z>,其中几个大家可能都会遇到。因为一遍又一遍地写“Ctrl”不方便,所有Unix社区使用一种简写表示方法:字符^(插入记号)。当看到这个字符后面有另一个字符时,它意味着“按住<Ctrl>键”。例如,^A意味着按住<Ctrl>键并按下<A>键。另外还有<Ctrl-A>或者C-a等表示方法,它们的含义都相同。
根据约定,在写<Ctrl>组合键时通常使用大写字母。例如,我们通常写^A,从来不写^a。使用大写字母这些组合键容易阅读。

为了习惯这种表示方法,我们先看一看下面的例子。这是稍候要提到的stty命令的一部分输出。


erase
kill
werase
rprnt
flush
lnext
^H
^U
^W 
^R
^O
^V

susp
intr
quit
stop
eof
^Z/^Y
^C
^\
^S/^Q
^D
stty 命令的输出告诉我们按下哪些组合键会发送特定的信号。细节并不重要,希望您注意的是表示方法。在这个例子中,发送erase信号要使用^H。也就是是说,按住<Ctrl>键并按<H>键。对于kill信号,要使用^U;而对于werase信号,则使用^W;等等
<Ctrl>键是所谓的修饰键的一个例子。修饰键指按住这些键的时候再去按另一个键。例如,当键入^H时,<Ctrl>键"修饰"<H>”键。
在标准的PC键盘上,修饰键有<Shift>, <Ctrl>和<Alt>。<Shift>键有两种用途;键入大写字母及键入双字符键中的顶部字符。例如键入美国标准键盘上的&(和号)字符,需要按<Shift-7>。 <Ctrl>键用于键入特殊信号。<Alt>键是最新的修饰键。因为当Unix开发出来时,该键还不存在,所以它不是标准Unix键盘的一部分。因此,在使用标准Unix CLI(命令行界面)时不需要该键。但是,GUI使用<Alt>键。

2. 键入过程中使用的信号: erase、werase、kill
键入过程中有3个键盘信号可以使用:erasewerasekillerase删除最后一个键入的字符,werase删除最后一个键入的单词,而Kill则删除整行。
按下<Backspace>或者<Delete>键(取决于键盘及其映射)通常可以发送erase信号。看一看键盘主部分右上角的大键,在几乎所有情况下,这就是映射到erase信号的键,在键入信息时,按下这个键可以删除刚刚键入的最后一个字符。
对于大多数终端和PC来说,使用的是<Backspace>键,而对于Macintosh来说,使用的是<Delete>键。如果使用的是Sun公司的计算机,它的键盘拥有这两个键,且两者紧挨在一起,那么这时使用<Delete>键(靠上的键)。
提示:
对于大多数键盘,按下<Backspace>键发送erase信号。而对于Macintosh来说,按下<Delete>键发送erase信号。您使用哪个键取决于您自己的键盘。
您应该还记着,前面提到一些键盘有<Enter>键,而其他键盘有<Return>键。道理是相同的。Unix只关心当按下这个键时发送的是什么信号。只要按下正确的键,Unix不会关心它是如何命名的。
以后,当提及<Backspace>键时,或者指<Backspace>,或者指<Delete>,哪一个都可以在系统上使用,只要您的键盘提供。同理,当提及<Return>键时,或者指<Return>,或者指<Enter>,选择使用哪一个取决于您的键盘。
下面示范一个使用erase信号的例子。假设希望输入命令date(显示时间和日期),但是将它拼错成datx。在按<Return>键之前,按<Backspace>(或者<Delete》键删除最后一个字母,然后再进行纠正:

datx<Backspace>e

在计算机屏幕上,当按下<Backspace>键时x将消失。如果希望删除不止一个字符,可以连续按<Backspace>键。
下一个信号werase,告诉Unix删除刚刚键入的最后一个单词。werase信号对应的键通常是^W。当希望纠正一个或者多个刚刚键入的单词时,这个键非常有用。当然,也可以重复地按<Backspace>键,但是当希望删除整个单词时,^W要快许多。
下面举一个例子。您希望使用less程序显示3个命名为data、secret和top-secret的文件的内容。使用的命令为:

less data secret top-secret

您键入了命令,但是,在按下<Return>键之前,您注意到有人在您身后。因此,您决定最好不再显示secret和top-secret文件。所以您按下^W两次,删除最后两个单词:

less data secret top-secret^w^w

在计算机屏幕上,首先是单词top-secret消失,然后是单词secret消失。接下来您可以按下<Return>键运行该命令。
在键入时使用的第三个信号是kill。映射到kill的信号通常是^X或者^U取决于系统如何设置)。该信号告诉Unix删除整行。
例如,假如您准备显示前面提到的3个文件的内容。您键入了命令,但是按<Return>键之前,有人跑进房间。您按下^X(或者^U)键删除整行命令:

less data secret top-secret^X

在计算机屏幕上,整行内容消失。
提示:
Kill键盘信号不会停止程序。它只删除刚键入的一行。为了停止程序,需要使用intr信号,该信号对应的键是^C或者<Delete>。



信号
作用
erase
<Backspace>/<Delete>
删除最后一个键入的字符
werase
^W
删除最后一个键入的单词
kill
^X/^U
删除整行



3. <Backspace>/<Delete>
Unix的设计使用了早期Teletype终端上可用的基本键:字母表中的字母,数字,标点符号,<Shift>键,<Return>键和<Ctrl>键。实际上,到现在,您仍然可以只依靠这些基本键使用Unix CLI。
现代键盘添加了其他键,例如<Backspace>, <Alt>, <Pageup>, <Pagedown>, 功能键,光标控制(箭头)键等。这些键中最有的要属<Backspace>键(在Macintosh机上为<Delete>键)。原因与发展简要如下:
1970年纸带的物理配置对现在计算机上的<Backspace>键的工作方式有直接影响。当时人使用Teletype机器,而且在键入穿孔到纸带上的信息,每键入一个字符,机器就在纸带上穿一组孔。这些孔对应于键入字符的ASCII码。但是偶然犯了一个错误该怎么办:
现代的PC,简单的按下<Backspace>即可。
在当时解决方法分为两部分,并且涉及特殊的Teletype命令。首先,按下<Ctrl-H>键,向纸带穿孔机发送一个BS(backspace,退格)命令。这致使穿孔机移回到前一行(发生错误的位置)。然后,按下<Rubout(擦掉)>键,发送DEL命令。这将使穿孔机在8个位置上都穿上孔(通过将一个字符加穿8个孔,也就是说,通过二进制码转换成8个1),可以有效删除该字符。因此,对于早期的Unix开发人员,删除一个错误需要两步不同的操作:使用^H退格,然后使用<Rubout>将错误擦掉。他们面临的问题是,哪一个应该映射erase信号,^H还是<Rubout>呢?他们选择了^H
很快,计算机公司开始制造有<Backspace>键的终端,为了方便,这个键被编程为具有按下^H相同的含义。这两个都映射到erase信号上,删除错误。
后来,<Rubout>键名称被改为<Delete>键。<Delete>键也生成DEL码(最初用于“删除”纸带上的一个字符)。然后这些公司决定使用DEL码取代^H代表退格。
使事情更加混乱的是,当编写Unix文档时存在一个问题。BS码有一种简单的表示方法,即^H,但是DEL码没有一种简单的表达方式。为了解决这个问题,人们选择了^?标记来表示DEL。
但是与^H不同的,^?并不是一个真正的组合键。也就是说,您不能按住<Ctrl>键再按?(问号)键。^?只是两个字符的缩写,意味着“whichever key on your keyboard that sends the code that used to be called DEL(您的键盘上某一个用来发送DEL代码的键)“。
但是,使事情更槽糕的时,后来Unix系统被配置成<Backspace>等同于^?(DEL),而不是^H(BS)。在这种情况下,^?映射到erase,而不是^H
情况就是这样,如果您的键盘上有<Backspace>键,那么它将映射到erase信号。PC机是这种情况。如果没有<Backspace>键,那么您的键盘上将有一个<Delete>键映射到erase信号。Macintosh机是这种情况。
如果您使用的是Sun公司的计算机,那么键盘上既有<Backspace>键又有<Delete>键,这时<Backspace>键将等同于^H,而<Delete>键将等同于^?
为了避免^H^?之间的混淆,一些Unix系统定义了一个额外的信号erase2。例如,FreeBSD就是这样的情况。
erase2的效果和erase相同。也就是说,它删除刚键入的最后一个字符。它们之间的区别是^H键映射到一个信号——erase或者erase2,而^?映射到另一个信号。这样,无论<Backspace>发送^H还是^?,都能正常工作。
提示:
1981年8月,当IBM PC刚生产出来时,它提供了一种全新的键盘。该键盘(与现在我们使用的键盘几乎相同)拥有好几个新键,例如<lnsert>,<Delete>,<Pageup>,<Pagedown>等等。
重要的是要意识到PC机键盘上的<Delete>键与旧终端、Macintosh机或Sun公司的计算机上的<Delete>键并不相同。它是一个完全不同的键。
如果拥有一台PC机,那么您可以自己证实这一点。在Unix命令行中输入一些内容,但是不要按下<Return>键。现在按<Backspace>键几次。注意最后几个字符被删除了。这是因为,在您的计算机上,<Backspace>键或者者等同于^H,或者等同于^?,无论何种情况,<Backspace>键都会映射到erase信号上。
现在按<Delete>键(<lnsert>键的旁边)。它不删除前面的字符,因为它没有映射到erase信号上。
4. Unix键盘中神秘字符^H
假设您正在使用自己的PC通过网络链接到一台远程Unix主机,您正在键入命令。突然犯了一个键入错误。
您连续按<Backspace>键几次,却发现没有删除最后几个键入的字符,而是在屏幕上显示:

^H^H^H

出现这样的问题原因在于,您的计算机上<Backspace>键等同于^H,而^H被映射到erase信号上。这就是为什么在您的机器上,<Backspace>键工作正常的原因。
但是在远程主机上,^?映射到erase信号上了。当您按下<Backspace>键时,发送的^H在远程主机上没有意义。这就是在远程主机上<Backspace>没有发挥作用的原因。
解决这个问题的方法有4中。
第一,您可以使用其他键修复键入错误。即不再使用<Backspace>键每次删除一个字符,而是使用^W删除整个单词,或者使用^X/^U删除整行。
第二,您可以找出向远程主机发送^?的键。在大多数系统上,<Ctrl-Backspace>可以完成这一任务。试试它,看看这个组合键能不能正常删除字符(如果使用Macintosh机,可以试一下<Option-Backspace>。
第三,您可以修改连接远程主机的程序的配置。大多数通信程序允许控制<Backspace>键发送^H还是发送^?。如果程序允许这样做,那么您可以配置该程序,从而保证无论何,当您连接这种主机时,<Backspace>发送的是^?,而不是^H
最后,您可以改变远程主机的映射,从而将^H而不是^?映射到erase信号上。一旦这样做了,<Backspace>将正常工作。这通常是最佳的解决办法,特别是在需要大量使用远程主机的情况下。
在进行该修改时,您所需做的全部工作就是在每次登录到远程主机时都要执行的初始化文件中放置一条特定的命令。命令如下:

stty erase ^H

5. 停止程序
Unix提供几种停止或者暂停程序的信号。这些信号是intr、quit、stop、和susp。我们将轮流讨论这些信号。一会儿您将看到,非常有趣的是,stop信号并不是用来停止程序的信号。5.1

5.1. 停止程序: intr
在大多数系统上,intr键是^C。但是在另一些系统上,使用的是<Delete>键。
intr(interrupt,中断)信号实际上有两个用途。首先,可以使用它停止一切将死的程序。假如您输入一条命令,这条命令需要花费很长时间才能结束啊,因此您决定不再等待而停止该命令。只需按下^C,这条远程命令将会终止,而你将返回到shell提示。
一些程序被编程为忽略intr信号。在这种情况下,程序总会提供一种明确定义的结束程序的方法(一些"quit"类型的命令)。通过忽略intr信号,程序可以防止您不小心按下^C而导致程序故障。在这种情况下,我们的程序封闭(trap)了 intr信号。
例如,您正在使用vi文本编辑器编辑一个文件,如果您按下^C,会发生什么情况呢?vi封闭(trap)了 intr信号,因此它不会停止。为了停止该程序,您需要使用vi的退出命令。如果vi没有封闭(trap)了 intr,那么您按下^C将终止程序,您还没有保存的数据将会丢失。
注意,有时候您可能看到将intr信号称为"break(中断程序运行)“键。如果您使用的是PC机,那么您可能知道^C充当Microsoft Windows下命令行程序的中断程序运行键,可以看出,这一思想(还有许多其他思想)取自Unix。
当您在shell提示处键入Unix命令时,intr信号的第二个用途就出现了。如果键入了一条命令,而您改变了主意,可以按下^C取代<Return>。按下^C将完全取消命令。
确定不要混淆了intr键(^C/<Delete>)和kiIl(^U/^X)键。当键入一条命令时,intr取消命令,而kill删除命令行上的所有字符。从效果上看,它们拥有相同的结果:正在键入的内容被删除,可以再输入一条新命令。
但是,只有intr停止程序。不管kiIl的名称如何,它不会真的杀死程序。

5.2 Unix键盘中停止程序: quit
除了intr(^C)之外,还有另外一种键盘信号quit,可以用来停止程序。Quit键通常是^\(<Ctrl-反斜线)。
Intrquit之间的区别并不大。以前,quit主要由需要终止测试程序的高级程序员使用。当按下^\时,它不仅停止程序,而且还会告诉Unix为此时内存中的内容制作一份副本。该信息存储在一个磁芯文件(core file),也就是一个命名为core(计算机内存的老名称)的文件中。然后程序员可以使用特殊的工具分析磁芯文件,查找什么地方除了问题。
现在,程序员拥有了更好的调试程序工具,因此,在大多数系统上,quit信号不再生成磁芯文件,尽管一些编程环境仍然在使用磁芯文件帮助调试。如果没有调试过程序,但是一个名为core的文件神秘的出现在您的一个目录中,那么意味着您运行的程序出现严重的错误而终止。除非真的需要这个文件,否则您可以删除它。实际上,您应该删除这个文件,因为core文件相当庞大,没有理由去浪费空间。

5.3. 暂停显示: stop,start
当程序在屏幕底部写一行输出时,其他行都要向上移动一个位置,该过程称之为向上滚动。如果程序生成输出太快,那么数据在阅读之前就滚动出屏幕了。
如果希望看—个这样的例子,可以使用下述两条命令中的一条。其中dmesg命令显示系统启动过程中得全部消息。另外一个命令是cat,它显示Termcap文件的内容:

dmesg
cat /etc/termcap


cat命令将数据连接起来,发送到默认输出位置上(或者“标准输 出”)。在这个例子中,cat将文件/etc/termcap中的数据复制到显示器上。但是,复制过程很快,大多数数据在阅读之前就滚动出屏幕了,这就是这个例子的目的。
在这种情况中,您有3种选择。首先,如果错过的数据不重要,那么您可以忽略这些数据。其次,可以重新启动生成数据的程序,并将该程序的输出发送到一个所谓的分页程序(例如less),从而每次一屏地显示输出结果。在本章前面使用下述命令时我们就是这样做的:

less /etc/termcap

对于dmesg来说,我们可以使用一个不同的命令来利用|(竖线)字符。这就是所谓的“管道符号”。管道的思想就是将dmesg的输出重新路由到less

dmesg | less
最后,您可以按下^S键发送stop信号。这个信号告诉Unix临时停止屏幕显示。一旦显示过程暂停,您可以通过按下^Q发送start信号重新启动屏幕显示,这两个信号容易记忆,即“S”代表Stop(停止),“Q”代表Qontinue(也就是continue,即继续)。
^S^Q的使用相当便利。但是,您应该理解^S只是告诉Unix停止输出的显示。它不会暂停正在执行的程序。程序继续执行,不会停止生成输出。
Unix将存储输出,因此不会有输出丢失,一旦您按下了^Q,剩下的全部输比将显示。如果在屏幕显示暂停时生成了大量的新数据行,那么一旦按下了^Q,这些新数据行将飞速地冲过。
顺便说一下,您可能会奇怪,为什么选择^S^Q来映射start和stop信号?答案是,在Teletype ASR33上,<Ctrl-Q>发送XON码,这个代码打开纸带阅读机;而<Ctrl-S>发送XOFF码,这个代码关闭纸带阅读机。


提示:
如果您的终端曾经神秘地锁住,那么可以试一试^Q。您可能不小心地按下了^S,暂停了屏幕显示。
当所有的事情看上去都神秘停止是,按下^Q不会造成任何伤害。



5.4 文件结束信号: eof
有时候,您使用的程序期望您从键盘输入数据。当数据输入完,没有数据再输入时,可以按下^D发送eof(end of file,文件结束)信号指示这一点
下面去一个例子,在后面,我们将讨论提供内置计算器服务的程序bc。一旦启动了bc,就可以一个接一个地输入计算。在每个计算之后,bc程序显示答案。当结束计算时,按下^D告诉bc程序没有数据了。在接收到eof信号之后,程序就会终止。


沒有留言:

張貼留言