/*
* 文件名: start.S
* 作者: 朱老师
* 描述: 演示轮询方式处理按键
*/
#define WTCON 0xE2700000
#define SVC_STACK 0xd0037d80
.global _start // 把_start链接属性改为外部,这样其他文件就可以看见_start了
_start:
// 第1步:关看门狗(向WTCON的bit5写入0即可)
ldr r0, =WTCON
ldr r1, =0x0
str r1, [r0]
// 第2步:设置SVC栈
ldr sp, =SVC_STACK
// 第3步:开/关icache
mrc p15,0,r0,c1,c0,0; // 读出cp15的c1到r0中
//bic r0, r0, #(1<<12) // bit12 置0 关icache
orr r0, r0, #(1<<12) // bit12 置1 开icache
mcr p15,0,r0,c1,c0,0;
// 从这里之后就可以开始调用C程序了
bl key_init
bl key_polling
// 汇编最后的这个死循环不能丢
b .
#define GPJ0CON 0xE0200240
#define GPJ0DATA 0xE0200244
#define GPD0CON 0xE02000A0
#define GPD0DATA 0xE02000A4
#define rGPJ0CON *((volatile unsigned int *)GPJ0CON)
#define rGPJ0DAT *((volatile unsigned int *)GPJ0DATA)
#define rGPD0CON *((volatile unsigned int *)GPD0CON)
#define rGPD0DAT *((volatile unsigned int *)GPD0DATA)
// 亮1个led
void led1(void)
{
rGPJ0CON = 0x11111111;
rGPD0CON = 0x11111111;
rGPJ0DAT = ~(1 << 3);
rGPD0DAT = 0xff;
}
void led2(void)
{
rGPJ0CON = 0x11111111;
rGPD0CON = 0x11111111;
rGPJ0DAT = ~(1 << 4);
rGPD0DAT = 0xff;
}
void led3(void)
{
rGPJ0CON = 0x11111111;
rGPD0CON = 0x11111111;
rGPJ0DAT = ~(1 << 5);
rGPD0DAT = 0xff;
}
void led4(void)
{
rGPJ0CON = 0x11111111;
rGPD0CON = 0x11111111;
rGPJ0DAT = 0xff;
rGPD0DAT = ~(1 << 1);
}
void led_off(void)
{
rGPJ0CON = 0x11111111;
rGPD0CON = 0x11111111;
rGPJ0DAT = 0xff;
rGPD0DAT = 0xff;
}
// 定义操作寄存器的宏
#define GPH0CON 0xE0200C00
#define GPH0DAT 0xE0200C04
#define GPH2CON 0xE0200C40
#define GPH2DAT 0xE0200C44
#define rGPH0CON (*(volatile unsigned int *)GPH0CON)
#define rGPH0DAT (*(volatile unsigned int *)GPH0DAT)
#define rGPH2CON (*(volatile unsigned int *)GPH2CON)
#define rGPH2DAT (*(volatile unsigned int *)GPH2DAT)
// 初始化按键
void key_init(void)
{
// 设置GPHxCON寄存器,设置为输入模式
// GPH0CON的bit8~15全部设置为0,即可
rGPH0CON &= ~(0xFF<<8);
// GPH2CON的bit0~15全部设置为0,即可
rGPH2CON &= ~(0xFFFF<<0);
}
void key_polling(void)
{
// 依次,挨个去读出每个GPIO的值,判断其值为1还是0.如果为1则按键按下,为0则弹起
// 轮询的意思就是反复循环判断有无按键,隔很短时间
while (1)
{
// 对应开发板上标着LEFT的那个按键
if (rGPH0DAT & (1<<2))
{
// 为1,说明没有按键
led_off();
}
else
{
// 为0,说明有按键
led1();
}
// 对应开发板上标着DOWN的那个按键
if (rGPH0DAT & (1<<3))
{
// 为1,说明没有按键
led_off();
}
else
{
// 为0,说明有按键
led2();
}
// 对应开发板上标着UP的那个按键
if (rGPH2DAT & (1<<0))
{
// 为1,说明没有按键
led_off();
}
else
{
// 为0,说明有按键
led3();
}
// 对应开发板上标着UP的那个按键
if (rGPH2DAT & (1 << 1))
{
// 为1,说明没有按键
led_off();
}
else
{
// 为0,说明有按键
led4();
}
}
}