2
\$\begingroup\$

I am trying to do uart program in pic. I want to display characters send by controller to pc. But i am not able to do this. following is my code

#include<pic.h>

__CONFIG(0x3f72);

#define FOSC       10000     //10Mhz==>10000Khz
#define BAUD_RATE   9.6     //9600 Baudrate
#define BAUD_VAL   ((char)(FOSC/ (16 * BAUD_RATE )) – 1)     

void main()
{
 unsigned char ReceiveChar;  
 TRISC=0xc0;   //RC7,RC6 set to usart mode(INPUT)
 TXSTA=0x24;   //Transmit Enable
 SPBRG=BAUD_VAL; //9600 baud at 10Mhz
 RCSTA=0x90;   //Usart Enable, Continus receive enable
 TXREG='0';

 while(1)
 {
   if (RCIF==1) //char received? Send 'A' back to Terminal
       {
     ReceiveChar=RCREG;

     if(TXIF==1)
     TXREG=ReceiveChar;
   }  
  }
}  
\$\endgroup\$
  • \$\begingroup\$ #define BAUD_VAL has a potential bug: you should never use char type for arithmetic, because it has implementation-defined signedness. \$\endgroup\$ – Lundin Sep 22 '15 at 11:46
3
\$\begingroup\$

Well your code looks OK, but do you know that microchip provides PIC18 peripheral library so you can directly use functions, instead of putting values to registers.

Following is the sample code you can use:

#include <plib.h>
#pragma config FNOSC = PRIPLL       
#pragma config POSCMOD = HS         
#pragma config FPLLMUL = MUL_18     
#pragma config FPLLIDIV = DIV_2     
#pragma config FPBDIV = DIV_1       
#pragma config FPLLODIV = DIV_1     
#pragma config FWDTEN = OFF         
#define SYSTEM_FREQUENCY        {define you system frequency here}
#define BAUDRATE                115200
int main()
{
 int pbFreq;
 pbFreq=SYSTEMConfigPerformance(SYSTEM_FREQUENCY);
OpenUART( UART_EN | UART_NO_PAR_8BIT | UART_1STOPBIT, UART_RX_ENABLE | UART_TX_ENABLE, (pbFreq/16/BAUDRATE)-1);
 while(1)
 {
   putsUART("Hello World.!");
 }
}
\$\endgroup\$
  • \$\begingroup\$ thnks for library \$\endgroup\$ – user46573544 Sep 16 '15 at 7:06
  • \$\begingroup\$ PIC libraries use 32 bit arithmetic? I don't believe that... there must be a bug here. And you should avoid 32 bit numbers in the first place. Keep in mind that this is by the far slowest CPU in the world which is still produced. The OP:s method of calculating the baudrate is better, since it is done by the pre-processor. Unless you for some reason have need of a variable system clock, why calculate anything in runtime? \$\endgroup\$ – Lundin Sep 22 '15 at 11:54
  • \$\begingroup\$ Rationale: on a 8 bit MCU, int is 16 bits and thus the literal 115200 is of type long. Which is why the expression pbFreq/16/BAUDRATE doesn't make any sense. \$\endgroup\$ – Lundin Sep 22 '15 at 11:59
  • \$\begingroup\$ @Lundin yes you are right.! I am sorry for 16bit. This is just a demo code which OP can replace it with the functions used by 8bit MCU. This worked great for 32bit MCU.! \$\endgroup\$ – Aircraft Sep 23 '15 at 4:22
  • \$\begingroup\$ @CZAbhinav This would be why you shouldn't use int in embedded systems, but uint16_t or uint32_t. It forces you to consider overflows. \$\endgroup\$ – Lundin Sep 23 '15 at 6:15

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.