Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

[PIC] IS it possible to sent multiple bytes of data using Spi of pic18f452

Status
Not open for further replies.

AmmarAkhlaq

Junior Member level 1
Joined
Dec 12, 2013
Messages
17
Helped
0
Reputation
0
Reaction score
0
Trophy points
1
Activity points
162
IS it possible to sent multiple bytes of data using Spi of pic18f452.

can any one tell me that is it possible in SPI to sent data package of multiple bytes by master to the slave and slave save the each byte in separate variable or array index:
some thing like:
master sent out say: byte1 then byte2 then byte3 connectively : when slave receives first byte 1 it save it to x of in array[0],when byte 1 comes slave save it to y or array[1] and so on after receiving whole package from mater the slave out put each byte to leds after some delay. while receiving new package of data from master slave should display previously received data to LEds until transfer of new package completes. Both master and slave are Pic18f452. I am using MIKroC complier
I tried it may times but no success so far need advice or help to get it done.
here code for master
PHP:
Code:
unsigned char theta1,theta2,theta3,Count2,Count3,datain,intiCom,ready,Thetax=0,Thetay,Thetaz,x,y,z1,reset;
unsigned char Write(char dataout);
void mapInput();
void SysInit();
void sent_data(unsigned char Theta1 ,unsigned char Theta2 , unsigned char Theta3 );
void main(){
            SysInit();
            PORTB=0xF0;
            while(1)
            {
                sent_data(95,100,70);
                delay_ms(150);
                sent_data(85,80, 50);
}           }
void Write(unsigned char dataout)
{
      PORTC.B2=0;          // SS select low  slave is selected  port C pin 2
      delay_ms(50);        // wait.
      SPI1_Write(dataout); // transmit the dataout
      while(SSPSTAT.BF);   // wait till end of data transmission
      datain=SSPBUF;
      PORTC.B2=1;
      delay_ms(50);        // wait.
}
void SysInit()
{
     TRISA=0xFF; // configure Port A as input
     ADCON1=0x06;// disable ADC and make all the pins of Port A as digital input.
     TRISD=0x00; // configure Port D as output
     PORTD=0x00; // Clear all pin of Port D
     TRISB=0x00; // configure Port B as output
     PORTB=0x00; // Clear all pin of Port B
     TRISE=0x00; // configure Port B as output
     PORTE=0x00; // Clear all pin of Port B
     TRISC.B2=0; // Output for Slave select
     TRISC.B3=0; // SCK output
     TRISC.B4=1; // SDI input
     TRISC.B5=0; // SDO output
     PORTC.B2=1; // SS select high no slave is select
     //Set SPI1 module to master mode, clock = Fosc/4, data sampled at the middle of interval,
     //clock idle state low and data transmitted at low to high edge:
     SPI1_Init_Advanced(_SPI_MASTER_OSC_DIV4, _SPI_DATA_SAMPLE_MIDDLE, _SPI_CLK_IDLE_LOW, _SPI_LOW_2_HIGH); // Setup the spi
}

void sent_data(unsigned char Theta1 ,unsigned char Theta2 , unsigned char Theta3 )
{

       PORTC.B2=0;          // SS select low  slave is selected  port C pin 2 f
       delay_ms(50);
       Write(Theta1);
       delay_ms(20);
       Write(Theta2);
       delay_ms(20);
       Write(Theta3);
       delay_ms(20);
       Write(0x0A);
       delay_ms(20);
       PORTC.B2=1;
       
}
Here slave code:
PHP:
Code:
slave Code:
void InitTimer1();
void SysInit();
void Interrupt();
void mydelay_10us(long int a);
unsigned short datain,dataout;
unsigned char Received(unsigned short dataout);
unsigned long int total,high1,high2,high3,low,theta1,Required_delay1=0,theta2;
unsigned long int Required_delay2=0,theta3,Required_delay3=0;
unsigned char intiCom=0,ready=0,Thetax=0,x,Thetay,y,Thetaz,z1,update;
void main(){
  SysInit();
  InitTimer1();
  ready==1;
  theta1=90;
  theta2=90;
  theta3=90;
  while(1)
         {
                Thetax  = (long int) SPI1_Read(0x01);
                delay_ms(500);
                Thetay= (long int) SPI1_Read(0x01);
                delay_ms(500);
                Thetaz = (long int) SPI1_Read(0x01);
                delay_ms(500);
                PortB=0x0F;
                update=SPI1_Read(0x01);
               if(update==0x0A)
            {
                theta1 = Thetax;
                theta2 = Thetay;
                theta3= Thetaz;
                PORTB=theta3 ;
            }
         }
}
void SysInit()
{
  ADCON1=0x06; // disable ADC and make all the pins of Port A as digital input
  TRISA=0xFF;
  PORTA=0x00;
  TRISB=0x00;
  PORTB=0x00;
  TRISD=0x00;
  PORTD=0x00;
  TRISE=0x00;
  PORTE=0;
  TRISC.B6=0;
  TRISC.B7=0;
  TRISC.B4=1; //SDI input
  TRISC.B3=1; //SCK input from master
  TRISC.B5=0; //SDO output
  SSPSTAT.SMP=0; //input data sampled at middle
  SSPSTAT.CKE=0; // transition from idle to active
  SPI1_Init_Advanced(_SPI_SLAVE_SS_ENABLE, _SPI_DATA_SAMPLE_MIDDLE, _SPI_CLK_IDLE_LOW, _SPI_LOW_2_HIGH);
}
 
