예제 #1
0
/******************************************************************************
 * @fn      aesDmaInit
 *
 * @brief   Initilize DMA for AES engine
 *
 * input parameters
 *
 * @param   None
 *
 * @return  None
 */
void aesDmaInit( void )
{
  halDMADesc_t *ch;

  /* Fill in DMA channel 1 descriptor and define it as input */
  ch = HAL_DMA_GET_DESC1234( HAL_DMA_AES_IN );
  HAL_DMA_SET_DEST( ch, HAL_AES_IN_ADDR );              /* Input of the AES module */
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );         /* Using the length field */
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_BYTE );   /* One byte is transferred each time */
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE );    /* A single byte is transferred each time */
  HAL_DMA_SET_TRIG_SRC( ch, HAL_DMA_TRIG_ENC_DW );      /* Setting the AES module to generate the DMA trigger */
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_1 );          /* The address for data fetch is incremented by 1 byte */
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_0 );          /* The destination address is constant */
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_DISABLE );       /* The DMA complete interrupt flag is not set at completion */
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );          /* Transferring all 8 bits in each byte */
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH );         /* DMA has priority */

  /* Fill in DMA channel 2 descriptor and define it as output */
  ch = HAL_DMA_GET_DESC1234( HAL_DMA_AES_OUT );
  HAL_DMA_SET_SOURCE( ch, HAL_AES_OUT_ADDR );           /* Start address of the segment */
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );         /* Using the length field */
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_BYTE );   /* One byte is transferred each time */
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE );    /* A single byte is transferred each time */
  HAL_DMA_SET_TRIG_SRC( ch, HAL_DMA_TRIG_ENC_UP );      /* Setting the AES module to generate the DMA trigger */
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_0 );          /* The address for data fetch is constant */
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_1 );          /* The destination address is incremented by 1 byte */
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_DISABLE );       /* The DMA complete interrupt flag is not set at completion */
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );          /* Transferring all 8 bits in each byte */
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH );         /* DMA has priority */
}
예제 #2
0
/**************************************************************************************************
 * @fn          HalFlashWrite
 *
 * @brief       This function writes 'cnt' bytes to the internal flash.
 *
 * input parameters
 *
 * @param       addr - Valid HAL flash write address: actual addr / 4 and quad-aligned.
 * @param       buf - Valid buffer space at least as big as 'cnt' X 4.
 * @param       cnt - Number of 4-byte blocks to write.
 *
 * output parameters
 *
 * None.
 *
 * @return      None.
 **************************************************************************************************
 */
void HalFlashWrite(uint16 addr, uint8 *buf, uint16 cnt)
{
  halDMADesc_t *ch = HAL_NV_DMA_GET_DESC();

  HAL_DMA_SET_SOURCE(ch, buf);
  HAL_DMA_SET_DEST(ch, &FWDATA);
  HAL_DMA_SET_VLEN(ch, HAL_DMA_VLEN_USE_LEN);
  HAL_DMA_SET_LEN(ch, (cnt * HAL_FLASH_WORD_SIZE));
  HAL_DMA_SET_WORD_SIZE(ch, HAL_DMA_WORDSIZE_BYTE);
  HAL_DMA_SET_TRIG_MODE(ch, HAL_DMA_TMODE_SINGLE);
  HAL_DMA_SET_TRIG_SRC(ch, HAL_DMA_TRIG_FLASH);
  HAL_DMA_SET_SRC_INC(ch, HAL_DMA_SRCINC_1);
  HAL_DMA_SET_DST_INC(ch, HAL_DMA_DSTINC_0);
  // The DMA is to be polled and shall not issue an IRQ upon completion.
  HAL_DMA_SET_IRQ(ch, HAL_DMA_IRQMASK_DISABLE);
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS);
  HAL_DMA_SET_PRIORITY(ch, HAL_DMA_PRI_HIGH);
  HAL_DMA_CLEAR_IRQ(HAL_NV_DMA_CH);
  HAL_DMA_ARM_CH(HAL_NV_DMA_CH);

  FADDRL = (uint8)addr;
  FADDRH = (uint8)(addr >> 8);
  FCTL |= 0x02;         // Trigger the DMA writes.
  while (FCTL & 0x80);  // Wait until writing is done.
}
예제 #3
0
/**************************************************************************************************
 * @fn          HalUARTInitSPI
 *
 * @brief       Initialize the SPI UART Transport.
 *
 * input parameters
 *
 * None.
 *
 * output parameters
 *
 * None.
 *
 * @return      None.
 */
