CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

DMX problems receiving characters

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
Guest
Guest







DMX problems receiving characters
PostPosted: Thu Oct 26, 2006 6:11 pm     Reply with quote

I am using an 18F6520 at 16Mhz to receive DMX. I am using a hardware UART and an SN75176 level convertor. I am not getting valid level data. I am not attempting to detect the start of a DMX packet yet I am only resetting the port (cycling CREN) when I get an Overrun. I always get 0x82 as the level data no matter what level I send. The rcsta byte changes with different levels, ie. when sending 1>512@0 I get FERR (0xD4 for rcsta), when sending levels above zero I get 0xD1. Does anyone have any ideas what I am doing wrong or how to trouble shoot this further?


Below are relavent sections of code

Code:

#use rs232(baud=9600,parity=N,xmit=PIN_G1,rcv=PIN_G2,bits=8, ERRORS, STREAM=Serial)
#use rs232(baud=250000,parity=N,xmit=PIN_C6,rcv=PIN_C7,bits=9, STREAM=DMX)

#int_rda //DMX receive interupt service routine
void DMX_isr()
{
   while (PIR1bits.RCIF)
   {
      fputc(DMX_rcsta, Serial);
      fputc(data, Serial);

      if (rcsta.OERR) //Overrun
      {
         rcsta.CREN = 0;
         rcsta.CREN = 1;
      }
   }
   return;
}
Mark



Joined: 07 Sep 2003
Posts: 2838
Location: Atlanta, GA

View user's profile Send private message Send e-mail

PostPosted: Thu Oct 26, 2006 9:06 pm     Reply with quote

You code never reads the data value from the uart. You also can't transmit those data byte inside the ISR. You will always get an overrun error.
Guest
Guest







reading data from uart
PostPosted: Fri Oct 27, 2006 8:41 am     Reply with quote

So do I need to use fgetc to read from the uart? Then put read data into a buffer and send from the buffer between interrupts? Thank you for the help.
Mark



Joined: 07 Sep 2003
Posts: 2838
Location: Atlanta, GA

View user's profile Send private message Send e-mail

PostPosted: Fri Oct 27, 2006 8:48 am     Reply with quote

That would do it.

also take a look at

http://www.ccsinfo.com/forum/viewtopic.php?t=21092&highlight=dmx

http://www.ccsinfo.com/forum/viewtopic.php?t=17513&highlight=dmx
Guest
Guest







Thanks
PostPosted: Fri Oct 27, 2006 6:37 pm     Reply with quote

Thanks Mark! Its funny how it works when you actually read the value from the uart! Better a stupid mistake than a hardware problem. Thank you again for your help.
spradecom.rnd



Joined: 27 Apr 2010
Posts: 16
Location: Mumbai

View user's profile Send private message Send e-mail Visit poster's website

DMX receiving problem
PostPosted: Wed Aug 11, 2010 12:13 am     Reply with quote

I wrote a code like the others based on Mark's code found in this forum, following the same ideas, but it doesn't work. The first problem is that the usart never generates a FERR error to detect the break. Second problem is about baud rate. Is this
Code:
#USE RS232(baud=250000,rcv=PIN_C7,xmit=PIN_C6) 
enough for setting baud rate or do we have to separately initialize using SPBRg reg ?

Here is my code
Code:

#include <16F1938.h>
#device adc=8

#FUSES NOWDT                    //No Watch Dog Timer
//#FUSES INTRC_IO                 //Internal RC Osc, no CLKOUT
#FUSES HS                       //High speed Osc (> 4mhz for PCM/PCH) (>10mhz for PCD)
#FUSES NOPUT                    //No Power Up Timer
#FUSES NOPROTECT                //Code not protected from reading
#FUSES MCLR                     //Master Clear pin enabled
#FUSES NOCPD                    //No EE protection
#FUSES NOBROWNOUT               //No brownout reset
#FUSES IESO                     //Internal External Switch Over mode enabled
#FUSES FCMEN                    //Fail-safe clock monitor enabled
#FUSES WDT_SW 
 #FUSES NOCLKOUT 
 #FUSES NOWRT                    //Program memory not write protected
#FUSES NOVCAP 
#FUSES PLL 
 #FUSES STVREN                   //Stack full/underflow will cause reset
#FUSES BORV19   
   #FUSES NOLVP                    //No low voltage prgming, B3(PIC16) or B5(PIC18) used for I/O
#FUSES NODEBUG                  //No Debug mode for ICD

#use delay(clock =16000000)

#USE RS232(baud=250000,rcv=PIN_C7,xmit=PIN_C6)
//-----------Register Definition---------------------

//----------------------------------------------------
/************************************************************************
*                    Registrers USART                                    *
************************************************************************/

#word SPBRG = 0x19B
//#word MCU_SPBRG = 0x19B


#byte RCSTA = 0x19D 
//#byte MCU_RCSTA = 0x19D


#byte TXSTA = 0x19E
//#byte MCU_TXSTA = 0x19E

#byte RCREG = 0x199
//#byte MCU_RCREG = 0x199


#byte PIR1  = 0x011
//#byte MCU_PIR1 = 0x011


#byte PIE1  = 0x091
//#byte MCU_PIE1 = 0x091

#byte INTCON = 0x00B
//#byte MCU_INTCON = 0x00B


#bit SPEN   = RCSTA.7   //Serial port enable bit
#bit RX9   = RCSTA.6    // 9-bit receive enable
#bit SREN   = RCSTA.5   
#bit CREN   = RCSTA.4   // Continuos receive enable bit
#bit ADDEN   = RCSTA.3
#bit FERR   = RCSTA.2   //Frame error bit
#bit OERR   = RCSTA.1   //Overrun error bit
#bit RX9D   = RCSTA.0   

#bit BRGH   = TXSTA.2
#bit SYNC    = TXSTA.4

#bit RCIF  = PIR1.5

#bit RCIE  = PIE1.5

#bit GIE    = INTCON.7
#bit PEIE   = INTCON.6

//----------------------------------------------------

#byte BAUDCON = 0x19F
#bit    ABDEN = BAUDCON.0
#bit    WUE = BAUDCON.1
#bit    BRG16 = BAUDCON.3
#bit    SCKP = BAUDCON.4
#bit    RCIDL = BAUDCON.6
#bit    ABDOVF = BAUDCON.7

/************************************************************************
*                  Function Decleration                         *
************************************************************************/

void Interrupt_USART_Rx(void);
 void togglea1(void);
void togglea0(void);
//---------------------------------------------------------------------

/************************************************************************
*                   Global Variables                                 *
************************************************************************/

#define MAX_PWMS 3

/*Rx Buffer for dmx stream */

//int8 Rx_Buffer[512];
int8 Rx_Buffer[MAX_PWMS];
/*Current levels -0 to 255 */

int8 DMX_Levels[MAX_PWMS];


int1 Check_levels=0;


#include <main.h>

#int_RDA

void  RDA_isr(void)
{


//void Interrupt_USART_Rx(void)
//{
   #define WAIT_FOR_NEXT_BYTE 0
  #define WAIT_FOR_BREAK     1
  #define WAIT_FOR_START     2
  #define RECEIVE_DATA       3


 
  static int8 Rx_State = WAIT_FOR_BREAK;
 


 int8 data;   

 
union
{
    unsigned char fullbyte;
    struct {
        unsigned char RX9D:1; //bit0
        unsigned char OERR:1;
        unsigned char FERR:1;
        unsigned char ADDEN:1;
        unsigned char CREN:1;
        unsigned char SREN:1;
        unsigned char RX9:1;
        unsigned char SPEN:1; //bit7
    } bits ;
  }rcsta;


  static int8 *ptr_Rx;

       
static unsigned int DMX_512_Count = 0;



  while(RCIF) 
  {
              //togglea1();
      rcsta.fullbyte = RCSTA;   

// read data - reading data also clears 'rcif' flag
// and reading 'rcreg' will cause the second 'rcsta' to be loaded if there is one
 
    data = RCREG;

    if (rcsta.bits.OERR)             //check for overrun
    {
       
     //If there Overrun then  reset the reception
      CREN = 0;
      CREN = 1;
     //  received a buffer overun so, wait for a good data byte before looking for
// a break signal
    // togglea1();

      Rx_State = WAIT_FOR_NEXT_BYTE;

      return;
    }


    switch (Rx_State)
    {
      case WAIT_FOR_NEXT_BYTE:
        if (!rcsta.bits.FERR) 
        //togglea1();
       Rx_State = WAIT_FOR_BREAK;
        break;




      case WAIT_FOR_BREAK:

/* If we did receive a framing error, make sure that the data is 0.
   This means that we did Receive the break signal for at least 44us. */


        if (rcsta.bits.FERR)       // frame eror bit
        {
             togglea1();
          if (!data)
         
            //togglea1();
            Rx_State = WAIT_FOR_START;
             
        }
        break;


      case WAIT_FOR_START:
         // check for a framing error. if we receive one we will have to wait
// until we receive a good data byte before we begin looking for our break signal
        if (rcsta.bits.FERR)
                       
            // togglea1();
                   
            Rx_State = WAIT_FOR_NEXT_BYTE;
            /* The start code for our data packet should always start with 0. */               
        else
        {
          if (!data)
          {
           /* Initialize our index to our reception buffer */
            ptr_Rx = Rx_Buffer;
           
              Rx_State = RECEIVE_DATA;
          }
        }
        break;

      case RECEIVE_DATA:
       
        if (rcsta.bits.FERR) 
        {
         
          if (!data)


            Rx_State = WAIT_FOR_START;
          else
            Rx_State = WAIT_FOR_NEXT_BYTE;
        }
        else
        {
         /* Store the data received in the reception buffer */
               *ptr_Rx=data;
               ptr_Rx++;
         
               if(ptr_Rx > &Rx_Buffer[MAX_PWMS-1] )
               {
                 
                  Check_levels=1;
                  Rx_State= WAIT_FOR_BREAK;
               }

        }
        break;
    }
  }
  return;
//}


}


void main()
{


int8 i;

SPBRG=0x03;
BRG16 = 0 ;     
BRGH=1;         
SYNC=0;           
SPEN=1;         

RX9=1;            // 9 bit reception
//RX9D=1;
CREN=1;           // enable reception
ADDEN=0;
FERR=1;
OERR=1;

delay_ms(3000);






   setup_adc_ports(NO_ANALOGS| VSS_VDD);
   setup_adc(ADC_CLOCK_DIV_2);
   setup_spi(SPI_SS_DISABLED);
   setup_lcd(LCD_DISABLED);
   setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
   setup_timer_1(T1_DISABLED);
   setup_timer_2(T2_DIV_BY_16,255,1);
   setup_ccp1(CCP_PWM);
   setup_ccp2(CCP_PWM);
   setup_ccp4(CCP_PWM);
 
   set_pwm1_duty(0);
   set_pwm2_duty(0);
   set_pwm4_duty(0);
   setup_comparator(NC_NC_NC_NC);// This device COMP currently not supported by the PICWizard
   enable_interrupts(INT_RDA);
   enable_interrupts(GLOBAL);

   //TODO: User Code



//set_pwm1_duty(127);
//set_pwm2_duty(127);
//set_pwm4_duty(127);
delay_ms(1000);




GIE=1;            // enable all interrupts
PEIE=1;           // enable peripheral interrupts
RCIE=1;           // enable receive interrupt


while (TRUE)
   {
// set_pwm1_duty(700);
//set_pwm2_duty(700);
//set_pwm4_duty(700);
//--------------------------------------



      if (Check_levels)
      {
         Check_levels=0;

         DMX_Levels[0]=Rx_Buffer[0];
         DMX_Levels[1]=Rx_Buffer[1];
         DMX_Levels[2]=Rx_Buffer[2];
         set_pwm1_duty(DMX_Levels[0]);
         set_pwm2_duty(DMX_Levels[1]);
         set_pwm4_duty(DMX_Levels[2]);

      }
     
//----------------------------------------
 


    }

}


  //----------------------------
  void togglea1(void)
     {
       output_high(PIN_A1);
          delay_ms(200);
       output_low(PIN_A1);
           delay_ms(200);
     }

void togglea0(void)
     {
       output_high(PIN_A0);
          delay_ms(100);
       output_low(PIN_A0);
           delay_ms(100);
    }
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group