分类: LINUX
2012-09-25 11:03:57
GPIO寄存器映射:
FIODIR:高速GPIO端口方向寄存器,该寄存器单独控制每个端口的管脚的方
向。
FIOMASK:端口高速屏蔽寄存器,写,置位,清零和读端口(通过写FIOPIN、PIOSET、FIOCLR和读FIOPIN来执行)改变和返回时,只对该寄存器为0的位有效。
FIOPIN:高速端口管脚值寄存器,使用FIOMASK。不管引脚方向或可选的功能选择如何,数字端口管脚的当前状态可从该寄存器中读出(只要管脚不配置为ADC的输入)。通过相与(AND)反向的FIOMASK来屏蔽读出的值。写该寄存器,向FIOMASK中为0的位填入对应的值。注:如果读FIOPIN寄存器,那么不管物理引脚的状态如何,在FIOMASK中被1屏蔽的位始终读出为0。
FIOSET:高速端口输出置位寄存器,使用FIOMASK。该寄存器控制输出引脚的状态。写1使相应的端口产生高电平。写0没有影响。读该寄存器返回端口输出寄存器的当前内容。只可以更改FIOMASK中由0使能的位。
FIOCLR:高速端口输出清零的寄存器,使能FIOMASK。该寄存器控制输出引脚的状态,写1使相应的端口引脚产生低电平,写0没影响。只可以更改FIOMASK中由0使能的位。
LPC1700系列Cortex-M3具有5个端口,所以他们具有5组控制寄存器,这些寄存器均为
32位宽,每一位对应一个不同的I/O口,一个GPIO引脚在某一时刻,只受四个位的控制,这四个位分别在该GPIO引脚所属端口的四个控制寄存器中。
1)GPIO端口方向寄存器FIOxDIR
当引脚被配置为GPIO端口引脚时,该寄存器用来控制引脚的方向。GPIO端口方向寄存器为FIO0DIR,FIO1DIR,FIO2DIR,FIO3DIR,FIO4DIR。
位 |
符号 |
描述 |
复位 |
31:0 |
FP0DIR |
高速GPIO方向PORTx控制位。 0:输入引脚 1:输出引脚 |
0x0 |
FP1xDIR | |||
FP2DIR | |||
FP3DIR | |||
FP4DIR |
例:FIO0DIR = 0xFFFFFFFF ;//高速P0口32个引脚全部为输出引脚。
除了FIODIR寄存器以外,GPIO口也可通过一些字节和半字节访问寄存器的控制。
FIOxDIR0 |
高速GPIO端口x方向控制寄存器0,。FIOxDIR0寄存器中的位0对应管脚Px.0,位7对应管脚Px.7 |
8位 |
0x00 |
FIOxDIR1 |
高速GPIO端口x方向控制寄存器1,。FIOxDIR1寄存器中的位0对应管脚Px.8,位7对应管脚Px.15 |
8位 |
0x00 |
FIOxDIR2 |
高速GPIO端口x方向控制寄存器2,。FIOxDIR2寄存器中的位0对应管脚Px.16,位7对应管脚Px.23 |
8位 |
0x00 |
FIOxDIR3 |
高速GPIO端口x方向控制寄存器3,。FIOxDIR3寄存器中的位0对应管脚Px24,位7对应管脚Px.31 |
8位 |
0x00 |
FIOxDIRL |
高速GPIO端口x方向低半字寄存器,。FIOxDIRL寄存器中的位0对应管脚Px.0,位15对应管脚Px15 |
16位 |
0x0000 |
FIOxSETU |
高速GPIO端口x方向高半字寄存器,。FIOxSETU寄存器中的位0对应管脚Px16,位15对应管脚Px31 |
16位 |
0x0000 |
操作实例:
FIO0DIR0 = 0xFF ;//P0口的0-7脚全部为输出脚
FIO1DIR1 = 0x00 ;//P1口的8-15脚全部为输入脚
2)GPIO端口输出置位寄存器FIOxSET
当引脚在输出模式中被配置为GPIO时,该寄存器控制在端口引脚产生高电平输出。向该寄存器的某些位写入1时,对应的引脚将输出高电平,写入0无效,如果需要引脚输出低电平,不能通过向FIOSET写入0来实现,而是要使用FIOCLR来完成。
如果一个引脚被配置为输入或者其他功能,那么写FIOSET将不能引起IO引脚电平变化。
读FIOSET寄存器将返回GPIO输出寄存器中的值,也就是当前IO引脚的输出电平状态。该值由前一次FIOSET和FIOCLR(或FIOPIN)的写操作觉得。该值与从FIOPIN寄存器读取的值可能有所不同。因为它不反应任何外部环境对引脚的影响。比如某个引脚设置输出高电平,而被外部强制拉低,那么从FIOSET读出该位将是1,而从FIOPIN读出该位将为0.
GPIO端口输出置位寄存器为FIO0SET,FIO1SET,FIO2SET,FIO3SET,FIO4SET。通过FIOSET寄存器来访问端口引脚受到FIOMASK寄存器相应位的限制。
位 |
符号 |
描述 |
复位 |
31:0 |
FP0SET |
高速GPIO输出值设置2。 0:控制的引脚输出不变 1:控制的引脚输出为高电平 |
0x0 |
FP1xSET | |||
FP2SET | |||
FP3SET | |||
FP4SET |
操作实例:FIO0SET = 0xFF ;//P0口的0-7脚通过高速总线输出高电平。
除了FIOSET寄存器以外,GPIO口也可通过一些字节和半字节访问寄存器的控制。
FIOxSET0 |
高速GPIO端口x方向控制寄存器0,。FIOxSET0寄存器中的位0对应管脚Px.0,位7对应管脚Px.7 |
8位 |
0x00 |
FIOxSET1 |
高速GPIO端口x方向控制寄存器1,。FIOxSET1寄存器中的位0对应管脚Px.8,位7对应管脚Px.15 |
8位 |
0x00 |
FIOxSET2 |
高速GPIO端口x方向控制寄存器2,。FIOxSET2寄存器中的位0对应管脚Px.16,位7对应管脚Px.23 |
8位 |
0x00 |
FIOxSET3 |
高速GPIO端口x方向控制寄存器3,。FIOxSET3寄存器中的位0对应管脚Px24,位7对应管脚Px.31 |
8位 |
0x00 |
FIOxSETL |
高速GPIO端口x方向低半字寄存器,。FIOxSETL寄存器中的位0对应管脚Px.0,位15对应管脚Px15 |
16位 |
0x0000 |
FIOxSETU |
高速GPIO端口x方向高半字寄存器,。FIOxSETU寄存器中的位0对应管脚Px16,位15对应管脚Px31 |
16位 |
0x0000 |
操作实例:FIO0SETL = 0xFFFF ;//高速P0口的0-15脚通过高速总线输出高电平
3)GPIO端口输出清零寄存器FIOxCLR
当引脚咋输出模式中被配置为GPIO时,该寄存器咋端口引脚产生低电平输出,向某位写入1会使相应的引脚产生低电平,同时清零FIOxSET寄存器的相应的位。写入0无效。如果引脚被配置为输入或其他功能,那么写FIOxCLR对引脚没有影响。
GPIO端口输出置位寄存器为FIO0CLR,FIO1CLR,FIO2CLR,FIO3CLR,FIO4CLR。通过FIOCLR寄存器来访问端口引脚受到FIOMASK寄存器相应位的限制。
符号 |
描述 |
复位 | |
31:0 |
FP0CLR |
高速GPIO输出值清零。 0:控制的引脚输出不变 1:控制的引脚输出为低电平 |
0x0 |
FP1CLR | |||
FP2CLR | |||
FP3CLR | |||
FP4CLR |
4)GPIO端口引脚值寄存器FIOxPIN
该寄存器提供了端口引脚的值(配置为ADC功能的引脚除外),该寄存器将给出引脚的当前值,而不管引脚是否配置为输入或输出,或作为GPIO或可选的数字功能。例如,特殊的端口引脚可能具有GPIO输入,GPIO输出,UART接收和PWM输出作为可选的功能。无论该引脚配置成何种功能,都可以从相应的FIOxPIN寄存器读取其当前的逻辑状态。
如果引脚配置为模拟功能(如ADC输入),这种情况下,从FIOxPIN寄存器中读取的引脚值无效。
写FIOxPIN寄存器时,FIOPIN寄存器的值会保持到输出寄存器中,而输出寄存器控制着引脚的输出电平状态。即,通过修改FIOPIN寄存器可以改变引脚的电平输出状态,由于这种特性影响整个端口,因此在应用中要小心。
GPIO端口引脚值寄存器为FIO0PIN,FIO1PIN,FIO2PIN,FIO3PIN,FIO4PIN。
位 |
符号 |
描述 |
复位 |
31:0 |
FP0PIN |
高速GPIO输出值设置位。 0:控制的引脚输出低电平 1:控制的引脚输出为高电平 |
0x0 |
FP1PIN | |||
FP2PIN | |||
FP3PIN | |||
FP4PIN |
5)高速GPIO端口屏蔽寄存器FIOxMASK
该寄存器用来屏蔽某些端口引脚,被屏蔽的引脚将无法通过FIOxPIN,FIOxSET,或FIOxCLR寄存器访问。
a> 向屏蔽寄存器中的某些位写入1时,屏蔽对应的引脚,此时,不能通过FIOxPIN,FIOxSET,FIOxCLR寄存器操作该引脚。
b> 写入0时,对应引脚正常,未被屏蔽,此时,可以通过FIOPIN,FIOSET,FIOCLR寄存器操作该引脚。
通过读写访问,该寄存器中为0的位使能相应物理引脚的访问。如果该寄存器中的位为1,则相应为不能通过写访问改变,并且读操作时将不能再FIOxPIN寄存器中反映出来。
位 |
符号 |
描述 |
复位 |
31:0 |
FP0MASK |
高速GPIO物理引脚控制访问。 0:控制引脚受到FIOxSET,FIOxCLR,FIOxPIN寄存器的写操作影响。引脚的当前状态可从FIOxPIN寄存器中读出。 1:控制的引脚不受FIOxSET,FIOxCLR,FIOxPIN寄存器的写操作影响。读取FIOxPIN寄存器时,该位将不会通过物理引脚的状态更新。 |
0x0 |
FP1MASK | |||
FP2MASK | |||
FP3MASK | |||
FP4MASK |
操作实例:FIO0MASK = 0xFFFFFF00; //P0口的0-7位可以输出,其他脚被屏蔽
除了32位长仅可进行字访问的FIOxMASK寄存器外,每个高速GPIO口也可以通过一些字节和半字节访问的寄存器来控制。
GPIO中断控制器:
LPC1700系列Cortex-M3的GPIO引脚还有一个功能:中断。端口PORT0和PORT2的每一个引脚都可以配置为上升沿中断或者下降沿中断,也可以设置为边沿产生中断。端口PORT0和TPORT2的中断通道与外部中断3(EINT3)相同,都是通道37。.端口PORT0和PORT2的中断功能可以唤醒处于掉电模式下的CPU。
GPIO引脚的中断寄存器可以分为两组:控制寄存器和状态寄存器。其中控制寄存器决定引脚中断的触发方式,状态寄存器则反映IO状态的当前状态。
控制寄存器 |
描述 |
访问 |
复位值 |
IntEnR |
上升沿GPIO中断使能 |
R/W |
0x0 |
IntEnF |
下降沿GPIO中断使能 |
R/W |
0x0 |
IntClr |
GPIO中断标志位清零 |
WO |
0x0 |
状态寄存器 |
描述 |
访问 |
复位值 |
IntStatR |
上升沿GPIO中断状态 |
RO |
0x0 |
IntStatF |
下降沿GPIO中断状态 |
RO |
0x0 |
IntStatus |
GPIO整体中断状态 |
RO |
0x0 |
1) GPIO整体中断状态寄存器IOIntStatus
该寄存器反映了GPIO端口上的中断状态,对于LPC1700系列Cortex-M3,只有PORT0和PORT2端口具有中断功能。
位 |
符号 |
描述 |
复位值 |
0 |
P0Int |
P0 GPIO中断挂起状态。 0:在P0上没有挂起的状态。 1:在P0上至少有一个挂起的中断。 |
0 |
1 |
- |
保留,从保留位读取的值未定义 |
NA |
2 |
P2Int |
P2 GPIO中断挂起状态。 0:在P2中没有挂起的中断。 1:在P2上至少有一个挂起的中断 |
0 |
31:2 |
- |
保留,从保留位读取的值未定义 |
NA |
操作实例:if(IOIntStatus & 0x01) //如果PORT0上有中断挂起
2) 上升沿寄存器的GPIO中断使能IO0IntEnRo
该寄存器的每个位使能相应GPIO端口引脚的上升沿中断,若无此管脚,则对应位为保留位。
位 |
符号 |
描述 |
复位值 |
31-0 |
P0xER P2xER |
上升沿中断触发使能位。 IOxIntEnR的位0对应引脚Px..0 IOxIntR的位31对应引脚Px.31. 0:上升沿中断禁能 1:上升沿中断使能 |
0 |
操作实例:IO0IntEnR = IO0IntEnR | 0x01 //使能P0.0引脚上升沿中断。
该寄存器的每个位使能相应GPIO端口引脚的下降沿中断,若无此管脚,则对应位为保留位。
位 |
符号 |
描述 |
复位值 |
31-0 |
P0xEF P2xEF |
下降沿中断触发使能位。 IOxIntEnF的位0对应引脚Px..0 IOxIntF的位31对应引脚Px.31. 0:下降沿中断禁能 1:下降沿中断使能 |
0 |
操作实例:IO0IntEnR = IO0IntEnF | 0x01 //使能P0.0引脚下降沿中断。
3) 上升沿寄存器的GPIO中断状态IO0IntStatR和IO2IntStatR
该只读寄存器的每个位表示相应端口的上升中断状态。若无此管脚,则对应位为保留位。
位 |
符号 |
描述 |
复位值 |
31-0 |
P0xREI P2xREI |
上升沿中断状态。 IOxIntStatR的位0对应引脚Px..0 IOxIntStatR的位31对应引脚Px.31. 0:对应引脚没有上升沿中断 1:对应引脚出现上升沿中断 |
0 |
操作实例:If(IO0IntStatR & 0x01) //如果P0.0上有上升沿中断产生。
4) 下降沿寄存器的GPIO中断状态IO0IntStatF和IO2IntStatF
该只读寄存器的每个位表示相应端口的下降沿中断状态。若无此引脚,则对应位为保留位。
位 |
符号 |
描述 |
复位值 |
31-0 |
P0xFEI P2xFEI |
上升沿中断状态。 IOxIntStatF的位0对应引脚Px..0 IOxIntStatF的位31对应引脚Px.31. 0:对应引脚没有下降沿中断 1:对应引脚出现下降沿中断 |
0 |
5)GPIO中断标志清零寄存器IO0IntClr和IO2IntClr
向改寄存器的某些位写入1,将清零对应引脚的中断标志。若无此管脚,则对应位为保留位。
位 |
符号 |
描述 |
复位值 |
31-0 |
P0xCI P2xCI |
清零GPIO端口中断。IOxIntClr的位1对应引脚Px.0,IOxIntClr的位31对应引脚Px.31。 0:在IOxIntStatR和/或IOxIntStatF的相应位不变。 1:在IOxIntStatR和/或IOxIntStatF中的相应位清零。 |
0 |
GPIO使用注意事项:
1) 连续访问FIOSET和FIOCLR影响相同的GPIO引脚/位
配置为输出的GPIO引脚的状态通过写引脚的FIOSET和FIOCLR寄存器决定。对FIOSET/FIOCLR的寄存器的最后访问决定引脚的最终输出。
FIO0DIR = 0x0000 0080 ;//引脚P0.7配置为输出
FIO0CLR = 0x0000 0080;//P0.7变为低电压
FIO0SET = 0x0000 0080;//P0.7变为高电压
FIO0CLR = 0x0000 0080;//P0.7变为低电压
2) 写FIOSET/FIOCLR & FIOPIN
从一组IO口线上输出变量Data中保存的值需四步,
首先,设置引脚连接模块和引脚方向,
输出数据时先清零所有输出IO口线,
在把Data变量的值写入到FIOxSET寄存器中,
那么该变量中为1的位将在相应的IO口线中反映出来,而变量中为0 的位将不影响相应引脚输出的电平状态,仍然保持低电平。
操作实例:
#define DataBus 0xFF //定义数据口位置的宏
PINSEL0 &= 0xFFFF 0000; //第一步:设置引脚连接模块,将P0.0-P0.7设置为GPIO功能
FIO0DIR |= DataBus; //第二步:将所有数据IO口设置为输出
FIO0CLR = DataBus; //第三步:将所有数据IO口设置为低电平输出
FIO0SET = DataBus; //第四步:将要输出的数据从IO口输出
在第三步和第四步之间存在一个中间状态,虽然这个中间状态比较短暂,但是如果应用系统中不允许出现这样的中间状态,则可以考虑下面的方法。
介绍FIOPIN寄存器时,该写寄存器可以直接控制输出寄存器:
#define DataBus 0xFF //定义表示数据口线的位置
PINSEL0 &= 0xFFFF 0000; //第一步:设置引脚连接模块,将P0.0-P0.7设置为GPIO功能
FIO0DIR |= DataBus ; //第二步:将属于数据IO设置为输出
FIO0PIN = (IO0SET & 0xFFFFFF00) | DataBus ;//第三步:将要输出的数据从IO口输出
写FIOPIN寄存器是直接对相应端口的所有GPIO引脚生效的,也就是说写入值中为1的所对应的GPIO引脚将输出高电平,为0的位所对应的GPIO引脚将输出低电平,高低电平是同时发生的,所以不存在中间状态。这样的操作在一些场合中是不安全的,因为它有可能影响到不想修改的位。
3) GPIO端口上0和1的瞬时输出
先写FIOSET再写FIOCLR寄存器可使引脚先输出1在输出0,有的系统允许这段延时时间,但某些应用要求一个GPIO口的一组引脚同时输出一个二进制数,这可以通过写端口的FIOPIN寄存器实现。
下面的代码实现的是:P0.[31:16]和P0.[7:0]输出保持不变的同时将P0.[15:8]设置为0xA5,不管P0.[15:8]之前是何值:
FIO0PIN = (FIO0PIN & 0xFFFF 00FF) | 0x0000A500;
使用高速端口访问可以得到相同的结果:
方法1:使用32位可访问高速GPIO寄存器
FIO0MASK = 0xFFFF00FF;
FIO0PIN = 0x00000A500;
方法2:使用16位可访问高速GPIO寄存器
FIO0MASK = 0x00FF ;
FIO0FINL = 0xA500 ;
方法3:使用8位可访问高速GPIO寄存器
FIO0PIN = 0xA5;
4)I2C接口引脚:
LPC1700系列Cortex-M3大部分的IO引脚为推挽方式输出,但是具有I2C总线功能的IO引脚为开漏输出(P0.27 P0.28)。使用这些开漏输出的引脚作为GPIO功能,并用于高电平输出或者引脚状态输入时,要接上拉电阻才能正常使用。
4) GPIO引脚驱动能力
推挽输出的IO正常拉出,灌入电流均为4mA,短时间极限值为40mA。
5) P0.29 P0.30
P0.29与P0.30在作为GPIO使用时,只能同时设置为输入模式或者同时设置为输出模式,不能设置为不同的模式。例如:只有FIO0DIR[29] = FIO0DIR[30] = 1时,P0.29和P0.30才是输出模式,否则全是输入模式。即,只要其中有一个为0,则便是输入模式。
GPIO应用实例:
1) 将P0.0设置为输出高电平
PINSEL0 &= 0xFFFFFFFC ; //第一步:设置引脚连接模块,将P0.0设置为GPIO
FIO0DIR |= 0x00000001 ; //第二步:将P0.0设置为输出
FIO0SET = 0x00000001; //第三步:将P0.0 设置为输出高电平
2) 使用GPIO控制蜂鸣器
使用P0.7控制蜂鸣器间隔的鸣叫。使用高速IO来控制。
#define BEEPCON 0x0000 0080 //P0.7引脚控制蜂鸣器,点电平蜂鸣
FIOSEL0 = 0x0000 0000 ; //设置引脚连接GPIO
FIO0DIR = BEEPCON ; //设置IO为输出
While(1)
{
FIO0SET = BEEPCON ; //BEEPCON = 1
Delay(10);
FIO0CLR = BEEPCON; //BEEPCON = 0
Delay(10);
}
3)读取引脚的电平状态
使用高速GPIO,读取某(几)个IO口的电平状态要完成三步:
Uint Pinstat ; //定义一个32位的变量用于存放IO状态
PINSEL0 &= 0xFFFF FFFC ; //第一步:设置引脚连接模块,将P0.0设置为GPIO
PIN0DIR &= 0xFFFF FFFE ; //第二步:把P0.0设置为输入状态
Pinstat = FIO0PIN & 0x01 ; // 第三步:通过FIN0PIN寄存器获取P0.0当前的电平状态。