static void HalUARTInitSPI(void)
{
#if (HAL_UART_SPI == 1)
  PERCFG &= ~HAL_UART_PERCFG_BIT;    /* Set UART0 I/O to Alt. 1 location on P0 */
#else
  PERCFG |= HAL_UART_PERCFG_BIT;     /* Set UART1 I/O to Alt. 2 location on P1 */
#endif
#if defined HAL_SPI_MASTER
  PxSEL |= HAL_UART_Px_SEL_M;        /* SPI-Master peripheral select */
  UxCSR = 0;                         /* Mode is SPI-Master Mode */
  UxGCR =  15;                       /* Cfg for the max Rx/Tx baud of 2-MHz */
  UxBAUD = 255;
#elif !defined HAL_SPI_MASTER
  PxSEL |= HAL_UART_Px_SEL_S;        /* SPI-Slave peripheral select */
  UxCSR = CSR_SLAVE;                 /* Mode is SPI-Slave Mode */
#endif
  UxUCR = UCR_FLUSH;                 /* Flush it */
  UxGCR |= BV(5);                    /* Set bit order to MSB */

  P2DIR &= ~P2DIR_PRIPO;
  P2DIR |= HAL_UART_PRIPO;

  /* Setup GPIO for interrupts by falling edge on SPI_RDY_IN */
  PxIEN |= SPI_RDYIn_BIT;
  PICTL |= PICTL_BIT;

  SPI_CLR_RDY_OUT();
  PxDIR |= SPI_RDYOut_BIT;

  /* Setup Tx by DMA */
  halDMADesc_t *ch = HAL_DMA_GET_DESC1234( HAL_SPI_CH_TX );
  
  /* Abort any pending DMA operations (in case of a soft reset) */
  HAL_DMA_ABORT_CH( HAL_SPI_CH_TX );

  /* The start address of the destination */
  HAL_DMA_SET_DEST( ch, DMA_UxDBUF );

  /* Using the length field to determine how many bytes to transfer */
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );

  /* One byte is transferred each time */
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_BYTE );

  /* The bytes are transferred 1-by-1 on Tx Complete trigger */
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE );
  HAL_DMA_SET_TRIG_SRC( ch, DMATRIG_TX );

  /* The source address is incremented by 1 byte after each transfer */
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_1 );
  HAL_DMA_SET_SOURCE( ch, spiTxPkt );

  /* The destination address is constant - the Tx Data Buffer */
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_0 );

  /* The DMA Tx done is serviced by ISR */
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_ENABLE );

  /* Xfer all 8 bits of a byte xfer */
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );

  /* DMA has highest priority for memory access */
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH );

  /* Setup Rx by DMA */
  ch = HAL_DMA_GET_DESC1234( HAL_SPI_CH_RX );
  
  /* Abort any pending DMA operations (in case of a soft reset) */
  HAL_DMA_ABORT_CH( HAL_SPI_CH_RX );

  /* The start address of the source */
  HAL_DMA_SET_SOURCE( ch, DMA_UxDBUF );

  /* Using the length field to determine how many bytes to transfer */
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );

  /* The trick is to cfg DMA to xfer 2 bytes for every 1 byte of Rx.
   * The byte after the Rx Data Buffer is the Baud Cfg Register,
   * which always has a known value. So init Rx buffer to inverse of that
   * known value. DMA word xfer will flip the bytes, so every valid Rx byte
   * in the Rx buffer will be preceded by a DMA_PAD char equal to the
   * Baud Cfg Register value.
   */
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_WORD );

  /* The bytes are transferred 1-by-1 on Rx Complete trigger */
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE_REPEATED );
  HAL_DMA_SET_TRIG_SRC( ch, DMATRIG_RX );

  /* The source address is constant - the Rx Data Buffer */
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_0 );

  /* The destination address is incremented by 1 word after each transfer */
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_1 );
  HAL_DMA_SET_DEST( ch, spiRxBuf );
  HAL_DMA_SET_LEN( ch, SPI_MAX_PKT_LEN );

  /* The DMA is to be polled and shall not issue an IRQ upon completion */
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_DISABLE );

  /* Xfer all 8 bits of a byte xfer */
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );

  /* DMA has highest priority for memory access */
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH );

  volatile uint8 dummy = *(volatile uint8 *)DMA_UxDBUF;  /* Clear the DMA Rx trigger */
  HAL_DMA_CLEAR_IRQ(HAL_SPI_CH_RX);
  HAL_DMA_ARM_CH(HAL_SPI_CH_RX);
  (void)memset(spiRxBuf, (DMA_PAD ^ 0xFF), SPI_MAX_PKT_LEN * sizeof(uint16));
}
예제 #4
0
/******************************************************************************
 * @fn      HalUARTInitDMA
 *
 * @brief   Initialize the UART
 *
 * @param   none
 *
 * @return  none
 *****************************************************************************/
static void HalUARTInitDMA(void)
{
  halDMADesc_t *ch;
#if (HAL_UART_DMA == 1)
  PERCFG &= ~HAL_UART_PERCFG_BIT;    // Set UART0 I/O to Alt. 1 location on P0.
#else
  PERCFG |= HAL_UART_PERCFG_BIT;     // Set UART1 I/O to Alt. 2 location on P1.
#endif
  PxSEL  |= HAL_UART_Px_SEL;         // Enable Peripheral control of Rx/Tx on Px.     p0.2 P0.3 set peripheral   //i0 setting
  UxCSR = CSR_MODE;                  // Mode is UART Mode.
  UxUCR = UCR_FLUSH;                 // Flush it.

  P2DIR &= ~P2DIR_PRIPO;                                                                                        //ÓÅÏȼ¶
  P2DIR |= HAL_UART_PRIPO;

  if (DMA_PM)
  {
    // Setup GPIO for interrupts by falling edge on DMA_RDY_IN.
    PxIEN |= DMA_RDYIn_BIT;
    PICTL |= PICTL_BIT;

    HAL_UART_DMA_CLR_RDY_OUT();
    PxDIR |= DMA_RDYOut_BIT;
  }

#if !HAL_UART_TX_BY_ISR
  // Setup Tx by DMA.
  ch = HAL_DMA_GET_DESC1234( HAL_DMA_CH_TX );

  // Abort any pending DMA operations (in case of a soft reset).
  HAL_DMA_ABORT_CH( HAL_DMA_CH_TX );

  // The start address of the destination.
  HAL_DMA_SET_DEST( ch, DMA_UxDBUF );

  // Using the length field to determine how many bytes to transfer.
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );

  // One byte is transferred each time.
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_BYTE );

  // The bytes are transferred 1-by-1 on Tx Complete trigger.
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE );
  HAL_DMA_SET_TRIG_SRC( ch, DMATRIG_TX );

  // The source address is incremented by 1 byte after each transfer.
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_1 );

  // The destination address is constant - the Tx Data Buffer.
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_0 );

  // The DMA Tx done is serviced by ISR in order to maintain full thruput.
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_ENABLE );

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );

  // DMA has highest priority for memory access.
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH);
#endif

  // Setup Rx by DMA.
  ch = HAL_DMA_GET_DESC1234( HAL_DMA_CH_RX );

  // Abort any pending DMA operations (in case of a soft reset).
  HAL_DMA_ABORT_CH( HAL_DMA_CH_RX );

  // The start address of the source.
  HAL_DMA_SET_SOURCE( ch, DMA_UxDBUF );

  // Using the length field to determine how many bytes to transfer.
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );

  /* The trick is to cfg DMA to xfer 2 bytes for every 1 byte of Rx.
   * The byte after the Rx Data Buffer is the Baud Cfg Register,
   * which always has a known value. So init Rx buffer to inverse of that
   * known value. DMA word xfer will flip the bytes, so every valid Rx byte
   * in the Rx buffer will be preceded by a DMA_PAD char equal to the
   * Baud Cfg Register value.
   */
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_WORD );

  // The bytes are transferred 1-by-1 on Rx Complete trigger.
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE_REPEATED );
  HAL_DMA_SET_TRIG_SRC( ch, DMATRIG_RX );

  // The source address is constant - the Rx Data Buffer.
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_0 );

  // The destination address is incremented by 1 word after each transfer.
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_1 );
  HAL_DMA_SET_DEST( ch, dmaCfg.rxBuf );
  HAL_DMA_SET_LEN( ch, HAL_UART_DMA_RX_MAX );

  // The DMA is to be polled and shall not issue an IRQ upon completion.
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_DISABLE );

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );

  // DMA has highest priority for memory access.
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH);

  volatile uint8 dummy = *(volatile uint8 *)DMA_UxDBUF;  // Clear the DMA Rx trigger.
  HAL_DMA_CLEAR_IRQ(HAL_DMA_CH_RX);
  HAL_DMA_ARM_CH(HAL_DMA_CH_RX);
  (void)memset(dmaCfg.rxBuf, (DMA_PAD ^ 0xFF), HAL_UART_DMA_RX_MAX * sizeof(uint16));
}
예제 #5
0
/**************************************************************************************************
 * @fn          DMAExecCrc
 *
 * @brief       This function assumes CRC has been initialized and sets up and
 *              starts a dma tranfer from a flash page to the CRC HW module.
 *
 * @note        This function assumes DMA channel 0 is available for use.
 *
 * input parameters
 *
 * @param       page - A valid flash page number.
 * @param       offset - A valid offset into the page.
 * @param       len - A valid number of bytes to calculate crc of.
 *
 * @return      None.
 **************************************************************************************************
 */
