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.

UART2 is not working on pic18f46k22

Status
Not open for further replies.

ep.hobbyiest

Full Member level 4
Joined
Jul 24, 2014
Messages
212
Helped
1
Reputation
2
Reaction score
1
Trophy points
18
Activity points
1,487
Hi,
I am using PIC18F46k22 controller with 4 MHz crystal. Compiler is XC8.
I configured UART but it is not working. Not single character is transmitting.

Code:
void initUART(void)
{
    TRISBbits.TRISB6 = 1;
    TRISBbits.TRISB7 = 1;
    
    TXSTA2 = 0x00;
    BAUDCON2 = 0x00;
    SPBRG2 = 25;
    RCSTA2 = 0x90;
    
}

void UartSendChar(char ch)
{
    TXSTA2bits.TXEN = 1;
    TXREG2 = ch;
    while(PIR3bits.TX2IF==0);
    PIR3bits.TX2IF = 0;
}

What i am doing wrong?
 

hello,

What about hardware init ?

ANSELB = 0;
and
PMD0bits.UART2MD=0; // USART2 enable



UART2 with C18

Code:
void Init_UART2_TeleInfo(void)
{
PMD0bits.UART2MD=0;  // USART2 enable    
Delay_mS(10);
// init 1200,E,7,1  10Mhz avec IT en rx
// voir para 18.5 spec sheet DS41159B page 186
Open2USART( USART_TX_INT_OFF &
USART_RX_INT_ON &       //interrupt  possible
USART_ASYNCH_MODE &
USART_CONT_RX &
//USART_SINGLE_RX &
USART_EIGHT_BIT &        // use of 7 bits 8em bit =Parite
USART_BRGH_LOW,208);  // 16Mhz FOSC interne sans PLL  ... OK 
// .. OK avec surcharge ci dessous ...voir dtasheet page 283 
//TXSTA2bits.BRGH=0;  //at 40MHz
TXSTA2bits.BRGH=1;  // at 20Mhz
BAUDCON2bits.BRG16=1;
//SPBRGH2=0x08; //2083 pour Q=10Mhz x 4 (PLL) => 40Mhz avec BRGH=0;
//SPBRG2=0x23;
SPBRGH2=0x10; //4160 pour Q=20Mhz avec BRGH=1;
SPBRG2=0x40;
//SPBRGH2=0x1A; //6656  pour FOSC=8x4=32Mhz avec BRGH=0;
//SPBRG2=0x00;
//SPBRGH2=0x0D; //3332  pour FOSC=16x4=64Mhz avec BRGH=0;
//SPBRG2=0x04;
}  

void Init_UART2_19200(void)
{
    
PMD0bits.UART2MD=0;  // USART2 enable    
Open2USART( USART_TX_INT_OFF &
USART_RX_INT_ON &       //interrupt  possible
USART_ASYNCH_MODE &
USART_CONT_RX &
USART_EIGHT_BIT &        
USART_BRGH_HIGH,65);   // @ 20Mhz  19200bds  // 16Mhz FOSC interne sans PLL  ... OK 

}
 
Try this. Do your own BAUD calculation.

This should work for UART1 on a 44pin TQFP. Change ANSEL and TRIS bits if your UART comes out on different pins

Code:
void Init_RS232(void) {

	// RS232 Initialization

        ANSELCbits.ANSC6=0;                                                                     // Disable AN18
        ANSELCbits.ANSC7=0;                                                                     // Disable AN19
        TRISCbits.RC6=0;                                                                        // Set TX as output
        TRISCbits.RC7=1;                                                                        // Set RX as input

	RCSTA1bits.SPEN=0;									// Disable serial port to make changes	
	TXSTA1bits.SYNC=0;									// Asynchronous
	TXSTA1bits.BRGH=1;									// Enable 16 bit baud rate gen.
	SPBRG1=BAUD;										// 115,200

	TXSTA1bits.TXEN=1;									// Enable TX
	RCSTA1bits.CREN=1;									// Enable RX
	RCSTA1bits.SPEN=1;									// Enable Serial port
	PIE1bits.RC1IE=1;									// Interupt on RX
	
	INTCONbits.PEIE=1;									// Enable peripheral interrupts
	INTCONbits.GIE=1;									// Enable global interupts
}

void Send_RS232(unsigned char Tx_data) {

	TXREG1=Tx_data;										// Send it
        while (!TXSTA1bits.TRMT);							        // Wait for character to finish
}
 
Id PIDP package then UART2 is on PORTD. Set TRISD bits accordingly and also clear ANSELD.
 

Hello,


This one function ( UART1) is working.. tested in real condition
OK at 4MHz and (also tested at 16 Mhz)
BRG16 must be set ..
and also
added UART2 !

Subroutines

Code:
  void Init_UART1(void) 
  {
        ANSELC.ANSC6=0;   // Disable AN18
        ANSELC.ANSC7=0;   // Disable AN19
        TRISC.RC6=0;      // Set TX as output
        TRISC.RC7=1;      // Set RX as input


    RCSTA1.SPEN=0;    // Disable serial port to make changes
    TXSTA1.SYNC=0;    // Asynchronous


    // test at 16MHz 19200  .. OK
    //TXSTA1.BRGH=1; // Enable 16 bit baud rate gen.
    //BAUDCON1.BRG16=1;
    //SPBRG1=208;    // 19200 at 16Mhz   error -0.32%


         TXSTA1.BRGH=1;    // at 4Mhz
         BAUDCON1.BRG16=1;
         SPBRG1=52;     //19200 bauds eror 1,73%


    TXSTA1.TXEN=1;    // Enable TX
    RCSTA1.CREN=1;    // Enable RX
    RCSTA1.SPEN=1;    // Enable Serial port
    
   // Interrupt  not yet enable
    PIE1.RC1IE=1;
    INTCON.PEIE=0;
    INTCON.GIE=0;
}


