Skip to content

Instantly share code, notes, and snippets.

@makestuff
Last active December 28, 2015 14:49
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save makestuff/7517475 to your computer and use it in GitHub Desktop.
Save makestuff/7517475 to your computer and use it in GitHub Desktop.
Generating ARMv2 code with a gcc cross-compiler
$ cat regs.c
typedef unsigned int uint32;
#define BLTCON1 *((volatile uint32 *)0xFFFFFF00)
#define BLTCON2 *((volatile uint32 *)0xFFFFFF04)
#define BLTCON3 *((volatile uint32 *)0xFFFFFF08)
void foo(uint32 x, uint32 y, uint32 z) {
BLTCON1 = x;
BLTCON2 = y;
BLTCON3 = z;
}
$ armeb-unknown-eabi-gcc -march=armv2 -O2 -S -Wall -Wextra -Wundef -Wconversion -pedantic-errors -std=c99 regs.c
regs.c:1: warning: target CPU does not support interworking
$ cat regs.s
.arch armv2
.fpu softvfp
.eabi_attribute 20, 1
.eabi_attribute 21, 1
.eabi_attribute 23, 3
.eabi_attribute 24, 1
.eabi_attribute 25, 1
.eabi_attribute 26, 1
.eabi_attribute 30, 2
.eabi_attribute 18, 4
.file "regs.c"
.text
.align 2
.global foo
.type foo, %function
foo:
@ args = 0, pretend = 0, frame = 0
@ frame_needed = 0, uses_anonymous_args = 0
@ link register save eliminated.
mvn r3, #0
str r0, [r3, #-255]
str r1, [r3, #-251]
str r2, [r3, #-247]
mov pc, lr
.size foo, .-foo
.ident "GCC: (crosstool-NG 1.19.0) 4.3.2"
$
wget http://crosstool-ng.org/download/crosstool-ng/crosstool-ng-1.19.0.tar.bz2
bunzip2 -c crosstool-ng-1.19.0.tar.bz2 | tar xf -
cd crosstool-ng-1.19.0
./configure --enable-local
make
./ct-ng armeb-unknown-eabi
./ct-ng build
export PATH=${PATH}:${HOME}/x-tools/armeb-unknown-eabi/bin
armeb-unknown-eabi-gcc -march=armv2 ...
Copy link

ghost commented Nov 17, 2013

/*********************************************************************
----------------------------------------------------------------------
File        : Startup.s
Purpose     : Generic startup code
---------------------------END-OF-HEADER------------------------------
*/

/*********************************************************************
*
*       Defines, used for the processor status register
*
**********************************************************************
*/
        ARM_MODE_USER  = 0x10        /* Normal User Mode                             */
        ARM_MODE_FIQ   = 0x11        /* FIQ Fast Interrupts Mode                     */
        ARM_MODE_IRQ   = 0x12        /* IRQ Standard Interrupts Mode                 */
        ARM_MODE_SVC   = 0x13        /* Supervisor Interrupts Mode                   */
        ARM_MODE_ABORT = 0x17        /* Abort Processing memory Faults Mode          */
        ARM_MODE_UNDEF = 0x1B        /* Undefined Instructions Mode                  */
        ARM_MODE_SYS   = 0x1F        /* System Running in Priviledged Operating Mode */
        ARM_MODE_MASK  = 0x1F

        I_BIT          = 0x80        /* Disables IRQ when I bit is set               */
        F_BIT          = 0x40        /* Disables FIQ when F bit is set               */

/*********************************************************************
*
*       Vector table
*
**********************************************************************
*/
        .text
        .global  __vector
        .global  _exit

        .extern  Reset_Handler

        .arm
        .section .vectors, "ax"

__vector:
        ldr     pc,Reset_Addr   /* RESET                 vector */


Reset_Addr:     .word   Reset_Handler

__vector_end:

/*********************************************************************
*
*       Standard C (crt0) initialization function
*
**********************************************************************
*/
        .global OS_GetStackInfo
        .extern  __low_level_init
        .extern  main

crt0:
        /*
         * Call __low_level_init to initiliaze hardware
         * before calling c-standard startup
         */
        ldr     r0,=__low_level_init
        mov     lr, pc
        bx      r0
        /*
         * Relocate .data section
         * (Copy from ROM to RAM)
         */
        ldr   r1, =_etext
        ldr   r2, =_data
        ldr   r3, =_edata
LoopRel:
        cmp   r2, r3
        ldrlo r0, [r1], #4
        strlo r0, [r2], #4
        blo   LoopRel

        /*
         * Clear .bss section
         */
        ldr   r1, =__bss_start__
        ldr   r2, =__bss_end__
        ldr   r3, =0
bss_clear_loop:
        cmp   r1, r2
        strne r3, [r1], #+4
        bne   bss_clear_loop
        /*
         *  Prepare and call main()
         */
        mrs   r0, cpsr
        bic   r0, r0, #(I_BIT | F_BIT)     /* Enable FIQ and IRQ interrupt */
        msr   cpsr, r0
        mov   r0, #0                         /* No arguments are passed to main */
        mov   r1, #0
        ldr   r2, =main
        mov   lr, pc
        bx    r2
_exit:  b     _exit                          /* We should never come to here, just for sureness. */

/*********************************************************************
*
*       __low_level_init
*
**********************************************************************
*/
__low_level_init:
        bx lr
        .weak __low_level_init

/**********************************************************************
* Reset_Handler
*
* Execution starts here.
* After a reset, the mode is ARM, Supervisor, interrupts disabled.
*/
        .global  Reset_Handler
        .global  end
        .arm
        .section .text, "ax"

Reset_Handler:
        /*
         * Setup a stack for each mode
         */
        msr   CPSR_c, #ARM_MODE_UNDEF | I_BIT | F_BIT   /* Undefined Instruction Mode */
        ldr   sp, =__stack_und_end__

        msr   CPSR_c, #ARM_MODE_ABORT | I_BIT | F_BIT   /* Abort Mode */
        ldr   sp, =__stack_abt_end__

        msr   CPSR_c, #ARM_MODE_FIQ   | I_BIT | F_BIT   /* FIQ Mode */
        ldr   sp, =__stack_fiq_end__

        msr   CPSR_c, #ARM_MODE_IRQ   | I_BIT | F_BIT   /* IRQ Mode */
        ldr   sp, =__stack_irq_end__

        msr   CPSR_c, #ARM_MODE_SVC   | I_BIT | F_BIT   /* Supervisor Mode */
        ldr   sp, =__stack_svc_end__

        /*
         * Now enter crt0 function,
         * which does low-level and segment initialization.
         * and then calls main().
         */
        ldr   r0, =crt0
        mov   lr, pc
        bx    r0
end:    b     end
        .end

Copy link

ghost commented Nov 17, 2013

Compiled with -march=armv2 , so this startup routine needs to be converted to a non-thumb instruction set.

||=== HelloWorld, Debug ===|
Setup\startup.S|1|warning: target CPU does not support THUMB instructions [enabled by default]|
Setup\startup.S|84|Error: selected processor does not support ARM mode `bx r0'|
Setup\startup.S|111|Error: selected processor does not support ARM mode `mrs r0,cpsr'|
Setup\startup.S|113|Error: selected processor does not support ARM mode `msr cpsr,r0'|
Setup\startup.S|118|Error: selected processor does not support ARM mode `bx r2'|
Setup\startup.S|128|Error: selected processor does not support ARM mode `bx lr'|
Setup\startup.S|145|Error: selected processor does not support ARM mode `msr CPSR_c,#ARM_MODE_UNDEF|I_BIT|F_BIT'|
Setup\startup.S|148|Error: selected processor does not support ARM mode `msr CPSR_c,#ARM_MODE_ABORT|I_BIT|F_BIT'|
Setup\startup.S|151|Error: selected processor does not support ARM mode `msr CPSR_c,#ARM_MODE_FIQ|I_BIT|F_BIT'|
Setup\startup.S|154|Error: selected processor does not support ARM mode `msr CPSR_c,#ARM_MODE_IRQ|I_BIT|F_BIT'|
Setup\startup.S|157|Error: selected processor does not support ARM mode `msr CPSR_c,#ARM_MODE_SVC|I_BIT|F_BIT'|
Setup\startup.S|167|Error: selected processor does not support ARM mode `bx r0'|
||=== Build finished: 11 errors, 1 warnings (0 minutes, 0 seconds) ===|

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment