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

📄 ppc860sioscc.c

📁 powerPC866 系列平台BSP移植开发的参考代码
💻 C
📖 第 1 页 / 共 2 页
字号:

            if ((pChan->channelMode == SIO_MODE_POLL) && (arg == SIO_MODE_INT))
                {
		int i;

                for (i=0; i < pChan->uart.txBdNum; i++)
                    while (pChan->uart.txBdBase
                           [(pChan->uart.txBdNext + i) % pChan->uart.txBdNum].
                           statusMode & SCC_UART_TX_BD_READY);

                }

            if (arg == SIO_MODE_INT)
		{
                *CISR(pChan->regBase) = pChan->uart.intMask
                    ;   /* reset the SCC's interrupt status bit */

		*CIMR(pChan->regBase) |= pChan->uart.intMask
                    ;   /* enable this SCC's interrupt  */

		pChan->uart.pSccReg->scce = SCC_UART_SCCX_RX
                    ;   /* reset the receiver status bit */

                pChan->uart.pSccReg->sccm = SCC_UART_SCCX_RX | SCC_UART_SCCX_TX
                    ;   /* enables the receive and transmit interrupts */
		}
            else
		{
                pChan->uart.pSccReg->sccm = 0
                    ;   /* mask off the receive and transmit interrupts */

		*CIMR(pChan->regBase) &= (~(pChan->uart.intMask));
                    ;   /* mask off this SCC's interrupt */

                }

            pChan->channelMode = arg;

            intUnlock(oldlevel);

            break;

        case SIO_MODE_GET:
            *(int *)arg = pChan->channelMode;
            return (OK);

        case SIO_AVAIL_MODES_GET:
            *(int *)arg = SIO_MODE_INT | SIO_MODE_POLL;
            return (OK);

	default:
	    status = ENOSYS;
	}

    return (status);
    }

/*******************************************************************************
*
* ppc860SccInt - handle an SCC interrupt
*
* This routine gets called to handle SCC interrupts.
*/

void ppc860SccInt
    (
    PPC860SCC_CHAN *pChan
    )
    {
    char outChar;
    FAST UINT16 dataLen = 0;

    /* check for a receive event */

    if (pChan->uart.pSccReg->scce & SCC_UART_SCCX_RX)
	{
        pChan->uart.pSccReg->scce = SCC_UART_SCCX_RX;

	while (!(pChan->uart.rxBdBase[pChan->uart.rxBdNext].statusMode &
		 SCC_UART_RX_BD_EMPTY))
	    {
	    /* process all filled receive buffers */

	    outChar = pChan->uart.rxBdBase[pChan->uart.rxBdNext].dataPointer[0];

            pChan->uart.rxBdBase[pChan->uart.rxBdNext].statusMode |=
                SCC_UART_RX_BD_EMPTY;

            /* incr BD count */

            pChan->uart.rxBdNext = (pChan->uart.rxBdNext + 1) %
                                  pChan->uart.rxBdNum;

            /* acknowledge interrupt */

            pChan->uart.pSccReg->scce = SCC_UART_SCCX_RX;
            (*pChan->putRcvChar) (pChan->putRcvArg,outChar);

	    if (pChan->channelMode == SIO_MODE_POLL)
		break;
	    }
	}

    /* check for a transmit event and if a character needs to be output */

    if ( (pChan->uart.pSccReg->scce & SCC_UART_SCCX_TX) &&
         (pChan->channelMode != SIO_MODE_POLL) )
	{
        pChan->uart.pSccReg->scce = SCC_UART_SCCX_TX;

        if ((*pChan->getTxChar) (pChan->getTxArg, &outChar) == OK)
	    {
	    do
	        {
	        pChan->uart.txBdBase[pChan->uart.txBdNext].dataPointer[dataLen++]
		    = outChar;

                if (pChan->channelMode == SIO_MODE_POLL)
                    break;
	        }
	    while ((dataLen < pChan->uart.txBufSize) &&
                   ((*pChan->getTxChar) (pChan->getTxArg, &outChar)
		       == OK));

	    pChan->uart.txBdBase[pChan->uart.txBdNext].dataLength  = dataLen;

            /* acknowledge interrupt */

            pChan->uart.pSccReg->scce = SCC_UART_SCCX_TX;

	    /* send transmit buffer */

	    pChan->uart.txBdBase[pChan->uart.txBdNext].statusMode |=
	        SCC_UART_TX_BD_READY;


	    /* incr BD count */
 	    pChan->uart.txBdNext = (pChan->uart.txBdNext+ 1) % pChan->uart.txBdNum;
	    }
	}

    /* acknowledge all other interrupts - ignore events */

    pChan->uart.pSccReg->scce = (pChan->uart.pSccReg->scce & ~(SCC_UART_SCCX_RX |
                               SCC_UART_SCCX_TX));

    *CISR(pChan->regBase) = pChan->uart.intMask;
    }

/*******************************************************************************
*
* ppc860SccStartup - transmitter startup routine
*/