Last edited:

This is a software problem. You give us no information, so there's no way to tell you what you are doing wrong.

Break this problem down:

1) Are you transmitting the data properly?
2) Are you receiving the data properly?
3) Is it being properly stored in your array(s)?
4) Does your LED display routine operate properly?
 

master is transmitting data correctly and but slave it not properly displaying It. I am using micro C.

- - - Updated - - -

I have added the code in my post.
need advice.
 

master is transmitting data correctly and but slave it not properly displaying It. I am using micro C.

- - - Updated - - -

I have added the code in my post.
need advice.

Okay, can you verify that you are receiving data properly? (forget about DISPLAYING it for the moment). Do you have some sort of in-circuit debugger you can use to put in breakpoints, etc.?
 

I noticed later that the OP has posted different flavours of his faulty SPI slave code. See some hints in this thread https://www.edaboard.com/threads/312257/

Both versions are executing delay time in the slave while the master sends new data. Receiver overrun will neccessarily happen.
 

I have pic kit3 don't know if it is debugger or not
I am receiving the data but i think i am doing some thing wrong while managing it in slave probably some kind of over ridding is happing due to which if statement is not getting execute. i tired displaying the update variable to leds it showed some garbage value in place of 0x0A and it was continuously changing

- - - Updated - - -

How to over come that receiver overrun issue then?
 

I haven't looked too closely at your code, but why would you put a delay in the receiver? The receiver should always be willing to accept data unless its buffer is full. Since there is no intrinsic handshaking protocol in SPI, you need to consider how data is transmitted and received.
 

I haven't looked too closely at your code, but why would you put a delay in the receiver? The receiver should always be willing to accept data unless its buffer is full. Since there is no intrinsic handshaking protocol in SPI, you need to consider how data is transmitted and received.

