Bài tập buổi 6: Timer 1 + External interrupt

Manhdd

Cố Vấn CLB
Staff member
Timer 1 chỉ là mở rộng của timer 0 && các bạn chỉ mới biết về led + nút nhấn => nội dung bài tập này cũng không có gì khó. Mình chỉ gợi mở một số bài để các bạn tham khảo, có thể tự tìm hiểu thêm:
1. Sửa phần Intermediate level ở bài 5, thay việc dùng CLK ngoài nối vào T0CKI (Timer0) bằng việc dùng CLK ngoài nối vào T1CKI (Timer1).
2. Cũng sửa phần Intermediate level ở bài 5, thay việc dùng CLK ngoài của timer bằng việc dùng ngắt ngoài nối vào chân RB0 để điều khiển.
3. Sử dụng thạch anh 32768 Hz, qua timer 1 để đếm giây cho led 7 đoạn.
...

Các bạn nén các file : .c và .hex lại rồi nộp tới email: pif.picc5@gmail.com với cú pháp sau ở chủ đề thư:
[C5..] [BT..] [N..] _Họ tên_ ...​
Ví dụ: [C5A] [N1] [BT6] _ Dương Lập Đức _ .... (...: có thể ghi thêm nội dung gì đó)
Danh sách nhóm xem tại đây . Chúng ta sẽ tổng kết lại và loại bớt các bạn không nộp bài tập vào buổi 7.

Buổi sau chúng ta sẽ học về LCD. Về lập trình không có gì khó, quan trọng là các bạn chuẩn bị đủ mạch LCD + LCD (giá LCD 16x2 hình như là 65k). Hầu như mọi hướng dẫn đều có trong TUT rồi, có câu hỏi gì cứ việc hỏi nhé!

Buổi sau là buổi cuối, các bạn sẽ chọn nhóm (2- 3 người) để làm bài tập giữa khoá. Chúng ta sẽ gom 2 lớp lại và học buổi sáng thứ bảy thôi (bạn nào không đi được có thể nhờ bạn đăng ký nhóm dùm, còn nội dung bài học LCD có thể tự học, rất dễ).
Các bạn thảo luận các vấn đề về led 7 đoạn, đệm dòng, ghi dịch, ma trận led, ma trận nút nhấn, ... tại luồng sau. Có thể tham khảo mini project1 của lớp c4 tại đây .

Cố gắng chọn cho mình 1 đề tài phù hợp nhé! ^^

PS: Đính kèm là code mẫu Timer 1 + External interrupt.
 

Attachments

Manhdd

Cố Vấn CLB
Staff member
Mình có coi qua bài tập buổi 5 của một số bạn, đáng chú ý là rất nhiều bạn chỉ cho chương trình chạy trong ngắt Isr, khiến hàm Isr rất dài . Hình như các bạn đang lầm lẫn, cho rằng hàm Isr là nơi chạy chương trình thì phải ??

Mình xin nhắc lại, chương trình chính của chúng ta là main(), và chủ yếu chạy trong while(1) của main().
Tác vụ Isr được gọi khi 1 ngắt đã cho phép xảy ra (như ngắt timer thì mỗi khi timer tràn). Con trỏ chương trình sẽ lập tức nhảy vào Isr để thi hành các tác vụ cần thiết. Sau khi chạy hết Isr, con trỏ chương trình sẽ trở lại vị trí cũ trước khi ngắt trong hàm main. Nếu như có ngắt nữa thì những việc trên sẽ được lặp lại.
MCU có nhiều nguồn ngắt và điều rất cần thiết là phải thi hành Isr thật nhanh để quay trở về main() trước khi có ngắt mới. Do vậy, khi viết code cần phải tinh giảm tối đa các tác vụ xử lý trong ngắt (như bằng việc thay đổi biến toàn cục, main() sẽ kiểm tra biến toàn cục này khi cần thiết, ...). Vì chương trình của các bạn chỉ có 1 ngắt và thời gian giữa 2 ngắt liên tiếp là khá dài nên nhiều bạn không chú ý điều này.
Mong các bạn rút kinh nghiệm cho những lần sau :d
 

pkdbkhcm

Trứng gà
cho mình hỏi tí!!! trong cái code mẫu của timer1 đoạn set giá trị cho TMR1:
// T1 Module Register (initial value)
TMR1H = 128;
TMR1L = 0; // = 256
tại sao là 256, mình ko hiểu!!!!! Cái thanh ghi này 16 bit, 8 bit cao TMR1H đã đc set là 10000000, 8 bit thấp TMR1L set là 00000000 thì giá trị thanh ghi TMR1 fai la 2^15 chứ sao là 2^8??????
 

Manhdd

Cố Vấn CLB
Staff member
Chú thích // = 256 là dành cho byte thấp của TMR1, chứ không phải toàn thanh ghi đâu bạn. Mình chú thích để các bạn hiểu thêm rằng trình dịch sẽ tự cắt bit 8 để có giá thị là 0x00.
 

Jan

Trứng gà
Có tài liệu hướng dẫn về timer1 không. Thấy nó khác với timer0, đọc vào chẳng hiểu gì cả
 

Manhdd

Cố Vấn CLB
Staff member
Có tài liệu hướng dẫn về timer1 không. Thấy nó khác với timer0, đọc vào chẳng hiểu gì cả
Timer 1 đã có code mẫu rồi mà. Tài liệu học tập chính là datasheet đó.
Bạn nên chịu khó một tí nha!
 

Jan

Trứng gà
void interrupt isr() // interrupt service rountine
{

if (TMR1IF && TMR1IE) //Interrupt Flag is on
{
TMR1ON = 0; // Stop timer1
TMR1IF = 0; // pull down interrupt flag
t++;
if (t>3) t=1;
// reset T1
TMR1H = 128;
TMR1L = 0; // = 256
TMR1ON = 1; // Allow timer1 1o count
}
}
Tại sao tắt timer1 rồi xét t rồi lại bật lên?
Và xung lock ngoài đưa vào là từ cái gì đưa vào?
 

Manhdd

Cố Vấn CLB
Staff member
Tại sao tắt timer1 rồi xét t rồi lại bật lên?
Trong ngắt này, chúng ta tạm dừng timer 1 để đặt lại giá trị đầu. Timer 1 sẽ được chạy tiếp sau đó.

Và xung lock ngoài đưa vào là từ cái gì đưa vào?
Bạn xem kĩ sơ đồ khối của Timer 1. Nguồn xung clock ngoài do bit T1OSCEN định:
- 0: lấy nguồn xung gắn vào chân T1CKI (RC0) (tương tự timer 0)
- 1: lấy nguồn dao động từ thạch anh gắn vào 2 chân T1OSI (RC1) và T1OSO (RC0).
 
Top