No puedo escribir a USART en PIC18F26J50. Aquí está mi configuración:
- El reloj es de 48MHz;
- Estoy usando un controlador RS485 (SN65HVD1781) en modo semidúplex. El PIN de dirección para esto está conectado a RA2;
- Estoy usando un convertidor de USB a RS485 que obtuve de eBay. Tiene un chip FT232R y un transceptor 485;
- El compilador es C18 v3.47. Intentando obtener 115200bps, 8N1;
-
Aquí está el programa que estoy usando:
#define RS485_READ 1 #define RS485_WRITE 0 PRIVATE high8( BYTE x ) { return (BYTE)( x >> 8 ); } PRIVATE low8( BYTE x ) { return (BYTE)( x & 0xFF ); } void main (void) { (VOID)clockInit(); // disables analog-to-digital conversion // (enables digital IO on all AD pins) ANCON0 = 0x1F; ANCON1 = 0x1F; // enables rs485 write (output) TRISAbits.TRISA2 = 0; TXSTA1bits.SYNC = 0; TXSTA1bits.BRGH = 1; // set BRGH bit TXSTA1bits.TXEN = 1; // enable TX RCSTA1bits.SPEN = 1; RCSTA1bits.CREN = 1; TRISCbits.TRISC6 = 0; TRISCbits.TRISC7 = 1; // Rx1 set input BAUDCON1bits.BRG16 = 1; // set 16 bits SPBRG BAUDCON1bits.RCIDL = 1; // set receive active SPBRGH1 = high8(104); // set UART speed SPBRGH SPBRG1 = low8(104); // set UART speed SPBRGL CM1CONbits.CON = 0; // disables comparator /* Loop forever */ while (1) { LATAbits.LATA2 = RS485_WRITE; while( !TXSTA1bits.TRMT ); // Ready ? TXREG1 = 0x55; // yes, send char LATAbits.LATA2 = RS485_READ; } }
Aquí están los fusebits que estoy usando:
// CONFIG1L
#pragma config WDTEN = OFF // Watchdog Timer (disabled)
#pragma config PLLDIV = 2 // PLL Prescaler Selection bits (Divide by 2 (8 MHz internal oscillator input))
#pragma config STVREN = ON // Stack Overflow/Underflow Reset (Enabled)
#pragma config XINST = OFF // Extended Instruction Set (Enabled)
// CONFIG1H
#pragma config CPUDIV = OSC1 // CPU System Clock Postscaler (CPU system clock divide by 2)
#pragma config CP0 = OFF // Code Protect (Program memory is not code-protected)
// CONFIG2L
#pragma config OSC = INTOSCPLL // Oscillator (INTOSCPLL)
#pragma config T1DIG = OFF // T1OSCEN Enforcement (Secondary Oscillator clock source may be selected)
#pragma config LPT1OSC = OFF // Low-Power Timer1 Oscillator (High-power operation)
#pragma config FCMEN = OFF // Fail-Safe Clock Monitor (Enabled)
#pragma config IESO = OFF // Internal External Oscillator Switch Over Mode (Enabled)
// CONFIG2H
#pragma config WDTPS = 32768 // Watchdog Postscaler (1:32768)
// CONFIG3L
#pragma config DSWDTOSC = INTOSCREF // DSWDT Clock Select (DSWDT uses INTRC)
#pragma config RTCOSC = T1OSCREF // RTCC Clock Select (RTCC uses T1OSC/T1CKI)
#pragma config DSBOREN = OFF // Deep Sleep BOR (Enabled)
#pragma config DSWDTEN = OFF // Deep Sleep Watchdog Timer (Enabled)
#pragma config DSWDTPS = G2 // Deep Sleep Watchdog Postscaler (1:2,147,483,648 (25.7 days))
// CONFIG3H
#pragma config IOL1WAY = OFF // IOLOCK One-Way Set Enable bit (The IOLOCK bit (PPSCON<0>) can be set/cleared as needed)
#pragma config MSSP7B_EN = MSK7 // MSSP address masking (7 Bit address masking mode)
// CONFIG4L
#pragma config WPFP = PAGE_63 // Write/Erase Protect Page Start/End Location (Write Protect Program Flash Page 63)
#pragma config WPEND = PAGE_WPFP // Write/Erase Protect Region Select (valid when WPDIS = 0) (Page WPFP<5:0> through Configuration Words erase/write protected)
#pragma config WPCFG = OFF // Write/Erase Protect Configuration Region (Configuration Words page not erase/write-protected)
// CONFIG4H
#pragma config WPDIS = OFF // Write Protect Disable bit (WPFP<5:0>/WPEND region ignored)
Y aquí está la función clockInit:
INT16 clockInit( VOID )
{
INT16 rc = ERROR_VALUE_NOT_INITIALIZED;
// disables reference oscillator output
REFOCONbits.ROON = 0;
// device enters IDLE mode on SLEEP instruction
OSCCONbits.IDLEN = 1;
// system clock is from primary oscillator
OSCCONbits.SCS = 0;
// selects base frequency as 8MHz
OSCCONbits.IRCF = IOF_8MHz;
// wait until oscillator is running
while( !OSCCONbits.OSTS );
// low speed USB (6MHz clock)
UCFGbits.FSEN = 0;
// enable PLL
OSCTUNEbits.PLLEN = 1;
rc = ERROR_SUCCESS;
return rc;
}
¿Puede alguien señalarme lo que estoy haciendo mal?