【问题标题】:No interrupts being triggered in UART Receive on PIC18F2680PIC18F2680 上的 UART 接收中没有触发中断
【发布时间】:2012-04-12 02:19:35
【问题描述】:

我已经使用这段代码好几天了,无法弄清楚为什么我的中断没有被触发。我知道数据正在成功通过,因为我在逻辑分析仪上使用了探头,而且我的波特率是正确的,因为我可以通过 UART 成功传输。

此时我迷路了,我一遍又一遍地阅读数据表,无法弄清楚我的问题。我将尝试仅包含相关代码,但足以让您了解我的项目中的工作方式。

如果您发现此代码有问题,请告诉我。

谢谢!

main.c 中的代码 sn-ps:

    // USART RX interrupt priority
    IPR1bits.RCIP = 0;
    IPR1bits.TXIP = 0;

    // configure the hardware USART device
    OpenUSART(USART_TX_INT_OFF & USART_RX_INT_ON & USART_ASYNCH_MODE & USART_EIGHT_BIT &
        USART_CONT_RX & USART_BRGH_LOW, 14);

来自 interrupts.c 的代码 sn-ps

    //----------------------------------------------------------------------------
    // Low priority interrupt routine
    // this parcels out interrupts to individual handlers
    #pragma code
    #pragma interruptlow InterruptHandlerLow

    // This works the same way as the "High" interrupt handler

    void InterruptHandlerLow() {

    // check to see if we have an interrupt on USART RX
    if (PIR1bits.RCIF) {
        PIR1bits.RCIF = 0; //clear interrupt flag
        uart_recv_int_handler();
    }
    // check to see if we have an interrupt on USART TX
    if (PIR1bits.TXIF && PIE1bits.TXIE) {
        // cannot clear TXIF, this is unique to USART TX
        // so just call the handler
        uart_tx_int_handler();
    }
    }

UART RX 中断处理程序 sn-p:

    void uart_recv_int_handler() {
        int msgLen;

        //if (DataRdyUSART()) {
        uc_ptr->buffer[uc_ptr->buflen] = RCREG;
        //uc_ptr->buffer[uc_ptr->buflen] = ReadUSART();
            uc_ptr->buflen++;
       }
    }

【问题讨论】:

  • 您是否尝试过“轮询”UART?会发生什么,它接收字符好吗?
  • 这个我还没试过,明天下午我可以测试一下,告诉你结果如何。
  • 你没有显示也没有提到全局中断启用标志。数据表第 9 节指出,对于默认中断策略,“INTCON<6>PEIE 位,它启用/禁用所有外设中断源。INTCON<7>GIE 位,它启用/禁用所有中断源。 "如果您为中断启用了优先级 (IPEN),那么您需要设置 GIEHGIEL.

标签: embedded interrupt pic microchip uart


【解决方案1】:

你有没有 - 正确设置 trisC6/7? - 如果您有一个在这些引脚上多路复用模拟输入的部件,您是否禁用了它们? - 您的 BRG 值是否已针对这部分和这些振荡器设置进行验证?

另见

http://www.piclist.com/techref/microchip/rs232.htm

我迁移到 dspic,但我曾经在中断下进行串行接收。这是我在中断中遇到的(serialin1 是两个循环缓冲区的幂,lastserialin1 是指向它的指针,ser1bufinmask 是缓冲区1的大小)

if (PIR1bits.RCIF == 1)  /* check if RC interrupt (receive USART) must be serviced 
{
    while (PIR1bits.RCIF == 1)   /* flag becomes zero if buffer/fifo is empty */
    {
      lastserialin1=(lastserialin1+1)&ser1bufinmask;
      serialin1[lastserialin1]=RCREG;
    }
}

初始化我的UART:

// Configure USART
TXSTA = 0x20;  // transmit enable
RCSTA = 0x90;  // spen en cren
RCONbits.IPEN      = 1;  /* Interrupt Priority Enable Bit. Enable priority levels on interrupts */

INTCONbits.GIE     = 1;  /* Set GIE. Enables all high priority unmasked interrupts */
INTCONbits.GIEL    = 1;  /* Set GIEL. Enables all low priority unmasked interrupts */

TRISCbits.TRISC6    = 0;    // page 237
TRISCbits.TRISC7    = 1;    // page 237

Open1USART (  
               USART_TX_INT_OFF 
               &
            USART_RX_INT_ON &
            USART_ASYNCH_MODE &
            USART_EIGHT_BIT &           // 8-bit transmit/receive
            USART_CONT_RX &             // Continuous reception
                       //               USART_BRGH_HIGH, 155);      // High baud rate, 155 eq 19k2
            USART_BRGH_HIGH, brgval);       // High baud rate, 25 eq 115k2 

IPR1bits.RCIP       = 0;
PIR1bits.RCIF       = 0;

使用 brgval 计算

     #define GetInstructionClock()  (GetSystemClock()/4)
     #define GetPeripheralClock()   GetInstructionClock()

     // See if we can use the high baud rate setting
     #if ((GetPeripheralClock()+2*BAUD_RATE)/BAUD_RATE/4 - 1) <= 255
        #define BRGVAL ((GetPeripheralClock()+2*BAUD_RATE)/BAUD_RATE/4 - 1)
        #define BRGHVAL (1)
     #else  // Use the low baud rate setting
        #define BRGVAL ((GetPeripheralClock()+8*BAUD_RATE)/BAUD_RATE/16 - 1)
        #define BRGHVAL (0)
     #endif

【讨论】:

  • 我相信是 trisC6/7 位成就了我。谢谢!
猜你喜欢
  • 2015-09-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-09-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-07-05
相关资源
最近更新 更多