Here is I am posting updated code for both slave and master with the video clip of what I got so far. red leds are data transmitted by master while yellow is data received by slave . I should get continues sending and receiving but it is not happing. You can see it in video clip..
Help me out I badly needed :sad:
PHP:
unsigned char Theta1,Theta2,Theta3,Count2,Count3,datain,intiCom,  ready,Thetax=0,Thetay,Thetaz,x,y,z1,reset;
unsigned char Write(char dataout);
void mapInput();
void SysInit();
void sent_data(unsigned char Theta1 ,unsigned char Theta2 , unsigned char Theta3 );
void main(){
      SysInit();
      intiCom=0;
      PORTB=0xFF;
      delay_ms(1000);
      PORTB=0x00;
      intiCom=Write(0x0F); // inititalize the communication:    1
      //Send 0x0F if reviced is F0 the Communication line is stablish
      PORTB = intiCom;
      //Delay_ms(500);
      if(intiCom==0xF0)
      {
         while(1)
         {
             sent_data(45,45,1);
             delay_ms(500);
             sent_data(45,45,2);
         }
      }


}
unsigned char Write(unsigned char dataout)
{

      PORTD = dataout;
      PORTC.B2=0;          // SS select low  slave is selected  port C pin 2
      delay_ms(50);        // wait
      SPI1_Write(dataout); // transmit the dataout
      while(SSPSTAT.BF);   // wait till end of data transmission
      delay_ms(50);        // wait.
      PORTC.B2=1;
      return  SSPBUF;
}
void SysInit()
{
     TRISA=0xFF; // configure Port A as input
     ADCON1=0x06;// disable ADC and make all the pins of Port A as digital input.
     TRISD=0x00; // configure Port D as output
     PORTD=0x00; // Clear all pin of Port D
     TRISB=0x00; // configure Port B as output
     PORTB=0x00; // Clear all pin of Port B
     TRISC.B2=0; // Output for Slave select
     TRISC.B3=0; // SCK output
     TRISC.B4=1; // SDI input
     TRISC.B5=0; // SDO output
     PORTC.B2=1; // SS select high no slave is select
     //Set SPI1 module to master mode, clock = Fosc/4, data sampled at the middle of interval,
     //clock idle state low and data transmitted at low to high edge:
     SPI1_Init_Advanced(_SPI_MASTER_OSC_DIV4, _SPI_DATA_SAMPLE_MIDDLE, _SPI_CLK_IDLE_LOW, _SPI_LOW_2_HIGH); // Setup the spi
}
void sent_data(unsigned char Theta1 ,unsigned char Theta2 , unsigned char Theta3 )
{

          ready=Write(0x10);            //2
          Delay_ms(50);
          if(ready==0x70)
          {
              Thetax=Write(Theta1);     //3
              Delay_ms(50);
          }
          if(Thetax==0x30)
          {
                x=Write(0x05);          //4
                Delay_ms(50);
          }
          if(x==0x40)
          {
            Thetay=Write(Theta2);       //5
            Delay_ms(50);
          }
          if(Thetay==0x50)
          {
             y=Write(0x06);             //6

             Delay_ms(50);
          }
          if(y==0x60)
         {
            Thetaz=Write(Theta3);       //7
            //PORTB=Thetaz;
            Delay_ms(50);
         }
         if(Thetaz==0x80)
         {
                z1=Write(0x08);         //8
                //PORTB=z1;
                Delay_ms(50);
         }
         if((z1==0x90)&&(y==0x60)&&(x==0x40))
         {
             reset= Write(0x09);        //9
             z1=0;
             y=0;
             x=0;
             Thetaz=0;
             Thetay=0;
             Thetax=0;
             ready=0;
             PORTB=Theta3;

         }

}
slave code
PHP:
void mydelay_10us(long int a);
unsigned short datain,dataout;
unsigned char Received(unsigned short dataout);
unsigned long int total,high1,high2,high3,low,theta1,Required_delay1  =0,theta2;
unsigned long int Required_delay2=0,theta3,Required_delay3=0;
unsigned char intiCom=0,ready=0,Thetax=0,x,Thetay,y,Thetaz,z1,up  date;
void main(){
  SysInit();
  InitTimer1();
  theta1=90;
  theta2=90;
  theta3=90;
  intiCom=0;
  intiCom=Received(0xF0);
  //  inititalize  the communication:
  //  Send 0x0F if reveiced is F0 the Communication line is stablish
  while(1)
  {
      ready = Received(0x70);             // 2  Ready for communication
      //PORTB  =  ready;
      if(ready==0x10)
      {
          Thetax = Received(0x30);        // 3  receive theta 1 is ready
          //PORTB =  Thetax;
          x = Received(0x40);             // 4  conform that Theta 1 has been recived
      }
      if(x==0x05)
      {
           Thetay=Received(0x50);         // 5  receive theta2 if reception of theta 1 is conformed
           //PORTB = Thetay;
           y= Received(0x60);             // 6  conform that Theta 2 has been recived
      }
      if(y==0x06)
      {
            Thetaz=Received(0x80);        // 7  receive theta3 if reception of theta 2 is conformed
            //PORTB = Thetaz;
            z1 = Received(0x90);          // 8  conform that Theta 3 has been recived
      }
      if((z1==0x08)&&(y==0x06)&&(x==0x05)) //  after conformation of all the theta 1 2 3
      {
           
            update=Received(0xA0);        // 9 if update comand is revieced the chage the value of angles.
           
            if(update==0x09)
            {
                theta1=(long int)Thetax;
                theta2=(long int)Thetay;
                theta3=(long int)Thetaz;
                PORTB=theta3;
                update=0;
                z1 = 0;
                x  = 0;
                y  = 0;
                ready=0;
            }
      
      }
  }

}
unsigned char Received(unsigned short dataout)
{
     datain= SPI1_Read(dataout);
     return datain;
}
void SysInit()
{
  ADCON1=0x06;    // disable ADC and make all the pins of Port A as digital input
  TRISA=0xFF;
  PORTA=0x00;
  TRISB=0x00;
  PORTB=0x00;
  TRISD=0x00;
  PORTD=0x00;
  TRISE=0x00;
  PORTE=0x00;
  TRISC.B6=0;
  TRISC.B7=0;
  TRISC.B4=1;    // SDI input
  TRISC.B3=1;    // SCK input from master
  TRISC.B5=0;    // SDO output
  SSPSTAT.SMP=0; // input data sampled at middle
  SSPSTAT.CKE=0; // transition from idle to active
  SPI1_Init_Advanced(_SPI_SLAVE_SS_ENABLE, _SPI_DATA_SAMPLE_MIDDLE, _SPI_CLK_IDLE_LOW, _SPI_LOW_2_HIGH);
}
video is in zip file attached
help me out I will really appreciate
 

Attachments

  • New folder.rar
    9.9 MB · Views: 83
Last edited:

Status
Not open for further replies.

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top