void DMAExecCrc(uint8 page, uint16 offset, uint16 len) {

  uint8 memctr = MEMCTR;  // Save to restore.
  
  // Calculate the offset into the containing flash bank as it gets mapped into XDATA.
  uint16 address = (offset + HAL_FLASH_PAGE_MAP) +
                   ((page % HAL_FLASH_PAGE_PER_BANK) * HAL_FLASH_PAGE_SIZE);

  // Pointer to DMA config structure
  halDMADesc_t *dmaCh0_p = &dmaCh0;
  
#if !defined HAL_OAD_BOOT_CODE
  halIntState_t is;
#endif

  page /= HAL_FLASH_PAGE_PER_BANK;  // Calculate the flash bank from the flash page.

#if !defined HAL_OAD_BOOT_CODE
  HAL_ENTER_CRITICAL_SECTION(is);
#endif
  
  // Calculate and map the containing flash bank into XDATA.
  MEMCTR = (MEMCTR & 0xF8) | page;  // page is actually bank
  
  // Start address for CRC calculation in the XDATA mapped flash bank
  HAL_DMA_SET_SOURCE(dmaCh0_p, address);
  
  // Destination for data transfer, RNDH mapped to XDATA
  HAL_DMA_SET_DEST(dmaCh0_p, 0x70BD);
  
  // One whole page (or len) at a time
  HAL_DMA_SET_LEN(dmaCh0_p, len);
  
  // 8-bit, block, no trigger
  HAL_DMA_SET_WORD_SIZE(dmaCh0_p, HAL_DMA_WORDSIZE_BYTE);
  HAL_DMA_SET_TRIG_MODE(dmaCh0_p, HAL_DMA_TMODE_BLOCK);
  HAL_DMA_SET_TRIG_SRC(dmaCh0_p, HAL_DMA_TRIG_NONE);
  
  // SRC += 1, DST = constant, no IRQ, all 8 bits, high priority
  HAL_DMA_SET_SRC_INC(dmaCh0_p, HAL_DMA_SRCINC_1);
  HAL_DMA_SET_DST_INC(dmaCh0_p, HAL_DMA_DSTINC_0);
  HAL_DMA_SET_IRQ(dmaCh0_p, HAL_DMA_IRQMASK_DISABLE);
  HAL_DMA_SET_M8(dmaCh0_p, HAL_DMA_M8_USE_8_BITS);
  HAL_DMA_SET_PRIORITY(dmaCh0_p, HAL_DMA_PRI_HIGH);
  
  // Tell DMA Controller where above configuration can be found
  HAL_DMA_SET_ADDR_DESC0(&dmaCh0);
  
  // Arm the DMA channel (0)
  HAL_DMA_ARM_CH(0);
  
  // 9 cycles wait
  asm("nop"); asm("nop"); asm("nop"); asm("nop"); asm("nop"); asm("nop");
  asm("nop"); asm("nop"); asm("nop"); asm("nop"); asm("nop");
  
  // Start DMA tranfer
  HAL_DMA_MAN_TRIGGER(0);
  
  // Wait for dma to finish.
  while(DMAREQ & 0x1);
  
  // Restore bank mapping
  MEMCTR = memctr;

#if !defined HAL_OAD_BOOT_CODE
  HAL_EXIT_CRITICAL_SECTION(is);
#endif
}
예제 #6
0
/**************************************************************************************************
 * @fn          HalSpiDmaInit
 *
 * @brief       This function initializes the DMA for the SPI driver.
 *
 * input parameters
 *
 * None.
 *
 * output parameters
 *
 * None.
 *
 * @return      None.
 **************************************************************************************************
 */
