以下是代码部分
#define CON (volatile unsigned long*)0xA0000280
#define DAT (volatile unsigned long*)0xA0000284
/*
* 用于段描述符的一些宏定义
*/
#define MMU_FULL_ACCESS (3 << 10) /* 访问权限 */
#define MMU_DOMAIN (0 << 5) /* 属于哪个域 */
#define MMU_SPECIAL (1 << 4) /* 必须是1 */
#define MMU_CACHEABLE (1 << 3) /* cacheable */
#define MMU_BUFFERABLE (1 << 2) /* bufferable */
#define MMU_SECTION (2) /* 表示这是段描述符 */
#define MMU_SECDESC (MMU_FULL_ACCESS | MMU_DOMAIN | MMU_SPECIAL | MMU_SECTION)
#define MMU_SECDESC_WB (MMU_FULL_ACCESS | MMU_DOMAIN | MMU_SPECIAL | MMU_CACHEABLE | MMU_BUFFERABLE | MMU_SECTION)
void create_page_table(void)
{
//对我的GPIO进行映射
unsigned long *ttb = (unsigned long *)0x20000000;//建立段描述符的基地址
unsigned long vaddr, paddr;//虚拟地址,物理地址
vaddr = 0xA0000000;
paddr = 0xE0200000;
*(ttb + (vaddr >> 20)) = (paddr & 0xFFF00000) | MMU_SECDESC;
//取虚拟地址高12位 将物理基地址取出 权限等的设置
//对我的内存进行映射
vaddr = 0x20000000;
paddr = 0x20000000;
while (vaddr < 0x24000000)
{
*(ttb + (vaddr >> 20)) = (paddr & 0xFFF00000) | MMU_SECDESC_WB;//使用MMU时通常打开Cache,Write buffer
vaddr += 0x100000;//每一个表项只能映射1M
paddr += 0x100000;
}
}
void mmu_init()
{
__asm__(
/*设置TTB*/
"ldr r0, =0x20000000\n"
"mcr p15, 0, r0, c2, c0, 0\n"
/*不进行权限检查*/
"mvn r0, #0\n"
"mcr p15, 0, r0, c3, c0, 0\n"
/*使能MMU*/
"mrc p15, 0, r0, c1, c0, 0\n"
"orr r0, r0, #0x0001\n"
"mcr p15, 0, r0, c1, c0, 0\n"
:
:
);
}
int gboot_main()
{
create_page_table();
mmu_init();
*(CON) = 0x1;
*(DAT) = 0x0;
return 0;
}