TODOPIC
Microcontroladores PIC => dsPIC => Mensaje iniciado por: brutto en 16 de Febrero de 2011, 08:29:37
-
hola, estoy comenzando con el manejo de los dspic y mi primera tarea era encender un led durante medio segundo y apagarlo continuamente pero no me funciona correctamente el tiempo de encendido y apagado, he probado a cambiar los valores fcy y delay_ms pero sigue sin ajustarse al medio segundo, ¿alguien sabe que hago mal?
este es el codigo:
/** INCLUDES *****/
#include "p33FJ128MC202.h"
#define FCY 40000000UL
#include <libpic30.h>
/**** CONFIGURACION BITS ***/
_FOSCSEL(FNOSC_FRC);
_FOSC(FCKSM_CSECMD & OSCIOFNC_ON & POSCMD_NONE);
_FWDT(FWDTEN_OFF); //wdt disable
_FICD (JTAGEN_OFF&ICS_PGD1);//jtad disable icd enable en PGD1
_FPOR(FPWRT_PWR1);
int main (void)
{
int a,i,j;
Oscilador_init();
puertos_init();
i=0;
LATBbits.LATB4=0;
while (1)
{
LATBbits.LATB4=1;
__delay_ms(1000);
LATBbits.LATB4=0;
__delay_ms(1000);
}
} // FINAL VOID MAIN
void Oscilador_init(void)
{
// Configure Oscillator to operate the device at 40Mhz
// Fosc= Fin*M/(N1*N2), Fcy=Fosc/2
// Fosc= 8M*40/(2*2)=80Mhz for 8M input clock
PLLFBD=38; // M=40
CLKDIVbits.PLLPOST=0; // N1=2
CLKDIVbits.PLLPRE=0; // N2=2
OSCTUN=0; // 7.37Mhz
// Disable Watch Dog Timer
RCONbits.SWDTEN=0;
// Clock switching to incorporate PLL
__builtin_write_OSCCONH(0x01); // Initiate Clock Switch to PLL
__builtin_write_OSCCONL(0x01); // Start clock switching
while (OSCCONbits.COSC != 0b001); // Wait for Clock switch to occur
while(OSCCONbits.LOCK !=1); //wait for PLL to lock
}
void puertos_init(void)
{
ADPCFG = 0xFFFF;
TRISB=0x00;
LATB=0;
}
por cierto, uso el pickit3 conectado al dspic directamente, usando el mplab para alimentar el voltaje.
gracias de antemano
-
Revisa por aquí (http://www.ucontrol.com.ar/forosmf/tutoriales-guias-y-cursos-en-ucontrol/pic24-y-c30-un-mundo-de-diversiones!-d/msg21867/#msg21867)
Al final explico un problema que encontré en la librería.
Saludos!
-
En C30 o HiTech los delays tienen un rango de operación que va de 0 a 100ms para __delay_ms(). Si necesitas duraciones en segundos, anida varios delays juntos.
Si metes un valor mayor a 100, el delay se vuelve errático.
-
En C30 o HiTech los delays tienen un rango de operación que va de 0 a 100ms para __delay_ms(). Si necesitas duraciones en segundos, anida varios delays juntos.
Si metes un valor mayor a 100, el delay se vuelve errático.
Igual es fácil solucionarlo ;-)
-
muchisimas gracias por la aportacion, no lei por ningun lado lo que c30 estaba limitado a 100ms en esa libreria, ahora funciona ok.
GRACIAS.
-
muchisimas gracias por la aportacion, no lei por ningun lado lo que c30 estaba limitado a 100ms en esa libreria, ahora funciona ok.
GRACIAS.
Haciendo pruebas es como uno se da cuenta. Pero puedes hacer como Suky y mejorarla. O como yo, anidarla y salir del paso. :D
#define DelayMs(x) __delay_ms(x)
#define DelayUs(x) __delay_us(x)
//Nota: __delay_ms() no trabaja más de 100ms, el tiempo falla
//Nota: __delay_us() no trabaja más de 100us, el tiempo falla
///////////////////////////////////////////////////////////////////////////
void DelaySeg(unsigned char segundos)
{
segundos*=10; //lo paso a 100ms
for(segundos=segundos; segundos>0; --segundos)
{
DelayMs(100);
}
}
///////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////
void DelayMedioSeg(unsigned char medio_seg)
{
medio_seg *= 5;
for(medio_seg=medio_seg; medio_seg>0; --medio_seg)
{
DelayMs(100);
}
}
///////////////////////////////////////////////////////////////////////////
-
Hola trata de utilizar este codigo, la verdad ami me ha resultado y los tiempos son muy exactos ya que utilizo los timers del DSPIC para milisegundos. Los retardos para usegundos pueden variar por algunas fracciones, pero hay que recordar que estamos trabajando a 64MHZ, JEJEJE. Puedes comprobarlo con el stopwatch de MPLAB. Saludos.
void Delayms( unsigned t) //retardo 1mseg
{
PR1 = 16000;
TMR1 = 0;
T1CON = 0x8000; //Timer1 activo con prescaler de 1:1
t=t+1; //compensacion
while(t--)
{
while(!IFS0bits.T1IF); // Se queda ciclando mientras T1IF = 0
IFS0bits.T1IF = 0; // Pasa 1ms, limpia T1IF y se repite el ciclo
}
}
void Delayus( unsigned t) //retardo 1mseg
{
PR1 = 16;
TMR1 = 0;
T1CON = 0x8000; //Timer1 activo con prescaler de 1:1
while(t--)
{
while(!IFS0bits.T1IF); // Se queda ciclando mientras T1IF = 0
IFS0bits.T1IF = 0; // Pasa 1ms, limpia T1IF y se repite el ciclo
}
}