Problem in PIC to PIC Synchronous Communication

Thread Starter

Tajiknomi

Joined Mar 18, 2010
34
The purpose of my simulation was to implement Synchronous communication between two PIC's. One as a master and another as a slave. I have read the data sheet in order to understand the configuration before programming both.
So i have programmed both PIC (16f877A) using IDE (MicroC pro) & Simulated the circuit in Proteus-8 professional.

How the circuit should work ? (Kindly check the attached snapshot)
1) The master PIC should acknowledge the IOC(Interrupt on change) at RB5.
2) After moving to IOC ISR, it should transmit the status of PORTA serially to Slave PIC.
3) The Slave PIC should receive the byte & transfer the byte to its PORTB.


Problem : The transmitter (Master PIC) transmits the byte but the "Receiver (Slave PIC) receive-interrupt ISR doesn't execute"

Note : In the Transmit ISR & Receive ISR both contains a line which flip the bits of PORTB. But when i execute the program, it works fine for Master PIC (transmitter) but doesn't work for Slave(Receiver), which means that Transmit ISR execute fine but Receive ISR doesn't execute at all !

Transmitter (Master Code)

Code:
/*     USRT Transmit module ( Synchronous Transmission ) (Master Mode)
        It will transfer data via Tx pin respectively
        Baud Rate = 9600
        BRGH = 1 (High speep Baud rate generator) -- Used to Minimize the percentage error in baud rate (Visit Data sheet to see it)
        Frequency of MCU = 4MHz
        For different frequencies, calculate value of SPBRG = [Fosc/4(Desire-Baud.Rate)]-1
        Value computed for SPBRG should be convert to Hexa before putting it in SPBRG (as in the below code)

        IOC (Interrupt on change) pins [RB4-RB7], when signal status is changed on one of these pins,it will cause interrupt
        In ISR module, PORTA [RA0-RA3] will be read in variable "dummy" and transfer synchronously
*/

char dummy = 0x00;
void interrupt(){

if (INTCON.RBIF == 1){                        // Change interrupt
           PORTB.f0 = !PORTB.f0;              // Its just for checking that program execute this section or not (For each PORTB-Change-Interrupt) It works
           TXREG = PORTA;                     // Assign PORTA to Tx reg
           dummy=PORTB;                       //  MUST Read PORTB, otherwise flag (RBIF) will not clear
           INTCON.RBIF = 0;                   // Clear flag
}

}
  void main()
  {
      TRISA = 0x0F; TRISB.f0=0;                  // [RA0-RA3] = Inputs
      TRISB.f5 = 1;                              // RA5 = Input (Used as IOC (interrupt on change))
      ADCON1 = 0x06;                             // PORTA I/O as Digital I/O
      SPBRG = 0x67;                             // decimal = 103, Baud-rate = 9600 , BRGH = 0
      TXSTA.SYNC=1; RCSTA.SPEN=1; TXSTA.CSRC=1; // Master clock from BRG, Synchronous mode, Enable Serial ports
      TXSTA.TXEN=1;                            // Transmission Enable
      INTCON=0xC8;                             // {Global interrupts , PORTB Change interrupt} = Enable

      while(1);
  }


Receiver (Slave code)


Code:
//     USRT Recive module ( Synchronous Receiving) (Slave Mode)

char dummy=0x00;
void interrupt(){

if (INTCON.RCIF == 1){           // Byte Received ?

           dummy = RCREG;        // Read the Byte
           PORTB = ~PORTB;       // Used for checking whether this ISR is executing after every transmission or NOT ? (IT DOESN'T)
           INTCON.RCIF = 0;      // Clear Flag
}

}
  void main()
  {

      TRISB = 0x00;                // PORTB = Output
      TXSTA.SYNC=1; RCSTA.SPEN=1; //  Enable Synchronous mode , Enable Serial ports
      TXSTA.CSRC=0;               //  Clock source =  Master device
      PIE1.RCIE=1;                // Recieve interrupt Enable
      RCSTA.CREN=1;               // Continous receive enable bit
      INTCON.GIE=1; INTCON.PEIE=1; // Global and Peripheral interrupts Enable
      PORTB = 0x00;                // Clear PORTB
      while(1);                    // Do nothing
  }
 
Last edited:

Papabravo

Joined Feb 24, 2006
21,158
Something does not compute. In synchronous mode you need transmit data and transmit clock on one module. On the other module you need receive data and receive clock.

On the schematic you must connect:
  1. transmit clock to receive clock
  2. transmit data to receive data
It is not clear from your symbols which is which, but they are possibly correct. In the firmware the pins must be correctly configured for this to work. I think pin 25 is the clock and pin 26 is the data. Is that correct?

Also I don't see any configuration for RC6 and RC7 or the the synchronous clock.

Synchronous communication is half duplex with two wires, that is the data only moves in one direction.
 
Last edited:

ErnieM

Joined Apr 24, 2011
8,377
Even after you rewire both Tx lines to the others Rx lines I would be very surprised any simulator could simulate the reception of data out of one device and into another like this, though I am most familiar with the sim in MPLAB which is quite elementary.

Check the Proteus manual to see how good simulated outputs are at driving other pins.

You may need to test transmit and receive separately in sim while they work flawlessly on the real chips, which is why I prefer to build the dang thing and use an in circuit debugger to test the code.

Even the lowly PICkit can do in circuit debugging, though I am unsure if MicroC is capable inside MPLAB.
 

Thread Starter

Tajiknomi

Joined Mar 18, 2010
34
@Papabravo : If i am not wrong, pins connections are fine. In synchronous i have connected the DT to DT and Ck to Ck. I have configured properly (From the Data-sheet) & reviewed my configuration many times so that i can possibly find some configuration error, but i wasn't lucky.
Configuration -- > Transmitting code : Line {31,32} , Receiving code : Line {18,19,20,21}
@ErnieM : Today i just thought about maybe Proteus isn't able to cope it (Synchronously). But i don't know yet. I haven't use Sim simulator though, i will try it if it worked in this scenario.

I am just trying to perform all Serial Communication Protocol in order for better understanding so that in future i maybe able to use these in practical devices. If there any simulation environment other then Proteus which can cope with these situations, I will be glad to hear it.

P.S : Thanks for your kind replies
 
Last edited:
Top