void Send_UART1(unsigned char Tx_data)
{
        while (TXSTA1.TRMT==0);
    TXREG1=Tx_data;
}


void UART1_Print_CText(const char *txt)
 { char cx;
   cx=*(txt);
   while (cx>0)
   {  cx=*(txt++);
      Send_UART1(cx);
      }
}


  void Init_UART2(void) 
  {
        ANSELB=0;   // NO analog on port B
        TRISB.B6=0;      // Set TX as output
        TRISB.B7=1;      // Set RX as input
        PMD0.UART2MD=0;  // USART2 enable
    RCSTA2.SPEN=0;    // Disable serial port to make changes
    TXSTA2.SYNC=0;    // Asynchronous


    // test at 16MHz 19200  .. OK
    //TXSTA1.BRGH=1; // Enable 16 bit baud rate gen.
    //BAUDCON1.BRG16=1;
    //SPBRG1=208;    // 19200 at 16Mhz   error -0.32%


         TXSTA2.BRGH=1;
         BAUDCON2.BRG16=1;
         SPBRG2=52;     //19200 bauds eror 1,73%


    TXSTA2.TXEN=1;    // Enable TX
    RCSTA2.CREN=1;    // Enable RX
    RCSTA2.SPEN=1;    // Enable Serial port
 // RX Interrupt  not yet enable
        PIE1.RC2IE=0;
    INTCON.PEIE=0;    // disable peripheral interrupts
    INTCON.GIE=0;    // disable global interupts
}


void Send_UART2(unsigned char Tx_data)
{
        while (TXSTA2.TRMT==0);
    TXREG2=Tx_data;
}


void UART2_Print_CText(const char *txt)
 { char cx;
   cx=*(txt);
   while (cx>0)
   {  cx=*(txt++);
      Send_UART2(cx);
      }
}

code for testing ...



Code:
void main() 
{


 #ifdef OSCILLATEUR_INTERNE
 // 1MHz par defaut car OSCON RAZ au reset
    OSCCON=0;
 // OSCCON=0b01110000;
 // OSCCONbits.IRCF2=1; //HFINTOSC - (16 MHz)
 // OSCCONbits.IRCF1=1;
 // OSCCONbits.IRCF0=1;
   OSCCON.IRCF2=1; //HFINTOSC - (4 MHz)
   OSCCON.IRCF1=0;
   OSCCON.IRCF0=1;
  // SCS<1:0> System Clock Select bit
  // 1x = Internal oscillator block
  // 01 = Secondary (SOSC) oscillator
  // 00 = Primary clock (determined by FOSC<3:0> in CONFIG1H).
  OSCCON.SCS1=1;
  OSCCON.SCS0=0;
  OSCTUNE=0;
  OSCTUNE.PLLEN=0;  // 1= avec PLL => 64Mhz ou 40Mhz   0 =sans PLL => 16Mhz  ou 10Mhz
  #else
  // FOSC=Q=20MHz
 #endif
 




  Init_UART1();
  Delay_ms(10);
  Send_UART1(10);Send_UART1(13); // CRLF
  UART1_Print_CText("Debut de test UART1 RC6=TX RC7=RX  19200,8,N,1  Fosc=4 Mhz\r\n");
  Send_UART1(65);Send_UART1(66);Send_UART1(67);  // send ABC
  Send_UART1(10);Send_UART1(13); // CRLF
  for (i=65;i<128;i++)
  {
   Send_UART1((unsigned char)i);
   }
   Send_UART1(10);Send_UART1(13);
   UART1_Print_CText("Fin test UART1 \r\n");
   Send_UART1(10);Send_UART1(13);
   
   UART1_Print_CText("Debut de test UART2 ..\r\n");


    Init_UART2();
    Delay_ms(10);
  Send_UART2(10);Send_UART2(13);
  UART2_Print_CText("Debut de test  UART2 RB6=TX  RB7=RX  19200,8,N,1  Fosc=4 Mhz\r\n");
  Send_UART2(65);Send_UART2(66);Send_UART2(67);
  Send_UART2(10);Send_UART2(13); // CRLF
  for (i=65;i<128;i++)
  {
   Send_UART2((unsigned char)i);
   }
   Send_UART2(10);Send_UART2(13);
   UART2_Print_CText("Fin test UART2 \r\n");
   Send_UART2(10);Send_UART2(13);
   
    while(1);
    
}

display result for UART1 test

Debut de test RS232 19200,8,N,1 Fosc=4 Mhz
ABC
ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~
Fin test RS232



UART2 test

Debut de test UART2 RB6=TX RB7=RX 19200,8,N,1 Fosc=4 Mhz
ABC
ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~
Fin test UART2
 

sorry,i didn't pay attention for theMCU type,
my example is for 18F26K22 .. without port D
just adapt input and output UART2


Code:
ANSELD=0;   // NO analog on port B
TRISD.B6=0;      // Set TX as output (TX2  EUSART asynchronous transmit data output)
TRISD.B7=1;      // Set RX as input  (RX2  EUSART asynchronous receive data in.)
 
Last edited:

I tried example gave by you and its working.
I change the port setting and change the confi and its start working.

Code:
    ANSELD = 0x00;
    TRISDbits.TRISD6 = 1;
    TRISDbits.TRISD7 = 1;
 

Status
Not open for further replies.

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top