打印
[DSP编程]

DSP28335SCI中断FIFO问题!

[复制链接]
3359|3
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
本为酱油|  楼主 | 2016-12-9 22:18 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
DSP要和屏幕通信,SCI方式。单独查询发送的时候没问题,加了中断接收后,DSP发送出去的数据错了,且很多重复数据。接收数据是10个字一包,我用的10级接收FIFO,自己再另建个FIFO,接20个字处理一次。不知道哪里出问题了。代码如下:/****问题是单独发送可以,加了中断接收后,发送出来的数据乱了*********/
#include "DSP28x_Project.h"     // Device Headerfile and Examples Include File
#include "AD7656.h"
#include "math.h"
#include "modbus.h"
#include "control.h"

//===========================================================================
unsigned int check=0,fup=0,fdown=0; int cs; int counter=0; int counter2=0;

void InitEPwmMod(unsigned int lh_freq);                //ePWM模块设置
void InitEPwm6ADC(double f);//AD采样电路出发脉冲生成,f为KHz
interrupt void ADC_Int(void);//AD采样中断函数
interrupt void cpu_timer0_isr(void);//定时器0用于产生定时中断
//interrupt void scibTxFifoIsr(void);
interrupt void sciaRxFifoIsr(void);
void Gpio_select(void);
void protect(void);

void scia_fifo_init(void);
//void scic_fifo_init(void);
//void scib_fifo_init(void);

