I cannot get the XGATE to respond to an interrupt. This is my first attempt at running the XGATE.
I'm using 9S12XD256 (0L15Y), CodeWarrior Debugger v6.1 (b9061), and P&E USB MultiLink (rev C).
I'm trying to get the XGATE to process an interrupt from ATD0. The IRQ from ATD0 processes OK when directed to the CPU12, so the interrupt source is OK. My configuration:
1. Set up the XGATE's vector table and VBR, and verified by examining memory in the debugger.
2. Set the RQST and priority in XINT for ATD0, and verified by examining memory.
3. Enabled XGE in XGMCTL. However, when I read this in memory with the debugger, I see that XGDBG is also set. I suspect that this is a clue. I just can't figure out how XGDBG is getting set.
Is this something that the debugger is doing behind my back? Or is it somehow possible that the XGATE executed one instruction of RAM after it was zero blanked (causing a BRK), and before the XGATE code was copied down into RAM. I know, this is really grasping at straws. But I'm running out of theories.
Other clues: When I examine the XGATE's processor registers, everthing is 0's, like it just came out of reset.
I've set up the XGATE vector table so that the VBR points lower in memory than the actual table origin at C800'x, to avoid wasting RAM on the unused vectors between offset $00 and $62 (channels lower then $32). I noticed that since my vector table is butted up against the lowest RAM address (C800'x), the VBR actually points into non-existant memory space. Reading between the lines in AN3555 "Investigating XGATE s/w Errors", I'm guessing that this is OK. But is this alright to do?
I have an error handler in all of the XGATE's unused vectors, and that never is called (based on incrementing a counter in the error handler, and monitoring that location with the debugger).
I know that the debugger is running, because I can see the registers in the ATD changing when viewed in a memory window.
I have verified that the correct derivative is selected. For grin's I turned on the "verify after load" option, and had no complaints.
I have looked at the alignment for the vector table, et al, and it seems OK.
Because I can load a program, I assume that the device is no secured.
Does anyone have suggestions about what to try next? The XGDBC set bit looks like a smoking gun, but I'm not sure how to deal with it.
Thanks in advanced!!!
I found it -- CodeWarrior Debugger apparently was setting the XGDBG bit (all on its own). In the S12(X) debugger manual (v 5.0, revised 27 Feb 2009) on page 652, I found the command "XGDBGCLEARONRUN": Clear XGDBG bit on run. Executing this in the command window after loading seems to have fixed things.
I'm still not clear on how or why the debugger was setting XGDBG. But now the XGATE runs my ATD0 thread as intended. YES!!
A somewhat related question: In order to "fat-finger" change the XGATE's registers as they appear in the XGATE's register block (shown in the memory window at 0x0380), emperically I find that I must first set XGE = 0 and XGDBG = 1. This setting is also needed to change XGCHID. However, reading the MC9S12XDP512 Data Sheet rev 2.19 indicates no such limitation. ie, The data sheet only says that the part must be in debug mode (OK), and unsecured (it is). The data sheet says nothing about a dependency on the XGATE being disabled.
Any thoughts? Is there more info about this XGE dependency located somewhere else?
The CPU12 and the XGATE each have their own debug mode:
The part of the MC9S12XDP512 Data Sheet (Chapter 6 "XGATE") that were mentioning refers to the XGATE's debug mode. The XGATE's debug mode determines who has contol over the the RISC core's resources. If XGDBG is cleared, then the RISC core has full access to the registers. If XGDBG is set, then the RISC core is stopped and all registers can be read and written through the memory mapped interface. The state of the XGE bit has no influence on the accesibility of the registers.
The are three ways to set the XGDBG:
You can pretty much exclude the second option, because the XGPC register wouldn't read zero in this case. Have a look at the XGCHID register. It will tell you which thread was running when the XGDBG bit was set.
The debugger must have put the XGATE into debug mode (via option 1 or 3) before it had a chance to execute any code. What happens if you clear the XGDBG flag? Does the XGATE start to execute the ATD code then? If not, are you able to launch the ATD ISR manually by writing to the XGCHID register?
There is another way to keep the XGATE from executing code. If you set the XGFRZ bit, the XGATE will halt everytime the CPU12 enters BDM active mode. Make sure this bit is cleared if you're only debugging XGATE code.
Did you create XGATE enabled project using project wizard? If you didn't, then I think you should try it. If you did, then please note that wizard generated project triggers XGATE software trigger 0 thread at the end of SetupXGATE routine. And XGATE software thread doesn't untrigger itself. So it will run and run again and again.
Your ATD0 thread setup should be very similar to provided SetupXGATE routine. You should only
1) additionally route ATD0 interrupt
ROUTE_INTERRUPT(Vatd0, 0x81); /* RQST=1 and PRIO=1 */
Vatd0 vector address is defined in derivative header file.
2) suppress XGSWT= 0x0101; line.
3) Make XGATE vectors table pointing to ATD0 thread.
I guess debugger sets XGDBG bit.
Yes, it's OK VBR points to not existing memory, provided interrupt controller doesn't trigger those not existing vectors. Codewarrior example also points VBR to not existing memory.