⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 uart_drv.c

📁 freescale的基于802.15.4的无线通讯例程
💻 C
📖 第 1 页 / 共 2 页
字号:
/*****************************************************************************
* All the SCI hardware related functions are implemented in this file
*
*
* (c) Copyright 2006, Freescale, Inc. All rights reserved.
*
* Freescale Confidential Proprietary
*
* No part of this document must be reproduced in any form - including copied,
* transcribed, printed or by any electronic means - without specific written
* permission from Freescale Semiconductor Danmark A/S.
*****************************************************************************/

#include "UART_Interface.h"
#include "TMR_Interface.h"

#if (gUART_Enabled_d == 1)

#if ((gUART_OnSCI1_d == 1) || (gUART_OnSCI2_d == 1))
/*****************************************************************************
******************************************************************************
* Private macros
******************************************************************************
*****************************************************************************/

/* Enable / disable Tx interrupt */
#define SCIx_EnableTxInts()    { SCIxC2 |= gUART_TxInterrupt_c; }
#define SCIx_DisableTxInts()   { SCIxC2 &= ~gUART_TxInterrupt_c; }

/* Enable / disable Rx interrupt */
#define SCIx_EnableRxInts()		{ SCIxC2 |= 0x20; }
#define SCIx_DisableRxInts()	{ SCIxC2 &= 0xDF; }

/* The UART task handles the following events: */
enum {
  mTxSuccessEvent_c   = 0x01,
  mRxSuccessEvent_c   = 0x02,
  mRxTimeoutEvent_c   = 0x04,
  mRxWaterMarkEvent_c = 0x08,
};

/*****************************************************************************
******************************************************************************
* Private prototypes
******************************************************************************
*****************************************************************************/
 
/* Timeout handler for the UART */
void UART_Timeout(uint8_t timerId);

/*****************************************************************************
******************************************************************************
* Private type definitions
******************************************************************************
*****************************************************************************/

/*****************************************************************************
******************************************************************************
* Private memory declarations
******************************************************************************
*****************************************************************************/
 
/* FIFO (implemented as circular buffer) */
static uint8_t maFIFO[gUART_FIFOLen_c];   
static uint8_t mhFIFO = 0, mtFIFO = 0; /* Head and tail in FIFO */

/* For backup until request is complete */
static irp_t *mpRxIrp = NULL, *mpTxIrp = NULL;

/* Counts the transmit data */
static uint8_t mcTx;
/* Counts the receiving data */
static uint8_t mcRx;
/* Dynamic water mark */
static uint8_t mFIFOWaterMark;

/*****************************************************************************
******************************************************************************
* Public function definitions
******************************************************************************
*****************************************************************************/

/*****************************************************************************
* The callback function that handle the timeout. 
*
* Interface assumptions:
* Arguments:
* taskId - ID of receiving task
* 
* Return value:
* None
* 
* Revision history:
* date   Author   Comments
* ------ ------   --------
* 240406 AL,FSL  Updated
*****************************************************************************/
void UART_Timeout(uint8_t timerId)
{
  (void)timerId; /* To avoid compiler warning */
  
  /* Signal to UART task that a timeout happened */
  TS_SendEvent(gUartTaskID_c, mRxTimeoutEvent_c);
}

