AVR External Interrupts
Chúng ta đã xem xét các khái niệm cơ bản về Ngắt AVR, bây giờ chúng ta hãy tiếp tục và sử dụng tính năng Ngắt ngoài trên AVR MCU.
Basics
Khi một ngắt xảy ra, việc thực hiện chương trình hiện tại sẽ bị dừng lại, ngữ cảnh được lưu và điều khiển sẽ chuyển đến Quy trình Dịch vụ Ngắt (ISR). Khi ISR được thực thi, việc thực thi chương trình chính được tiếp tục. Điều này thường xảy ra với hầu hết các bộ điều khiển Micro đơn giản. Chúng tôi đã làm việc với Atmega32 cho loạt bài này, tuy nhiên sẽ không có nhiều khác biệt khi làm cho nó hoạt động với các MCU AVR khác. Bây giờ, chúng ta hãy xem cách cấu hình Ngắt ngoài trong AVR.
Các bước để cấu hình Ngắt:
1.Đặt các bit INT1 và INT0 trong thanh ghi điều khiển ngắt chung (GICR)
2.Cấu hình thanh ghi điều khiển MCU (MCUCR) để chọn loại ngắt.
3.Đặt bit Kích hoạt ngắt toàn cục (I-bit) trong Thanh ghi trạng thái AVR (SREG)
4.Xử lý ngắt trong mã Quy trình Dịch vụ Ngắt.
INT1 và INT0 cho phép hai ngắt. MCUCR giúp định cấu hình loại ngắt, mức, cạnh được kích hoạt, v.v. I-bit trong SREG là điều khiển chính cho tất cả các ngắt trong bộ điều khiển vi mô AVR. Quan sát trình tự nó được bật sau khi tất cả các ngắt được cấu hình. Điều này ngăn chặn, bất kỳ ngắt nào xảy ra trước khi phần còn lại của chúng được cấu hình.
Thanh ghi điều khiển ngắt chung (GICR)
Thanh ghi GICR được hiển thị bên dưới được sử dụng để kích hoạt ngắt INT0 và INT1. Các ngắt này tương ứng với hai chân vật lý PD3 và PD4 tương ứng. INT0 được cấu hình để tạo ra mức thấp được kích hoạt và INT1 như là cạnh giảm kích hoạt ngắt tương ứng. Bộ đếm là số tăng và được hiển thị khi xảy ra ngắt.
7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
---|---|---|---|---|---|---|---|
INT1 | INT0 | INT2 | - | - | - | IVSEL | IVCE |
TG điều khiển MCU (MCUCR)
Thanh ghi MCUCR cho phép chúng ta cấu hình loại ngắt mà chúng ta cần như bảng dưới đây:
7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
---|---|---|---|---|---|---|---|
SE | SM2 | SM1 | SM0 | ISC11 | ISC10 | ISC01 | ISC00 |
ISC01 | ISC00 | Description |
---|---|---|
0 | 0 | The low level of INT0 generates an interrupt request. |
0 | 1 | Any logical change on INT0 generates an interrupt request. |
1 | 0 | The falling edge of INT0 generates an interrupt request. |
1 | 1 | The rising edge of INT0 generates an interrupt request. |
General Interrupt Flag Register(GIFR)
7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
---|---|---|---|---|---|---|---|
INTF1 | INTF0 | INTF2 | - | - | - | - | - |
Chúng tôi sẽ kết nối hai công tắc với hai chân ngắt và hiển thị trạng thái trên màn hình LCD. Các kết nối được hiển thị trong hình ảnh bên dưới.
Code
#include<avr/io.h> #include<avr/interrupt.h> #include<util/delay.h> #include "lcd.h" volatile int cnt_zero,cnt_one; ISR (INT0_vect) //External interrupt_zero ISR { cnt_zero++; } ISR (INT1_vect) //External interrupt_one ISR { cnt_one++; } int main() { DDRC=0xff; //Configure PORTC(Lcd databus) as output DDRD=0xe0; //Configure INT0,INT1 as input and PORTD5-PORTD7(rs,rw,en) as output LCD_SetUp(PB_0,PB_1,PB_2,P_NC,P_NC,P_NC,P_NC,PB_4,PB_5,PB_6,PB_7); LCD_Init(2,16); GICR=0xc0; //Enable External Interrupts INT0 and INT1 MCUCR=0x08; //Configure INT0 active low level triggered and INT1 as falling edge sei(); // Enable global interrupts by setting global interrupt enable bit in SREG while(1) { LCD_Printf("EINT0:%4u\n",cnt_zero); LCD_Printf("EINT1:%4u\n",cnt_one); } }
GIẢI THÍCH CODE
ADD các thư viện.
#include<avr/io.h> #include<avr/interrupt.h> #include<util/delay.h> #include "lcd.h"
Chương trình con INTERUPT 0
ISR (INT0_vect) //External interrupt_zero ISR { cnt_zero++; }
Chương trình con INTERUPT 1
ISR (INT1_vect) //External interrupt_one ISR { cnt_one++; }
TRONG HÀM MAIN.
DDRC=0xff; //Configure PORTC(Lcd databus) as output - PORT C KẾT NỐI LCD.
TẤT CẢ NHỮNG MÃ CÒN LẠI ĐÃ GHI CHÚ TRONG CODE.
TRONG WHILE(1)
LCD_Printf("EINT0:%4u\n",cnt_zero); // KHI NGẮT 0 TÁC ĐỘNG cnt_zero TĂNG LÊN 1.
LCD_Printf("EINT1:%4u\n",cnt_one); // KHI NGẮT 1 TÁC ĐỘNG cnt_one TĂNG LÊN 1.
TẤT CẢ HIỂN THỊ RA LCD.