static void HalSpiDmaInit(void)
{
  halDMADesc_t *ch;

  // Setup Tx by DMA
  ch = HAL_DMA_GET_DESC1234(HAL_DMA_CH_TX);

  // The start address of the source and destination.
  HAL_DMA_SET_SOURCE(ch, halSpiBuf);
  HAL_DMA_SET_DEST(ch, DMA_UDBUF);

  // Transfer the first byte + the number of bytes indicated by the first byte + 2 more bytes.
  HAL_DMA_SET_VLEN(ch, HAL_DMA_VLEN_1_P_VALOFFIRST_P_2);
  HAL_DMA_SET_LEN(ch, HAL_SPI_BUF_LEN);

  // One byte is transferred each time.
  HAL_DMA_SET_WORD_SIZE(ch, HAL_DMA_WORDSIZE_BYTE);

  // The bytes are transferred 1-by-1 on Tx Complete trigger.
  HAL_DMA_SET_TRIG_MODE(ch, HAL_DMA_TMODE_SINGLE);
  HAL_DMA_SET_TRIG_SRC(ch, DMATRIG_TX);

  // The source address is incremented by 1 byte after each transfer.
  HAL_DMA_SET_SRC_INC(ch, HAL_DMA_SRCINC_1);

  // The destination address is constant - the Tx Data Buffer.
  HAL_DMA_SET_DST_INC(ch, HAL_DMA_DSTINC_0);

  // The DMA shall issue an IRQ upon completion.
  HAL_DMA_SET_IRQ(ch, HAL_DMA_IRQMASK_ENABLE);

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8(ch, HAL_DMA_M8_USE_8_BITS);

  // DMA has highest priority for memory access.
  HAL_DMA_SET_PRIORITY(ch, HAL_DMA_PRI_HIGH);

  //////////////////////////////////////////////////////////////////////////////

  // Setup Rx by DMA.
  ch = HAL_DMA_GET_DESC1234(HAL_DMA_CH_RX);

  // The start address of the source and destination.
  HAL_DMA_SET_SOURCE(ch, DMA_UDBUF);
  HAL_DMA_SET_DEST(ch, halSpiBuf);

  // Transfer the first byte + the number of bytes indicated by the first byte + 2 more bytes.
  HAL_DMA_SET_VLEN(ch, HAL_DMA_VLEN_1_P_VALOFFIRST_P_2);
  HAL_DMA_SET_LEN(ch, HAL_SPI_BUF_LEN);

  HAL_DMA_SET_WORD_SIZE(ch, HAL_DMA_WORDSIZE_BYTE);

  // The bytes are transferred 1-by-1 on Rx Complete trigger.
  HAL_DMA_SET_TRIG_MODE(ch, HAL_DMA_TMODE_SINGLE);
  HAL_DMA_SET_TRIG_SRC(ch, DMATRIG_RX);

  // The source address is constant - the Rx Data Buffer.
  HAL_DMA_SET_SRC_INC(ch, HAL_DMA_SRCINC_0);

  // The destination address is incremented by 1 byte after each transfer.
  HAL_DMA_SET_DST_INC(ch, HAL_DMA_DSTINC_1);

  // The DMA shall issue an IRQ upon completion.
  HAL_DMA_SET_IRQ(ch, HAL_DMA_IRQMASK_ENABLE);

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8(ch, HAL_DMA_M8_USE_8_BITS);

  // DMA has highest priority for memory access.
  HAL_DMA_SET_PRIORITY(ch, HAL_DMA_PRI_HIGH);
}
예제 #7
0
/******************************************************************************
 * @fn      HalUARTInitDMA
 *
 * @brief   Initialize the UART
 *
 * @param   none
 *
 * @return  none
 *****************************************************************************/
