[fpc-devel] Arm Thumb2 - Stellaris status
Jeppe Græsdal Johansen
jjohan07 at student.aau.dk
Sat Aug 20 23:14:35 CEST 2011
Den 20-08-2011 22:24, David Welch skrev:
>
> thumb2 is an extension to thumb not arm, you can mix thumb and arm in
> T variants like the v4T v5T and anything after that v6 on up, except
> for the cortex-m variants which are thumb+thumb2 only and cannot
> execute ARM 32 bit instructions (yes thumb2 32 bit thumb extensions
> but nothing from the ARM instruction set).
>
> Here is an example of the problem I am seeing:
>
> took a clean copy from svn
>
> svn co http://svn.freepascal.org/svn/fpc/trunk fpc
>
> cd fpc
>
> make clean buildbase installbase CROSSINSTALL=1 OS_TARGET=embedded
> CPU_TARGET=arm INSTALL_PREFIX=/fpcarm
>
>
> ---- test.pp ----
> procedure Wait(d : dword);
> begin
> while d<>0 do
> dec(d);
> end;
>
> begin
>
> while true do
> begin
> Wait($20000);
> end;
> end.
> ---- test.pp ----
>
>
> ./compiler/ppcrossarm -Parm -Tembedded -Wpstm32f103re -Cpcortexm3 test.pp
> Free Pascal Compiler version 2.7.1 [2011/08/20] for arm
> Copyright (c) 1993-2011 by Florian Klaempfl and others
> Target OS: Embedded
> Compiling test.pp
> Assembling program
> Linking test
> /opt/embarm/arm-embedded-ld: warning: library search path
> "/usr/local/lib/fpc/2.7.1/units/arm-embedded/rtl/" is unsafe for
> cross-compilation
> 14 lines compiled, 0.0 sec
>
> then dumped the binary:
>
> 08000000 <_START-0x158>:
> 8000000: 2000fffc strdcs pc, [r0], -ip
> 8000004: 08000405 stmdaeq r0, {r0, r2, sl}
> 8000008: 08000405 stmdaeq r0, {r0, r2, sl}
> 800000c: 08000405 stmdaeq r0, {r0, r2, sl}
> 8000010: 08000405 stmdaeq r0, {r0, r2, sl}
> 8000014: 08000405 stmdaeq r0, {r0, r2, sl}
> 8000018: 08000405 stmdaeq r0, {r0, r2, sl}
> ...
> 08000194 <PASCALMAIN>:
> 8000194: 46ec mov ip, sp
> 8000196: e92d 4800 stmdb sp!, {fp, lr}
> 800019a: f1ac 0b04 sub.w fp, ip, #4
> 800019e: b08a sub sp, #40 ; 0x28
> 80001a0: f000 f844 bl 800022c <FPC_INITIALIZEUNITS>
> 80001a4: e004 b.n 80001b0 <PASCALMAIN+0x1c>
> 80001a6: bf00 nop
> 80001a8: f44f 3000 mov.w r0, #131072 ; 0x20000
> 80001ac: f7ff ffd8 bl 8000160 <P$PROGRAM_WAIT$LONGWORD>
> 80001b0: e7fa b.n 80001a8 <PASCALMAIN+0x14>
> 80001b2: f000 f8ff bl 80003b4 <FPC_DO_EXIT>
> 80001b6: 46dd mov sp, fp
> 80001b8: b001 add sp, #4
> 80001ba: e91d 8800 ldmdb sp, {fp, pc}
> 80001be: bf00 nop
> ...
> 08000404 <STM32F103__FPC_START>:
> 8000404: e59f103c ldr r1, [pc, #60] ; 8000448
> <STM32F103__FPC_START+0x44>
> 8000408: e59f203c ldr r2, [pc, #60] ; 800044c
> <STM32F103__FPC_START+0x48>
> 800040c: e59f303c ldr r3, [pc, #60] ; 8000450
> <STM32F103__FPC_START+0x4c>
> 8000410: e1520003 cmp r2, r3
> 8000414: 94910004 ldrls r0, [r1], #4
>
>
> First off 0x08000405 implies a thumb target but it is not thumb code,
> it is arm code so 0x08000404 would be correct but that is still wrong
> because cores with that vector table (cortex-m) cannot execute arm
> instructions.
It implies thumb mode, which is the only valid mode on Cortex-M3
> Looking at that first instruction in the reset handler
>
> 08000404 <STM32F103__FPC_START>:
> 8000404: e59f103c ldr r1, [pc, #60] ; 8000448
> <STM32F103__FPC_START+0x44>
The problem is that you are using an RTL built for ARM. That's what the
warning is about. You installed the compiler in /fpcarm, but it's using
units from /usr/local/lib/fpc/2.7.1/units/arm-embedded/rtl/
A correctly compiled unit would look like this:
00000000 <STM32F103__FPC_START>:
0: f8df 1034 ldr.w r1, [pc, #52] ; 38
<STM32F103__FPC_START+0x38>
4: 4a0d ldr r2, [pc, #52] ; (3c
<STM32F103__FPC_START+0x3c>)
6: 4b0e ldr r3, [pc, #56] ; (40
<STM32F103__FPC_START+0x40>)
8: 429a cmp r2, r3
a: bf9e ittt ls
> IPUBWL
> 1110 01011001 r15, r1, 0x03C
>
> And that was properly decoded by objdump, immediate offset
> rn+offset12, load, word sized, etc.
> PC is 0x800040C at that time so load address is 0x800040C+0x03C =
> 0x8000448
>
> You can tell both by 32 bit numbers in the dump but the dominance of
> an 0xE as the first nibble also implies these are arm instructions not
> thumb (need to see a long chunk of code to see the pattern). Had they
> been thumb instructions but decoded wrong by the disassembler then the
> first and fourth nibbles would have been dominated by like 6's and 7's
> or at least would stand out compared to the other
> nibbles.
>
> if we decode this as thumb/thumb2
>
> 0xE59F
>
> //B(2) unconditional branch
> if((inst&0xF800)==0xE000)
> {
> rb=(inst>>0)&0x7FF;
> if(rb&(1<<10)) rb|=(~0)<<11;
> rb<<=1;
> rb+=pc;
> rb+=2;
> write_register(15,rb);
> return(0);
> }
>
> 1110010110011111
>
> 11100 10110011111
>
> ...11111110110011111
> ...111111101100111110
> ...11 1111 1011 0011 1110
>
> pc = 0x405+4 = 0x409
> pc + 0x...FFB3E =
> 0x409 - (0x4C1 + 1) = 0x7FFFF47
>
> Unconditional branch to 0x07FFFF47 so it is a valid instruction, but
> doesnt make much sense
>
>
> This does though, the start code from stm32f103.pp
>
> .globl _start
> .text
> _start:
>
> // Copy initialized data to ram
> ldr r1,.L_etext
> ldr r2,.L_data
> ldr r3,.L_edata
> .Lcopyloop:
> cmp r2,r3
> ittt ls
> ldrls r0,[r1],#4
> strls r0,[r2],#4
> bls .Lcopyloop
>
> The instructions the assembler was able to encode it did:
>
> 8000404: e59f103c ldr r1, [pc, #60]
> 8000408: e59f203c ldr r2, [pc, #60]
> 800040c: e59f303c ldr r3, [pc, #60]
> 8000410: e1520003 cmp r2, r3
> 8000414: 94910004 ldrls r0, [r1], #4
> ....
> 8000448: 08000468 stmdaeq r0, {r3, r5, r6, sl}
> 800044c: 20000000 andcs r0, r0, r0
> 8000450: 20000048 andcs r0, r0, r8, asr
>
>
> 0x08000468 is the word aligned address for the end of the text segment
> and 0x20000000 the beginning of text for this example so that is
> correct as well.
>
> and interestingly the ittt ls instruction is discarded.
>
> The code from stm32f103.pp
>
> ldr r1,.L_etext
> ldr r2,.L_data
> ldr r3,.L_edata
> .Lcopyloop:
> cmp r2,r3
> ittt ls
> ldrls r0,[r1],#4
> strls r0,[r2],#4
> bls .Lcopyloop
>
> when assembled should look like this
>
> 00000000 <.text>:
> 0: 4904 ldr r1, [pc, #16] ; (14 <.text+0x14>)
> 2: 4a05 ldr r2, [pc, #20] ; (18 <.text+0x18>)
> 4: 4b05 ldr r3, [pc, #20] ; (1c <.text+0x1c>)
> 6: 429a cmp r2, r3
> 8: bf9e ittt ls
> a: f851 0b04 ldrls.w r0, [r1], #4
> e: f842 0b04 strls.w r0, [r2], #4
> 12: e7f8 bls.n 6 <.text+0x6>
> 14: 00000001 andeq r0, r0, r1
> 18: 00000002 andeq r0, r0, r2
> 1c: 00000003 andeq r0, r0, r3
>
> with different addresses of course...when assembled for thumb.
>
> So it doesnt look like that is happening
>
> Pascal main is definitely thumb+thumb2.
>
> 08000194 <PASCALMAIN>:
> 8000194: 46ec mov ip, sp
> 8000196: e92d 4800 stmdb sp!, {fp, lr}
> 800019a: f1ac 0b04 sub.w fp, ip, #4
> 800019e: b08a sub sp, #40 ; 0x28
>
> More info about my setup:
>
> svn info
>
> URL: http://svn.freepascal.org/svn/fpc/trunk
> Repository Root: http://svn.freepascal.org/svn/fpc
> Repository UUID: 3ad0048d-3df7-0310-abae-a5850022a9f2
> Revision: 18278
> Node Kind: directory
> Schedule: normal
> Last Changed Author: florian
> Last Changed Rev: 18278
> Last Changed Date: 2011-08-19 18:06:52 -0400 (Fri, 19 Aug 2011)
>
> Ubuntu 10.4 or something like that 64 bit host.
> Linux dwelch-desktop 2.6.32-33-generic #72-Ubuntu SMP Fri Jul 29
> 21:07:13 UTC 2011 x86_64 GNU/Linux
>
> fpc is what you apt-get so probably a little behind but stable in the
> eyes of ubuntu or debian.
>
> fpc
> Free Pascal Compiler version 2.4.0-2ubuntu1.10.04 [2011/06/17] for x86_64
> Copyright (c) 1993-2009 by Florian Klaempfl
> /usr/lib/fpc/2.4.0/ppcx64 [options] <inputfile> [options]
> Put + after a boolean switch option to enable it, - to di
>
> GNU assembler (Sourcery G++ Lite 2011.03-42) 2.20.51.20100809
> Copyright 2010 Free Software Foundation, Inc.
> This program is free software; you may redistribute it under the terms of
> the GNU General Public License version 3 or later.
> This program has absolutely no warranty.
> This assembler was configured for a target of `arm-none-eabi'.
>
>
>
>
> So what did I do wrong? and what is the unsafe thing about?
>
> Thanks,
> David
>
>
>
> On 08/20/2011 11:23 AM, Jeppe Græsdal Johansen wrote:
>> Den 20-08-2011 16:46, David Welch skrev:
>>> I was hoping for thumb support but I now see that the choices are
>>> limited to arm and thumb+thumb2 (without any separation between thumb
>>> and thumb2). Actually thumb2 wasnt working for me, I got an arm+thumb2
>>> mix, so I will ride this along for a while and see what comes up,
>>> otherwise limit my use to ARM targets, or start working on a thumb
>>> backend. Adding backends as well as arm embedded are of interest to me
>>> so I may work on a little of both.
>> Why thumb support? The choices are indeed currently only either ARM or
>> Thumb2(which is Thumb+32 bit extensions). Thumb2 is a variable length
>> instruction set that looks like an arm+thumb mix, so I guarantee you
>> that it works :)
>> _______________________________________________
>> fpc-devel maillist - fpc-devel at lists.freepascal.org
>> http://lists.freepascal.org/mailman/listinfo/fpc-devel
>> .
>
> _______________________________________________
> fpc-devel maillist - fpc-devel at lists.freepascal.org
> http://lists.freepascal.org/mailman/listinfo/fpc-devel
More information about the fpc-devel
mailing list