Relay Driver Controlled by Serial using 16F877A

Thread Starter

karloz34

Joined Oct 6, 2015
1
Hello community,

I'm attempting to implement a serial controlled relay driver using a PIC16F877A uC.

My circuit can be described in the next manner: A +12v input, a LM7805 for a net of +5v, a MAX232 for TTL signal conversion, PIC16F877A for serial communication and controlling the output port on which eight relays will be controlled. Each relay will power up a +12v strobe light at a time.

I have the schematic done but I'm struggling with the programming of the PIC, I have read several tutorials on using USART for serial communication an I have the following code:

// PIC16F877A Configuration Bit Settings
#include <xc.h>
// CONFIG0
#pragma config CP = OFF // Code protection OFF
#pragma config DEBUG = OFF // Debugger OFF
#pragma config WRT = OFF // Flash program memory write OFF
#pragma config CPD = OFF // Data EEPROM memory code protection OFF
#pragma config LVP = OFF // Low voltage In-circuit serial programming OFF
#pragma config BODEN = ON // Brown-out reset enable ON
#pragma config PWRTE = OFF // Power-up timer enable OFF
#pragma config WDTE = OFF // Watchdog timer enable OFF
#pragma config FOSC = HS // Oscillator HS : High speed crystal

#define STRLEN 12

volatile unsigned char t;
volatile unsigned char rcindex;
volatile unsigned char rcbuf[STRLEN];

void USART_init(void)
{
TXSTAbits.TXEN = 1; // enable transmitter
TXSTAbits.BRGH = 1; // high baud rate mode
RCSTAbits.CREN = 1; // enable continous receiving

// configure I/O pins
TRISCbits.TRISC7 = 1; // RX pin is input
TRISCbits.TRISC6 = 1; // TX pin is input (automatically configured)

SPBRG = 25; // set baud rate to 9600 baud (4MHz/(16*baudrate))-1

PIE1bits.RCIE = 1; // enable USART receive interrupt
RCSTAbits.SPEN = 1; // enable USART
}

void USART_putc(unsigned char c)
{
while (!TXSTAbits.TRMT); // wait until transmit shift register is empty
TXREG = c; // write character to TXREG and start transmission
}

void USART_puts(unsigned char *s)
{
while (*s)
{
USART_putc(*s); // send character pointed to by s
s++; // increase pointer location to the next character
}
}

int main(void)
{
USART_init();

USART_puts("Initialized!\n");

INTCONbits.PEIE = 1; // enable peripheral interrupts
INTCONbits.GIE = 1; // enable interrupts


TRISD = 0; //Define PORTD as output

while(1)
{
if (rcbuf == "relay1")
PORTBbits.RB0 =1;
}

return 0;
}

void interrupt ISR(void)
{
if (PIR1bits.RCIF) // check if receive interrupt has fired
{
t = RCREG; // read received character to buffer

// check if received character is not new line character
// and that maximum string length has not been reached
if ( (t != '\n') && (rcindex < STRLEN) )
{
rcbuf[rcindex] = t; // append received character to string
rcindex++; // increment string index
}
else
{
rcindex = 0; // reset string index
USART_puts(rcbuf); // echo received string
}

PIR1bits.RCIF = 0; // reset receive interrupt flag
}
}
Let's take a look at the main loop:

while(1)
{
if (rcbuf == "relay1")
PORTBbits.RB0 = 1;
}
Will this set RB0 to high when the string at rcbuff is relay1?

Any easier way of setting this up?

Thanks, any help will be greatly appreciated.
 

JohnInTX

Joined Jun 26, 2012
4,787
C will not compare strings directly. Use strcmp or strncmp which you will find in the libraries. These are described in Appendix A of the XC8 compiler User's Guide. You'll have to include string.h to use them.

Good luck.
 
Last edited:
Top