ARM汇编基础:内存管理与寻址

ARM处理器的内存管理是嵌入式系统和操作系统开发的核心内容。本文将详细介绍ARM架构的内存管理单元(MMU)、虚拟内存机制、缓存系统以及相关的汇编编程技术。

ARM内存架构概述

内存层次结构

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
@ ARM内存层次结构示例
@ CPU -> L1 Cache -> L2 Cache -> Main Memory -> Storage

.section .data
memory_info: .ascii "ARM Memory Hierarchy\n"
cache_line_size: .word 32 @ 缓存行大小(字节)
page_size: .word 4096 @ 页面大小(字节)

.section .text
.global memory_hierarchy_demo

memory_hierarchy_demo:
@ 演示不同内存访问模式

@ 1. 寄存器访问(最快)
mov r0, #42
mov r1, r0

@ 2. L1缓存访问
ldr r2, =cache_line_size
ldr r3, [r2]

@ 3. 主内存访问
ldr r4, =memory_info
ldrb r5, [r4]

@ 4. 预取指令优化内存访问
pld [r4, #64] @ 预取64字节后的数据到缓存

bx lr

内存映射和地址空间

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
@ ARM内存映射示例
.section .data
@ 典型的ARM内存布局
@ 0x00000000 - 0x7FFFFFFF: 用户空间
@ 0x80000000 - 0xFFFFFFFF: 内核空间

user_data: .word 0x12345678
kernel_addr: .word 0x80000000

.section .text
.global memory_mapping_demo

memory_mapping_demo:
@ 检查地址空间
ldr r0, =user_data
ldr r1, =kernel_addr

@ 比较地址范围
cmp r0, #0x80000000
movlt r2, #1 @ 用户空间地址
movge r2, #0 @ 内核空间地址

@ 地址对齐检查
and r3, r0, #3 @ 检查4字节对齐
cmp r3, #0
moveq r4, #1 @ 已对齐
movne r4, #0 @ 未对齐

bx lr

虚拟内存管理

页表结构

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
@ ARM页表管理
.section .data
@ 页表项结构(简化版)
page_table_base: .word 0x10000000

@ 页表项标志位
.equ PTE_PRESENT, 0x01 @ 页面存在
.equ PTE_WRITABLE, 0x02 @ 可写
.equ PTE_USER, 0x04 @ 用户可访问
.equ PTE_ACCESSED, 0x20 @ 已访问
.equ PTE_DIRTY, 0x40 @ 已修改

.section .text
.global page_table_demo

page_table_demo:
@ 创建页表项
ldr r0, =page_table_base

@ 虚拟地址到物理地址的映射
mov r1, #0x1000 @ 虚拟页号
mov r2, #0x2000 @ 物理页号

@ 计算页表项地址
lsr r3, r1, #10 @ 页目录索引
and r4, r1, #0x3FF @ 页表索引

@ 构造页表项
orr r5, r2, #PTE_PRESENT
orr r5, r5, #PTE_WRITABLE
orr r5, r5, #PTE_USER

@ 存储页表项
add r6, r0, r4, lsl #2
str r5, [r6]

bx lr

@ 地址转换函数
.global virtual_to_physical

virtual_to_physical:
@ 输入:r0 = 虚拟地址
@ 输出:r1 = 物理地址

@ 提取页号和页内偏移
lsr r2, r0, #12 @ 页号
and r3, r0, #0xFFF @ 页内偏移

@ 查找页表
ldr r4, =page_table_base
ldr r5, [r4, r2, lsl #2]

@ 检查页面是否存在
tst r5, #PTE_PRESENT
beq page_fault

@ 计算物理地址
bic r6, r5, #0xFFF @ 清除标志位,获取物理页基址
orr r1, r6, r3 @ 物理页基址 + 页内偏移

mov r0, #0 @ 成功
bx lr

page_fault:
mov r0, #-1 @ 页面错误
bx lr

MMU配置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
@ MMU(内存管理单元)配置
.section .data
@ CP15协处理器寄存器定义
.equ CP15_CTRL, 0 @ 控制寄存器
.equ CP15_TTB, 2 @ 转换表基址寄存器
.equ CP15_DOMAIN, 3 @ 域访问控制寄存器
.equ CP15_FAULT_STATUS, 5 @ 故障状态寄存器
.equ CP15_FAULT_ADDR, 6 @ 故障地址寄存器

@ MMU控制位
.equ MMU_ENABLE, 0x01 @ 使能MMU
.equ CACHE_ENABLE, 0x04 @ 使能数据缓存
.equ ICACHE_ENABLE, 0x1000 @ 使能指令缓存

.section .text
.global mmu_init

mmu_init:
@ 禁用MMU和缓存
mrc p15, 0, r0, c1, c0, 0 @ 读取控制寄存器
bic r0, r0, #MMU_ENABLE
bic r0, r0, #CACHE_ENABLE
bic r0, r0, #ICACHE_ENABLE
mcr p15, 0, r0, c1, c0, 0 @ 写回控制寄存器

@ 设置转换表基址
ldr r1, =page_table_base
mcr p15, 0, r1, c2, c0, 0 @ 设置TTB

@ 设置域访问控制
mov r2, #0x55555555 @ 所有域设为客户模式
mcr p15, 0, r2, c3, c0, 0

@ 清除TLB
mov r3, #0
mcr p15, 0, r3, c8, c7, 0 @ 清除整个TLB

@ 使能MMU和缓存
orr r0, r0, #MMU_ENABLE
orr r0, r0, #CACHE_ENABLE
orr r0, r0, #ICACHE_ENABLE
mcr p15, 0, r0, c1, c0, 0

bx lr

@ TLB管理
.global tlb_operations

tlb_operations:
@ 清除整个TLB
mov r0, #0
mcr p15, 0, r0, c8, c7, 0

@ 清除指定地址的TLB项
ldr r1, =0x12345000
mcr p15, 0, r1, c8, c7, 1

@ 清除指定ASID的TLB项
mov r2, #1
mcr p15, 0, r2, c8, c7, 2

bx lr

缓存管理

缓存操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
@ ARM缓存管理
.section .data
cache_test_data: .space 1024, 0x55

.section .text
.global cache_operations

cache_operations:
@ 数据缓存操作

@ 1. 清除数据缓存行
ldr r0, =cache_test_data
mcr p15, 0, r0, c7, c6, 1 @ 清除指定地址的数据缓存行

@ 2. 清除并无效化数据缓存行
mcr p15, 0, r0, c7, c14, 1 @ 清除并无效化

@ 3. 预取数据到缓存
pld [r0] @ 预取当前地址
pld [r0, #32] @ 预取下一个缓存行

@ 4. 内存屏障
dsb @ 数据同步屏障
dmb @ 数据内存屏障
isb @ 指令同步屏障

@ 指令缓存操作

@ 5. 无效化指令缓存
mov r1, #0
mcr p15, 0, r1, c7, c5, 0 @ 无效化整个指令缓存

@ 6. 无效化指令缓存行
mcr p15, 0, r0, c7, c5, 1 @ 无效化指定地址的指令缓存行

@ 7. 刷新分支预测器
mcr p15, 0, r1, c7, c5, 6 @ 刷新分支预测器

bx lr

@ 缓存一致性管理
.global cache_coherency

cache_coherency:
@ DMA操作前的缓存管理
ldr r0, =cache_test_data
mov r1, #1024

@ DMA写入前:清除缓存确保数据写回内存
add r2, r0, r1
clean_loop:
cmp r0, r2
bge clean_done
mcr p15, 0, r0, c7, c10, 1 @ 清除数据缓存行
add r0, r0, #32 @ 下一个缓存行
b clean_loop
clean_done:

@ DMA读取后:无效化缓存确保读取最新数据
ldr r0, =cache_test_data
add r2, r0, r1
invalidate_loop:
cmp r0, r2
bge invalidate_done
mcr p15, 0, r0, c7, c6, 1 @ 无效化数据缓存行
add r0, r0, #32
b invalidate_loop
invalidate_done:

bx lr

缓存性能优化

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
@ 缓存友好的编程技术
.section .data
matrix_a: .space 1024 @ 32x32字节矩阵
matrix_b: .space 1024
matrix_c: .space 1024

.section .text
.global cache_friendly_matrix_multiply

cache_friendly_matrix_multiply:
@ 缓存友好的矩阵乘法
@ 使用分块算法减少缓存缺失

ldr r0, =matrix_a
ldr r1, =matrix_b
ldr r2, =matrix_c

mov r3, #0 @ i = 0
outer_loop:
cmp r3, #32
bge multiply_done

mov r4, #0 @ j = 0
middle_loop:
cmp r4, #32
bge outer_next

@ 预取下一行数据
add r5, r0, r3, lsl #5 @ matrix_a[i]
add r5, r5, #32
pld [r5]

mov r5, #0 @ k = 0
mov r6, #0 @ sum = 0
inner_loop:
cmp r5, #32
bge store_result

@ 计算 matrix_a[i][k] * matrix_b[k][j]
add r7, r0, r3, lsl #5 @ matrix_a[i]
ldrb r8, [r7, r5] @ matrix_a[i][k]

add r7, r1, r5, lsl #5 @ matrix_b[k]
ldrb r9, [r7, r4] @ matrix_b[k][j]

mul r10, r8, r9
add r6, r6, r10

add r5, r5, #1
b inner_loop

store_result:
@ 存储结果
add r7, r2, r3, lsl #5 @ matrix_c[i]
strb r6, [r7, r4] @ matrix_c[i][j] = sum

add r4, r4, #1
b middle_loop

outer_next:
add r3, r3, #1
b outer_loop

multiply_done:
bx lr

@ 数据预取优化
.global prefetch_optimization

prefetch_optimization:
ldr r0, =cache_test_data
mov r1, #1024
mov r2, #0 @ sum = 0

@ 预取策略:提前预取64字节
sum_loop:
cmp r1, #0
ble sum_done

@ 预取未来的数据
pld [r0, #64]

@ 处理当前数据
ldr r3, [r0]
add r2, r2, r3

add r0, r0, #4
sub r1, r1, #4
b sum_loop

sum_done:
mov r0, r2 @ 返回总和
bx lr

内存保护和安全

内存保护单元(MPU)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
@ MPU配置(适用于Cortex-M系列)
.section .data
@ MPU区域配置
.equ MPU_REGION_0, 0
.equ MPU_REGION_1, 1
.equ MPU_REGION_2, 2

@ 访问权限
.equ MPU_NO_ACCESS, 0x00
.equ MPU_RW_PRIV, 0x01 @ 特权读写
.equ MPU_RW_ALL, 0x03 @ 全部读写
.equ MPU_RO_PRIV, 0x05 @ 特权只读
.equ MPU_RO_ALL, 0x06 @ 全部只读

.section .text
.global mpu_init

mpu_init:
@ 禁用MPU
ldr r0, =0xE000ED94 @ MPU_CTRL寄存器
mov r1, #0
str r1, [r0]

@ 配置区域0:代码段(只读)
ldr r0, =0xE000ED98 @ MPU_RNR(区域号寄存器)
mov r1, #MPU_REGION_0
str r1, [r0]

ldr r0, =0xE000ED9C @ MPU_RBAR(基址寄存器)
ldr r1, =0x08000000 @ Flash基址
str r1, [r0]

ldr r0, =0xE000EDA0 @ MPU_RASR(属性寄存器)
mov r1, #0x06000000 @ 1MB大小
orr r1, r1, #MPU_RO_ALL @ 只读权限
orr r1, r1, #0x01 @ 使能区域
str r1, [r0]

@ 配置区域1:RAM段(读写)
ldr r0, =0xE000ED98
mov r1, #MPU_REGION_1
str r1, [r0]

ldr r0, =0xE000ED9C
ldr r1, =0x20000000 @ RAM基址
str r1, [r0]

ldr r0, =0xE000EDA0
mov r1, #0x04000000 @ 256KB大小
orr r1, r1, #MPU_RW_ALL @ 读写权限
orr r1, r1, #0x01 @ 使能区域
str r1, [r0]

@ 使能MPU
ldr r0, =0xE000ED94
mov r1, #0x05 @ 使能MPU和默认内存映射
str r1, [r0]

bx lr

内存访问检查

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
@ 内存访问权限检查
.section .text
.global memory_access_check

memory_access_check:
@ 输入:r0 = 地址,r1 = 访问类型(0=读,1=写)
@ 输出:r0 = 0(允许),-1(拒绝)

@ 检查地址范围
ldr r2, =0x08000000 @ Flash起始地址
ldr r3, =0x08100000 @ Flash结束地址

cmp r0, r2
blt check_ram
cmp r0, r3
bge check_ram

@ Flash区域:只允许读取
cmp r1, #0
moveq r0, #0 @ 读取允许
movne r0, #-1 @ 写入拒绝
bx lr

check_ram:
ldr r2, =0x20000000 @ RAM起始地址
ldr r3, =0x20040000 @ RAM结束地址

cmp r0, r2
blt access_denied
cmp r0, r3
bge access_denied

@ RAM区域:读写都允许
mov r0, #0
bx lr

access_denied:
mov r0, #-1
bx lr

@ 内存故障处理
.global memory_fault_handler

memory_fault_handler:
@ 保存上下文
push {r0-r12, lr}

@ 读取故障信息
ldr r0, =0xE000ED28 @ CFSR(可配置故障状态寄存器)
ldr r1, [r0]

@ 检查内存管理故障
tst r1, #0xFF
bne handle_mem_fault

@ 检查总线故障
tst r1, #0xFF00
bne handle_bus_fault

@ 检查用法故障
tst r1, #0xFFFF0000
bne handle_usage_fault

b fault_exit

handle_mem_fault:
@ 处理内存管理故障
ldr r2, =0xE000ED34 @ MMFAR(内存管理故障地址)
ldr r3, [r2]
@ 记录故障地址和类型
b fault_exit

handle_bus_fault:
@ 处理总线故障
ldr r2, =0xE000ED38 @ BFAR(总线故障地址)
ldr r3, [r2]
b fault_exit

handle_usage_fault:
@ 处理用法故障
b fault_exit

fault_exit:
@ 清除故障标志
str r1, [r0]

@ 恢复上下文
pop {r0-r12, lr}
bx lr

DMA和内存一致性

DMA配置和管理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
@ DMA内存传输
.section .data
dma_source: .space 1024, 0xAA
dma_dest: .space 1024, 0x00

.section .text
.global dma_memory_transfer

dma_memory_transfer:
@ DMA传输前的缓存管理
ldr r0, =dma_source
ldr r1, =dma_dest
mov r2, #1024

@ 清除源数据的缓存(确保数据写回内存)
bl cache_clean_range

@ 无效化目标区域的缓存(确保读取最新数据)
mov r0, r1
bl cache_invalidate_range

@ 配置DMA控制器(简化示例)
ldr r3, =0x40026000 @ DMA控制器基址

@ 设置源地址
ldr r4, =dma_source
str r4, [r3, #0x00]

@ 设置目标地址
ldr r4, =dma_dest
str r4, [r3, #0x04]

@ 设置传输长度
mov r4, #1024
str r4, [r3, #0x08]

@ 启动DMA传输
mov r4, #0x01
str r4, [r3, #0x0C]

@ 等待传输完成
wait_dma:
ldr r4, [r3, #0x10] @ 状态寄存器
tst r4, #0x01 @ 检查完成标志
beq wait_dma

@ DMA传输后的缓存管理
ldr r0, =dma_dest
mov r2, #1024
bl cache_invalidate_range

bx lr

@ 缓存清除函数
cache_clean_range:
@ 输入:r0 = 起始地址,r2 = 大小
add r1, r0, r2 @ 结束地址
bic r0, r0, #31 @ 对齐到缓存行边界

clean_loop_range:
cmp r0, r1
bge clean_range_done
mcr p15, 0, r0, c7, c10, 1 @ 清除缓存行
add r0, r0, #32
b clean_loop_range

clean_range_done:
dsb @ 数据同步屏障
bx lr

@ 缓存无效化函数
cache_invalidate_range:
@ 输入:r0 = 起始地址,r2 = 大小
add r1, r0, r2
bic r0, r0, #31

invalidate_loop_range:
cmp r0, r1
bge invalidate_range_done
mcr p15, 0, r0, c7, c6, 1 @ 无效化缓存行
add r0, r0, #32
b invalidate_loop_range

invalidate_range_done:
dsb
bx lr

内存调试和性能分析

内存访问监控

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
@ 内存访问性能监控
.section .data
access_counter: .word 0
cache_miss_counter: .word 0

.section .text
.global memory_performance_monitor

memory_performance_monitor:
@ 启用性能监控单元(PMU)

@ 使能用户模式访问PMU
mrc p15, 0, r0, c9, c14, 0 @ PMUSERENR
orr r0, r0, #1
mcr p15, 0, r0, c9, c14, 0

@ 使能性能计数器
mrc p15, 0, r0, c9, c12, 0 @ PMCR
orr r0, r0, #1 @ 使能所有计数器
orr r0, r0, #2 @ 重置所有计数器
mcr p15, 0, r0, c9, c12, 0

@ 配置事件计数器0:L1数据缓存缺失
mov r0, #0
mcr p15, 0, r0, c9, c12, 5 @ 选择计数器0
mov r0, #0x03 @ L1数据缓存缺失事件
mcr p15, 0, r0, c9, c13, 1 @ 设置事件类型

@ 配置事件计数器1:内存访问
mov r0, #1
mcr p15, 0, r0, c9, c12, 5
mov r0, #0x19 @ 内存访问事件
mcr p15, 0, r0, c9, c13, 1

@ 使能计数器
mov r0, #0x80000003 @ 使能周期计数器和事件计数器0,1
mcr p15, 0, r0, c9, c12, 1

bx lr

@ 读取性能计数器
.global read_performance_counters

read_performance_counters:
@ 读取周期计数器
mrc p15, 0, r0, c9, c13, 0 @ PMCCNTR

@ 读取事件计数器0(缓存缺失)
mov r1, #0
mcr p15, 0, r1, c9, c12, 5
mrc p15, 0, r1, c9, c13, 2

@ 读取事件计数器1(内存访问)
mov r2, #1
mcr p15, 0, r2, c9, c12, 5
mrc p15, 0, r2, c9, c13, 2

@ 计算缓存缺失率
@ miss_rate = cache_misses / memory_accesses
cmp r2, #0
beq no_accesses

@ 简单的百分比计算(miss_rate * 100)
mov r3, #100
mul r1, r1, r3
udiv r3, r1, r2 @ 缓存缺失率(百分比)

no_accesses:
bx lr

内存泄漏检测

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
@ 简单的内存分配跟踪
.section .data
heap_start: .word 0x20010000
heap_end: .word 0x20020000
heap_current: .word 0x20010000

@ 分配块头部结构
.struct 0
block_size: .struct . + 4
block_magic: .struct . + 4
block_next: .struct . + 4
block_header_size: .struct .

.equ MAGIC_ALLOCATED, 0xDEADBEEF
.equ MAGIC_FREE, 0xFEEDFACE

.section .text
.global heap_malloc

heap_malloc:
@ 输入:r0 = 请求大小
@ 输出:r0 = 分配的地址(失败时为0)

push {r1-r4, lr}

@ 对齐到4字节边界
add r0, r0, #3
bic r0, r0, #3

@ 加上头部大小
add r1, r0, #block_header_size

@ 检查是否有足够空间
ldr r2, =heap_current
ldr r3, [r2]
add r4, r3, r1

ldr r1, =heap_end
ldr r1, [r1]
cmp r4, r1
bgt malloc_fail

@ 设置块头部
str r0, [r3, #block_size] @ 大小
ldr r1, =MAGIC_ALLOCATED
str r1, [r3, #block_magic] @ 魔数
str r4, [r3, #block_next] @ 下一个块

@ 更新堆指针
str r4, [r2]

@ 返回数据区域地址
add r0, r3, #block_header_size
pop {r1-r4, lr}
bx lr

malloc_fail:
mov r0, #0
pop {r1-r4, lr}
bx lr

.global heap_free

heap_free:
@ 输入:r0 = 要释放的地址

push {r1-r3, lr}

@ 检查地址有效性
cmp r0, #0
beq free_done

@ 获取块头部地址
sub r1, r0, #block_header_size

@ 检查魔数
ldr r2, [r1, #block_magic]
ldr r3, =MAGIC_ALLOCATED
cmp r2, r3
bne free_done @ 无效块或已释放

@ 标记为已释放
ldr r3, =MAGIC_FREE
str r3, [r1, #block_magic]

@ 清零数据区域(调试用)
ldr r2, [r1, #block_size]
mov r3, #0
clear_loop:
cmp r2, #0
ble free_done
str r3, [r0], #4
sub r2, r2, #4
b clear_loop

free_done:
pop {r1-r3, lr}
bx lr

@ 内存泄漏检查
.global check_memory_leaks

check_memory_leaks:
push {r0-r4, lr}

ldr r0, =heap_start
ldr r0, [r0]
ldr r1, =heap_current
ldr r1, [r1]

mov r2, #0 @ 泄漏计数

check_loop:
cmp r0, r1
bge check_done

@ 检查块状态
ldr r3, [r0, #block_magic]
ldr r4, =MAGIC_ALLOCATED
cmp r3, r4
addeq r2, r2, #1 @ 发现泄漏

@ 移动到下一个块
ldr r0, [r0, #block_next]
b check_loop

check_done:
mov r0, r2 @ 返回泄漏数量
pop {r0-r4, lr}
bx lr

总结

ARM架构的内存管理是嵌入式系统开发的核心技术:

核心概念

  • 虚拟内存:提供地址空间隔离和保护
  • MMU/MPU:硬件级内存管理和保护
  • 缓存系统:提高内存访问性能
  • DMA一致性:确保数据一致性

关键技术

  • 页表管理:虚拟到物理地址转换
  • 缓存操作:清除、无效化、预取
  • 内存屏障:确保内存访问顺序
  • 性能监控:分析内存访问模式

实际应用

  • 操作系统:进程隔离和内存保护
  • 嵌入式系统:实时性能优化
  • 驱动程序:DMA和硬件交互
  • 安全系统:内存访问控制

最佳实践

  • 合理配置MMU/MPU提供内存保护
  • 使用缓存友好的算法提高性能
  • 正确处理DMA一致性问题
  • 实施内存泄漏检测和调试

掌握ARM内存管理技术能够帮助开发者构建高性能、安全可靠的嵌入式系统和操作系统。

版权所有,如有侵权请联系我