[fpc-devel] ARM vs Thumb2 - can't have both

John Clymer john at johnclymer.net
Mon Aug 22 07:15:44 CEST 2011

Yes, all my references of Thumb meant Thumb2.

The problem is not building the compiler - the compiler works correctly 
supporting Thumb2 and ARM.

The problems is building the libraries.  Doing a standard build process, the 
compile chain gets into the rtl/embedded folder.  It makes one pass through and 
compiles the SYSTEM unit.  This gets built in whatever mode the crosscompiler 
has been told to be in.  It defaults to ARM code, unless told to Thumb2 code 
(via a CROSSOPT=-Cpcortexm3 on the MAKE command line - or via an override in the 
RTL.CFG file in the embedded folder.)

Now, if it's in Thumb2 mode - it compiles the STM32 and STELLARIS unit files 
fine, and makes a Thumb2 SYSTEM ppu.  But, then it chokes on compiling the ARM 
controller unit files.

BUT - if it's in ARM mode, it will compile everything, including the start-up 
routines for the Thumb2 parts - in full blown ARM mode.  This will make the 
compiler finish it's job.   BUT attempting to run anything on a M3 device will 
fail - as the M3 can NOT run ARM code.

So, in order to get a working setup for an M3 device, one needs to manually 
remove the ARM controller files from the makefile, then re-build with 
-Cpcortexm3 in the RTL.CFG file in the embedded folder (or it could be added to 
the Makefile) - OR the make "clean buildbase installbase" line needs to have a 
CROSSOPT=-Cpcortexm3 added.  Otherwise the system and startup files end up being 
ARM files.

<ARCH> is ARM - but that is NOT the code generation, that is strictly because 
the company's name is ARM.
<SYSTEM> is "embedded" - as that's what I'm building
<CPUTYPE>  (not referenced in any build files) is either ARM (for ARMV3-V5) OR 
Thumb2 (for Cortex M3 OR armv7m)

Again, the compiler builds just fine - it's the RTL that has the issue.  If you 
are having troubles building for Cortex, the magic that I'm using to make it 
work is:

make clean buildbase installbase CROSSINSTALL=1 OS_TARGET=embedded 
CPU_TARGET=arm CROSSBINDIR=/home/stimey/CodeSourcery/bin 
BINUTILSPREFIX=arm-none-eabi-  CROSSOPT=-Cpcortexm3 

The CROSSOPT item forces the RTL to be compiled as M3 / Thumb2.


From: David Welch <dwelch at dwelch.com>
To: FPC developers' list <fpc-devel at lists.freepascal.org>
Sent: Mon, August 22, 2011 8:25:11 AM
Subject: Re: [fpc-devel] ARM vs Thumb2 - can't have both

All I am saying is thumb (not thumb2) is common between many ARM cores and the 
cortex-m3.  These lpc21xx parts use an ARM7TDMI which is an ARMv4T and supports 
thumb.  the lpc2000 are also ARM7TDMI's and LPC1000 is cortex-m0 which is the 
successor to cortex-m3 so no doubt it is thumb/thumb2 based as well.  All of the 
ARM based microcontrollers I know of (have used) str7, stm32, lpc2000, lpc1000, 
stellaris, sam7 (at91sam7) support thumb instructions (if you limit yourself to 
the original ARMv4T supported instructions).  the sam9 and str9 both appear to 
be ARMv5T based so they support thumb as well.

So long as all code modules use a "thumb interwork" as folks like to call it 
interface, then dules like PASCALMAIN can be compiled for arm, thumb or thumb2 
and be called and return to arm, thumb or thumb2 code, mix and match at will.

Obviously the exception table or vector table at address zero has to be 
different for ARM7 vs cortex-m, no way to work around that.  If that is the root 
of the problem and that code wants to move out of the target specific rtl 
(stellaris.pp, lpc21x4.pp, etc) then, yeah, there is a big problem.

If the exception and vector tables can be custom to the target as they are now 
(stellaris.pp, lpc21x4.pp, etc) then you could do a couple of things.

