第十四章 端口
我们前面讲过,各种存储器都和 CPU 的地址线、数据线、控制线相连。CPU在操控它们的时候,把它们都当作内存来对待,把它们总地看做一个由若干存储单元组成的逻辑存储器,这个逻辑存储器我们称其为内存地址空间(可参见1.15节)。
在PC机系统中,和CPU通过总线相连的芯片除各种存储器外,还有以下3种芯片。
(1)各种接口卡(比如,网卡、显卡)上的接口芯片,它们控制接口卡进行工作;
(2)主板上的接口芯片,CPU通过它们对部分外设进行访问;
(3)其他芯片,用来存储相关的系统信息,或进行相关的输入输出处理。
在这些芯片中,都有一组可以由CPU读写的寄存器。这些寄存器,它们在物理上可能处于不同的芯片中,但是它们在以下两点上相同。
(1)都和CPU的总线相连,当然这种连接是通过它们所在的芯片进行的;
(2) CPU对它们进行读或写的时候都通过控制线向它们所在的芯片发出端口读写命令。
可见,从 CPU 的角度,将这些寄存器都当作端口,对它们进行统一编址,从而建立了一个统一的端口地址空间。每一个端口在地址空间中都有一个地址。
CPU可以直接读写3个地方的数据
1.CPU内部的寄存器
2.内存单元
3.端口
14.1 端口的读写
1.对端口的读写不能用mov、push、pop等内存读写指令
端口的读写指令只有两条:【in】和【out】分别用于从端口读取数据和往端口写入数据
2.CPU执行内存访问指令和端口访问指令时,总线上的信息:
1.访问内存
mov ax,ds:[8]; 假设执行前(ds)=0
执行时,与总线相关的操作:
1.CPU通过地址线将地址信息8发出
2.CPU通过控制线发出内存读命令,选中存储器芯片,并通知它,将要从中读取数据
3.存储器将8号单元中的数据通过数据线送入CPU
2.访问端口
这里的【端口】是对硬件开放的端口
in al,60h; 从60h号端口读入一个字节
执行时与总线相关的操作
1.CPU通过地址线将地址信息60h发出
2.CPU通过控制线发出端口读命令,选中端口所在的芯片,并通知它,将要从中读取数据
3.端口所在的芯片将60h端口中的数据通过数据线送入CPU
**注意:在in和out指令中,只能使用ax或al来存放从端口中读入的数据或要发送到端口中的数据
访问8位端口时用al,访问16位端口时用ax
3.对0-255以内的端口进行读写
in al,20h ;从20h端口读一个字节
out 20h,al ;往20h端口写一个字节
4.对256-65535的端口进行读写时,端口号放在【dx】中
mov dx,3f8h ;将端口号3f8送入dx
in al,dx ;从3f8h端口读一个字节
out dx,al ;从3f8h端口写一个字节
14.2 CMOS RAM芯片
1.PC机中有一个CMOS RAM芯片,Complementary Metal Oxide Semiconductor Random Access Memory,CMOSRAM网络释义:互补金属氧化物半导体随机存取存储器.
其有如下特征
1.包含一个实时钟和一个有128个存储单元的RAM存储器。(早期的计算机为64字节)
2.该芯片靠电池供电。因此,关机后其内部的实时钟仍可以正常工作,RAM中的信息不丢失
3.128字节的RAM中,内部实时钟占用0-0dh单元来保存时间信息,其余大部分分单元用于
保存系统配置信息,供系统启动时bios程序读取
bios也提供了相关的程序,使我们可以在开机的时候配置CMOS RAM中的系统信息
**补充:BIOS
BIOS是英文"Basic Input Output System"的缩略词,直译过来后中文名称就是"基本输入输出系统"。
在IBM PC兼容系统上,是一种业界标准的固件接口。BIOS这个字眼是在1975年第一次由CP/M操作系统中出现。
BIOS是个人电脑启动时加载的第一个软件
4.该芯片内部有两个端口,端口地址为70h和71h。CPU通过这两个端口读写CMOS RAM。
5.70h为地址端口,存放要访问的CMOS RAM单元的地址;71h为数据端口,存放从选定的CMOS RAM单元中读取的数据
或要写入到其中的数据
2.比如:读CMOS RAM的2号单元:
1.将2送入端口70h
2.从71h读取2号单元的内容
14.3 shl和shr指令
shl和shr是逻辑移位指令,shift left/right后面的课程中我们要用到移位指令
1.shl逻辑左移指令,功能为:
1.将一个寄存器或内存单元中的数据向左移位
2.将最后移出的移位写入cf中
3.最低位用0补充
例如有如下指令:
mov al,01001000b
shl al,1 ;将al中的数据左移一位
执行后(al)=100100000b,cf=0.
如果移动位数大于1时,必须将移动位数放在cl中
2.shr逻辑右移指令,与shl刚好相反
14.4 CMOS RAM中存储的时间信息
在CMOS RAM中存放着当前时间
秒:00h
分:02h
时:04h
日:07h
月:08h
年:09h
这6个信息的长度都为1个字节
这些数据以BCD码的方式存放,一个字节可以表示两个BCD码
CMOS RAM存储时间信息的单元中存储了用两个BCD码表示的两个十进制数
高4位的BCD码表示十位,低四位的BCD码表示个位
【编程】:在屏幕中间显示当前的月份
1.CMOS RAM芯片回顾:
1.70h为地址端口,存放要访问的CMOS RAM单元的地址
2.71h为数据端口,存放从选定的CMOS RAM单元中【读取】的数据,或【写入】其中的数据
2.分析
这个程序主要做两部分工作
1.从CMOS RAM的8号单元读取当前月份的BCD码
要读取CMOS RAM的信息,我们首先要向地址端口70h写入要访问的单元的地址
mov al,8
out 70h,al
然后从数据端口71h中取得指定单元中的数据
in al,71h
2.将用BCD码表示的月份以十进制的形式显示到屏幕上
;编程:在屏幕中间显示当前的月份
code segment
assume cs:code
start:
mov al,8
out 70h,al
in al,71h
mov ah,al
mov cl,4
shr ah,cl
and al,00001111b
add ah,30h
add al,30h
mov bx,0b800h ;显存
mov es,bx
mov byte ptr es:[160*12+40*2],ah ;显示月份的十位数码
mov byte ptr es:[160*12+40*2+2],al ;显示月份的个位数码
mov ax,4c00h
int 21h
code ends
end start
【实验十四】编程:以“年/月/日 时:分:秒”的格式,显示当前日期和时间