//unsigned char sdataC[15];
unsigned char sdataA[40],sdataB[40],rdataB[40],pretc=0;//pretc=0 指示灯绿色 pretc=1 指示灯红色
Uint16 rdata_pointB;                //SCIB接收数据检测
//unsigned int sdataA[40];
unsigned int sw1=0;
Uint16 i=0,j=0,j1=0,k=0,a=2,b=2;   // Send data for SCI-B
Uint16 lh_1=0,lh_2=0,lh_3=150,lh_4=300,lh_5=300,lh_6=0;  //Recive data from SCI-A
unsigned int freq=300,freqt=300,sciRxcounter=0;// Initialization Frequency is 300Hz     unsigned int range 0-65535
void main(void)
{
//        int i=0;
//        Uint16 j=0;
        InitSysCtrl();

        DELAY_US(10000L);
        DELAY_US(10000L);
        DELAY_US(10000L);

   InitEPwm1Gpio();
   InitEPwm2Gpio();

   Gpio_select();
   InitEPwm6Gpio();    //AD_CLOCK
   InitEPwm6ADC(20.0);


//        Configure XINT1
   XIntruptRegs.XINT1CR.bit.POLARITY = 0;      // Falling edge interrupt
   XIntruptRegs.XINT1CR.bit.ENABLE = 1;                //        Enable XINT1
   asm("NOP");
   GpioDataRegs.GPBCLEAR.bit.GPIO60=1;

   InitXintf();
   InitSciGpio();

   DINT;

   InitPieCtrl();

   IER = 0x0000;
   IFR = 0x0000;
   InitPieVectTable();

   EALLOW;  // This is needed to write to EALLOW protected registers
   PieVectTable.TINT0 = &cpu_timer0_isr;
   EDIS;

   EALLOW;  // This is needed to write to EALLOW protected registers
   PieVectTable.SCIRXINTA = &sciaRxFifoIsr;
//   PieVectTable.SCITXINTA = &sciaTxFifoIsr;
   EDIS;

   EALLOW;        //This is needed to write to EALLOW protected registers
   PieVectTable.XINT1 = &ADC_Int;//Set XINT1 in PIE
   EDIS;    //This is needed to disable write to EALLOW protected registers

   EALLOW;
   SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 0;
   EDIS;

//   InitEPwmMod();
//   freq=300;   //Initialization output PWM 300Hz
   InitEPwmMod(freq);

   EALLOW;
   SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 1;
   EDIS;
           
   InitCpuTimers();//初始化时钟
//   ConfigCpuTimer(&CpuTimer0, 15000, 100000);  //定时器0定时10s中断一次
   ConfigCpuTimer(&CpuTimer0, 15000, 100000);
   CpuTimer0Regs.TCR.all = 0x4001; // Use write-only instruction to set TSS bit = 0
   CpuTimer0.InterruptCount = 0;   //计数初值为0

   PieCtrlRegs.PIECTRL.bit.ENPIE = 1;//使能PIE模块
   PieCtrlRegs.PIEIER9.bit.INTx1 = 1;//PIE: Group 9 interrupt 1 SCI-A 接收中断
  // PieCtrlRegs.PIEIER9.bit.INTx2 = 1;//PIE: Group 9 interrupt 2 SCI-A 发送中断
   PieCtrlRegs.PIEIER1.bit.INTx4 = 1;//Enable INTn in the PIE: Group 1 interrupt 4
   PieCtrlRegs.PIEIER1.bit.INTx7 = 1;// Enable TINT0 in the PIE: Group 1 interrupt 7
   IER |= M_INT1;//Enable CPU INT1;
   IER |= M_INT9;//Enable CPU INT1;
        scia_fifo_init();   
//    scib_fifo_init();   // Init SCI-A B C
//        scic_fifo_init();  

   EINT;   // Enable Global interrupt INTM
   ERTM;   // Enable Global realtime interrupt DBGM
for(i=0;i<40;i++)
{
        sdataA[i]=sdataB[i]=rdataB[i]=0x00;        
}
for(;;)  
//--------------------传送数据至上位机--------------------
        {
    sdataB[0]=0x03;
        sdataB[1]=0x06;
        sdataB[2]=0x02;
        sdataB[3]=00;              //01:16位数据高8位(人为设定地址位)
    sdataB[4]=Ig;//电压信号     //01:16位数据低8位(人为设定地址位)
    //sdataB[4]=100;
    sdataB[5]=00;               //02高8位
    sdataB[6]=freq*0.5; // 工作频率     02低8位
    //sdataB[6]=300*0.5;
        sdataB[7]=00;              //03高8位
        sdataB[8]=pretc; //03低8位
    //sdataB[8]=1;
        sdataB[9]=00;              //04高8位
        sdataB[10]=Ib;//04低8位
        check=CRC16(sdataB,11);//CRC校验,check是16位,故应右移8位
        sdataB[11]=(check>>8)&(0x00FF);
        sdataB[12]=check&0x00FF;

        freq=freqt;
        if(sciRxcounter == 2)
        {
                /*******以下6句共用于禁止SCI-A接收中断*************/
                DINT;//禁止全局中断  INTM = 1
                PieCtrlRegs.PIEIER9.bit.INTx1 = 0;//0-禁止接收中断   1-允许接收中断
        for(lh_6=30;lh_6<35;lh_6++)     sdataA[lh_6] = rdataB[lh_6];//5个空周期
                PieCtrlRegs.PIEIFR9.bit.INTx1 = 0;//清除外设中断位
                PieCtrlRegs.PIEACK.all = PIEACK_GROUP9;//清除ACK位
                EINT;//使能全局中断  INTM = 0
                /*******以上6句共用于禁止SCI-A接收中断*************/
               
                for(lh_6=0;lh_6<20;lh_6++)                sdataA[lh_6] = rdataB[lh_6];//取回FIFO里的20个数据
                for(lh_6=0;lh_6<20;lh_6++)
                {
                        if(sdataA[lh_6] == 0x06)
                        {
                                lh_3 =         sdataA[lh_6+6];        //取回来数据是100-250,表示200-500
                                lh_4 = lh_3*2;      //数据回归到200-500
                        }
                }
                freqt = lh_4;   //屏幕发回来的真实想要数值
                if((freqt<501) && (freqt>199))
                {        
                        if(freq != freqt)
                        {
                                lh_5 = freqt;
                                InitEPwmMod(freqt);        
                        }
                }
                sciRxcounter =0;
        }
        DELAY_US(10000L);     // it need to commented out for Frequence changes
        /*发送数据正常应该是03 02 06 00 Ig 00 Freq 00 pretc 00 Ib CRC CRC共13个字*/
        /* 其中Freq 根据串口接收到的值改变*/
        for(i=0;i<13;i++)
          {
           SciaRegs.SCITXBUF=sdataB[i];//SCITXBUF:SCIB发送器数据缓冲寄存器
      }           
      PieCtrlRegs.PIEIER9.bit.INTx1 = 1; //0-禁止接收中断   1-允许接收中断
    }   
}

