---
# System prepended metadata

title: ByteWise - Breakdown the Minimal Bootloader for Cortex-M
tags: [bytewise]

---

---
title: ByteWise - Breakdown the Minimal Bootloader for Cortex-M
tags: bytewise,
---

# Breakdown the Minimal Bootloader in Cortex-M

```c
static void start_app(void *pc, void *sp) {
    __asm(
        "           \n\
        msr msp, r1 \n\
        bx r0       \n\
        "
    );
}

int main() {
    ...
    start_app(app_vectors->pfnReset_Handler, app_vectors->pvStack);
    
    while(1)  // should never be reached
}
```
This is a mininal bootloader codes, in `main`, it call `start_app` with two parameters, 
- `app_vectors->pfnReset_Handler`: **the pointer to the application's `ResetHandler`** 
- `app_vectors->pvStack` : **the pointer to the start address of the stack**.

In the `start_app(...)`, it reconfigure the **Main Stack Pointer**,  `msp` to the ***sp*** and jumps to where ***pc*** points to, that is, the `ResetHandler()` of the application.

:::success
:question: It still unclear to me why it use `r0` and `r1` in the inlined assembly instead of using `pc` and the `sp` directly? On top of this, why `r0` and `r1` represent the two arguments?

:::danger
> [10.1 Passing Arguments in Registers](https://bob.cs.sonoma.edu/IntroCompOrg-RPi/sec-reg-use.html#p-1645), *Introduction to Computer Organization: ARM Assembly Language Using the Raspberry Pi* by Robert G. Plantz

> When one C function calls another, only the **first four** arguments to the called function are passed in registers. Reading a C argument list from left to right, the following table shows the order in which the arguments are stored in the registers. **If more arguments need to be passed, they are stored on the stack**.


| Argument | Register |
| -------- | -------- |
| arg1     | `r0`     |
| arg2     | `r1`     |
| arg3     | `r2`     |
| arg4     | `r3`     |


