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

📄 sdc.c

📁 S3C2410平台下蓝牙编程与实验
💻 C
📖 第 1 页 / 共 2 页
字号:
/*************************************************************************
*
*               Copyright Mentor Graphics Corporation 2003
*                         All Rights Reserved.
*
* THIS WORK CONTAINS TRADE SECRET AND PROPRIETARY INFORMATION WHICH IS
* THE PROPERTY OF MENTOR GRAPHICS CORPORATION OR ITS LICENSORS AND IS
* SUBJECT TO LICENSE TERMS.
*
*************************************************************************/
/*************************************************************************
*
* FILE NAME                                     VERSION
*
*  sdc.c                                Nucleus PLUS\S3C2410X\ADS
*
* DESCRIPTION
*
*  This file contains the Serial Driver specific functions.
*
* DATA STRUCTURES
*
*  SD_PORT *       :   An array of pointers to serial port structures.
*
* FUNCTIONS
*
*  SDC_Init_Port
*  SDC_Date_Ready
*  SDC_Put_String
*  SDC_LISR
*  SDC_Get_Char
*  SDC_Put_Char
*  SDC_Set_Baud_Rate
*
* DEPENDENCIES
*
*  nucleus.h
*  sd_defs.h
*  sd_extr.h
*   target.h
* protocol.h
*  externs.h
*      ppp.h
*
*************************************************************************/
#include "sd_defs.h"
#include "sd_extr.h"
#include "def.h"


/* Define a small array to hold pointers to the two UART data
   structures. This is used by the LISR to find the correct
   data structure for the interrupt being handled. */
SD_PORT         *SDC_Port_List[SD_MAX_UARTS];

/* Define prototypes for functions local to this module. */
static  VOID    SDC_Set_Baud_Rate(UNSIGNED, SD_PORT *);

/************** Begin Board Specific Section ****************/

/************** End Board Specific Section **************/

