mc9s12c32 interrupts

12
ELEC 3040/3050 ELEC 3040/3050 Lab 4 Lab 4 Double Counters Double Counters Using Interrupt-Driven I/O Using Interrupt-Driven I/O

Upload: rktiwary256034

Post on 12-Dec-2015

252 views

Category:

Documents


4 download

DESCRIPTION

embedded system

TRANSCRIPT

Page 1: MC9S12C32 Interrupts

ELEC 3040/3050 ELEC 3040/3050 Lab 4Lab 4

Double CountersDouble CountersUsing Interrupt-Driven I/OUsing Interrupt-Driven I/O

Page 2: MC9S12C32 Interrupts

Goals of this lab exerciseGoals of this lab exercise

Add an additional counter to count upon interrupt-Add an additional counter to count upon interrupt-driven input/output (I/O)driven input/output (I/O)

Last week – Last week – softwaresoftware controlled timing of data controlled timing of data transferstransfers CPU in an “endless loop” scanning the switchesCPU in an “endless loop” scanning the switches Difficult to respond in the middle of delay loopDifficult to respond in the middle of delay loop

This week – push-button should This week – push-button should interruptinterrupt the CPU the CPU when it is pressedwhen it is pressed Allows CPU to do “other tasks” when the push-button is idleAllows CPU to do “other tasks” when the push-button is idle Increment the ISR counter only when the PB is pressedIncrement the ISR counter only when the PB is pressed

Page 3: MC9S12C32 Interrupts

MC9S12C32 InterruptsMC9S12C32 Interrupts

Two external interrupt pins on the MC9S12C32 are Two external interrupt pins on the MC9S12C32 are tested after each instruction:tested after each instruction: IRQ# (interrupt request)IRQ# (interrupt request)

Logically AND’ed with I (interrupt flag) in the processor’s Logically AND’ed with I (interrupt flag) in the processor’s Condition Code Register (CCR)Condition Code Register (CCR)

When I=1, IRQ# is “masked” or “disabled”When I=1, IRQ# is “masked” or “disabled” (this is the power-on condition)(this is the power-on condition) When IF=0, IRQ# is “unmasked or “enabled”When IF=0, IRQ# is “unmasked or “enabled” ANDCC #%11101111 ANDCC #%11101111 clears I=0; C function clears I=0; C function EnableInterrupts;EnableInterrupts; ORCC #%00010000ORCC #%00010000 sets I=1; C function sets I=1; C function DisableInterrupts;DisableInterrupts;

XIRQ# (non-maskable interrupt)XIRQ# (non-maskable interrupt) Logically AND’ed with X (non-maskable interrupt flag) in the Logically AND’ed with X (non-maskable interrupt flag) in the

processor’s Condition Code Register (CCR)processor’s Condition Code Register (CCR) Once X cleared to 0, to enable interrupts, it cannot be reset Once X cleared to 0, to enable interrupts, it cannot be reset

again, so interupts cannot be disabledagain, so interupts cannot be disabled

Page 4: MC9S12C32 Interrupts

IRQ# operationIRQ# operation

IRQ# is active-low, and can be configured IRQ# is active-low, and can be configured as either as either level-sensitivelevel-sensitive or or edge-triggerededge-triggered Level-sensitive => signal must be at its active Level-sensitive => signal must be at its active

level when checked by the CPUlevel when checked by the CPU Must be held active until acknowledged by the CPUMust be held active until acknowledged by the CPU Must be deactivated when acknowledged to prevent Must be deactivated when acknowledged to prevent

multiple interruptsmultiple interrupts Momentary activations might go unnoticed Momentary activations might go unnoticed

(including activations while I=0)(including activations while I=0) Edge-triggered => an active transition on the Edge-triggered => an active transition on the

signal sets a flip-flop in the CPU that remains signal sets a flip-flop in the CPU that remains set until the CPU acknowledges the interruptset until the CPU acknowledges the interrupt

