Tôi muốn thiết lập một bộ đếm thời gian để gọi một chức năng 800 lần mỗi giây. Tôi đang sử dụng Arduino Mega và Timer3 với bộ tổng hợp 1024. Để chọn yếu tố bộ đếm trước tôi đã xem xét các bước sau:
- CPU yêu cầu: 16 MHz
- Độ phân giải thời gian: 65536 (16 bit)
- Chia CPU freq bởi prescaler chọn: 16x10 ^ 6/ 1024 = 15.625
- Chia phần còn lại thông qua freq 62500/800 = 19 mong muốn .
- Đặt kết quả + 1 vào thanh ghi OCR3.
Tôi đã sử dụng bảng sau để đặt các thanh ghi của TCCR3B:
Lỗi
Không thể biên dịch mã. Đây là lỗi được trả về bởi trình biên dịch:
Servo \ Servo.cpp.o: Trong chức năng '__vector_32': C: \ Chương trình tập tin (x86) \ Arduino \ library \ Servo / Servo.cpp: 110: nhiều định nghĩa của '__vector_32' AccelPart1_35.cpp.o: C: \ Tệp chương trình (x86) \ Arduino / AccelPart1_35.ino: 457: lần đầu tiên được xác định tại đây c: / tệp chương trình (x86) / arduino / phần cứng / công cụ / avr / bin /../ lib / gcc / avr / 4.3.2 /. ./../../../avr/bin/ld.exe: Vô hiệu hóa thư giãn: nó sẽ không hoạt động với nhiều định nghĩa
Mật mã
volatile int cont = 0;
unsigned long aCont = 0;
void setup()
{
[...]
// initialize Timer3
cli(); // disable global interrupts
TCCR3A = 0; // set entire TCCR3A register to 0
TCCR3B = 0; // same for TCCR3B
// set compare match register to desired timer count: 800 Hz
OCR3A = 20;
// turn on CTC mode:
TCCR3B |= (1 << WGM12);
// Set CS10 and CS12 bits for 1024 prescaler:
TCCR3B |= (1 << CS30) | (1 << CS32);
// enable timer compare interrupt:
TIMSK3 |= (1 << OCIE3A);
// enable global interrupts:
sei();
}
void loop()
{
// Print every second the number of ISR invoked -> should be 100
if ( millis() % 1000 == 0)
{
Serial.println();
Serial.print(" tick: ");
Serial.println(contatore);
contatore = 0;
}
}
[...]
// This is the 457-th line
ISR(TIMER3_COMPA_vect)
{
accRoutine();
contatore++;
}
void accRoutine()
{
// reads analog values
}
Làm thế nào để giải quyết xung đột với thư viện servo?
GIẢI PHÁP
Xung đột được giải quyết bằng cách sử dụng mã sau đây. Nó biên dịch nhưng bộ đếm được liên kết với bộ định thời 800Hz không làm tăng giá trị của nó.
volatile int cont = 0;
void setup()
{
Serial.begin(9600);
// Initialize Timer
cli(); // disable global interrupts
TCCR3A = 0; // set entire TCCR3A register to 0
TCCR3B = 0; // same for TCCR3B
// set compare match register to desired timer count: 800 Hz
OCR3B = 20;
// turn on CTC mode:
TCCR3B |= (1 << WGM12);
// Set CS10 and CS12 bits for 1024 prescaler:
TCCR3B |= (1 << CS30) | (1 << CS32);
// enable timer compare interrupt:
TIMSK3 |= (1 << OCIE3B);
// enable global interrupts:
sei();
Serial.println("Setup completed");
}
void loop()
{
if (millis() % 1000 == 0)
{
Serial.print(" tick: ");
Serial.println(cont);
cont = 0;
}
}
ISR(TIMER3_COMPB_vect)
{
cont++;
}
Vì vấn đề chính đã được giải quyết, tôi đã tạo một câu hỏi khác ở đây liên quan đến vấn đề tăng số lượt truy cập.
#define _useTimer3
dòng hoặc thử đặt #undef _useTimer3
quyền sau khi bao gồm.