/****************************************************************************
* FUNCTION
*
*    SDC_Init_Port
*
* DESCRIPTION
*
*    This function intializes the COM port that will be used for PPP
*    communications.
*
* CALLED BY
*
*    Application
*
* CALLS
*
*    NU_Local_Control_Interrupts
*    SDC_Set_Baud_Rate
*
* INPUTS
*
*    SD_PORT *     :   device initialization structure.
*
* OUTPUTS
*
*    STATUS        :   Returns NU_SUCCESS if successful initialization,
*                      else a negative value is returned.
*
****************************************************************************/
STATUS  SDC_Init_Port(SD_PORT *uart)
{


    STATUS      status = NU_SUCCESS;
    UINT32      temp32;
    UINT32      mode;
    UINT32      submsk;
    static INT  num_ports = 0;

    if (uart->communication_mode == SERIAL_MODE)
    {
        /* Check for max allowed UARTS. */
        if (num_ports >= SD_MAX_UARTS)

           /* We have already initialized the max allowed UARTS. */
           status = NU_UART_LIST_FULL;
    }

    if (status == NU_SUCCESS)
    {
        /* Check the supplied parity */
        if ((uart->parity != SD_PARITY_NONE) &&
             (uart->parity != SD_PARITY_EVEN) &&
             (uart->parity != SD_PARITY_ODD))

        /* The supplied parity is not valid */
        status = NU_INVALID_PARITY;

        /* Check the supplied number of data bits */
        else if ((uart->data_bits != SD_DATA_BITS_5) &&
                 (uart->data_bits != SD_DATA_BITS_6) &&
                 (uart->data_bits != SD_DATA_BITS_7) &&
                 (uart->data_bits != SD_DATA_BITS_8))

            /* The supplied data bits value is not valid */
            status = NU_INVALID_DATA_BITS;

        /* Check the supplied number of stop bits */
        else if ((uart->stop_bits != SD_STOP_BITS_1) &&
                 (uart->stop_bits != SD_STOP_BITS_2))

            /* The supplied stop bits value is not valid */
            status = NU_INVALID_STOP_BITS;

        /* Verify the baud rate is within acceptable range */
        else if ((uart->baud_rate < 1200) || (uart->baud_rate > 115200))

            /* The baud rate is out of range */
            status = NU_INVALID_BAUD;

    /************** Begin Board Specific Section ****************/

        /* Validate the com port. */
        else if ((uart->com_port == SD_UART0) ||
                 (uart->com_port == SD_UART1) ||
                 (uart->com_port == SD_UART2))
        {
            /* Handle UART0 */
            if (uart->com_port == SD_UART0)
            {
                /* Set the vector inside this structure */
                uart->vector = SD_UART0_VECTOR;

                /* Set the base address for this UART. */
                uart->base_address = SD_UART0_BASE;
            }
            /* Handle UART1. */
            else if (uart->com_port == SD_UART1)
            {
                /* Set the vector inside this structure */
                uart->vector = SD_UART1_VECTOR;

                /* Set the base address for this UART. */
                uart->base_address = SD_UART1_BASE;
            }
            /* Handle UART2. */
            else
            {
                /* Set the vector inside this structure */
                uart->vector = SD_UART2_VECTOR;

                /* Set the base address for this UART. */
                uart->base_address = SD_UART2_BASE;
            }

        }
        else

        /************** End Board Specific Section **************/

            /* Not a supported port. */
            status = NU_INVALID_COM_PORT;
    }

    if (uart->communication_mode == SERIAL_MODE)
    {
         /* Make sure all the above was completed. Then store off this
           UART stucture and initialize the chip. */
        if (status == NU_SUCCESS)
        {
            SDC_Port_List[num_ports++] = uart;

        }
    }

    if (status == NU_SUCCESS)
    {
        /* Allocate memory for the data buffers. PPP only requires a TX
           buffer so the allocation will be a little different for PPP mode. */
        if (status == NU_SUCCESS)
        {
            /* Setup the RX SD buffer */
            uart->rx_buffer_read = uart->rx_buffer_write = 0;

            uart->rx_buffer_status = NU_BUFFER_EMPTY;

          }
    }


    if (status == NU_SUCCESS)
    {
        /* Disable interrupts */
//        int_level = NU_Local_Control_Interrupts(NU_DISABLE_INTERRUPTS);

        /************** Begin Board Specific Section *************/

        /* Clear Control registers */
        SD_OUTDWORD (uart->base_address + SD_ULCON_OFFSET, 0);
        SD_OUTDWORD (uart->base_address + SD_UCON_OFFSET, 0);
        SD_OUTDWORD (uart->base_address + SD_UFCON_OFFSET, 0x00000000);
        SD_OUTDWORD (uart->base_address + SD_UMCON_OFFSET, 0x00000000);

        /* Setup baud rate */
        SDC_Set_Baud_Rate(uart->baud_rate, uart);

        /* Setup Mode, Parity, Stop Bits and Data Size in ULCON Reg. */
        SD_OUTBYTE (uart->base_address + SD_ULCON_OFFSET,
            (uart->parity | uart->data_bits | uart->stop_bits));

        /* Enable Rx and Tx in UCON register. */
        SD_OUTWORD (uart->base_address + SD_UCON_OFFSET,
            (SD_UCON_RX_ENABLE | SD_UCON_RX_INT_LEVEL | SD_UCON_TX_INT_LEVEL|SD_UCON_TX_ENABLE));

        /* Get characters from receiver until Receive Ready bit not set */
        do
        {
            temp32 = SD_INDWORD(uart->base_address + SD_URXH_OFFSET);

        /* Keep looping until RX ready bit not set */
        } while (SD_INDWORD(uart->base_address + SD_UTRSTAT_OFFSET) & SD_USTAT_RX_RDY);

        /* Get current interrupt controller mask register value */
        temp32 = SD_INDWORD (SD_INT_BASE + SD_INT_MSK_OFFSET);

        /* Get current interrupt controller mode register value */
        mode = SD_INDWORD (SD_INT_BASE + SD_INT_MOD_OFFSET);

        /* Get current interrupt sub mask register value */
        submsk = SD_INDWORD (SD_INT_BASE + SD_INT_SUBMSK_OFFSET);

        /* Unmask / set mode in interrupt controller */
        if (uart->com_port == SD_UART0)
        {
            /* Unmask UART0 interrupts (mask and submask) */
            temp32 &= ~SD_INT_UART0;
            submsk &=( ~(SD_INT_RXD0)|SD_INT_TXD0);

            /* Ensure mode bits are cleared first */
            mode &= ~SD_INT_UART0;

            /* Set mode bits based on define in SD_DEFS.H */
            mode |= (SD_INT_UART0 * SD_UART0_INT_MODE);
        }
        else if (uart->com_port == SD_UART1)   /* Otherwise handle UART1. */
        {
            /* Unmask UART1 interrupts */
            temp32 &= ~SD_INT_UART1;
            submsk &= (~(SD_INT_RXD1 )|SD_INT_TXD1);

            /* Ensure mode bits are cleared first */
            mode &= ~SD_INT_UART1;

            /* Set mode bits based on define in SD_DEFS.H */
            mode |= (SD_INT_UART1 * SD_UART1_INT_MODE);
        }
        else /* Otherwise handle UART2. */
        {
            /* Unmask Console UART interrupts */
            temp32 &= ~SD_INT_UART2;
            submsk &= (~(SD_INT_RXD2 )|SD_INT_TXD2);

            /* Ensure mode bits are cleared first */
            mode &= ~SD_INT_UART2;

            /* Set mode bits based on define in SD_DEFS.H */
            mode |= (SD_INT_UART2 * SD_UART2_INT_MODE);
        }

        /* Write updated mask register value back to interrupt controller */
        SD_OUTDWORD (SD_INT_BASE + SD_INT_MSK_OFFSET, temp32);

        /* Write updated mode register value back to interrupt controller */
        SD_OUTDWORD (SD_INT_BASE + SD_INT_MOD_OFFSET, mode);

        /* Write updated interrupt sub mask register value */
        SD_OUTDWORD (SD_INT_BASE + SD_INT_SUBMSK_OFFSET, submsk);

        /************** End Board Specific Section *************/

        /* Initialize the error counters. */
        SDC_Reset(uart);

    }



    /* Return status of initialization */
    return (status);
}