Page 5: MC9S12C32 Interrupts

CPU interrupt responseCPU interrupt response

1.1. Suspend the current taskSuspend the current task2.2. Save the state of the CPU (registers) on the stackSave the state of the CPU (registers) on the stack3.3. Set I=1 to mask additional interruptsSet I=1 to mask additional interrupts4.4. Fetch an “interrupt vector” from the interrupt vector Fetch an “interrupt vector” from the interrupt vector

table to jump to interrupt service routine (ISR)table to jump to interrupt service routine (ISR) ISR deals with the interrupting device/event, and is unique to ISR deals with the interrupting device/event, and is unique to

each device/event type each device/event type Interrupt vector is the starting address of an ISR (PC value) Interrupt vector is the starting address of an ISR (PC value) Interrupt vector table is stored in memory, ending at $FFFFInterrupt vector table is stored in memory, ending at $FFFF

1.1. Execute the ISRExecute the ISR

1.1. Resume the suspended taskResume the suspended task

Page 6: MC9S12C32 Interrupts

HC12 Interrupt Vector TableHC12 Interrupt Vector Table

Vector Address Interrupt Source

$FFFE Reset

$FFFC Clock monitor failure reset

$FFFA COP failure reset

$FFF8 Unimplemented instruction trap

$FFF6 SWI

$FFF4 XIRQ

$FFF2 IRQ

$FFF0 Real time interrupt

$FFEE Capture timer channel 0

…. etc.

Complete table in Cady text & MC9S12C32 ref manual (pg 61)

Page 7: MC9S12C32 Interrupts

Guidelines for writing ISRsGuidelines for writing ISRs Assembly language: HC12 automatically saves/restores Assembly language: HC12 automatically saves/restores

all CPU registers all CPU registers not necessarily so on other CPUsnot necessarily so on other CPUs

Terminate ISR with “RTI” (return from interrupt) in Terminate ISR with “RTI” (return from interrupt) in assembly languageassembly language Restores CPU registers from stackRestores CPU registers from stack

Cannot predict what the CPU is doing when an interrupt Cannot predict what the CPU is doing when an interrupt occurs, so data for an ISR must come from “global” occurs, so data for an ISR must come from “global” variables, and not from:variables, and not from: CPU registers (used by interrupted program)CPU registers (used by interrupted program) C variables local to an interrupted program (created in the stack)C variables local to an interrupted program (created in the stack) Cannot always predict what program/subprogram might be Cannot always predict what program/subprogram might be

runningrunning Can reset I=0 within an ISR to allow nested interruptsCan reset I=0 within an ISR to allow nested interrupts

Page 8: MC9S12C32 Interrupts

Initialization for interrupt supportInitialization for interrupt support Recall that I=1 at power-on/resetRecall that I=1 at power-on/reset Create the interrupt vector table entry for all Create the interrupt vector table entry for all

Assembly language:Assembly language:org $fff2org $fff2 ;address of IRQ# vector;address of IRQ# vectordc.wdc.w irq_routine ;IRQ# vectorirq_routine ;IRQ# vector

C: declare function as an ISR:C: declare function as an ISR:interrupt void IRQ_ISR(void) {}interrupt void IRQ_ISR(void) {}

C: add file C: add file isr_vectors.cisr_vectors.c to your project (from class web) to your project (from class web)1. Add your function prototype(s) at top of file: 1. Add your function prototype(s) at top of file:

extern void near IRQ_ISR(void);extern void near IRQ_ISR(void); 2. Change 2. Change UnimplementedISRUnimplementedISR to your ISR function name to your ISR function name

(IRQ_ISR) (IRQ_ISR) for each vector(s) used in your projectfor each vector(s) used in your project Initialize any data (globals) needed for Initialize any data (globals) needed for isrisr Enable interrupts when everything is readyEnable interrupts when everything is ready

