[Câu hỏi] Về ngắt trong PIC 16F887

IceSandwich

Thành Viên PIF
Em đang viết chương trình dò line cho robot, đọc adc của 8 chân từ AN0 -> AN7 nhưng gặp vấn đề sau đây:

Ý tưởng của chương trình là đọc adc trả về của cảm biến để biết vị trí trên line, sau đó định thời gian cứ mỗi 1ms đọc cảm biến 1 lần. Ở đây em dùng quét 8 kênh adc sau đó định thì bằng timer0 để đọc.

Em xây dựng hàm
Code:
sensor_read()
, chỉ cần gọi nó là sẽ thay đổi giá trị của biến
Code:
sensor
và đặt nó trong ngắt timer0.

Chương trình viết riêng cho đọc cảm biến thì chạy tốt, cả timer0 cũng chạy đúng luôn, nhưng khi ghép 2 module lại thì nó lại chạy sai (tức ko chạy)

Em nghĩ vấn đề ở đây là khi muốn đọc adc thì phải xử lí ngắt adc, cùng lúc đó định thì timer0 tràn 1ms thì vào ngắt, tức khi timer0 tràn thì vào ngắt xử lí adc, như vậy có nghĩa là đang ở trong ngắt của timer0 thì lại gọi ngắt của adc ra và em nghĩ lỗi xảy ra ở chỗ đó.

Cấu trúc trong ngắt của em là:
Code:
void interrupt isr()
{
if(ADIF && ADIE)
{
// Code xử lí trong ngắt ADC
};

if(T0IF && T0IE)
{
// Code xử lí ngắt t0
}
}
Em chưa tìm ra cách khắc phục vấn đề này, mong anh chị và các bạn giúp đỡ :)
 
một số góp ý cho bạn như thế này.
- khi vào chương trình phục vụ ngắt thì bạn nên kiểm tra và xoá cờ báo ngắt trước khi làm các việc khác.
- giải thuật của bạn nên thực hiện như thế này thì sẽ ổn hơn:
+ đầu tiên bạn cho time chạy để tạo chu kỳ lấy mẫu. sau khi mẫu ADC thứ 8 được lấy thì bạn cho timer chạy sau khi timer tràn thì lại vào kích hoạt lấy mẫu thứ nhất. và cho phép ngắt ADC. ADC vào ngắt lần 1 thì lấy mẫu thứ 2 và cứ thế cho đến khi lấy đũ 8 mẫu.
+ hoặc bạn cho thời gian timer chạy dày hơn thử xem. vì trong pic16F887 không có nhiều vector ngắt mà chỉ có một nên khi trong hàm ngắt thằng nào viết trước thì thằng đó được ưu tiên trước, thằng nào viết sau thì sẽ được ưu tiên sau.
 

IceSandwich

Thành Viên PIF
Trong chương trình em xây dựng hàm
Code:
sensor_volt()
, khi gọi hàm đó thì sẽ quét lần lượt 8 kênh ADC và lấy mẫu điện áp của từng sensor và cứ lần lượt từng con sensor thì phải vào ngắt ADC 1 lần để lấy giá trị cho nó.
Sau đó trong hàm
Code:
sensor_read()
em gọi lại hàm trên, sau đó là đoạn code so sánh điện áp để đưa ra giá trị cho biến
Code:
sensor
.

Em có thắc mắc là vì khi tràn timer0 vào ngắt và xử lí ngắt t0 thì trong code ngắt t0 em lại gọi hàm sensor_read(), khi đó thì xảy ra trường hợp đang trong ngắt T0 lại gọi ngắt ADC. Không biết PIC có cho phép vấn đề đó ko?
 
thực ra là nó không đáp ứng ngay lập tức mà nó sẽ đợi khi thoát khỏi ngắt thì mới vào lại. tốt nhất là bạn nên dùng theo cách này: sau khi mẫu ADC thứ 8 được lấy thì bạn cho timer chạy sau khi timer tràn thì lại vào kích hoạt lấy mẫu thứ nhất. và cho phép ngắt ADC. ADC vào ngắt lần 1 thì lấy mẫu thứ 2 và cứ thế cho đến khi lấy đũ 8 mẫu. rồi lại cho timer chạy.
 
Top