Other Parts Discussed in Thread: C2000WARE
Tool/software: Code Composer Studio
Hi,
I am trying to synchronize both my CPU01 and CPU02 using the IPC flags .I am running both the codes on their respective RAMs.The problem is the below line
IpcRegs.IPCSET.bit.IPC17 = 1;
is not getting set to one , that is IPC17 bit is not getting set to one in CPU02 code .
i have attached both codes below .
//
// Included Files
//
#include "F28x_Project.h"
#include "F2837xD_Ipc_drivers.h"
#define REFERENCE_VDAC 3
#define REFERENCE_VREF 2
#define DACA 1
#define REFERENCE REFERENCE_VDAC
#define CPUFREQ_MHZ 200
#define DAC_NUM DACA // pin no 30
void ConfigureADC(void);
void SetupADCContinuous(Uint16 channel);
void configureDAC(Uint16 dac_num);
interrupt void cpu_timer0_isr(void);
volatile struct DAC_REGS* DAC_PTR[4] = {0x0,&DacaRegs,&DacbRegs,&DaccRegs};
Uint32 samplingFreq_hz = 5000;
float freqResolution_hz = 0;
float cpuPeriod_us = 0;
Uint32 interruptCycles = 0;
float interruptDuration_us = 0;
float samplingPeriod_us = 0;
//
// Main
//
void main(void)
{
//
// Step 1. Initialize System Control:
// PLL, WatchDog, enable Peripheral Clocks
// This example function is found in the F2837xD_SysCtrl.c file.
//
InitSysCtrl();
//
// Step 2. Initialize GPIO:
// This example function is found in the F2837xD_Gpio.c file and
// illustrates how to set the GPIO to it's default state.
//
InitGpio();
//
// Step 3. Clear all interrupts and initialize PIE vector table:
// Disable CPU interrupts
//
DINT;
//
// Initialize the PIE control registers to their default state.
// The default state is all PIE interrupts disabled and flags
// are cleared.
// This function is found in the F2837xD_PieCtrl.c file.
//
InitPieCtrl();
IpcRegs.IPCCLR.all = 0xFFFFFFFF;
PieCtrlRegs.PIEIER1.bit.INTx13 = 1; // IPC0 ISR
IER |= 0x0001; // Enable INT1 in IER to enable PIE group 1
//
// Disable CPU interrupts and clear all CPU interrupt flags:
//
// IER = 0x0000;
IFR = 0x0000;
//
// Initialize the PIE vector table with pointers to the shell Interrupt
// Service Routines (ISR).
// This will populate the entire table, even if the interrupt
// is not used in this example. This is useful for debug purposes.
// The shell ISR routines are found in F2837xD_DefaultIsr.c.
// This function is found in F2837xD_PieVect.c.
//
InitPieVectTable();
//
// Enable global Interrupts and higher priority real-time debug events:
//
EINT; // Enable Global interrupt INTM
ERTM; // Enable Global realtime interrupt DBGM
//
// Spin here until CPU02 is ready
//
while(!IPCRtoLFlagBusy(IPC_FLAG17));
IPCRtoLFlagAcknowledge(IPC_FLAG17);
//
// Transfer ownership of ADCA to CPU02
//
EALLOW;
DevCfgRegs.CPUSEL11.bit.ADC_C = 1;
DevCfgRegs.CPUSEL14.bit.DAC_B = 1;
EDIS;
ConfigureADC();
SetupADCContinuous(3);
//
// Map Cpu Timer0 interrupt function to the PIE vector table
//
EALLOW;
PieVectTable.TIMER0_INT = &cpu_timer0_isr;
EDIS;
cpuPeriod_us = (1.0/CPUFREQ_MHZ);
samplingPeriod_us = (1000000.0/samplingFreq_hz);
configureDAC(DAC_NUM); // Configure DAC
InitCpuTimers(); // Initialize Cpu Timers
//
// Configure Cpu Timer0 to interrupt at specified sampling frequency
//
ConfigCpuTimer(&CpuTimer0, CPUFREQ_MHZ, 1000000.0/samplingFreq_hz);
//
// Start Cpu Timer0
//
CpuTimer0Regs.TCR.all = 0x4000;
//
// Enable interrupt
//
IER |= M_INT1;
PieCtrlRegs.PIEIER1.bit.INTx7 = 1; // enable interrupt 1.7 (TIMER0)
EINT;
ERTM;
do // take conversions indefinitely in loop
{
//
//enable ADCINT flag
//
EALLOW;
AdcaRegs.ADCINTSEL1N2.bit.INT1E = 1;
AdcaRegs.ADCINTFLGCLR.all = 0x000F;
EDIS;
AdcaRegs.ADCSOCFRC1.all = 0x0001; //software force start SOC0
AdcaRegs.ADCINTFLGCLR.bit.ADCINT1 = 1;// make sure INT1 flag is cleared
//
//disable ADCINT flag to stop sampling
//
EALLOW;
AdcaRegs.ADCINTSEL1N2.bit.INT1E = 0;
EDIS;
}while(1);
}
//
//DAC configuration
//
void configureDAC(Uint16 dac_num)
{
EALLOW;
DAC_PTR[dac_num]->DACCTL.bit.DACREFSEL = REFERENCE;
DAC_PTR[dac_num]->DACOUTEN.bit.DACOUTEN = 1;
DAC_PTR[dac_num]->DACVALS.all = 0;
DELAY_US(1000); // Delay for buffered DAC to power up
EDIS;
}
//
// ConfigureADC - Write ADC configurations and power up the ADC for both
// ADC A and ADC B
void ConfigureADC(void) //write configurations
{
EALLOW;
AdcaRegs.ADCCTL2.bit.PRESCALE = 6; //set ADCCLK divider to /4
AdcSetMode(ADC_ADCA, ADC_RESOLUTION_12BIT, ADC_SIGNALMODE_SINGLE);
AdcaRegs.ADCCTL1.bit.INTPULSEPOS = 1; //Set pulse positions to late
AdcaRegs.ADCCTL1.bit.ADCPWDNZ = 1; //power up the ADC
DELAY_US(1000);//delay for 1ms to allow ADC time to power up
EDIS;
}
//
// SetupADCContinuous - setup the ADC to continuously convert on one channel
//
void SetupADCContinuous(Uint16 channel)
{
// Uint16 acqps;
//
// Determine minimum acquisition window (in SYSCLKS) based on resolution
//
/* if(ADC_RESOLUTION_12BIT == AdcaRegs.ADCCTL2.bit.RESOLUTION)
{
acqps = 14; //75ns
}
else //resolution is 16-bit
{
acqps = 63; //320ns
}
*/
EALLOW;
AdcaRegs.ADCSOC0CTL.bit.CHSEL = channel; //SOC will convert on channel
AdcaRegs.ADCSOC0CTL.bit.ACQPS = 14;
AdcaRegs.ADCINTSEL1N2.bit.INT1E = 0; //disable INT1 flag
AdcaRegs.ADCINTSEL1N2.bit.INT1SEL = 1;
AdcaRegs.ADCINTSOCSEL1.bit.SOC0 = 2;
EDIS;
}
interrupt void cpu_timer0_isr(void)
{
CpuTimer1Regs.TCR.all = 0x0000; // Start Cpu Timer1 to indicate begin of interrupt
//
// Write current ADC value to buffered DAC A(A0 pin no 30)
//
DAC_PTR[DAC_NUM]->DACVALS.all = AdcaResultRegs.ADCRESULT0; // ADCC C3 pin no 24
PieCtrlRegs.PIEACK.all = PIEACK_GROUP1; // Acknowledge this interrupt to receive more interrupts from group 1
CpuTimer1Regs.TCR.all = 0x0010; // Stop Cpu Timer1 to indicate end of interrupt
interruptCycles = 0xFFFFFFFFUL - CpuTimer1Regs.TIM.all; // Calculate interrupt duration in cycles
interruptDuration_us = cpuPeriod_us * interruptCycles; // Calculate interrupt duration in micro seconds
CpuTimer1Regs.TCR.all = 0x0030; // Reload Cpu Timer1
}
//
// Included Files
//
#include "F28x_Project.h"
#include "F2837xD_Ipc_drivers.h"
#define REFERENCE_VDAC 3
#define REFERENCE_VREF 2
#define DACB 2
#define REFERENCE REFERENCE_VDAC
#define CPUFREQ_MHZ1 200
#define DAC_NUM1 DACB // pin no 70
void ConfigureADC1(void);
void SetupADCContinuous1(Uint16 channel1);
void configureDAC1(Uint16 dac_num1);
interrupt void cpu_timer1_isr(void);
volatile struct DAC_REGS* DAC_PTR[4] = {0x0,&DacaRegs,&DacbRegs,&DaccRegs};
Uint32 samplingFreq_hz1 = 5000;
float freqResolution_hz1 = 0;
float cpuPeriod_us1 = 0;
Uint32 interruptCycles1 = 0;
float interruptDuration_us1 = 0;
float samplingPeriod_us1 = 0;
//
// Main
//
void main(void)
{
InitSysCtrl();
DINT;
// Disable CPU interrupts
InitPieCtrl();
// Initialize the PIE control registers to their default state.
// Disable CPU interrupts and clear all CPU interrupt flags:
IER = 0x0000;
IFR = 0x0000;
InitPieVectTable();
//
//--- Let CPU1 know that CPU2 is ready
IpcRegs.IPCSET.bit.IPC17 = 1; // Set IPC17 to release CPU1
//
// Power up the ADC_B and DAC_B
//
EALLOW;
CpuSysRegs.PCLKCR13.bit.ADC_C = 1;
CpuSysRegs.PCLKCR16.bit.DAC_B = 1;
ConfigureADC1(); // Configure the ADC and power it up
SetupADCContinuous1(3);// Setup the ADC for continuous conversions on channel 0
EINT; // Enable Global interrupt INTM
ERTM; // Enable Global realtime interrupt DBGM
//
// Map Cpu Timer0 interrupt function to the PIE vector table
//
EALLOW;
PieVectTable.TIMER0_INT = &cpu_timer1_isr;
EDIS;
cpuPeriod_us1 = (1.0/CPUFREQ_MHZ1);
samplingPeriod_us1 = (1000000.0/samplingFreq_hz1);
configureDAC1(DAC_NU // Configure DAC
InitCpuTimers(); // Initialize Cpu Timers
//
// Configure Cpu Timer0 to interrupt at specified sampling frequency
//
ConfigCpuTimer(&CpuTimer0, CPUFREQ_MHZ1, 1000000.0/samplingFreq_hz1);
//
// Start Cpu Timer0
//
CpuTimer0Regs.TCR.all = 0x4000;
//
// Enable interrupt
//
IER |= M_INT1;
PieCtrlRegs.PIEIER1.bit.INTx7 = 1;
EINT;
ERTM;
do // take conversions indefinitely in loop
{
//
//enable ADCINT flag
//
EALLOW;
AdccRegs.ADCINTSEL1N2.bit.INT1E = 1;
AdccRegs.ADCINTFLGCLR.all = 0x000F;
EDIS;
AdccRegs.ADCSOCFRC1.all = 0x0001; //software force start SOC0
AdccRegs.ADCINTFLGCLR.bit.ADCINT1 = 1;
// make sure INT1 flag is cleared
//
//disable ADCINT flag to stop sampling
//
EALLOW;
AdccRegs.ADCINTSEL1N2.bit.INT1E = 0;
EDIS;
}while(1);
}
//
//DAC configuration
//
void configureDAC1(Uint16 dac_num1)
{
EALLOW;
DAC_PTR[dac_num1]->DACCTL.bit.DACREFSEL = REFERENCE;
DAC_PTR[dac_num1]->DACOUTEN.bit.DACOUTEN = 1;
DAC_PTR[dac_num1]->DACVALS.all = 0;
DELAY_US(1000); // Delay for buffered DAC to power up
EDIS;
}
//
// ConfigureADC - Write ADC configurations and power up the ADC for both
// ADC A and ADC B
void ConfigureADC1(void) //write configurations
{
EALLOW;
AdccRegs.ADCCTL2.bit.PRESCALE = 6; //set ADCCLK divider to /4
AdcSetMode(ADC_ADCC, ADC_RESOLUTION_12BIT, ADC_SIGNALMODE_SINGLE);
AdccRegs.ADCCTL1.bit.INTPULSEPOS = 1; //Set pulse positions to late
AdccRegs.ADCCTL1.bit.ADCPWDNZ = 1; //power up the ADC
DELAY_US(1000);//delay for 1ms to allow ADC time to power up
EDIS;
}
//
// SetupADCContinuous - setup the ADC to continuously convert on one channel
//
void SetupADCContinuous1(Uint16 channel1)
{
EALLOW;
AdccRegs.ADCSOC0CTL.bit.CHSEL = channel1; //SOC will convert on channel
AdccRegs.ADCSOC0CTL.bit.ACQPS =14;
AdccRegs.ADCINTSEL1N2.bit.INT1E = 0; //disable INT1 flag
AdccRegs.ADCINTSEL1N2.bit.INT1SEL = 1;
AdccRegs.ADCINTSOCSEL1.bit.SOC0 = 2;
EDIS;
}
interrupt void cpu_timer1_isr(void)
{
CpuTimer1Regs.TCR.all = 0x0000; // Start Cpu Timer1 to indicate begin of interrupt
//
// Write current ADC value to buffered DAC A(A0 pin no 30)
//
DAC_PTR[DAC_NUM1]->DACVALS.all = AdccResultRegs.ADCRESULT0; // ADC_A3 pin no 25
PieCtrlRegs.PIEACK.all = PIEACK_GROUP1; // Acknowledge this interrupt to receive more interrupts from group 1
CpuTimer1Regs.TCR.all = 0x0010; // Stop Cpu Timer1 to indicate end of interrupt
interruptCycles1 = 0xFFFFFFFFUL - CpuTimer1Regs.TIM.all; // Calculate interrupt duration in cycles
interruptDuration_us1 = cpuPeriod_us1 * interruptCycles1; // Calculate interrupt duration in micro seconds
CpuTimer1Regs.TCR.all = 0x0030; // Reload Cpu Timer1
}
Regards,
Ashwin