Assembly language:Assembly language: andcc #%11101111andcc #%11101111 C function:C function: EnableInterrupts;EnableInterrupts;

Page 9: MC9S12C32 Interrupts

//EXAMPLE: isr_vectors.c file (excerpt)extern void near _Startup(void); /* Startup routine */extern void near SWI_ISR(void); /* My SWI ISR */

#pragma CODE_SEG __NEAR_SEG NON_BANKED /* Interrupt section for this module. Placement will be in NON_BANKED area. */__interrupt void UnimplementedISR(void){ /* Unimplemented ISRs trap.*/ asm BGND;}

typedef void (*near tIsrFunc)(void);const tIsrFunc _vect[] @0xFF80 = { /* Interrupt table */ UnimplementedISR, /* vector 63 */ … UnimplementedISR, /* vector 05 */ SWI_ISR, /* vector 04 */ SWI is Vector 4 UnimplementedISR, /* vector 03 */ UnimplementedISR, /* vector 02 */ UnimplementedISR, /* vector 01 */ //_Startup /* Reset vector */ COMMENT OUT };

Page 10: MC9S12C32 Interrupts

Conventions for C in CodeWarriorConventions for C in CodeWarrior#include <hidef.h> #include <hidef.h> /* common defines and macros *//* common defines and macros */#include <mc9s12c32.h> #include <mc9s12c32.h> /* derivative information *//* derivative information *//* global variables definitions here *//* global variables definitions here *//* Define the interrupt service routine *//* Define the interrupt service routine */interrupt void IRQ_ISR(void) {interrupt void IRQ_ISR(void) { ... instructions for the interrupt service... instructions for the interrupt service}}/* Define the main program *//* Define the main program */void main(void) {void main(void) { ... initialize variables/devices/registers... initialize variables/devices/registers INTCR_IRQE = 1; INTCR_IRQE = 1; /* edge-triggered interrupts *//* edge-triggered interrupts */ EnableInterrupts; EnableInterrupts; /* enable interrupts *//* enable interrupts */ ... instructions for the main program... instructions for the main program}}

Page 11: MC9S12C32 Interrupts

Lab ExperimentLab Experiment

Modify HW to interrupt the CPU when PB1 is Modify HW to interrupt the CPU when PB1 is pressed (I/O ports should be the same)pressed (I/O ports should be the same) Use IRQ# interrupt input pin (Port E, bit 1) Use IRQ# interrupt input pin (Port E, bit 1)

SW should include a “main program” and the Push SW should include a “main program” and the Push Button ISRButton ISR The “main” program should do all initialization and then The “main” program should do all initialization and then

enter an endless loop in which a count is written to the enter an endless loop in which a count is written to the 7-segment display about once per second7-segment display about once per second Note that all column lines should be low until an interrupt Note that all column lines should be low until an interrupt

occursoccurs The ISR should increment in PB counter & display the The ISR should increment in PB counter & display the

current value of it for 5 seconds on the 7-seg display.current value of it for 5 seconds on the 7-seg display. Set a variable so the main program will not disturb the 7-Set a variable so the main program will not disturb the 7-

segment display for about 5 seconds after an interruptsegment display for about 5 seconds after an interrupt

Page 12: MC9S12C32 Interrupts

Debug suggestionsDebug suggestions

The ISR can write a unique pattern to LEDs or 7-The ISR can write a unique pattern to LEDs or 7-segment display to indicate that it was enteredsegment display to indicate that it was entered

Display the ISR counter on the other display to ensure it Display the ISR counter on the other display to ensure it is counting properly upon ISR executionis counting properly upon ISR execution

Global variables can be modified by the ISR to indicate Global variables can be modified by the ISR to indicate that the ISR was executedthat the ISR was executed

An “unimplemented ISR” error, detected by the An “unimplemented ISR” error, detected by the debugger, indicates that there was no interrupt vector in debugger, indicates that there was no interrupt vector in the vector tablethe vector table