|
/******************************************************************************
* Description: *
* This program illustrates the use of the PWM module in Complementary Output mode.*
* PWM1H and PWM2H are configured to be digital outputs, and PWM1L and PWM2L *
* are selected as PWM outputs. *
* *
*****************************************************************************/
#include <p33FJ64GS606.h>
#include "h\ConfigBit.h"
#include "h\Duty_Data.h"
void init_PWM1(void);
void init_OSC(void);
void init_PIN(void);
void SPWM(void);
void tmr1_16(void);
unsigned int i=0;
int main()
{
init_OSC();
init_PIN();
init_PWM1();
tmr1_16();
while(1)
{
SPWM();
//if(i>480)i=0;
};/* Infinite Loop */
}
void init_PWM1(void)
{
/* Select Edge-Aligned PWM*/
PWMCON1bits.CAM = 0; /* For Edge-Aligned Mode */
/* Select Center-Aligned PWM*/
// PWMCON1bits.CAM = 1; /* For Center-Aligned Mode */
//PWMCON1bits.ITB = 1; /* Enable Independent Time Base */
/* Select time base period control */
/* Choose one of these options */
//PWMCON1bits.ITB = 0; /* PTPER provides the PWM time period value */
PWMCON1bits.ITB = 1; /* PHASEx/SPHASEx provides the PWM time period value */
/*PTPER STPER PHASEX SPASEX=ACLK*8*PWM Time/(PCLKDIV)-8,
ACLK=REFCLK * M1/N;
ACLK=Fvco/N */
/* Choose PWM time period based on XT input clock */
/* PWM frequency is 100 kHz */
/* Choose one of the following options */
//PTPER = 592; /* When PWMCONx<9> TIB=0 PTPER = ((120*8*42us)/8-8 =5040 , where 24kHz*/
PHASE1 =5032; /* When PWMCONx<9> TIB= 1 */
//SPHASE1 = 9426; /* When PWMCONx<9> TIB= 1 */
PTCON2bits.PCLKDIV = 0;
/*~~~~~~~~~~~~~~~~~~~~~~~ PWM1 Configuration ~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
IOCON1bits.PENH = 1; /* PWM1H is controlled by PWM module */
IOCON1bits.PENL = 1; /* PWM1L is controlled by PWM module */
/* Select PWM I/O pin Mode ? Choose one of the following output modes */
IOCON1bits.PMOD = 0; /* For Complementary Output mode */
//IOCON1bits.PMOD = 1; /* For Redundant Output mode */
// IOCON1bits.PMOD = 2; /* For Push-Pull Output mode */
//IOCON1bits.PMOD = 3; /* For True Independent Output mode */
/*MDC PDCX SDCX=ACLK*8*PWM Duty/(PCLKDIV)
ACLK=REFCLK * M1/N;
ACLK=Fvco/N */
/* Select either Master Duty cycle or Independent Duty cycle */
PWMCON1bits.MDCS = 0; /* PDCX/SDCX provides duty cycle value */
// PWMCON1bits.MDCS = 1; /* MDC provides duty cycle value */
/* Initialize PWM Duty cycle value */
PDC1 =0;/* Independent Primary Duty Cycle is 3us from Equation 43-5 */
//SDC1 =180;/* Independent Secondary Duty Cycle is 3us from Equation 43-5 */
//MDC =180; /* Master Duty Cycle is 5 ?s from Equation 43-5 */
/*DTRX ALTDTRX=ACLK*8*Dead Time/(PCLKDIV)
ACLK=REFCLK * M1/N;
ACLK=Fvco/N */
/* Select Dead Time control */
/* Choose one of these options */
PWMCON1bits.DTC = 0; /* Positive Dead Time applied for all modes */
//PWMCON1bits.DTC = 1; /* Negative Dead Time applied for all modes */
/* Dead Time value for PWM generator */
/* Refer to Equation 43-7 */
DTR1 =0; /* Dead Time value is 100 ns */
ALTDTR1 = 0; /* Alternate Dead time value is 100 ns */
/* Initialize phase shift value for the PWM output */
/* Phase shifts are initialized when operating in Master Time Base */
//PHASE1 = 0; /* Primary phase shift value of 0 TIB=0 PWMXH phase*/
// SPHASE1 = 0; /* Secondary phase shift value of 0 ITB=0 PWMXL phase */
/* Enable Immediate update of PWM */
//PTCONbits.EIPU = 1;
/* Update Active period register immediately */
// PWMCON1bits.IUE = 1;
/* Update active duty cycle, phase offset, and independent time period immediately */
//SEVTCMP=0;
//TRGCON1bits.TRGDIV = 0; /* Trigger output divider set to trigge ADC on every trigger match event */
//TRGCON1bits.DTM = 1; /* Primary and Secondary triggers combined to create ADC trigger */
//TRGCON1bits.TRGSTRT = 0; /* First ADC trigger event occurs after four trigger match events */
//PTCONbits.SEIEN=1;
//PWMCON1bits.TRGIEN=1;
PTCONbits.PTEN=1;
}
void init_OSC(void)
{
/* Assume Primary Oscillator is 8 MHz and FCY = 30 MHz. */
/* Therefore, FOSC = 60 MHz */
/* Setup for the Auxiliary clock to use Fvco as the source */
/* Fosc = Primary Oscillator * (PLLDIV / PLLPOST * PLLPRE) */ /*Fosc=Fin*M/(N1*N2)*/
/* Fvco = Fosc * N2 */
/* Fosc = 60 MHz; N2 = 2; Fvco = 120 MHz; M = 30 */
/* Input to the Vco = 4 MHz; N1 = 2; Fin = 8 MHz */
ACLKCONbits.SELACLK = 0; /* Primary PLL (Fvco) provides the source
clock for the auxiliary clock divider */
/* Configuring PLL prescaler, PLL Post scaler, PLL divider */
PLLFBD =28; /* M = 30 */
CLKDIVbits.PLLPOST = 0; /* N1 = 2 */
CLKDIVbits.PLLPRE = 0; /* N2 = 2 */
// ACLKCONbits.APSTSCLR = 7; /* Divide Auxiliary click by 1 */
// while(OSCCONbits.LOCK == 1);/* Wait for PLL to lock */
CLKDIVbits.DOZE=0;
__builtin_write_OSCCONH(0x03);
__builtin_write_OSCCONL(0x01);
while(OSCCONbits.COSC != 0b011); /* Wait for new Oscillator to become FRC w/ PLL */
while(OSCCONbits.LOCK != 1); /* Wait for Pll to Lock */
ACLKCONbits.ASRCSEL = 1;
/* Input clock source is determined by ASRCSEL bit setting */
ACLKCONbits.FRCSEL = 0;
/* Auxiliary Oscillator provides the clock source */
ACLKCONbits.SELACLK = 1;
/* Divide Auxiliary clock by 1 */
ACLKCONbits.APSTSCLR =4;//N=8
/* Enable Auxiliary PLL */
ACLKCONbits.ENAPLL = 1;
/* Wait for Auxiliary PLL to Lock */
while(ACLKCONbits.APLLCK != 1);
}
void init_PIN(void)
{
TRISEbits.TRISE0 = 0; /* Set as a digital output */
TRISEbits.TRISE1 = 0; /* Set as a digital output */
LATEbits.LATE0 = 1;
LATEbits.LATE1 = 1;
TRISEbits.TRISE2 = 0; /* Set as a digital output */
TRISEbits.TRISE3 = 0; /* Set as a digital output */
LATEbits.LATE2 = 1;
LATEbits.LATE3 = 1;
TRISDbits.TRISD1=0;
//TRISDbits.TRISD2=0;
PORTDbits.RD1=0;
// PORTDbits.RD2=0;
};
void tmr1_16()
{
T1CON=0;
T1CONbits.TON = 0; // Disable Timer
T1CONbits.TCS =0; // Select internal instruction cycle clock
T1CONbits.TSYNC =1; // Enable Synchronization
T1CONbits.TGATE = 0; // Disable Gated Timer mode
T1CONbits.TSIDL=0;
T1CONbits.TCKPS = 0b00; // Select 1:1 Prescaler
TMR1 =0; // Clear timer register
PR1 =625; // Load the period value
IPC0bits.T1IP = 0x01; // Set Timer1 Interrupt Priority Level
IFS0bits.T1IF = 0; // Clear Timer1 Interrupt Flag
IEC0bits.T1IE = 1; // Enable Timer1 interrupt
T1CONbits.TON = 1; // Start Timer
}
/* Example code for Timer1 ISR*/
void __attribute__((__interrupt__, __shadow__)) _T1Interrupt(void)
{
i++;
/* Interrupt Service Routine code goes here */
TMR1=0;
IFS0bits.T1IF = 0; //Clear Timer1 interrupt flag
}
void SPWM(void)
{
PDC1 =Duty_Data[i];
//Enable Immediate update of PWM
PTCONbits.EIPU = 1;
//Update Active period register immediately
PWMCON1bits.IUE = 1;
if(i == 480)
{
PORTDbits.RD1=~PORTDbits.RD1;
i=0;
};
};
|
阿莫论坛20周年了!感谢大家的支持与爱护!!
一只鸟敢站在脆弱的枝条上歇脚,它依仗的不是枝条不会断,而是自己有翅膀,会飞。
|