commit 5b7a041b5df9da1add8515038342aa1a15d5d0b4
parent 78c59f4a1b6b2f3101551b20ee5f77ae30d97cf9
Author: Matsuda Kenji <info@mtkn.jp>
Date: Tue, 18 Apr 2023 11:05:44 +0900
use C to reprogram flash
Diffstat:
M | flash.s | | | 67 | ++++++++++++++++++++++++++++++++++++++++++++++--------------------- |
M | mach.s | | | 10 | ++++++++++ |
M | main.c | | | 18 | ++++++++++++++++++ |
3 files changed, 74 insertions(+), 21 deletions(-)
diff --git a/flash.s b/flash.s
@@ -7,9 +7,11 @@
// erase the region of flash starting at ofs and size bytes long in size.
// ofs must be aligned in 4K and size must be multiple of 4K
frerase:
- push {r4, lr}
+ push {r4, r5, r6, r7, lr}
ldr r4, rom_base
+ mov r5, r0
+ mov r6, r1
ldrh r0, [r4, #0x14] // rom_func_table
ldr r1, =('I' | 'F' << 8) // _connect_internal_flash()
@@ -27,13 +29,13 @@ frerase:
ldr r1, =('R' | 'E' << 8) // _flash_range_erase()
ldrh r2, [r4, #0x18] // rom_table_lookup
blx r2
- mov r5, r0
- mov r0, #0
- mov r1, #1
- lsl r1, r1, #12
- lsl r2, r1, #4
- mov r3, #0xd8
- blx r5
+ mov r7, r0
+ mov r0, r5
+ mov r1, r6
+ mov r2, #1
+ lsl r2, r2, #16 // 64K
+ mov r3, #0xd8 // block erase
+ blx r7
ldrh r0, [r4, #0x14] // rom_func_table
ldr r1, =('F' | 'C' << 8) // _flash_flush_cache()
@@ -42,19 +44,44 @@ frerase:
blx r0
ldrh r0, [r4, #0x14] // rom_func_table
- ldr r1, =('R' | 'P' << 8) // _flash_enter_cmd_xip()
+ ldr r1, =('C' | 'X' << 8) // _flash_enter_cmd_xip()
+ ldrh r2, [r4, #0x18] // rom_table_lookup
+ blx r2
+ blx r0
+
+ pop {r4, r5, r6, r7, pc}
+
+ .global frprog
+ // void frprog(uint32_t ofs, uint8_t *data, size_t count);
+ // ofs must be aligned in 256 and data must be multiple of 256
+frprog:
+ push {r4, r5, r6,r7, lr}
+
+ ldr r4, rom_base
+ mov r5, r0
+ mov r6, r1
+ mov r7, r2
+
+ ldrh r0, [r4, #0x14] // rom_func_table
+ ldr r1, =('I' | 'F' << 8) // _connect_internal_flash()
+ ldrh r2, [r4, #0x18] // rom_table_lookup
+ blx r2
+ blx r0
+
+ ldrh r0, [r4, #0x14] // rom_func_table
+ ldr r1, =('E' | 'X' << 8) // _flash_exit_xip()
+ ldrh r2, [r4, #0x18] // rom_table_lookup
+ blx r2
+ blx r0
+
+ ldrh r0, [r4, #0x14] // rom_func_table
+ ldr r1, =('R' | 'P' << 8) // _flash_range_program()
ldrh r2, [r4, #0x18] // rom_table_lookup
blx r2
mov r3, r0
- mov r0, #0
- ldr r1, sram_base
- mov r2, #1
- lsl r2, r2, #12
- add r1, r1, r2
- ldr r2, =0xdeadbeef
- str r2, [r1, #0]
- mov r2, #1
- lsl r2, r2, #8
+ mov r0, r5
+ mov r1, r6
+ mov r2, r7
blx r3
ldrh r0, [r4, #0x14] // rom_func_table
@@ -69,9 +96,7 @@ frerase:
blx r2
blx r0
- ldr r3, xip_base
- ldr r0, [r3, #0]
- bl printh
+ pop {r4, r5, r6, r7, pc}
.align 2
rom_base:
diff --git a/mach.s b/mach.s
@@ -228,6 +228,16 @@ printh_high:
bge printh_loop
pop {r4, r5, r6, pc}
+
+ .global ldr
+ // uint32_t ldr(uint32_t addr)
+ // load content at addr
+ldr:
+ ldr r0, [r0, #0]
+ bx lr
+
+
+
led_pr:
// print register with 2 leds
push {r0, r1, r2, r4, lr}
diff --git a/main.c b/main.c
@@ -1,10 +1,28 @@
+#include <stdint.h>
+#include <stddef.h>
+
extern void init(void);
extern void led_p2(void);
+extern void frerase(uint32_t, size_t);
+extern void frprog(uint32_t, uint8_t *, size_t);
+extern uint32_t ldr(uint32_t);
+extern void printh(uint32_t);
+extern void putchar(char);
int
main(void)
{
+ uint32_t ofs = 4 * 1024;
+ size_t size = 4 * 1024;
+ size_t count = 256;
+ uint8_t data[count];
+ for (int i = 0; i < count; i++)
+ data[i] = 0xde;
init();
+ frerase(ofs, size);
+ frprog(ofs, data, count);
+ printh(ldr(0x10001000));
+ putchar('\n');
while(1) {
led_p2();
}