Я не могу работать SPI с программным обеспечением EUART на PIC
Если я загружаю свой код в PIC18 с SPI и программным обеспечением EUART, я получаю NUL в док-станции и не получаю команду SPI в области. Похоже, что EUART и SPI не хотят работать вместе. Это для PIC18F45K80, связывающегося с QT1481. Я убежден, что проблема заключается в EUART.
Вот код в основном.
#include <xc.h>
#include "PIC.h"
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <pic18f45k80.h>
#define MSB 1
#define LSB 0
// SPI PIN CONFIGURATION
#define SCK_TRIS TRISCbits.TRISC3 = 0 ;
#define SDO_TRIS TRISCbits.TRISC5 = 0 ;
#define SDI_TRIS TRISCbits.TRISC4 = 1 ;
#define QTA_SS_TRIS TRISDbits.TRISD4 = 0 ;
#define QTB_SS_TRIS TRISEbits.TRISE2 = 0 ;
#define QTA_SS_LAT_LOW LATDbits.LATD4 = 0 ;
#define QTA_SS_LAT_HIGH LATDbits.LATD4 = 1 ;
#define QTB_SS_LAT_LOW LATEbits.LATE2 = 0 ;
#define QTB_SS_LAT_HIGH LATEbits.LATE2 = 1 ;
#define QTA_DRDY_TRIS TRISDbits.TRISD5 = 1 ;
#define QTB_DRDY_TRIS TRISDbits.TRISD2 = 1 ;
#define QTA_DRDY_LAT_LOW LATDbits.LATD5 = 0 ;
#define QTA_DRDY_LAT_HIGH LATDbits.LATD5 = 1 ;
#define QTB_DRDY_LAT_LOW LATDbits.LATD2 = 0 ;
#define QTB_DRDY_LAT_HIGH LATDbits.LATD2 = 1 ;
#define QTB_DRDY PORTDbits.RD2 ;
#define QTA_DRDY PORTDbits.RD5 ;
#define SPI_RX_IN_PROGRESS 0x0
// SOFTWARE EUART
#define UART_DEBUG 1 // 1 or 0
#define BAUDRATE 9600
#if BAUDRATE == 9600
#define BIT_TIME_US 104
#define ISYM_DELAY __delay_ms(5)
#elif BAUDRATE == 38400
#define BIT_TIME_US 26
#define ISYM_DELAY __delay_ms(1)
#elif BAUDRATE == 115200
#define BIT_TIME_US 9
#define ISYM_DELAY __delay_us(450)
#endif
#define UART_BIT_DELAY __delay_us(BIT_TIME_US)
#define ISYM_DELAY __delay_us(3*BIT_TIME_US)
#define UART_BYTE_MODE LSB
// FREQUENCY SELECT
#define _XTAL_FREQ 16000000
// SPI
void SPI_Initialize(void)
{
// SMP Middle; CKE Idle to Active;
SSPSTAT = 0b00000000;
// SSPEN enabled; WCOL no_collision; CKP Idle:High, Active:Low; SSPM FOSC/4; SSPOV no_overflow;
SSPCON1 = 0b00110001;
// SSPADD 0;
SSPADD = 0x00;
ADCON0 = 0 ;
ADCON1 = 0x0F ; //Makes all I/O digital
OSCCON = 0b01111100 ;
SCK_TRIS ;
SDO_TRIS ;
SDI_TRIS ;
QTA_SS_TRIS ;
QTB_SS_TRIS ;
QTA_DRDY_TRIS ;
QTB_DRDY_TRIS ;
}
signed char WriteSPI( unsigned char data_out )
{
unsigned char TempVar;
TempVar = SSPBUF; // Clears BF
PIR1bits.SSPIF = 0; // Clear interrupt flag
SSPCON1bits.WCOL = 0; //Clear any previous write collision
SSPBUF = data_out; // write byte to SSPBUF register
if ( SSPCON1 & 0x80 ) // test if write collision occurred
return ( -1 ); // if WCOL bit is set return negative #
else
while( !SSPSTATbits.BF ); // wait until bus cycle complete
return ( 0 ); // if WCOL bit is not set return non-negative#
}
unsigned char ReadSPI( void )
{
unsigned char TempVar;
TempVar = SSPBUF; // Clear BF
PIR1bits.SSPIF = 0; // Clear interrupt flag
SSPBUF = 0x00; // initiate bus cycle
while(!SSPSTATbits.BF); // wait until cycle complete
return ( SSPBUF ); // return with byte read
}
unsigned char DataRdySPI( void )
{
if ( SSPSTATbits.BF )
return ( +1 ); // data in SSPBUF register
else
return ( 0 ); // no data in SSPBUF register
}
void rlc_A(void)
{
char temp;
__delay_us(100); // required previous to check DRDY (pag 26)
while (PORTDbits.RD5 == 0) ; // wait until DRDY high
QTA_SS_LAT_LOW ; // Put SS low
__delay_us(10); // required if you are QT was in sleep mode (pag 22)
WriteSPI(0x0F); // Send a byte - Transmit data
__delay_us(2); // Wait for the byte to be shifted out
QTA_SS_LAT_HIGH ; // Put SS high
// Now transfer null command for getting the response
__delay_us(100); // required previous to check DRDY (pag 26)
while (PORTDbits.RD5 == 0) ; // wait until DRDY high
QTA_SS_LAT_LOW ; // Put SS low
__delay_us(10); // required if you are QT was in sleep mode
temp = ReadSPI(); // Read a byte from the
QTA_SS_LAT_HIGH ; // Stop transmitting data
}
// SOFTWARE EUART
void out_char(char character){
uint8_t i = 0;
RSOUT = 1; // MSB
ISYM_DELAY;
RSOUT = 0; // START
UART_BIT_DELAY;
for (i = 8; i>0; --i) {
#if UART_BYTE_MODE == MSB
// if (bit_order) { // Bit order determines how you will put the bits, from left to right (MSB) or right to left (LSB)
RSOUT = (character & 0x80) ? 1 : 0; // in MSB you compare the left-most bit doing an AND with 0x80, and put 1 if true, 0 elsewhere.
character <<= 1; // Shift the character to the left, discrading the bit just sent
#elif UART_BYTE_MODE == LSB
// } else {
RSOUT = (character & 0x01); // in LSB you compare the right-most bit doing an AND with 0x01, and put 1 if true, 0 else.
character >>= 1; // Shift the character to the right, discrading the bit just sent
#endif
// }
UART_BIT_DELAY;
}
RSOUT = 1; // STOP
}
void out_str(char * string, uint8_t len)
{
uint8_t i = 0;
for (i = 0; i< len; i++) {
out_char(string[i]);
}
}
void SYSTEM_Initialize(void)
{
PIN_MANAGER_Initialize() ;
SPI_Initialize() ;
BUZZER_Initialize() ;
}
void main(void)
{
SYSTEM_Initialize() ;
//buzz() ;
while(1){
rlc_A();
out_str("Sent OF",7);
}
}