static void ppc860SccStartup
    (
    PPC860SCC_CHAN *pChan		/* ty device to start up */
    )
    {
    char outChar;
    FAST UINT16 dataLen = 0;

    if (pChan->channelMode == SIO_MODE_POLL)
	return;

    /* check if buffer is ready and if a character needs to be output */

    if ((!(pChan->uart.txBdBase[pChan->uart.txBdNext].statusMode &
	   SCC_UART_TX_BD_READY)) &&
        ((*pChan->getTxChar) (pChan->getTxArg, &outChar) == OK))
	{
	do
	    {
	    pChan->uart.txBdBase[pChan->uart.txBdNext].dataPointer[dataLen++] =
		outChar;
	    }
	while ((dataLen < pChan->uart.txBufSize) &&
               ((*pChan->getTxChar) (pChan->getTxArg, &outChar)
               == OK));	/* fill buffer */

	/* send transmit buffer */

	pChan->uart.txBdBase[pChan->uart.txBdNext].dataLength  = dataLen;
	pChan->uart.txBdBase[pChan->uart.txBdNext].statusMode |=
	    SCC_UART_TX_BD_READY;

	/* incr BD count */

        pChan->uart.txBdNext = (pChan->uart.txBdNext + 1) % pChan->uart.txBdNum;
	}
    }

/******************************************************************************
*
* ppc860SccPollInput - poll the device for input.
*
* RETURNS: OK if a character arrived, ERROR on device error, EAGAIN
*          if the input buffer is empty.
*/

static  int ppc860SccPollInput
    (
    SIO_CHAN *   pSioChan,
    char *      thisChar
    )
    {
    PPC860SCC_CHAN * pChan = (PPC860SCC_CHAN *)pSioChan;

    if ( !(pChan->uart.pSccReg->scce & SCC_UART_SCCX_RX) )
        return (EAGAIN);

    if (pChan->uart.rxBdBase[pChan->uart.rxBdNext].statusMode &
	 SCC_UART_RX_BD_EMPTY)
        return (EAGAIN);

    /* get a character */

    *thisChar = pChan->uart.rxBdBase[pChan->uart.rxBdNext].dataPointer[0];

    /* set the empty bit */

    pChan->uart.rxBdBase[pChan->uart.rxBdNext].statusMode |=
                SCC_UART_RX_BD_EMPTY;

    /* incr BD count */

    pChan->uart.rxBdNext = (pChan->uart.rxBdNext + 1) %
                                  pChan->uart.rxBdNum;

    /* only clear RX event if no more characters are ready */

    if (pChan->uart.rxBdBase[pChan->uart.rxBdNext].statusMode &
         SCC_UART_RX_BD_EMPTY)
        pChan->uart.pSccReg->scce = SCC_UART_SCCX_RX;

    return (OK);
    }

/******************************************************************************
*
* ppc860SccPollOutput - output a character in polled mode.
*
* RETURNS: OK if a character arrived, ERROR on device error, EAGAIN
*          if the output buffer if full.
*/

static int ppc860SccPollOutput
    (
    SIO_CHAN *   pSioChan,
    char        outChar
    )
    {
    PPC860SCC_CHAN * pChan = (PPC860SCC_CHAN *)pSioChan;

    /* is the transmitter ready to accept a character? */

    if (pChan->uart.txBdBase[pChan->uart.txBdNext].statusMode &
	SCC_UART_TX_BD_READY)
	return(EAGAIN);

    /* reset the transmitter status bit */

    pChan->uart.pSccReg->scce = SCC_UART_SCCX_TX;

    /* write out the character */

    pChan->uart.txBdBase[pChan->uart.txBdNext].dataPointer[0] = outChar;

    pChan->uart.txBdBase[pChan->uart.txBdNext].dataLength  = 1;

    /* send transmit buffer */

    pChan->uart.txBdBase[pChan->uart.txBdNext].statusMode |=
							SCC_UART_TX_BD_READY;

    pChan->uart.txBdNext = (pChan->uart.txBdNext + 1) % pChan->uart.txBdNum;

    return (OK);
    }
/******************************************************************************
*
* ppc860SccCallbackInstall - install ISR callbacks to get put chars.
*/

static int ppc860SccCallbackInstall
    (
    SIO_CHAN *  pSioChan,
    int         callbackType,
    STATUS      (*callback)(),
    void *      callbackArg
    )
    {
    PPC860SCC_CHAN * pChan = (PPC860SCC_CHAN *)pSioChan;

    switch (callbackType)
        {
        case SIO_CALLBACK_GET_TX_CHAR:
            pChan->getTxChar    = callback;
            pChan->getTxArg     = callbackArg;
            return (OK);
        case SIO_CALLBACK_PUT_RCV_CHAR:
            pChan->putRcvChar   = callback;
            pChan->putRcvArg    = callbackArg;
            return (OK);
        default:
            return (ENOSYS);
        }
    }

⌨️ 快捷键说明

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