One would be the interwork thing.  The arm startup code, within the target 
specific rtl would have to do a two step to get from arm mode to thumb/interwork 
mode.  The arm cores traditionally handles exceptions in arm mode. What I 
described in the prior email but not necessarily exactly like that.  Any shared 
code between the ARM and cortex-m would be strictly thumb (limited to ARMv4T 
ideally).  Any instructions like mrs/msr that thumb is lacking would want to be 
calls to arm code in the target specific startup area.  The cortex-m vector 
table could simply point directly at the thumb mode shared code (and have 
matching named functions for mrs/msr and other instructions)

The second solution, would be to use the lowest common denominator, everything 
except the exception/vector tables, and some architecture specific stuff (like 
any need for mrs/msr calls) be compiled for thumb (limited to ARMv4T). 
Unfortunately there is no thumb backend.

With the second solution the compiler could be compiled one time, one way and so 
far all the targets are supported by that one compiler.

I guess a third solution would be to treat the cortex-m3 as a completely 
different architecture, in the same way that the avr is a separate target (looks 
like there is at least a directory for the avr, but the code is arm so a work in 
progress).  I would be super happy to see an msp430 target in there as well but 
that is another story.  From what you were talking about <ARCH><SYSTEM> becoming 
<ARCH><CPUTYPE><SYSTEM>, cortex-m could be a separate <ARCH> instead of being 
part of the ARM architecture and <ARCH><SYSTEM> would work.

Sorry for being dense, I am a newbie here so dont know enough about the detail 
to know where the problem is.  I still have not gotten past the problem I had 
trying to get that startup code to build right for the cortex-m3.  Lots of arm 
experience, almost no fpc experience.

I assume what you are calling a thumb system is the cortex-m3 based systems, you 
you cannot have arm code there.  I assume the <ARCH> is for now ARM (the company 
not the instruction set).  And <SYSTEM> is either ARM (the instruction set) or 
thumb2/cortex-m3?  Am I understanding that so far?  Or is <ARCH> ARM or 
cortex-m3 and <SYSTEM> is stellaris, lpc21x4, etc?


On 08/21/2011 10:36 PM, John Clymer wrote:
> Yes, I'm somewhat familiar with mixing Thumb and Arm in C.
> However, I believe the intent is to target FPC for the newbie market
> (that's what I'm getting from wanting all the hardware peripheral
> registers installed in the controller unit file...) A newbie is NOT
> going to have any luck intermixing the two.
> That also doesn't solve the problem of the SYSTEM unit. As the compiler
> is laid out now - the system unit sits in a directory of the name
> <ARCH>-<SYSTEM>. So, to support BOTH ARM and THUMB (i.e. Cortex and
> native ARM7TDMI) SYSTEM files, 2 different builds are needed. However -
> they can't both sit in the same directory (not with the current setup of
> Makefiles and code.)
> I've seen where the compiler inserts the system unit and controller
> units, so supporting both would only be a few lines of code there. I've
> also seen when running the compiler in verbose mode (-Va) that the -Cp
> processor switch is getting defined to a constant - so one could
> possibly massage the makefiles into supporting <ARCH>-<CPUTYPE>-<SYSTEM>
> directories to seperate the two system units.
> Otherwise, one has the following problem:
> 1) building for ARM - all the controllerunits compile (because the
> assembler can assemble the thumb startup code into arm startup code).
> However, when one builds a program with the resulting SYSTEM and
> controllerunit file, the startup will be in ARM mode and cause the
> program not to run.)
> 2) building in THUMB - the ARM startup code in the lpc and sam7
> controllerunit files fail to build - as they have ARM specific assembly
> code in them.
> However, if you are claiming that an ARM binary can be linked against a
> THUMB SYSTEM unit, then only the startup code remains to get fixed - and
> things aren't as messy as I'm perceiving them.
> John

fpc-devel maillist  -  fpc-devel at lists.freepascal.org
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.freepascal.org/pipermail/fpc-devel/attachments/20110821/0500b851/attachment.html>

More information about the fpc-devel mailing list