static void HalUARTInitDMA(void)
{
  halDMADesc_t *ch;

  P2DIR &= ~P2DIR_PRIPO;
  P2DIR |= HAL_UART_PRIPO;

#if (HAL_UART_DMA == 1)
  PERCFG &= ~HAL_UART_PERCFG_BIT;    // Set UART0 I/O to Alt. 1 location on P0.
#else
  PERCFG |= HAL_UART_PERCFG_BIT;     // Set UART1 I/O to Alt. 2 location on P1.
#endif
  PxSEL  |= HAL_UART_Px_RX_TX;       // Enable Tx and Rx on P1.
  ADCCFG &= ~HAL_UART_Px_RX_TX;      // Make sure ADC doesnt use this.
  UxCSR = CSR_MODE;                  // Mode is UART Mode.
  UxUCR = UCR_FLUSH;                 // Flush it.

  // Setup Tx by DMA.
  ch = HAL_DMA_GET_DESC1234( HAL_DMA_CH_TX );

  // The start address of the destination.
  HAL_DMA_SET_DEST( ch, DMA_UDBUF );

  // Using the length field to determine how many bytes to transfer.
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );

  // One byte is transferred each time.
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_BYTE );

  // The bytes are transferred 1-by-1 on Tx Complete trigger.
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE );
  HAL_DMA_SET_TRIG_SRC( ch, DMATRIG_TX );

  // The source address is incremented by 1 byte after each transfer.
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_1 );

  // The destination address is constant - the Tx Data Buffer.
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_0 );

  // The DMA Tx done is serviced by ISR in order to maintain full thruput.
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_ENABLE );

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );

  // DMA has highest priority for memory access.
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH );

  // Setup Rx by DMA.
  ch = HAL_DMA_GET_DESC1234( HAL_DMA_CH_RX );

  // The start address of the source.
  HAL_DMA_SET_SOURCE( ch, DMA_UDBUF );

  // Using the length field to determine how many bytes to transfer.
  HAL_DMA_SET_VLEN( ch, HAL_DMA_VLEN_USE_LEN );

  /* The trick is to cfg DMA to xfer 2 bytes for every 1 byte of Rx.
   * The byte after the Rx Data Buffer is the Baud Cfg Register,
   * which always has a known value. So init Rx buffer to inverse of that
   * known value. DMA word xfer will flip the bytes, so every valid Rx byte
   * in the Rx buffer will be preceded by a DMA_PAD char equal to the
   * Baud Cfg Register value.
   */
  HAL_DMA_SET_WORD_SIZE( ch, HAL_DMA_WORDSIZE_WORD );

  // The bytes are transferred 1-by-1 on Rx Complete trigger.
  HAL_DMA_SET_TRIG_MODE( ch, HAL_DMA_TMODE_SINGLE_REPEATED );
  HAL_DMA_SET_TRIG_SRC( ch, DMATRIG_RX );

  // The source address is constant - the Rx Data Buffer.
  HAL_DMA_SET_SRC_INC( ch, HAL_DMA_SRCINC_0 );

  // The destination address is incremented by 1 word after each transfer.
  HAL_DMA_SET_DST_INC( ch, HAL_DMA_DSTINC_1 );
  HAL_DMA_SET_DEST( ch, dmaCfg.rxBuf );
  HAL_DMA_SET_LEN( ch, HAL_UART_DMA_RX_MAX );

  // The DMA is to be polled and shall not issue an IRQ upon completion.
  HAL_DMA_SET_IRQ( ch, HAL_DMA_IRQMASK_DISABLE );

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8( ch, HAL_DMA_M8_USE_8_BITS );

  // DMA has highest priority for memory access.
  HAL_DMA_SET_PRIORITY( ch, HAL_DMA_PRI_HIGH );
}
/******************************************************************************
 * @fn      HalIrGenInitNec
 *
 * @brief   Initialize driver
 *
 * input parameters
 *
 * None.
 *
 * output parameters
 *
 * None.
 *
 * @return  None.
 *
 */
