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

📄 mxc_nb_uart.c

📁 i.mx31 3DS平台Nandboot引导程序源码
💻 C
字号:
/* * Copyright 2004-2006 Freescale Semiconductor, Inc. All Rights Reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA *//*! * @file mxc_nb_uart.c *  * @brief UART code required for SPL of NANDboot to send and receive data to  * terminal for user interaction.  * * @ingroup NANDboot */#include "mxc_nb_uart.h"#ifdef MXC91231#include "../ipl/mxc_setup_mxc91231.h"#endif#ifdef MXC91331#include "../ipl/mxc_setup_mxc91331.h"#endif#ifdef MXC91131#include "../ipl/mxc_setup_mxc91131.h"#endif#ifdef MX31#include "../ipl/mxc_setup_mx31.h"#endif#ifdef MX21#include "../ipl/mxc_setup_mx21.h"#endif/*! * This function configures MXC UART and its I/O pins. In order to use UART, * IOMUX configuration is required. This function configures IOMUX pins used by * UART to send and receive the data. UART is configured in polling mode.  The * transmitter FIFO is set to 2 characters and receiver to 1 characters. * * Refer to gpio.h in the respective MXC arch include directory for generating * the value of the IOMUX initialization constants for UART referred in this * function. */void mxcnb_uart_init(void){            volatile unsigned int *pMuxCtl, *pMuxComCtl;            volatile unsigned short *pPBCCtl;            volatile unsigned char dummy;            volatile int i = 0;          SETUP_IOMUX();	  *DEBUG_ADDR0 = 0xAA00AA00;#if  !(defined(MX31)||defined(MX21))            /* PBC setup */            pPBCCtl = (volatile unsigned short *)(PBC_BASE + 0x4);          /*Enable UART transceivers also reset the Ethernet/external UART */            pPBCCtl = (volatile unsigned short *)(PBC_BASE + 0x4);                    *pPBCCtl = 0x005F;            for (i = 0; i < 1000000; i++) {              }            pPBCCtl = (volatile unsigned short *)(PBC_BASE + 0x6);	   *pPBCCtl = 0x3;        /*clear reset the Ethernet */    	   for (i = 0; i < 100000; i++) {             }#endif                   /* config UART */#ifdef MX21	_reg_UCR2 = 0x61E6;	_reg_UCR1= 0x0;	_reg_UCR3 = 0x4;	_reg_UCR4 = 0x8000;	// configure appropriate pins for UART_1_RX, UART_1_TX, UART2_RX and UART2_TX			_reg_UCR1 = 0x0005; 		// UARTEN = 1,enable the clock	//UUCR2 = CTSC,TXEN,RXEN=1,reset, ignore IRTS bit, WS = 1 , 	//8 bit tx and rx,1 stop bit, disable parity		_reg_UCR2 = 0x6026;			_reg_UCR3 = 0x0004;				_reg_UCR4 = 0x8000;					// Set up reference freq divide for UART module 		// MX2 only support 16MHz output		// PerCLK1(31.99998691MHz)/UFCR[RFDIV] (2)= 15.99999673MHz		_reg_UFCR = 0x0A01; 				//clear loopback bit	_reg_UTS = 0x0000;	 _reg_UBIR = 837;	 _reg_UBMR = 9999;				// configure UBMR#else          _reg_UCR1 = 1;          /* Enable UART */          _reg_UCR2 = 0x4027;     /* CTS high, Ignore RTS, Word=8, RX/TX Enb */#ifdef MX31          _reg_UCR3 = 0x704;#endif          _reg_UFCR = UART_FIFO_CTRL;        /*          * The calculation:         *      (UMBR+1)/(UMIR+1) = RefFreq/(16*Baud)         * Where:         *      RefFreq = PerClock / UART_RFDIV         */         _reg_UBIR = MXC_UART_UBIR;         _reg_UBMR = MXC_UART_UBMR;#endif/* end of MX21*/}/*!  * This functions checks the Receive Data Ready bit in the UART Status  * Register USR2. Bit is set when data is received. * * @return      This function returns the RDR bit from the USR2 register  * of UART * */U8 mxcnb_uart_dataready(void){    mxcnb_wd_reset();    return _reg_USR2 & RDR_MASK;    /* check RDR bit */}/*! * This function gets data from UART. It is used to read character by  * character of the options and data received by the UART * * @result      It returns the character received by the UART * */     U8 mxcnb_uart_getdata(void){        /* wait until RDR bit set */        while (!mxcnb_uart_dataready()) {                /* Do nothing */                mxcnb_wd_reset();        }        return (U8)_reg_URXD;}/*! * This function sends data to UART. It waits for the transmit buffer to be  * empty by checking TXFE bit in UART status register . If buffer is empty it  * writes the character data into it. If carriage return character is found it  * will append line-feed character. * * @param       data            character data to send to UART * */void mxcnb_uart_putdata(U8 data){        /* wait until TXFE bit set */        while (!(_reg_USR2 & TXFE_MASK)) {                /* Do nothing */        }        /* write the data to the TX register */        _reg_UTXD = (U16)data;        /* if carriage return, append line-feed */        if (data == '\n')       {                /* wait until TXFE bit set */                while (!(_reg_USR2 & TXFE_MASK)) {                        /* Do nothing */                }                _reg_UTXD = '\r';        }}/*! * This function sends hex data to UART. It takes 32 bit integer data,  * converts it into ascii characters and sends it to UART. * * @param       hex_data                hex data to send to UART * */void mxcnb_uart_puthex(U32 hex_data){        U32  data;        int i;        for (i = 7; i >= 0; i--) {                        /*                  * Shift nibble at i+1 position to last position and                  * AND it with 0xF                  */                data = (hex_data >> 4*i)& 0xF;                if (data > 9) {                        data += 'A' - 0xa;   /* hex a to f to ascii 'A' to 'F' */                } else {                        data += '0';      /* hex 0 to 9 to ascii '0' to '9' */                }                mxcnb_uart_putdata(data);  /* send to UART */        }}/*! * This function sends a line of characters to UART. It calls  * \b mxcnb_uart_putdata() function to send each character of the line till it  * encounters the null character as the end of line. * * @param       line            pointer to string to be send to UART * */void mxcnb_uart_putstring(U8 *line){        while (*line) {                mxcnb_uart_putdata(*(line++));        }}/*! * This function gets a string data from UART. It reads character by character * using \b mxcnb_uart_getdata() function. It takes char pointer as a parameter * where the characters of the string are copied * * @param       str     pointer to string data received by UART * * @return      This function returns the size of the string read from UART. * */int mxcnb_uart_getstring(U8* str){        U8 ch;        int i = 0;      /* counter for size */        /*          * loop until carriage return is pressed or MAX_STRLEN has reached          */        do {                        /* wait for key press */                while (!mxcnb_uart_dataready()) {                        /* Do nothing */                }                /* read the character received by UART */                ch = mxcnb_uart_getdata();                /* check if not carriage return */                if (ch != '\r') {                        /* check if back space */                        if (ch == '\b') {                                if (i > 0) {                                        /* erase the character */                                        mxcnb_uart_putdata('\b');                                        mxcnb_uart_putdata(' ');                                        mxcnb_uart_putdata('\b');                                        str--;                                        *str = 0;                                        i--;                                }                        } else {                                mxcnb_uart_putdata(ch);                                *(str++) = ch;                                i++;                        }                }        } while ((ch != '\r') && (i < MAX_STRLEN - 1));         /* if and character is typed */        if (i > 0) {                *(str++) = 0;           /* mark end of string */        }        return i; /* Size of string */}/*! * This function reads hex data from UART and stores at the char pointer  * passed as a parameter. * * @param       str             pointer which points to ascii hex data * * @return  This function returns -1 if incorrect hex data is entered or the  * correct hex value entered. *  */int mxcnb_uart_gethex(U8 * str){        int size, i = 0;         U32 addr = 0;        U8 tmp;        /* get the ascii hex string from UART */        size = mxcnb_uart_getstring(str) - 1;        /* hex value cannot be greater than 4 bytes or 8 nibbles */        if (size <= 7 ) {                do {                                        tmp = 0;                        if (str[size - i] >= '0' && str[size - i] <= '9') {                                tmp = str[size - i] - '0';                        } else {                                if (str[size - i] >= (int)'a'                                                && str[size - i] <= (int)'f') {                                        tmp = (str[size - i] - 'a') + 0xa;                                } else {                                        if (str[size - i] >= (int)'A'                                                 && str[size - i] <= (int)'F') {                                                tmp = (str[size - i] - 'A') +                                                         0xa;                                        } else {                                                /* error if not ascii hex */                                                return -1;                                        }                                }                        }                        addr |= (tmp << (4 * i));                        i++;                } while ((size - i) >= 0);        } else {                return -1; /* error if more than 8 ascii hex */        }        return addr;}#if UNIT_TEST/*! * This function is used for unit test of UART functions. It will be included * in the code only if UNIT_TEST is enabled. */void mxcnb_uart_unit_test(void){        /* U8* str = "Enter data: "; */        U8* test_str = (U8*)DEBUG_ADDR3;        U32 hex;	*(DEBUG_ADDR0 + 1) = 0xAA11AA11;        /* to test 'mxcnb_uart_putdata' function */        mxcnb_uart_putdata('h');        mxcnb_uart_putdata('e');        mxcnb_uart_putdata('l');        mxcnb_uart_putdata('l');        mxcnb_uart_putdata('o');        mxcnb_uart_putdata('!');        mxcnb_uart_putdata('\n');        /* to test 'mxcnb_uart_putstring' function */        mxcnb_uart_putstring("\nEnter test data: ");                /* to test 'mxcnb_uart_getdata' and 'mxcnb_uart_getstring'*/        mxcnb_uart_getstring(test_str);        	*(DEBUG_ADDR0 + 2) = 0xAA22AA22;        /* reprint the string entered */        mxcnb_uart_putstring("\nYou entered: ");        mxcnb_uart_putstring(test_str);        /* to test 'mxcb_uart_gethex' and mxcb_uart_puthex' */        mxcnb_uart_putstring("\nEnter 4 bytes hex value: 0x");        hex = mxcnb_uart_gethex(test_str);        /* reprint the hex value entered */        if (hex != -1) {                mxcnb_uart_putstring("\n0x");                mxcnb_uart_puthex(hex);        }        else {                mxcnb_uart_putstring("\nIncorrect hex value");        }}#endif

⌨️ 快捷键说明

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