/****************************************************************************
* FUNCTION
*
*    SDC_Put_Char
*
* DESCRIPTION
*
*    This writes a character out to the serial port.
*
* CALLED BY
*
*    UART_Put_String
*    Application
*
* CALLS
*
*    Serial port macros
*
* INPUTS
*
*    UNSIGNED_CHAR :   Character to to be written to the serial port.
*    SD_PORT *     :   Serial port to send the char to.
*
* OUTPUTS
*
*    none
*
****************************************************************************/
VOID  SDC_Put_Char(UINT8 ch, SD_PORT *uart)
{
 
     /* Transmit the character */
    volatile int  status;
      SD_OUTDWORD (uart->base_address + SD_UTXH_OFFSET, ch);
      status = SD_INDWORD(uart->base_address + SD_UTRSTAT_OFFSET);
      while(!(status&0x4))
      {
      status = SD_INDWORD(uart->base_address + SD_UTRSTAT_OFFSET);
      }


}

/****************************************************************************
* FUNCTION
*
*    SDC_LISR
*
* DESCRIPTION
*
*    This is the entry function for the ISR that services the UART.
*
* CALLED BY
*
*    none
*
* CALLS
*
*    Serial port macros
*
* INPUTS
*
*    INT         :   Interrupt vector
*
* OUTPUTS
*
*    none
*
****************************************************************************/
VOID SDC_LISR(INT vector)
{
    SD_PORT         *uart;
    CHAR            receive;
    UINT32          status;
    INT             vector_found = NU_FALSE;
	
    	
    for(receive = 0 ; (SDC_Port_List[receive] != 0) &&
        (receive < SD_MAX_UARTS) && !vector_found ; receive++)
    {
        /* See if we found one. Better have since we got an interrupt
           from one. */
        if (SDC_Port_List[receive] -> vector == vector)
        {
            /* Point our local structure to it. */
            uart = SDC_Port_List[receive];
            vector_found =TRUE;
        }
    }

    /* Ensure vector was found */
    if (vector_found == TRUE)
    {
        /**************** Begin Board Specific Section **************/

        /* Get the uart status */
        status = SD_INDWORD(uart->base_address + SD_UTRSTAT_OFFSET);

        /* Check if receiver is ready - characters received */
        if (status & SD_USTAT_RX_RDY)
        {
            /* Get UART error status */
            status = SD_INDWORD (uart->base_address + SD_UERSTAT_OFFSET);

            /* Process every character in the receive FIFO */
            do
            {
                /* Clear any error bits */
                SD_OUTDWORD(uart->base_address + SD_UERSTAT_OFFSET,status);

                /* Get the received character from the receive holding register */
                receive = (UINT8)SD_INDWORD(uart->base_address + SD_URXH_OFFSET);

⌨️ 快捷键说明

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