|
我看了马老师的11章的实战练习的icp测频的方法,结合自己的问题编写了测频程序,可总有问题,查了半天也不知道哪错了。因为外围电路有限,无法输出所测得频率,所以我利用T0口ctc模式产生所测得频率的方波,来检测测频的正确与否。我的问题是无论给什么频率的信号,输出总是20kHz的信号。我测频的范围大概在50KHz到100KHz之间,比如100KHz,我用1MHz对其捕捉,一个周期只能计10个,所以我计64个周期,共640个,这样为了准确些。程序如下:
//ICC-AVR application builder : 2007-10-19 15:44:21
// Target : M48
// Crystal: 1.0000Mhz
#include <iom48v.h>
#include <macros.h>
unsigned int icp_v1,icp_v2;
char icp_n;
int icp_ok;
void port_init(void)
{
PORTB = 0x01;
DDRB = 0x00;
PORTC = 0x00; //m103 output only
DDRC = 0x00;
PORTD = 0x00;
DDRD = 0x40;
}
//TIMER1 initialize - prescale:1
// WGM: 0) Normal, TOP=0xFFFF
// desired value: 1Hz
// actual value: Out of range
void timer1_init(void)
{
TCCR1B = 0x00; //stop
TCNT1H = 0x00 /*INVALID SETTING*/; //setup
TCNT1L = 0x00 /*INVALID SETTING*/;
OCR1AH = 0x00 /*INVALID SETTING*/;
OCR1AL = 0x00 /*INVALID SETTING*/;
OCR1BH = 0x00 /*INVALID SETTING*/;
OCR1BL = 0x00 /*INVALID SETTING*/;
ICR1H = 0x00 /*INVALID SETTING*/;
ICR1L = 0x00 /*INVALID SETTING*/;
TCCR1A = 0x00;
TCCR1B = 0xC1; //start Timer
}
#pragma interrupt_handler timer1_capt_isr:11
void timer1_capt_isr(void)
{
//timer 1 input capture event, read (int)value in ICR1 using;
if (icp_n >= 64) // 第N个上升沿到
{
icp_v2 = ICR1; // 记录第N个上升沿时间
TIMSK1 = 0x00; // 禁止T/CI输入捕捉和溢出中断
icp_ok = 1;
}
else if (icp_n == 0)
{
icp_v1 = ICR1; // 记录第1个上升沿时间
}
icp_n++;
}
//call this routine to initialize all peripherals
void init_devices(void)
{
//stop errant interrupts until set up
CLI(); //disable all interrupts
port_init();
timer1_init();
MCUCR = 0x00;
EICRA = 0x00; //extended ext ints
EIMSK = 0x00;
TIMSK0 = 0x00; //timer 0 interrupt sources
TIMSK1 = 0x20; //timer 1 interrupt sources
TIMSK2 = 0x00; //timer 2 interrupt sources
PCMSK0 = 0x00; //pin change mask 0
PCMSK1 = 0x00; //pin change mask 1
PCMSK2 = 0x00; //pin change mask 2
PCICR = 0x00; //pin change enable
PRR = 0x00; //power controller
SEI(); //re-enable interrupts
//all peripherals are now initialized
icp_n = 0;
}
//
void main(void)
{
long fv;
unsigned int icp_2;
init_devices();
//insert your functional code here...
icp_ok=0;
while(1)
{
if (icp_ok == 1) // 完成一次测量
{
if (icp_v2 >= icp_v1) // 计算N个上升沿的时钟脉冲个数,
icp_2 = icp_v2 - icp_v1;
else
icp_2 = 65536 - icp_v1 + icp_v2;
fv=1000000*(long)64/icp_2; // 换算成频率值
TCCR0B = 0x00; //stop
TCNT0 = 0x00;
TCCR1B=0x00;
OCR0A=(int)(1000000/(2*fv)-1);
TCCR0A=0x42;
TCCR0B=0x01;
}
}
}
我的问题是无论给什么频率的信号,输出总是20kHz的信号,这是什么原因呢?
谢谢大家的帮助 |
阿莫论坛20周年了!感谢大家的支持与爱护!!
月入3000的是反美的。收入3万是亲美的。收入30万是移民美国的。收入300万是取得绿卡后回国,教唆那些3000来反美的!
|