Upload
roberta-stevens
View
214
Download
0
Embed Size (px)
Citation preview
ECE 371 – Unit 9
Interrupts (continued)
Example
• Set up Two Interrupt Request Inputs:
– Port H[0] Set Interrupt Flag on “0” to “1” transition (rising edge)
• Port H[1] Set Interrupt Flag on “1” to “0” transition (trailing edge)
Example (cont)
Response to Interrupts:
• Toggle H[4] on each H[0] Interrupt
• Toggle H[5] on each H[1] Interrupt
#include ece371.h/* Port H Port Definitions */#define PTH _P( 0x260)#define PTIH _P( 0x261)#define DDRH _P( 0x262)#define RDRH _P( 0x263) #define PERH _P( 0x264) #define PPSH _P( 0x265) #define PIEH _P( 0x266) #define PIFH _P( 0x267)
Example – Port H Interrupt
Interrupt Service Routine
Setting up (declaring) “myisr” as in Interrupt Service Routine:
void myisr() __attribute__ ((interrupt)); //should be at the //beginning of source file
/* 2 underscores before and after attribute */
/* Do not use #pragma, which is used in the text To establish in Interrupt Service Routine*/
#include <ece371.h>#include <ports_D256.h>void myisr() __attribute__ ((interrupt));
int main() {/* stack is initialized by c */
/* initialize interrupt vector for Port H */ SETVECT(0xFFCC,my_isr);
/* init Data Direction Bits for Port HBits 0 and 1 are InputBits 4 and 5 are OutputOther Bits assigned to other
applications /* DDRH = DDRH & 0xFC; // Bit 0 and 1 are Input DDRH = DDRH | 0x30; // Bit 4 and 5 are output
Example – Main Program
/* Set Bit 4 and 5 to full drive outputs */ RDRH = RDRH & 0xCF; //11001111
/* Enable Bit 0 and 1 Pull Device on Input */ PERH = PERH | 0x03; // Enable Bit 0 and 1 Pull Device PPSH = (PPSH & 0xFC) | 0x01; // Bit 0 Rise, Bit 1 Fall
/* Clear Pending Port H Bit 0 and 1 Interrupts */ PIFH = 0x03;
/* Enable Bit 0 and 1 to Interrupt */ PIEH = PIEH | 0x03; // Enable Interrupts
/* Enable Maskable Interrupt System */ ENABLE();
/* do main program processing */ while(TRUE); // loop}
void my_isr(void) { if ((PIFH&0x2)!=0) {//Bit 1 was source of interrupt PIFH = 0x02; // Clear Interrupt // Do interrupt specific action, complement Bit 5 PTH = PTH ^ 0x20; } if ((PIFH&0x01)!=0) {//Bit 0 was source of interrupt PIFH = 0x01; // Clear Interrupt // Do interrupt specific action, complement Bit 4 PTH = PTH ^ 0x10; } }
Example Interrupt Handler
• Use Each Bit of Port H as an Interrupt Request Input
• Count the Running Total of Interrupt Request that Occur on Each of the 8 Request Inputs
Another Example: 8-Switch CounterImplemented Using Interrupts
#include <ece371.h>#include <ports_D256.h>void myisr() __attribute__ ((interrupt));/* Port H definitions go here */int count[8]=0,0,0,0,0,0,0,0; // globalint main() {/* stack is initialized by c */
/* initialize interrupt vector for Port H */ SETVECT(0xFFCC,my_isr);
/* Init Data Direction Bits for Port HAll bits are input
/* DDRH = 0x00;
Another Example: (cont)
/* Enable Pull Devices on Port H all bits */ PERH = 0xFF; /* Interrupt on “1” to “0” Transitions all bits PPSH = 0x00;
/* Clear Pending Port H Interrupts all bits */ PIFH = 0xFF;
/* Enable all Port H bits to Interrupt */ PIEH = 0xFF; // Enable Interrupts
/* Enable Maskable Interrupt System */ ENABLE();
/* do main program processing */ while(TRUE); // loop}
void my_isr(void) { int i; for(i=0;i<8;i++) {if ((PIFH & (1<<i))!=0) {//Bit i was source of interrupt PIFH = (1<<i); // Clear Interrupt // Do interrupt specific action count[i]++; } } }
Method 1 for Implementing Interrupt Service Routine
void my_isr(void) { int i; unsigned char change; change = PIFH; // change bitsw PIFH = change; // Clear interrupt flag for(i=0, i<8, i++) if(((change>>i)&0x01)!=0) {count[i]++;} }
Method 2 for Implementing Interrupt Service Routine
Still Another Example: Interfacing a Keypad (Fig. 5.5) Using Interrupts
Use Port H
Keypad with Interrupts
• Port H[3:0]– Output– Full Drive– Set Bits to “0” (all at once)
• Port H[7:4]– Input– Interrupt on “1” to “0” (Key Pressed)
Cflag!=0 ?
c=cin;cflag=0;
Function “ci” to Read Keypad
ScanKeypad
cin=keypad charactercflag=1;
Interrupt
Main –ISR CommunicationShared Variables
==0
!=0
Intr. Service Routine
Passing Parameters Between Main Program and Interrupt Service Routine
unsigned char cin, cflag=0; /*global variables declared outside Interrupt Service Routine and all functions/*
//function to read keyboard:unsigned char ci(void){ while(cflag == 0); cflag=0; return cin;}
Main Program – Receiving Character from ISR
Int main(){ unsigned char c; PTH=0; // select all rows ENABLE(); // enable all interrupts ---- c=ci(); // input character from keypad //function ci defined on previous slide
----}
Tasks for Keypad ISR
• On a Port H Interrupt:– Clear Interrupt Flag Register with Write– Scan Keypad for Pressed Key– cin=key; cflag=1:– Set Port H outputs to “0
void kbisr() //define ISR{unsigned char mask[4]=0x0E,0x0D,0x0B,0x07;int i,j;
//1110, 1101, 1011, 0111 PIFH = PIFH; // clear interrupt request for(i=0;i<4;i++) {PTH = mask[i]; // assert row in keypad for(j=0;j<4;j++) {if((PTH>>4) == mask[j]) {if (((i<<2)+j)<10) {cin = ‘0’+(i<<2)+j;cflag=1;} else cin=‘A’+(i<<2)+j -10;cflag=1;} } } PTH = 0x00; // select all rows}
Keypad ISRvoid kbisr() __attribute__ ((interrupt)); //Establish kbisr as ISR