启用ATTINY1626 UART RX中断不触发ISR,如何解决?

问题描述 投票:0回答:2

我的 ATTINY1626 遇到接收中断问题。在池化模式下,我可以接收 UART 数据。但启用 UART RX 中断不会发生这种情况。我不知道哪里漏掉了一些与中断相关的配置。

如果有人遇到并解决了此类问题,请建议我。

下面是代码。

#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#include <avr/fuse.h>

#define F_CPU 16000000UL / 2
#define FUSE_OSCCFG_16MHZ  (0x7D)

//#define cli()             __asm__ __volatile__ ("cli" ::)         ///< Disables global interrupts
//#define sei()             __asm__ __volatile__ ("sei" ::)         ///< Enables global interrupts

volatile unsigned char gvc_Rxbyte = 0;

FUSES = {
    .WDTCFG     = FUSE_WDTCFG_DEFAULT,
    .BODCFG     = FUSE_BODCFG_DEFAULT,
    .OSCCFG     = FUSE_OSCCFG_16MHZ,    // Run at 16 MHz and Calibration registers of the 20 MHz oscillator are accessible
    .SYSCFG0    = FUSE_SYSCFG0_DEFAULT, // Reset Pin Configured as UPDI
    .SYSCFG1    = FUSE_SYSCFG1_DEFAULT, // start-up time between power-on and code execution
    .APPEND     = 0x14, // FUSE_APPEND_DEFAULT - 4K APP CODE
    .BOOTEND    = 0x04, // FUSE_BOOTEND_DEFAULT - 1K BOOT CODE
};

void send_string(unsigned char uartNo, char *s);

void usart0_init(unsigned long int baudRate)
{
    unsigned int baud = 0;
    cli();
    SREG &=~(1 << 7);
//  PORTMUX.EVSYSROUTEA |= (1 << 1);
    //uint8_t sregBackup = CPU_SREG;
//  cli();
    baud = (F_CPU / baudRate) * 4;  // BAUD = (64 * fCLK_PER) / (S * fBAUD)
    // S is the number of samples per bit
    // Asynchronous Normal mode: S = 16
    // Asynchronous Double-Speed mode: S = 8
    // Synchronous mode: S = 2
    
    USART0.BAUDL = (unsigned char) baud;            // Set the baud rate (USARTn.BAUD).
    USART0.BAUDH = (unsigned char) (baud >> 8);
    
    USART0.CTRLC = 0x03;            // Set the frame format and mode of operation (USARTn.CTRLC).
    //set character size to 8. parity = none. stop bits = 1. async usart.
    PORTB.DIR |= PIN2_bm;           // Configure the TXD pin as an output.
    PORTB.DIR &= ~PIN3_bm;          // Configure the RXD pin as an input.
    
    USART0.CTRLA |=(1<<USART_RXCIE_bp) | (1<<USART_ABEIE_bp);//0x84;
    USART0.CTRLB |=(1<<USART_RXEN_bp)|(1<<USART_TXEN_bp) ;          // Enable the transmitter and the receiver (USARTn.CTRLB).
    
     sei();
}

void usart0WriteByte(unsigned char dataByte)
{
    while(!(USART0.STATUS & USART_DREIF_bm)); // wait till tx register is free
    USART0.TXDATAL = dataByte;              // load data in the tx register
}

unsigned char usart0ReadByte(void)
{
    unsigned char rxByte = 0;
    while(!(USART0.STATUS & USART_RXCIF_bm)); // wait for rx register data
    rxByte = USART0.RXDATAL;                // read data from the rx register
    
    return rxByte;
}

void send_string(unsigned char uartNo, char *s)
{
    while(*s)
    {
        usart0WriteByte(*s);        
        s++;
    }
}

int main(void)
{
    //unsigned char i=0;
    cli();
    
    _PROTECTED_WRITE(CLKCTRL.MCLKCTRLA, CLKCTRL_CLKSEL_OSC20M_gc | (0<<CLKCTRL_CLKOUT_bp ));    ///< To out the clock on clock out pin
    _PROTECTED_WRITE(CLKCTRL.MCLKCTRLB, CLKCTRL_PDIV_2X_gc | CLKCTRL_PEN_bm );                  ///< To set the clock pre-scaler as DIVIDED BY 2
    
    usart0_init(115200);                ///< Initializing UART0 as debug interface.
    //_PROTECTED_WRITE(CPU_SREG, (1 << CPU_I_bp));  
    //send_string(0, "System Initialized\r\n");
    _delay_ms(1000);
    gvc_Rxbyte = 'B';   
    
    while (1)
    {
         //sei();
        ////gvc_Rxbyte = usart0ReadByte();
        //usart0WriteByte(gvc_Rxbyte);
        //_delay_ms(1000);
    }
}

ISR (USART0_RXC_vect)
{
    if(USART0.STATUS & USART_RXCIF_bm)
    {
        gvc_Rxbyte = USART0.RXDATAL;
    }
    gvc_Rxbyte = USART0.RXDATAL;                // read data from the rx register
    usart0WriteByte(gvc_Rxbyte);    
}
**

我尝试启用 UART RXIE 配置。启用全局中断。即使 ISR 也不调用接收缓冲区上可用的接收数据。

硬件路径似乎没问题,因为接收功能使用 POOLing 模式。

c interrupt uart avr-gcc attiny
2个回答
2
投票

看来您在 ISR 中读取了

USART0.RXDATAL
字节两次。如果您的
gvc_Rxbyte
为 0,可能是因为您第二次读取
USART0.RXDATAL
时覆盖了它。


0
投票

无法触发Microchip Studio生成的usart ISR。这个问题解决了吗

© www.soinside.com 2019 - 2024. All rights reserved.