void HalIrGenInitNec(void)
{
  
  // Set TICKSPD:4M
  CLKCONCMD &= ~HAL_IRGEN_CLKCON_TICKSPD_MASK;
  CLKCONCMD |= HAL_IRGEN_TICKSPD_4MHZ;

  // Select port direction to output: P1.1 set output(1)
  P1DIR |= HAL_IRGEN_P1SEL_PORT;

  // Initially clear the port so that there will be no conflict
  P1 &= ~HAL_IRGEN_P1SEL_PORT;

  // Select port function to peripheral: P1.1 set Peripherial(1)
  P1SEL |= HAL_IRGEN_P1SEL_PORT;

  // Select alternative 2 location for T1 CH1 output (P1.1)
  PERCFG |= HAL_IRGEN_PERCFG_T1CFG;
  
  // -- set up bit signal generation timer --
  // -- run timer once to make sure output is deactivated
  
  // Halt timer 1:Suspended
  T1CTL = HAL_IRGEN_T1CTL_MODE_SUSPEND;
  
  // Set up timer 1 channel 0 to compare mode 4
  T1CCTL0 = HAL_IRGEN_TxCCTLx_CMP_CLR_SET | HAL_IRGEN_TxCCTLx_MODE_COMPARE;

  // Set up timer 1 channel 1 to compare mode 4
  T1CCTL1 = HAL_IRGEN_TxCCTLx_CMP_CLR_SET | HAL_IRGEN_TxCCTLx_MODE_COMPARE;

  // Run one timer 1 until output is pulled low. 
  // T1CNTL = 0; // Set up timer comparators for single carrier pulse output
  T1CC0L = 2;
  T1CC0H = 0;
  T1CC1L = 1;
  T1CC1H = 0;
  
  // Clear timer 1
  // this will activate the output pin so start timer immediately.
  T1CNTL = 0;
  
  // Start timer 1: Set Modulo Mode
  T1CTL = HAL_IRGEN_BIT_TIMING_PRESCALER_DIV1 | HAL_IRGEN_T1CTL_MODE_MODULO;
  
  // Wait till the single bit is cleared
  while (T1CNTL == 0);
  
   // Stop timer 1
  T1CTL = HAL_IRGEN_T1CTL_MODE_SUSPEND;

  
#ifdef HAL_IRGEN_CARRIER
   // -- set up carrier signal generation timer --
  // Clear counter and halt the timer
  T3CTL = HAL_IRGEN_T3CTL_CLR;
  
  // Set up timer 3 channel 0 to compare mode 4
  T3CCTL0 = HAL_IRGEN_TxCCTLx_CMP_CLR_SET | HAL_IRGEN_TxCCTLx_MODE_COMPARE;
  
  // Set up timer 3 channel 1 to compare mode 4
  T3CCTL1 = HAL_IRGEN_TxCCTLx_CMP_CLR_SET | HAL_IRGEN_TxCCTLx_MODE_COMPARE;
  
  // Configure 38kHz carrier with 33% duty cycle
  T3CC0 = HAL_IRGEN_NEC_CARRIER_DUTY_CYCLE;
  T3CC1 = HAL_IRGEN_NEC_CARRIER_ACTIVE_PER;

  // Combine carrier signal (Timer 1 CH 1 and Timer 3 CH 1 output)
  IRCTL |= 1;
#endif // HAL_IRGEN_CARRIER
  
  // -- Configure DMA --
  
  // Select proper DMA channel descriptor structure
  
  // Set up DMA channel for CC0
#if HAL_IRGEN_DMA_CH_CC0 == 0
  pDmaDescCc0 = HAL_DMA_GET_DESC0();
#else
  pDmaDescCc0 = HAL_DMA_GET_DESC1234(HAL_IRGEN_DMA_CH_CC0);
#endif
  
  // The start address of the destination.
  HAL_DMA_SET_DEST(pDmaDescCc0, HAL_IRGEN_T1CC0L_ADDR);

  // Using the length field to determine how many bytes to transfer.
  HAL_DMA_SET_VLEN(pDmaDescCc0, HAL_DMA_VLEN_USE_LEN);

  // Two bytes are transferred each time.
  HAL_DMA_SET_WORD_SIZE(pDmaDescCc0, HAL_DMA_WORDSIZE_WORD);

  // One word is transferred each time .
  HAL_DMA_SET_TRIG_MODE(pDmaDescCc0, HAL_DMA_TMODE_SINGLE);
  
  // Timer 1 channel 1 trigger DMA xfer
  HAL_DMA_SET_TRIG_SRC(pDmaDescCc0, HAL_DMA_TRIG_T1_CH1);

  // The source address is incremented by 1 word after each transfer.
  HAL_DMA_SET_SRC_INC(pDmaDescCc0, HAL_DMA_SRCINC_1);

  // The destination address is constant - T1CC0.
  HAL_DMA_SET_DST_INC(pDmaDescCc0, HAL_DMA_DSTINC_0);

  // IRQ handler is set up to tigger on CC1
  HAL_DMA_SET_IRQ(pDmaDescCc0, HAL_DMA_IRQMASK_DISABLE);

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8(pDmaDescCc0, HAL_DMA_M8_USE_8_BITS);

  // Set highest priority
  HAL_DMA_SET_PRIORITY(pDmaDescCc0, HAL_DMA_PRI_HIGH);
  
  // Set source data stream
  HAL_DMA_SET_SOURCE(pDmaDescCc0, &halIrGenCc0Buf[0]);
  
  // Set up DMA channel for CC1
#if HAL_IRGEN_DMA_CH_CC1 == 0
  pDmaDescCc1 = HAL_DMA_GET_DESC0();
#else
  pDmaDescCc1 = HAL_DMA_GET_DESC1234(HAL_IRGEN_DMA_CH_CC1);
#endif  

  // The start address of the destination.
  HAL_DMA_SET_DEST(pDmaDescCc1, HAL_IRGEN_T1CC1L_ADDR);

  // Using the length field to determine how many bytes to transfer.
  HAL_DMA_SET_VLEN(pDmaDescCc1, HAL_DMA_VLEN_USE_LEN);

  // Two bytes are transferred each time.
  HAL_DMA_SET_WORD_SIZE(pDmaDescCc1, HAL_DMA_WORDSIZE_WORD);

  // One word is transferred each time
  HAL_DMA_SET_TRIG_MODE( pDmaDescCc1, HAL_DMA_TMODE_SINGLE );
  
  //  Timer 1 channel 1 trigger
  HAL_DMA_SET_TRIG_SRC(pDmaDescCc1, HAL_DMA_TRIG_T1_CH1);

  // The source address is not incremented since active periode is constant.
  HAL_DMA_SET_SRC_INC(pDmaDescCc1, HAL_DMA_SRCINC_0);

  // The destination address is constant - T1CC1.
  HAL_DMA_SET_DST_INC(pDmaDescCc1, HAL_DMA_DSTINC_0);

  // IRQ handler is set up so that sleep enable/disable can be determined.
  HAL_DMA_SET_IRQ(pDmaDescCc1, HAL_DMA_IRQMASK_ENABLE);

  // Xfer all 8 bits of a byte xfer.
  HAL_DMA_SET_M8(pDmaDescCc1, HAL_DMA_M8_USE_8_BITS);

  // Set highest priority
  HAL_DMA_SET_PRIORITY(pDmaDescCc1, HAL_DMA_PRI_HIGH);
  
  // Set source data stream. It is always constant.
  HAL_DMA_SET_SOURCE(pDmaDescCc1, &halIrGenCc1);
 
  // Timer is not running
  halIrGenTimerRunning = FALSE;
}