/****************************************************************************
* The UART task that copies data, manages timeouts, notifies the application
* callback function etc.
*
* Interface assumptions:
* 
* Arguments:
*   events - Bit mask.
*
* Return value:
* None
* 
* Revision history:
* date   Author   Comments
* ------ ------   --------
* 240406 AL,FSL   Updated
*****************************************************************************/
void UART_Main(event_t events)
{
  uint8_t cHead; /* Backup of head pointer in FIFO */
#if (gUART_ReinitEnabled_d == 1)  
  irp_t   *pIrp;
#endif

  /* Check why the task is run */

/*--------------------------------------------------------------------------*/  

  if (events & mTxSuccessEvent_c) {      
                   
    /* Call the users callback function with gUartTxSuccess_c response */
		mpTxIrp->returnValue = gUartTxSuccess_c;
#if (gUART_ReinitEnabled_d == 1)
    pIrp = mpTxIrp;
    mpTxIrp = NULL; /* No Tx IRP pending anymore */
    pIrp->reqData.rxtxParams.pfCallback(pIrp);
#else
    pIrp->reqData.rxtxParams.pfCallback(mpTxIrp);
#endif
  }
  
/*--------------------------------------------------------------------------*/                      

  if (events & mRxWaterMarkEvent_c) {      

    /* We need to continue receiving in the FIFO instead of disabling the */
    /* interrupt. If not, we may get data loss in between the application */
    /* processing a completed Rx Irp and sending a new Rx Irp             */

    /* Check if we have an Irp for receiving */
    if (NULL == mpRxIrp) {
      /* No Irp for receiving, throw away data from FIFO: Data loss! */
      mhFIFO = mtFIFO = 0; /* Head and tail in FIFO */            
      return;
    }
    
    /* Stop the timer */
    TMR_StopTimer(gUART_TimerID_c);
    
    cHead = mhFIFO;
    /* Copy all the data from the buffer */
    while ((cHead != mtFIFO) && (mcRx < mpRxIrp->reqData.rxtxParams.len)) {
		  
		  mpRxIrp->reqData.rxtxParams.pBuffer[mcRx++]= maFIFO[mtFIFO++];
		
		  if (mtFIFO == gUART_FIFOLen_c) {    									
		    mtFIFO = 0;
		  }
		} /* End while */
		  
		/* if the user buffer is full send a mRxSuccessEvent_c event */
    if ( mcRx == mpRxIrp->reqData.rxtxParams.len ) {
      TS_SendEvent(gUartTaskID_c, mRxSuccessEvent_c);
    } 
		else	{
		  /* Change the water mark */
		  if (( mpRxIrp->reqData.rxtxParams.len - mcRx ) < gUART_FIFOWaterMark_c) {
        mFIFOWaterMark	= mpRxIrp->reqData.rxtxParams.len - mcRx;
      }
			/* Restart the timer */
			TMR_StartTimer(gUART_TimerID_c, gUART_RxTimeout_c, UART_Timeout);
			/* Enable the Rx interrupt and enable the flow control */
			EnableFlow();
    }    
  }
  
/*--------------------------------------------------------------------------*/                           

  if (events & mRxSuccessEvent_c) {      
                   
    TMR_StopTimer(gUART_TimerID_c);
		/* Call the Callback function with gUartRxSuccess_c response */
    mpRxIrp->returnValue = gUartRxSuccess_c;     
    pIrp = mpRxIrp;
    mpRxIrp = NULL; /* No Rx IRP pending anymore */
    pIrp->reqData.rxtxParams.pfCallback( pIrp );    
  }
  
/*--------------------------------------------------------------------------*/                      

  if (events & mRxTimeoutEvent_c) {    

    /* Is the FIFO empty? */    
    if ( mhFIFO == mtFIFO ) {
      /* Yes, give the application whatever has already been received */
      DisableFlow();
      TMR_StopTimer(gUART_TimerID_c);
      /* Call the Callback function with gUartRxTimeout_c response
         and return the length */
      mpRxIrp->reqData.rxtxParams.len = mcRx;
      mpRxIrp->returnValue =  gUartRxTimeout_c; 
      pIrp = mpRxIrp;
      mpRxIrp = NULL; /* No Rx IRP pending anymore */
      pIrp->reqData.rxtxParams.pfCallback( pIrp );    
    }                                                  
    else {
                                      
      /* Empty the buffer */
      while (( mhFIFO != mtFIFO ) &&
             ( mcRx < mpRxIrp->reqData.rxtxParams.len )) {
			  
			  mpRxIrp->reqData.rxtxParams.pBuffer[mcRx++]= maFIFO[mtFIFO++];
			
			  if ( mtFIFO == gUART_FIFOLen_c ) {    									
          mtFIFO = 0;
			  }
			} /* End while */
                        									
		  /* If the user buffer is full send a mRxSuccessEvent_c event */
      if ( mcRx == mpRxIrp->reqData.rxtxParams.len ) {
        TS_SendEvent(gUartTaskID_c, mRxSuccessEvent_c);
        /* Disable the flow control */
        DisableFlow();  
      } 
      else {  				  
      	/* Restart the timer */
        TMR_StartTimer(gUART_TimerID_c, gUART_RxTimeout_c, UART_Timeout);
      }
    } /* End else */
  }
}

/*****************************************************************************
* Handles the application requests. Requests are submitted using Irp's (IO
* request packets). The Irp's can be allocated on the stack or on the heap,
* however, when the Irp contains a request of the types gRxUart_c or gTxUart_c
* the Irp must be allocated on the heap as the Irp is later returned to the
* application.
*
* Interface assumptions:
*   The parameters are placed on the heap for gTxUart_c and gRxUart_c requests.

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -