Sven Kopacz

Unsupported instruction Exception on AC256 with DIVS

Discussion created by Sven Kopacz on Nov 24, 2008
Latest reply on Dec 31, 2008 by Sven Kopacz
Hello,

working on a project, I encountered the following using Codewarrior 6.1 that came with the new AC development board (target CPU is the Coldfire 51AC256 that came with the board):

I got some C source, which devides a global variable by a #define'd constant:


Code:
int test_function(void){#define SCALER 20static int position=0;// dial_turns is a global variable which is written by an interrupt service routineposition+=dial_turns/SCALER;dial_turns=0;return position;}


The compiled code will never get below the division line.
The assembly reads:

Code:
41A8  MVS.W   0x0080051E,D1   ; This fetches the global dial_turns variable41AA  MOVEQ   #20, D0   ; Loads the constant41B0  DIVS.W  D0, D1 ; Execute division  

 Using the debugger, I can step up to the DIVS.W mnemonic.
The registers will read D0=0x14 (yes, that's 20) and D1=0 at this point.
Executing the next assembly step will take me here:

Code:
/*** ===================================================================**     Method      :  Cpu_Cpu_Interrupt (bean MCF51AC256A_80)****     Description :**         This ISR services an unused interrupt/exception vector.**         This method is internal. It is used by Processor Expert only.** ===================================================================*/ISR(Cpu_Interrupt){}

 The assembly reads just RTE which will take me back to the faulty DIVS command, so the MCU is trapped in an infinite loop.

The question is, what is happening here. At first I thought about a division by zero, but I am dividing by a constant which is always loaded as #20. The divident is zero, yes, but that should just result in 0x00 in D1. So not to confuse, DIVS shall divide D1/D0 here and store in D1. That's 0x00/0x14.

I then took a look at the exception stack, which reads the following:

40 F4 20 00 00 00 41 A8

According to the prog.ref manual, the exception stack frame is the same for all kinds of traps, the latter LONG is the return pointer. The leading long though is made up of the exception cause and the vector number that has been accessed, which to me means this result:

40                 f4                 20               00

0100 0000   1111 0100   0010 0000   0000 0000

Format: 0100
FS[3-2]: 00
VEC: 00111101
FS[1-0]: 00

A fault status of 00 means
"0000 Not an access or address error nor an interrupted debug service routine"

Vector 00111101=decimal 61 means:
61 0F4 Fault Unsupported instruction

As far as I can see though, the prog manual does not state any exception from the DIVS command for the AC MCUs.

I might have overlooked just a tiny little thing which would have made a long story pretty short. If so, by all means, PLEASE point me to it.

If not, I have no idea what to do to prevent the compiler from generating commands the MCU is not capable of.

Any hints HIGHLY appreciated.

Regards,
 Sven




Message Edited by Kopone on 2008-11-24 12:04 AM

Outcomes