interrupt void ADC_Int(void)
{
        unsigned int i;
//        unsigned int fcnum,freq;
    //f is 20KHz 1 interrupt =0.05ms  10ms for key action once
    //counter num = 10/0.05         =200

        for(i=0;i<7;i++)
        {
                SampleTable[i]= * AD_CHIPSEL;
        }
        GpioDataRegs.GPASET.bit.GPIO0=1;

        Ug= (SampleTable[0]+10) * 0.000305176;//Ug
        Ia= (SampleTable[1]-20) * 0.000305176* 11.11111;//Ia
        XIntruptRegs.XINT1CR.bit.ENABLE = 1;
        PieCtrlRegs.PIEACK.all = PIEACK_GROUP1; // Enable to receive more interrupts from PIE1
        GpioDataRegs.GPACLEAR.bit.GPIO0=1;
        protect();
        }

interrupt void sciaRxFifoIsr(void)
        {
        //        unsigned int  lh_i;
            if(sciRxcounter == 0)
                {
                        for(lh_2=0;lh_2<10;lh_2++)
                                {
                                        rdataB[lh_2] = (SciaRegs.SCIRXBUF.all) & 0x00FF;        //读取数据
                                }
                }
                if(sciRxcounter == 1)
                {
                        //sciRxcounter =0;
                        for(lh_2=10;lh_2<20;lh_2++)
                                {
                                        rdataB[lh_2] = (SciaRegs.SCIRXBUF.all) & 0x00FF;        //读取数据
                                }
                }
                sciRxcounter++;
                /*正常收到的一组数据应该为06 FF FF FF FF 00 98 E7 5E 11 */

                SciaRegs.SCIFFRX.bit.RXFFOVRCLR = 1;                //清除溢出标志位
                SciaRegs.SCIFFRX.bit.RXFFINTCLR = 1;                //清除中断标注位
                SciaRegs.SCIFFTX.bit.TXFFINTCLR = 1;
                PieCtrlRegs.PIEACK.all |= 0x100;        
        }


void scia_fifo_init()
{
   SciaRegs.SCICCR.all =0x0007;    // 1 stop bit,  No loopback
                                   // No parity,8 char bits,
                                   // async mode, idle-line protocol
   SciaRegs.SCICTL1.all =0x0003;   // enable TX, RX, internal SCICLK,
                                   // Disable RX ERR, SLEEP, TXWAKE
   SciaRegs.SCICTL2.bit.TXINTENA =1;//使能发送中断
   SciaRegs.SCICTL2.bit.RXBKINTENA =1;//使能接收中断
   SciaRegs.SCIHBAUD    =0x0003; //这两个值根据LSPCLK决定,LOSPCP来决定LSPCLK 现在LOSPCP=0,所以LSPCLK=SYSCLK/1 即150MHZ;
   SciaRegs.SCILBAUD    =0x00D0;//SCI_PRD;波特率为19200--3D0
   SciaRegs.SCICCR.bit.LOOPBKENA =0; // 1-Enable 0-disable loop back
   SciaRegs.SCIFFTX.all=0xCD28;// 发送FIFO有13个字
   SciaRegs.SCIFFRX.all=0x0A21;// 接收FIFO有10个字
   SciaRegs.SCIFFCT.all=0x00;

   SciaRegs.SCICTL1.all =0x0023;     // Relinquish SCI from Reset
   SciaRegs.SCIFFTX.bit.TXFIFOXRESET=1;
   SciaRegs.SCIFFRX.bit.RXFIFORESET=1;
}




//--------------------------------------------------------------------------
//------------------------------NO MORE--------------------------------
//--------------------------------------------------------------------------

相关帖子

沙发
JY-DX-JY| | 2016-12-12 15:08 | 只看该作者
我觉得你还是先把SCI模块中断接收单独调好,再把屏幕功能加上比较好

使用特权

评论回复
板凳
hong7817| | 2016-12-19 21:08 | 只看该作者
没耐心看这么长的代码

使用特权

评论回复
地板
JUST1| | 2020-2-20 18:25 | 只看该作者
问题解决没有?

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

1

主题

2

帖子

0

粉丝