NXP's driver library for LPC17xx, ported to mbed's online compiler. Not tested! I had to fix a lot of warings and found a couple of pretty obvious bugs, so the chances are there are more. Original: http://ics.nxp.com/support/documents/microcontrollers/zip/lpc17xx.cmsis.driver.library.zip

Dependencies:   mbed

Committer:
igorsk
Date:
Wed Feb 17 16:22:39 2010 +0000
Revision:
0:1063a091a062

        

Who changed what in which revision?

UserRevisionLine numberNew contents of line
igorsk 0:1063a091a062 1 /**
igorsk 0:1063a091a062 2 * @file : lpc17xx_ssp.c
igorsk 0:1063a091a062 3 * @brief : Contains all functions support for SSP firmware library on LPC17xx
igorsk 0:1063a091a062 4 * @version : 1.0
igorsk 0:1063a091a062 5 * @date : 9. April. 2009
igorsk 0:1063a091a062 6 * @author : HieuNguyen
igorsk 0:1063a091a062 7 **************************************************************************
igorsk 0:1063a091a062 8 * Software that is described herein is for illustrative purposes only
igorsk 0:1063a091a062 9 * which provides customers with programming information regarding the
igorsk 0:1063a091a062 10 * products. This software is supplied "AS IS" without any warranties.
igorsk 0:1063a091a062 11 * NXP Semiconductors assumes no responsibility or liability for the
igorsk 0:1063a091a062 12 * use of the software, conveys no license or title under any patent,
igorsk 0:1063a091a062 13 * copyright, or mask work right to the product. NXP Semiconductors
igorsk 0:1063a091a062 14 * reserves the right to make changes in the software without
igorsk 0:1063a091a062 15 * notification. NXP Semiconductors also make no representation or
igorsk 0:1063a091a062 16 * warranty that such application will be suitable for the specified
igorsk 0:1063a091a062 17 * use without further testing or modification.
igorsk 0:1063a091a062 18 **********************************************************************/
igorsk 0:1063a091a062 19
igorsk 0:1063a091a062 20 /* Peripheral group ----------------------------------------------------------- */
igorsk 0:1063a091a062 21 /** @addtogroup SSP
igorsk 0:1063a091a062 22 * @{
igorsk 0:1063a091a062 23 */
igorsk 0:1063a091a062 24
igorsk 0:1063a091a062 25 /* Includes ------------------------------------------------------------------- */
igorsk 0:1063a091a062 26 #include "lpc17xx_ssp.h"
igorsk 0:1063a091a062 27 #include "lpc17xx_clkpwr.h"
igorsk 0:1063a091a062 28
igorsk 0:1063a091a062 29
igorsk 0:1063a091a062 30 /* If this source file built with example, the LPC17xx FW library configuration
igorsk 0:1063a091a062 31 * file in each example directory ("lpc17xx_libcfg.h") must be included,
igorsk 0:1063a091a062 32 * otherwise the default FW library configuration file must be included instead
igorsk 0:1063a091a062 33 */
igorsk 0:1063a091a062 34 #ifdef __BUILD_WITH_EXAMPLE__
igorsk 0:1063a091a062 35 #include "lpc17xx_libcfg.h"
igorsk 0:1063a091a062 36 #else
igorsk 0:1063a091a062 37 #include "lpc17xx_libcfg_default.h"
igorsk 0:1063a091a062 38 #endif /* __BUILD_WITH_EXAMPLE__ */
igorsk 0:1063a091a062 39
igorsk 0:1063a091a062 40
igorsk 0:1063a091a062 41 #ifdef _SSP
igorsk 0:1063a091a062 42
igorsk 0:1063a091a062 43 /* Private Types -------------------------------------------------------------- */
igorsk 0:1063a091a062 44 /** @defgroup SSP_Private_Types
igorsk 0:1063a091a062 45 * @{
igorsk 0:1063a091a062 46 */
igorsk 0:1063a091a062 47
igorsk 0:1063a091a062 48 /** @brief SSP device configuration structure type */
igorsk 0:1063a091a062 49 typedef struct
igorsk 0:1063a091a062 50 {
igorsk 0:1063a091a062 51 int32_t dataword; /* Current data word: 0 - 8 bit; 1 - 16 bit */
igorsk 0:1063a091a062 52 uint32_t txrx_setup; /* Transmission setup */
igorsk 0:1063a091a062 53 void (*inthandler)(LPC_SSP_TypeDef *SSPx); /* Transmission interrupt handler */
igorsk 0:1063a091a062 54 } SSP_CFG_T;
igorsk 0:1063a091a062 55
igorsk 0:1063a091a062 56 /**
igorsk 0:1063a091a062 57 * @}
igorsk 0:1063a091a062 58 */
igorsk 0:1063a091a062 59
igorsk 0:1063a091a062 60 /* Private Variables ---------------------------------------------------------- */
igorsk 0:1063a091a062 61 /* SSP configuration data */
igorsk 0:1063a091a062 62 static SSP_CFG_T sspdat[2];
igorsk 0:1063a091a062 63
igorsk 0:1063a091a062 64
igorsk 0:1063a091a062 65 /* Private Functions ---------------------------------------------------------- */
igorsk 0:1063a091a062 66 /** @defgroup SSP_Private_Functions
igorsk 0:1063a091a062 67 * @{
igorsk 0:1063a091a062 68 */
igorsk 0:1063a091a062 69
igorsk 0:1063a091a062 70 /**
igorsk 0:1063a091a062 71 * @brief Convert from SSP peripheral to number
igorsk 0:1063a091a062 72 */
igorsk 0:1063a091a062 73 static int32_t SSP_getNum(LPC_SSP_TypeDef *SSPx){
igorsk 0:1063a091a062 74 if (SSPx == LPC_SSP0) {
igorsk 0:1063a091a062 75 return (0);
igorsk 0:1063a091a062 76 } else if (SSPx == LPC_SSP1) {
igorsk 0:1063a091a062 77 return (1);
igorsk 0:1063a091a062 78 }
igorsk 0:1063a091a062 79 return (-1);
igorsk 0:1063a091a062 80 }
igorsk 0:1063a091a062 81
igorsk 0:1063a091a062 82
igorsk 0:1063a091a062 83 /*********************************************************************//**
igorsk 0:1063a091a062 84 * @brief Standard Private SSP Interrupt handler
igorsk 0:1063a091a062 85 * @param SSPx: SSP peripheral definition, should be
igorsk 0:1063a091a062 86 * SSP0 or SSP1.
igorsk 0:1063a091a062 87 * @return None
igorsk 0:1063a091a062 88 ***********************************************************************/
igorsk 0:1063a091a062 89 void SSP_IntHandler(LPC_SSP_TypeDef *SSPx)
igorsk 0:1063a091a062 90 {
igorsk 0:1063a091a062 91 SSP_DATA_SETUP_Type *xf_setup;
igorsk 0:1063a091a062 92 uint16_t tmp;
igorsk 0:1063a091a062 93 int32_t sspnum;
igorsk 0:1063a091a062 94
igorsk 0:1063a091a062 95 // Disable interrupt
igorsk 0:1063a091a062 96 SSPx->IMSC = 0;
igorsk 0:1063a091a062 97
igorsk 0:1063a091a062 98 sspnum = SSP_getNum(SSPx);
igorsk 0:1063a091a062 99 xf_setup = (SSP_DATA_SETUP_Type *)sspdat[sspnum].txrx_setup;
igorsk 0:1063a091a062 100
igorsk 0:1063a091a062 101 // save status
igorsk 0:1063a091a062 102 tmp = SSPx->RIS;
igorsk 0:1063a091a062 103 xf_setup->status = tmp;
igorsk 0:1063a091a062 104
igorsk 0:1063a091a062 105 // Check overrun error
igorsk 0:1063a091a062 106 if (tmp & SSP_RIS_ROR){
igorsk 0:1063a091a062 107 // Clear interrupt
igorsk 0:1063a091a062 108 SSPx->ICR = SSP_RIS_ROR;
igorsk 0:1063a091a062 109 // update status
igorsk 0:1063a091a062 110 xf_setup->status |= SSP_STAT_ERROR;
igorsk 0:1063a091a062 111 // Callback
igorsk 0:1063a091a062 112 if (xf_setup->callback != NULL){
igorsk 0:1063a091a062 113 xf_setup->callback();
igorsk 0:1063a091a062 114 }
igorsk 0:1063a091a062 115 return;
igorsk 0:1063a091a062 116 }
igorsk 0:1063a091a062 117
igorsk 0:1063a091a062 118 if ((xf_setup->tx_cnt != xf_setup->length) || (xf_setup->rx_cnt != xf_setup->length)){
igorsk 0:1063a091a062 119 /* check if RX FIFO contains data */
igorsk 0:1063a091a062 120 while ((SSPx->SR & SSP_SR_RNE) && (xf_setup->rx_cnt != xf_setup->length)){
igorsk 0:1063a091a062 121 // Read data from SSP data
igorsk 0:1063a091a062 122 tmp = SSP_ReceiveData(SSPx);
igorsk 0:1063a091a062 123
igorsk 0:1063a091a062 124 // Store data to destination
igorsk 0:1063a091a062 125 if (xf_setup->rx_data != NULL)
igorsk 0:1063a091a062 126 {
igorsk 0:1063a091a062 127 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 128 *(uint8_t *)((uint32_t)xf_setup->rx_data + xf_setup->rx_cnt) = (uint8_t) tmp;
igorsk 0:1063a091a062 129 } else {
igorsk 0:1063a091a062 130 *(uint16_t *)((uint32_t)xf_setup->rx_data + xf_setup->rx_cnt) = (uint16_t) tmp;
igorsk 0:1063a091a062 131 }
igorsk 0:1063a091a062 132 }
igorsk 0:1063a091a062 133 // Increase counter
igorsk 0:1063a091a062 134 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 135 xf_setup->rx_cnt++;
igorsk 0:1063a091a062 136 } else {
igorsk 0:1063a091a062 137 xf_setup->rx_cnt += 2;
igorsk 0:1063a091a062 138 }
igorsk 0:1063a091a062 139 }
igorsk 0:1063a091a062 140
igorsk 0:1063a091a062 141 while ((SSPx->SR & SSP_SR_TNF) && (xf_setup->tx_cnt != xf_setup->length)){
igorsk 0:1063a091a062 142 // Write data to buffer
igorsk 0:1063a091a062 143 if(xf_setup->tx_data == NULL){
igorsk 0:1063a091a062 144 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 145 SSP_SendData(SSPx, 0xFF);
igorsk 0:1063a091a062 146 xf_setup->tx_cnt++;
igorsk 0:1063a091a062 147 } else {
igorsk 0:1063a091a062 148 SSP_SendData(SSPx, 0xFFFF);
igorsk 0:1063a091a062 149 xf_setup->tx_cnt += 2;
igorsk 0:1063a091a062 150 }
igorsk 0:1063a091a062 151 } else {
igorsk 0:1063a091a062 152 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 153 SSP_SendData(SSPx, (*(uint8_t *)((uint32_t)xf_setup->tx_data + xf_setup->tx_cnt)));
igorsk 0:1063a091a062 154 xf_setup->tx_cnt++;
igorsk 0:1063a091a062 155 } else {
igorsk 0:1063a091a062 156 SSP_SendData(SSPx, (*(uint16_t *)((uint32_t)xf_setup->tx_data + xf_setup->tx_cnt)));
igorsk 0:1063a091a062 157 xf_setup->tx_cnt += 2;
igorsk 0:1063a091a062 158 }
igorsk 0:1063a091a062 159 }
igorsk 0:1063a091a062 160
igorsk 0:1063a091a062 161 // Check overrun error
igorsk 0:1063a091a062 162 if ((tmp = SSPx->RIS) & SSP_RIS_ROR){
igorsk 0:1063a091a062 163 // update status
igorsk 0:1063a091a062 164 xf_setup->status |= SSP_STAT_ERROR;
igorsk 0:1063a091a062 165 // Callback
igorsk 0:1063a091a062 166 if (xf_setup->callback != NULL){
igorsk 0:1063a091a062 167 xf_setup->callback();
igorsk 0:1063a091a062 168 }
igorsk 0:1063a091a062 169 return;
igorsk 0:1063a091a062 170 }
igorsk 0:1063a091a062 171
igorsk 0:1063a091a062 172 // Check for any data available in RX FIFO
igorsk 0:1063a091a062 173 while ((SSPx->SR & SSP_SR_RNE) && (xf_setup->rx_cnt != xf_setup->length)){
igorsk 0:1063a091a062 174 // Read data from SSP data
igorsk 0:1063a091a062 175 tmp = SSP_ReceiveData(SSPx);
igorsk 0:1063a091a062 176
igorsk 0:1063a091a062 177 // Store data to destination
igorsk 0:1063a091a062 178 if (xf_setup->rx_data != NULL)
igorsk 0:1063a091a062 179 {
igorsk 0:1063a091a062 180 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 181 *(uint8_t *)((uint32_t)xf_setup->rx_data + xf_setup->rx_cnt) = (uint8_t) tmp;
igorsk 0:1063a091a062 182 } else {
igorsk 0:1063a091a062 183 *(uint16_t *)((uint32_t)xf_setup->rx_data + xf_setup->rx_cnt) = (uint16_t) tmp;
igorsk 0:1063a091a062 184 }
igorsk 0:1063a091a062 185 }
igorsk 0:1063a091a062 186 // Increase counter
igorsk 0:1063a091a062 187 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 188 xf_setup->rx_cnt++;
igorsk 0:1063a091a062 189 } else {
igorsk 0:1063a091a062 190 xf_setup->rx_cnt += 2;
igorsk 0:1063a091a062 191 }
igorsk 0:1063a091a062 192 }
igorsk 0:1063a091a062 193 }
igorsk 0:1063a091a062 194 }
igorsk 0:1063a091a062 195
igorsk 0:1063a091a062 196 // If there more data to sent or receive
igorsk 0:1063a091a062 197 if ((xf_setup->rx_cnt != xf_setup->length) || (xf_setup->tx_cnt != xf_setup->length)){
igorsk 0:1063a091a062 198 // Enable all interrupt
igorsk 0:1063a091a062 199 SSPx->IMSC = SSP_IMSC_BITMASK;
igorsk 0:1063a091a062 200 } else {
igorsk 0:1063a091a062 201 // Save status
igorsk 0:1063a091a062 202 xf_setup->status = SSP_STAT_DONE;
igorsk 0:1063a091a062 203 // Callback
igorsk 0:1063a091a062 204 if (xf_setup->callback != NULL){
igorsk 0:1063a091a062 205 xf_setup->callback();
igorsk 0:1063a091a062 206 }
igorsk 0:1063a091a062 207 }
igorsk 0:1063a091a062 208 }
igorsk 0:1063a091a062 209
igorsk 0:1063a091a062 210 /**
igorsk 0:1063a091a062 211 * @}
igorsk 0:1063a091a062 212 */
igorsk 0:1063a091a062 213
igorsk 0:1063a091a062 214
igorsk 0:1063a091a062 215 /* Public Functions ----------------------------------------------------------- */
igorsk 0:1063a091a062 216 /** @addtogroup SSP_Public_Functions
igorsk 0:1063a091a062 217 * @{
igorsk 0:1063a091a062 218 */
igorsk 0:1063a091a062 219
igorsk 0:1063a091a062 220 /*********************************************************************//**
igorsk 0:1063a091a062 221 * @brief Setup clock rate for SSP device
igorsk 0:1063a091a062 222 * @param[in] SSPx SSP peripheral definition, should be
igorsk 0:1063a091a062 223 * SSP0 or SSP1.
igorsk 0:1063a091a062 224 * @param[in] target_clock : clock of SSP (Hz)
igorsk 0:1063a091a062 225 * @return None
igorsk 0:1063a091a062 226 ***********************************************************************/
igorsk 0:1063a091a062 227 void SSP_SetClock (LPC_SSP_TypeDef *SSPx, uint32_t target_clock)
igorsk 0:1063a091a062 228 {
igorsk 0:1063a091a062 229 uint32_t prescale, cr0_div, cmp_clk, ssp_clk;
igorsk 0:1063a091a062 230
igorsk 0:1063a091a062 231 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 232
igorsk 0:1063a091a062 233 /* The SSP clock is derived from the (main system oscillator / 2),
igorsk 0:1063a091a062 234 so compute the best divider from that clock */
igorsk 0:1063a091a062 235 if (SSPx == LPC_SSP0){
igorsk 0:1063a091a062 236 ssp_clk = CLKPWR_GetPCLK (CLKPWR_PCLKSEL_SSP0);
igorsk 0:1063a091a062 237 } else if (SSPx == LPC_SSP1) {
igorsk 0:1063a091a062 238 ssp_clk = CLKPWR_GetPCLK (CLKPWR_PCLKSEL_SSP1);
igorsk 0:1063a091a062 239 } else {
igorsk 0:1063a091a062 240 return;
igorsk 0:1063a091a062 241 }
igorsk 0:1063a091a062 242
igorsk 0:1063a091a062 243 /* Find closest divider to get at or under the target frequency.
igorsk 0:1063a091a062 244 Use smallest prescale possible and rely on the divider to get
igorsk 0:1063a091a062 245 the closest target frequency */
igorsk 0:1063a091a062 246 cr0_div = 0;
igorsk 0:1063a091a062 247 cmp_clk = 0xFFFFFFFF;
igorsk 0:1063a091a062 248 prescale = 2;
igorsk 0:1063a091a062 249 while (cmp_clk > target_clock)
igorsk 0:1063a091a062 250 {
igorsk 0:1063a091a062 251 cmp_clk = ssp_clk / ((cr0_div + 1) * prescale);
igorsk 0:1063a091a062 252 if (cmp_clk > target_clock)
igorsk 0:1063a091a062 253 {
igorsk 0:1063a091a062 254 cr0_div++;
igorsk 0:1063a091a062 255 if (cr0_div > 0xFF)
igorsk 0:1063a091a062 256 {
igorsk 0:1063a091a062 257 cr0_div = 0;
igorsk 0:1063a091a062 258 prescale += 2;
igorsk 0:1063a091a062 259 }
igorsk 0:1063a091a062 260 }
igorsk 0:1063a091a062 261 }
igorsk 0:1063a091a062 262
igorsk 0:1063a091a062 263 /* Write computed prescaler and divider back to register */
igorsk 0:1063a091a062 264 SSPx->CR0 &= (~SSP_CR0_SCR(0xFF)) & SSP_CR0_BITMASK;
igorsk 0:1063a091a062 265 SSPx->CR0 |= (SSP_CR0_SCR(cr0_div)) & SSP_CR0_BITMASK;
igorsk 0:1063a091a062 266 SSPx->CPSR = prescale & SSP_CPSR_BITMASK;
igorsk 0:1063a091a062 267 }
igorsk 0:1063a091a062 268
igorsk 0:1063a091a062 269
igorsk 0:1063a091a062 270 /*********************************************************************//**
igorsk 0:1063a091a062 271 * @brief De-initializes the SSPx peripheral registers to their
igorsk 0:1063a091a062 272 * default reset values.
igorsk 0:1063a091a062 273 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 274 * @return None
igorsk 0:1063a091a062 275 **********************************************************************/
igorsk 0:1063a091a062 276 void SSP_DeInit(LPC_SSP_TypeDef* SSPx)
igorsk 0:1063a091a062 277 {
igorsk 0:1063a091a062 278 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 279
igorsk 0:1063a091a062 280 if (SSPx == LPC_SSP0){
igorsk 0:1063a091a062 281 /* Set up clock and power for SSP0 module */
igorsk 0:1063a091a062 282 CLKPWR_ConfigPPWR (CLKPWR_PCONP_PCSSP0, DISABLE);
igorsk 0:1063a091a062 283 } else if (SSPx == LPC_SSP1) {
igorsk 0:1063a091a062 284 /* Set up clock and power for SSP1 module */
igorsk 0:1063a091a062 285 CLKPWR_ConfigPPWR (CLKPWR_PCONP_PCSSP1, DISABLE);
igorsk 0:1063a091a062 286 }
igorsk 0:1063a091a062 287 }
igorsk 0:1063a091a062 288
igorsk 0:1063a091a062 289
igorsk 0:1063a091a062 290
igorsk 0:1063a091a062 291 /********************************************************************//**
igorsk 0:1063a091a062 292 * @brief Initializes the SSPx peripheral according to the specified
igorsk 0:1063a091a062 293 * parameters in the SSP_ConfigStruct.
igorsk 0:1063a091a062 294 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 295 * @param[in] SSP_ConfigStruct Pointer to a SSP_CFG_Type structure
igorsk 0:1063a091a062 296 * that contains the configuration information for the
igorsk 0:1063a091a062 297 * specified SSP peripheral.
igorsk 0:1063a091a062 298 * @return None
igorsk 0:1063a091a062 299 *********************************************************************/
igorsk 0:1063a091a062 300 void SSP_Init(LPC_SSP_TypeDef *SSPx, SSP_CFG_Type *SSP_ConfigStruct)
igorsk 0:1063a091a062 301 {
igorsk 0:1063a091a062 302 uint32_t tmp;
igorsk 0:1063a091a062 303
igorsk 0:1063a091a062 304 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 305
igorsk 0:1063a091a062 306 if(SSPx == LPC_SSP0) {
igorsk 0:1063a091a062 307 /* Set up clock and power for SSP0 module */
igorsk 0:1063a091a062 308 CLKPWR_ConfigPPWR (CLKPWR_PCONP_PCSSP0, ENABLE);
igorsk 0:1063a091a062 309 } else if(SSPx == LPC_SSP1) {
igorsk 0:1063a091a062 310 /* Set up clock and power for SSP1 module */
igorsk 0:1063a091a062 311 CLKPWR_ConfigPPWR (CLKPWR_PCONP_PCSSP1, ENABLE);
igorsk 0:1063a091a062 312 } else {
igorsk 0:1063a091a062 313 return;
igorsk 0:1063a091a062 314 }
igorsk 0:1063a091a062 315
igorsk 0:1063a091a062 316 /* Configure SSP, interrupt is disable, LoopBack mode is disable,
igorsk 0:1063a091a062 317 * SSP is disable, Slave output is disable as default
igorsk 0:1063a091a062 318 */
igorsk 0:1063a091a062 319 tmp = ((SSP_ConfigStruct->CPHA) | (SSP_ConfigStruct->CPOL) \
igorsk 0:1063a091a062 320 | (SSP_ConfigStruct->FrameFormat) | (SSP_ConfigStruct->Databit))
igorsk 0:1063a091a062 321 & SSP_CR0_BITMASK;
igorsk 0:1063a091a062 322 // write back to SSP control register
igorsk 0:1063a091a062 323 SSPx->CR0 = tmp;
igorsk 0:1063a091a062 324 tmp = SSP_getNum(SSPx);
igorsk 0:1063a091a062 325 if (SSP_ConfigStruct->Databit > SSP_DATABIT_8){
igorsk 0:1063a091a062 326 sspdat[tmp].dataword = 1;
igorsk 0:1063a091a062 327 } else {
igorsk 0:1063a091a062 328 sspdat[tmp].dataword = 0;
igorsk 0:1063a091a062 329 }
igorsk 0:1063a091a062 330
igorsk 0:1063a091a062 331 tmp = SSP_ConfigStruct->Mode & SSP_CR1_BITMASK;
igorsk 0:1063a091a062 332 // Write back to CR1
igorsk 0:1063a091a062 333 SSPx->CR1 = tmp;
igorsk 0:1063a091a062 334
igorsk 0:1063a091a062 335 // Set clock rate for SSP peripheral
igorsk 0:1063a091a062 336 SSP_SetClock(SSPx, SSP_ConfigStruct->ClockRate);
igorsk 0:1063a091a062 337 }
igorsk 0:1063a091a062 338
igorsk 0:1063a091a062 339
igorsk 0:1063a091a062 340
igorsk 0:1063a091a062 341 /*****************************************************************************//**
igorsk 0:1063a091a062 342 * @brief Fills each SSP_InitStruct member with its default value:
igorsk 0:1063a091a062 343 * - CPHA = SSP_CPHA_FIRST
igorsk 0:1063a091a062 344 * - CPOL = SSP_CPOL_HI
igorsk 0:1063a091a062 345 * - ClockRate = 1000000
igorsk 0:1063a091a062 346 * - Databit = SSP_DATABIT_8
igorsk 0:1063a091a062 347 * - Mode = SSP_MASTER_MODE
igorsk 0:1063a091a062 348 * - FrameFormat = SSP_FRAME_SSP
igorsk 0:1063a091a062 349 * @param[in] SSP_InitStruct Pointer to a SSP_CFG_Type structure
igorsk 0:1063a091a062 350 * which will be initialized.
igorsk 0:1063a091a062 351 * @return None
igorsk 0:1063a091a062 352 *******************************************************************************/
igorsk 0:1063a091a062 353 void SSP_ConfigStructInit(SSP_CFG_Type *SSP_InitStruct)
igorsk 0:1063a091a062 354 {
igorsk 0:1063a091a062 355 SSP_InitStruct->CPHA = SSP_CPHA_FIRST;
igorsk 0:1063a091a062 356 SSP_InitStruct->CPOL = SSP_CPOL_HI;
igorsk 0:1063a091a062 357 SSP_InitStruct->ClockRate = 1000000;
igorsk 0:1063a091a062 358 SSP_InitStruct->Databit = SSP_DATABIT_8;
igorsk 0:1063a091a062 359 SSP_InitStruct->Mode = SSP_MASTER_MODE;
igorsk 0:1063a091a062 360 SSP_InitStruct->FrameFormat = SSP_FRAME_SPI;
igorsk 0:1063a091a062 361 }
igorsk 0:1063a091a062 362
igorsk 0:1063a091a062 363
igorsk 0:1063a091a062 364 /*********************************************************************//**
igorsk 0:1063a091a062 365 * @brief Enable or disable SSP peripheral's operation
igorsk 0:1063a091a062 366 * @param[in] SSPx SSP peripheral, should be SSP0 or SSP1
igorsk 0:1063a091a062 367 * @param[in] NewState New State of SSPx peripheral's operation
igorsk 0:1063a091a062 368 * @return none
igorsk 0:1063a091a062 369 **********************************************************************/
igorsk 0:1063a091a062 370 void SSP_Cmd(LPC_SSP_TypeDef* SSPx, FunctionalState NewState)
igorsk 0:1063a091a062 371 {
igorsk 0:1063a091a062 372 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 373 CHECK_PARAM(PARAM_FUNCTIONALSTATE(NewState));
igorsk 0:1063a091a062 374
igorsk 0:1063a091a062 375 if (NewState == ENABLE)
igorsk 0:1063a091a062 376 {
igorsk 0:1063a091a062 377 SSPx->CR1 |= SSP_CR1_SSP_EN;
igorsk 0:1063a091a062 378 }
igorsk 0:1063a091a062 379 else
igorsk 0:1063a091a062 380 {
igorsk 0:1063a091a062 381 SSPx->CR1 &= (~SSP_CR1_SSP_EN) & SSP_CR1_BITMASK;
igorsk 0:1063a091a062 382 }
igorsk 0:1063a091a062 383 }
igorsk 0:1063a091a062 384
igorsk 0:1063a091a062 385
igorsk 0:1063a091a062 386
igorsk 0:1063a091a062 387 /*********************************************************************//**
igorsk 0:1063a091a062 388 * @brief Enable or disable Loop Back mode function in SSP peripheral
igorsk 0:1063a091a062 389 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 390 * @param[in] NewState New State of Loop Back mode, should be:
igorsk 0:1063a091a062 391 * - ENABLE: Enable this function
igorsk 0:1063a091a062 392 * - DISABLE: Disable this function
igorsk 0:1063a091a062 393 * @return None
igorsk 0:1063a091a062 394 **********************************************************************/
igorsk 0:1063a091a062 395 void SSP_LoopBackCmd(LPC_SSP_TypeDef* SSPx, FunctionalState NewState)
igorsk 0:1063a091a062 396 {
igorsk 0:1063a091a062 397 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 398 CHECK_PARAM(PARAM_FUNCTIONALSTATE(NewState));
igorsk 0:1063a091a062 399
igorsk 0:1063a091a062 400 if (NewState == ENABLE)
igorsk 0:1063a091a062 401 {
igorsk 0:1063a091a062 402 SSPx->CR1 |= SSP_CR1_LBM_EN;
igorsk 0:1063a091a062 403 }
igorsk 0:1063a091a062 404 else
igorsk 0:1063a091a062 405 {
igorsk 0:1063a091a062 406 SSPx->CR1 &= (~SSP_CR1_LBM_EN) & SSP_CR1_BITMASK;
igorsk 0:1063a091a062 407 }
igorsk 0:1063a091a062 408 }
igorsk 0:1063a091a062 409
igorsk 0:1063a091a062 410
igorsk 0:1063a091a062 411
igorsk 0:1063a091a062 412 /*********************************************************************//**
igorsk 0:1063a091a062 413 * @brief Enable or disable Slave Output function in SSP peripheral
igorsk 0:1063a091a062 414 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 415 * @param[in] NewState New State of Slave Output function, should be:
igorsk 0:1063a091a062 416 * - ENABLE: Slave Output in normal operation
igorsk 0:1063a091a062 417 * - DISABLE: Slave Output is disabled. This blocks
igorsk 0:1063a091a062 418 * SSP controller from driving the transmit data
igorsk 0:1063a091a062 419 * line (MISO)
igorsk 0:1063a091a062 420 * Note: This function is available when SSP peripheral in Slave mode
igorsk 0:1063a091a062 421 * @return None
igorsk 0:1063a091a062 422 **********************************************************************/
igorsk 0:1063a091a062 423 void SSP_SlaveOutputCmd(LPC_SSP_TypeDef* SSPx, FunctionalState NewState)
igorsk 0:1063a091a062 424 {
igorsk 0:1063a091a062 425 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 426 CHECK_PARAM(PARAM_FUNCTIONALSTATE(NewState));
igorsk 0:1063a091a062 427
igorsk 0:1063a091a062 428 if (NewState == ENABLE)
igorsk 0:1063a091a062 429 {
igorsk 0:1063a091a062 430 SSPx->CR1 &= (~SSP_CR1_SO_DISABLE) & SSP_CR1_BITMASK;
igorsk 0:1063a091a062 431 }
igorsk 0:1063a091a062 432 else
igorsk 0:1063a091a062 433 {
igorsk 0:1063a091a062 434 SSPx->CR1 |= SSP_CR1_SO_DISABLE;
igorsk 0:1063a091a062 435 }
igorsk 0:1063a091a062 436 }
igorsk 0:1063a091a062 437
igorsk 0:1063a091a062 438
igorsk 0:1063a091a062 439
igorsk 0:1063a091a062 440 /*********************************************************************//**
igorsk 0:1063a091a062 441 * @brief Transmit a single data through SSPx peripheral
igorsk 0:1063a091a062 442 * @param[in] SSPx SSP peripheral selected, should be SSP
igorsk 0:1063a091a062 443 * @param[in] Data Data to transmit (must be 16 or 8-bit long,
igorsk 0:1063a091a062 444 * this depend on SSP data bit number configured)
igorsk 0:1063a091a062 445 * @return none
igorsk 0:1063a091a062 446 **********************************************************************/
igorsk 0:1063a091a062 447 void SSP_SendData(LPC_SSP_TypeDef* SSPx, uint16_t Data)
igorsk 0:1063a091a062 448 {
igorsk 0:1063a091a062 449 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 450
igorsk 0:1063a091a062 451 SSPx->DR = SSP_DR_BITMASK(Data);
igorsk 0:1063a091a062 452 }
igorsk 0:1063a091a062 453
igorsk 0:1063a091a062 454
igorsk 0:1063a091a062 455
igorsk 0:1063a091a062 456 /*********************************************************************//**
igorsk 0:1063a091a062 457 * @brief Receive a single data from SSPx peripheral
igorsk 0:1063a091a062 458 * @param[in] SSPx SSP peripheral selected, should be SSP
igorsk 0:1063a091a062 459 * @return Data received (16-bit long)
igorsk 0:1063a091a062 460 **********************************************************************/
igorsk 0:1063a091a062 461 uint16_t SSP_ReceiveData(LPC_SSP_TypeDef* SSPx)
igorsk 0:1063a091a062 462 {
igorsk 0:1063a091a062 463 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 464
igorsk 0:1063a091a062 465 return ((uint16_t) (SSP_DR_BITMASK(SSPx->DR)));
igorsk 0:1063a091a062 466 }
igorsk 0:1063a091a062 467
igorsk 0:1063a091a062 468 /*********************************************************************//**
igorsk 0:1063a091a062 469 * @brief SSP Read write data function
igorsk 0:1063a091a062 470 * @param[in] SSPx Pointer to SSP peripheral, should be SSP0 or SSP1
igorsk 0:1063a091a062 471 * @param[in] dataCfg Pointer to a SSP_DATA_SETUP_Type structure that
igorsk 0:1063a091a062 472 * contains specified information about transmit
igorsk 0:1063a091a062 473 * data configuration.
igorsk 0:1063a091a062 474 * @param[in] xfType Transfer type, should be:
igorsk 0:1063a091a062 475 * - SSP_TRANSFER_POLLING: Polling mode
igorsk 0:1063a091a062 476 * - SSP_TRANSFER_INTERRUPT: Interrupt mode
igorsk 0:1063a091a062 477 * @return Actual Data length has been transferred in polling mode.
igorsk 0:1063a091a062 478 * In interrupt mode, always return (0)
igorsk 0:1063a091a062 479 * Return (-1) if error.
igorsk 0:1063a091a062 480 * Note: This function can be used in both master and slave mode.
igorsk 0:1063a091a062 481 ***********************************************************************/
igorsk 0:1063a091a062 482 int32_t SSP_ReadWrite (LPC_SSP_TypeDef *SSPx, SSP_DATA_SETUP_Type *dataCfg, \
igorsk 0:1063a091a062 483 SSP_TRANSFER_Type xfType)
igorsk 0:1063a091a062 484 {
igorsk 0:1063a091a062 485 uint8_t *rdata8=NULL;
igorsk 0:1063a091a062 486 uint8_t *wdata8=NULL;
igorsk 0:1063a091a062 487 uint16_t *rdata16=NULL;
igorsk 0:1063a091a062 488 uint16_t *wdata16=NULL;
igorsk 0:1063a091a062 489 uint32_t stat;
igorsk 0:1063a091a062 490 uint32_t tmp;
igorsk 0:1063a091a062 491 int32_t sspnum;
igorsk 0:1063a091a062 492 int32_t dataword;
igorsk 0:1063a091a062 493
igorsk 0:1063a091a062 494 dataCfg->rx_cnt = 0;
igorsk 0:1063a091a062 495 dataCfg->tx_cnt = 0;
igorsk 0:1063a091a062 496 dataCfg->status = 0;
igorsk 0:1063a091a062 497
igorsk 0:1063a091a062 498
igorsk 0:1063a091a062 499 /* Clear all remaining data in RX FIFO */
igorsk 0:1063a091a062 500 while (SSPx->SR & SSP_SR_RNE){
igorsk 0:1063a091a062 501 tmp = (uint32_t) SSP_ReceiveData(SSPx);
igorsk 0:1063a091a062 502 }
igorsk 0:1063a091a062 503
igorsk 0:1063a091a062 504 // Clear status
igorsk 0:1063a091a062 505 SSPx->ICR = SSP_ICR_BITMASK;
igorsk 0:1063a091a062 506
igorsk 0:1063a091a062 507 sspnum = SSP_getNum(SSPx);
igorsk 0:1063a091a062 508 dataword = sspdat[sspnum].dataword;
igorsk 0:1063a091a062 509
igorsk 0:1063a091a062 510 // Polling mode ----------------------------------------------------------------------
igorsk 0:1063a091a062 511 if (xfType == SSP_TRANSFER_POLLING){
igorsk 0:1063a091a062 512 if (dataword == 0){
igorsk 0:1063a091a062 513 rdata8 = (uint8_t *)dataCfg->rx_data;
igorsk 0:1063a091a062 514 wdata8 = (uint8_t *)dataCfg->tx_data;
igorsk 0:1063a091a062 515 } else {
igorsk 0:1063a091a062 516 rdata16 = (uint16_t *)dataCfg->rx_data;
igorsk 0:1063a091a062 517 wdata16 = (uint16_t *)dataCfg->tx_data;
igorsk 0:1063a091a062 518 }
igorsk 0:1063a091a062 519 while ((dataCfg->tx_cnt != dataCfg->length) || (dataCfg->rx_cnt != dataCfg->length)){
igorsk 0:1063a091a062 520 if ((SSPx->SR & SSP_SR_TNF) && (dataCfg->tx_cnt != dataCfg->length)){
igorsk 0:1063a091a062 521 // Write data to buffer
igorsk 0:1063a091a062 522 if(dataCfg->tx_data == NULL){
igorsk 0:1063a091a062 523 if (dataword == 0){
igorsk 0:1063a091a062 524 SSP_SendData(SSPx, 0xFF);
igorsk 0:1063a091a062 525 dataCfg->tx_cnt++;
igorsk 0:1063a091a062 526 } else {
igorsk 0:1063a091a062 527 SSP_SendData(SSPx, 0xFFFF);
igorsk 0:1063a091a062 528 dataCfg->tx_cnt += 2;
igorsk 0:1063a091a062 529 }
igorsk 0:1063a091a062 530 } else {
igorsk 0:1063a091a062 531 if (dataword == 0){
igorsk 0:1063a091a062 532 SSP_SendData(SSPx, *wdata8);
igorsk 0:1063a091a062 533 wdata8++;
igorsk 0:1063a091a062 534 dataCfg->tx_cnt++;
igorsk 0:1063a091a062 535 } else {
igorsk 0:1063a091a062 536 SSP_SendData(SSPx, *wdata16);
igorsk 0:1063a091a062 537 wdata16++;
igorsk 0:1063a091a062 538 dataCfg->tx_cnt += 2;
igorsk 0:1063a091a062 539 }
igorsk 0:1063a091a062 540 }
igorsk 0:1063a091a062 541 }
igorsk 0:1063a091a062 542
igorsk 0:1063a091a062 543 // Check overrun error
igorsk 0:1063a091a062 544 if ((stat = SSPx->RIS) & SSP_RIS_ROR){
igorsk 0:1063a091a062 545 // save status and return
igorsk 0:1063a091a062 546 dataCfg->status = stat | SSP_STAT_ERROR;
igorsk 0:1063a091a062 547 return (-1);
igorsk 0:1063a091a062 548 }
igorsk 0:1063a091a062 549
igorsk 0:1063a091a062 550 // Check for any data available in RX FIFO
igorsk 0:1063a091a062 551 while ((SSPx->SR & SSP_SR_RNE) && (dataCfg->rx_cnt != dataCfg->length)){
igorsk 0:1063a091a062 552 // Read data from SSP data
igorsk 0:1063a091a062 553 tmp = SSP_ReceiveData(SSPx);
igorsk 0:1063a091a062 554
igorsk 0:1063a091a062 555 // Store data to destination
igorsk 0:1063a091a062 556 if (dataCfg->rx_data != NULL)
igorsk 0:1063a091a062 557 {
igorsk 0:1063a091a062 558 if (dataword == 0){
igorsk 0:1063a091a062 559 *(rdata8) = (uint8_t) tmp;
igorsk 0:1063a091a062 560 rdata8++;
igorsk 0:1063a091a062 561 } else {
igorsk 0:1063a091a062 562 *(rdata16) = (uint16_t) tmp;
igorsk 0:1063a091a062 563 rdata16++;
igorsk 0:1063a091a062 564 }
igorsk 0:1063a091a062 565 }
igorsk 0:1063a091a062 566 // Increase counter
igorsk 0:1063a091a062 567 if (dataword == 0){
igorsk 0:1063a091a062 568 dataCfg->rx_cnt++;
igorsk 0:1063a091a062 569 } else {
igorsk 0:1063a091a062 570 dataCfg->rx_cnt += 2;
igorsk 0:1063a091a062 571 }
igorsk 0:1063a091a062 572 }
igorsk 0:1063a091a062 573 }
igorsk 0:1063a091a062 574
igorsk 0:1063a091a062 575 // save status
igorsk 0:1063a091a062 576 dataCfg->status = SSP_STAT_DONE;
igorsk 0:1063a091a062 577
igorsk 0:1063a091a062 578 if (dataCfg->tx_data != NULL){
igorsk 0:1063a091a062 579 return dataCfg->tx_cnt;
igorsk 0:1063a091a062 580 } else if (dataCfg->rx_data != NULL){
igorsk 0:1063a091a062 581 return dataCfg->rx_cnt;
igorsk 0:1063a091a062 582 } else {
igorsk 0:1063a091a062 583 return (0);
igorsk 0:1063a091a062 584 }
igorsk 0:1063a091a062 585 }
igorsk 0:1063a091a062 586
igorsk 0:1063a091a062 587 // Interrupt mode ----------------------------------------------------------------------
igorsk 0:1063a091a062 588 else if (xfType == SSP_TRANSFER_INTERRUPT){
igorsk 0:1063a091a062 589 sspdat[sspnum].inthandler = SSP_IntHandler;
igorsk 0:1063a091a062 590 sspdat[sspnum].txrx_setup = (uint32_t)dataCfg;
igorsk 0:1063a091a062 591
igorsk 0:1063a091a062 592 while ((SSPx->SR & SSP_SR_TNF) && (dataCfg->tx_cnt != dataCfg->length)){
igorsk 0:1063a091a062 593 // Write data to buffer
igorsk 0:1063a091a062 594 if(dataCfg->tx_data == NULL){
igorsk 0:1063a091a062 595 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 596 SSP_SendData(SSPx, 0xFF);
igorsk 0:1063a091a062 597 dataCfg->tx_cnt++;
igorsk 0:1063a091a062 598 } else {
igorsk 0:1063a091a062 599 SSP_SendData(SSPx, 0xFFFF);
igorsk 0:1063a091a062 600 dataCfg->tx_cnt += 2;
igorsk 0:1063a091a062 601 }
igorsk 0:1063a091a062 602 } else {
igorsk 0:1063a091a062 603 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 604 SSP_SendData(SSPx, (*(uint8_t *)((uint32_t)dataCfg->tx_data + dataCfg->tx_cnt)));
igorsk 0:1063a091a062 605 dataCfg->tx_cnt++;
igorsk 0:1063a091a062 606 } else {
igorsk 0:1063a091a062 607 SSP_SendData(SSPx, (*(uint16_t *)((uint32_t)dataCfg->tx_data + dataCfg->tx_cnt)));
igorsk 0:1063a091a062 608 dataCfg->tx_cnt += 2;
igorsk 0:1063a091a062 609 }
igorsk 0:1063a091a062 610 }
igorsk 0:1063a091a062 611
igorsk 0:1063a091a062 612 // Check error
igorsk 0:1063a091a062 613 if ((stat = SSPx->RIS) & SSP_RIS_ROR){
igorsk 0:1063a091a062 614 // save status and return
igorsk 0:1063a091a062 615 dataCfg->status = stat | SSP_STAT_ERROR;
igorsk 0:1063a091a062 616 return (-1);
igorsk 0:1063a091a062 617 }
igorsk 0:1063a091a062 618
igorsk 0:1063a091a062 619 // Check for any data available in RX FIFO
igorsk 0:1063a091a062 620 while ((SSPx->SR & SSP_SR_RNE) && (dataCfg->rx_cnt != dataCfg->length)){
igorsk 0:1063a091a062 621 // Read data from SSP data
igorsk 0:1063a091a062 622 tmp = SSP_ReceiveData(SSPx);
igorsk 0:1063a091a062 623
igorsk 0:1063a091a062 624 // Store data to destination
igorsk 0:1063a091a062 625 if (dataCfg->rx_data != NULL)
igorsk 0:1063a091a062 626 {
igorsk 0:1063a091a062 627 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 628 *(uint8_t *)((uint32_t)dataCfg->rx_data + dataCfg->rx_cnt) = (uint8_t) tmp;
igorsk 0:1063a091a062 629 } else {
igorsk 0:1063a091a062 630 *(uint16_t *)((uint32_t)dataCfg->rx_data + dataCfg->rx_cnt) = (uint16_t) tmp;
igorsk 0:1063a091a062 631 }
igorsk 0:1063a091a062 632 }
igorsk 0:1063a091a062 633 // Increase counter
igorsk 0:1063a091a062 634 if (sspdat[sspnum].dataword == 0){
igorsk 0:1063a091a062 635 dataCfg->rx_cnt++;
igorsk 0:1063a091a062 636 } else {
igorsk 0:1063a091a062 637 dataCfg->rx_cnt += 2;
igorsk 0:1063a091a062 638 }
igorsk 0:1063a091a062 639 }
igorsk 0:1063a091a062 640 }
igorsk 0:1063a091a062 641
igorsk 0:1063a091a062 642 // If there more data to sent or receive
igorsk 0:1063a091a062 643 if ((dataCfg->rx_cnt != dataCfg->length) || (dataCfg->tx_cnt != dataCfg->length)){
igorsk 0:1063a091a062 644 // Enable all interrupt
igorsk 0:1063a091a062 645 SSPx->IMSC = SSP_IMSC_BITMASK;
igorsk 0:1063a091a062 646 } else {
igorsk 0:1063a091a062 647 // Save status
igorsk 0:1063a091a062 648 dataCfg->status = SSP_STAT_DONE;
igorsk 0:1063a091a062 649 }
igorsk 0:1063a091a062 650 return (0);
igorsk 0:1063a091a062 651 }
igorsk 0:1063a091a062 652
igorsk 0:1063a091a062 653 return (-1);
igorsk 0:1063a091a062 654 }
igorsk 0:1063a091a062 655
igorsk 0:1063a091a062 656 /*********************************************************************//**
igorsk 0:1063a091a062 657 * @brief Checks whether the specified SSP status flag is set or not
igorsk 0:1063a091a062 658 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 659 * @param[in] FlagType Type of flag to check status, should be one
igorsk 0:1063a091a062 660 * of following:
igorsk 0:1063a091a062 661 * - SSP_STAT_TXFIFO_EMPTY: TX FIFO is empty
igorsk 0:1063a091a062 662 * - SSP_STAT_TXFIFO_NOTFULL: TX FIFO is not full
igorsk 0:1063a091a062 663 * - SSP_STAT_RXFIFO_NOTEMPTY: RX FIFO is not empty
igorsk 0:1063a091a062 664 * - SSP_STAT_RXFIFO_FULL: RX FIFO is full
igorsk 0:1063a091a062 665 * - SSP_STAT_BUSY: SSP peripheral is busy
igorsk 0:1063a091a062 666 * @return New State of specified SSP status flag
igorsk 0:1063a091a062 667 **********************************************************************/
igorsk 0:1063a091a062 668 FlagStatus SSP_GetStatus(LPC_SSP_TypeDef* SSPx, uint32_t FlagType)
igorsk 0:1063a091a062 669 {
igorsk 0:1063a091a062 670 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 671 CHECK_PARAM(PARAM_SSP_STAT(FlagType));
igorsk 0:1063a091a062 672
igorsk 0:1063a091a062 673 return ((SSPx->SR & FlagType) ? SET : RESET);
igorsk 0:1063a091a062 674 }
igorsk 0:1063a091a062 675
igorsk 0:1063a091a062 676
igorsk 0:1063a091a062 677
igorsk 0:1063a091a062 678 /*********************************************************************//**
igorsk 0:1063a091a062 679 * @brief Enable or disable specified interrupt type in SSP peripheral
igorsk 0:1063a091a062 680 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 681 * @param[in] IntType Interrupt type in SSP peripheral, should be:
igorsk 0:1063a091a062 682 * - SSP_INTCFG_ROR: Receive Overrun interrupt
igorsk 0:1063a091a062 683 * - SSP_INTCFG_RT: Receive Time out interrupt
igorsk 0:1063a091a062 684 * - SSP_INTCFG_RX: RX FIFO is at least half full interrupt
igorsk 0:1063a091a062 685 * - SSP_INTCFG_TX: TX FIFO is at least half empty interrupt
igorsk 0:1063a091a062 686 * @param[in] NewState New State of specified interrupt type, should be:
igorsk 0:1063a091a062 687 * - ENABLE: Enable this interrupt type
igorsk 0:1063a091a062 688 * - DISABLE: Disable this interrupt type
igorsk 0:1063a091a062 689 * @return None
igorsk 0:1063a091a062 690 **********************************************************************/
igorsk 0:1063a091a062 691 void SSP_IntConfig(LPC_SSP_TypeDef *SSPx, uint32_t IntType, FunctionalState NewState)
igorsk 0:1063a091a062 692 {
igorsk 0:1063a091a062 693 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 694 CHECK_PARAM(PARAM_SSP_INTCFG(IntType));
igorsk 0:1063a091a062 695
igorsk 0:1063a091a062 696 if (NewState == ENABLE)
igorsk 0:1063a091a062 697 {
igorsk 0:1063a091a062 698 SSPx->IMSC |= IntType;
igorsk 0:1063a091a062 699 }
igorsk 0:1063a091a062 700 else
igorsk 0:1063a091a062 701 {
igorsk 0:1063a091a062 702 SSPx->IMSC &= (~IntType) & SSP_IMSC_BITMASK;
igorsk 0:1063a091a062 703 }
igorsk 0:1063a091a062 704 }
igorsk 0:1063a091a062 705
igorsk 0:1063a091a062 706
igorsk 0:1063a091a062 707 /*********************************************************************//**
igorsk 0:1063a091a062 708 * @brief Check whether the specified Raw interrupt status flag is
igorsk 0:1063a091a062 709 * set or not
igorsk 0:1063a091a062 710 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 711 * @param[in] RawIntType Raw Interrupt Type, should be:
igorsk 0:1063a091a062 712 * - SSP_INTSTAT_RAW_ROR: Receive Overrun interrupt
igorsk 0:1063a091a062 713 * - SSP_INTSTAT_RAW_RT: Receive Time out interrupt
igorsk 0:1063a091a062 714 * - SSP_INTSTAT_RAW_RX: RX FIFO is at least half full interrupt
igorsk 0:1063a091a062 715 * - SSP_INTSTAT_RAW_TX: TX FIFO is at least half empty interrupt
igorsk 0:1063a091a062 716 * @return New State of specified Raw interrupt status flag in SSP peripheral
igorsk 0:1063a091a062 717 * Note: Enabling/Disabling specified interrupt in SSP peripheral does not
igorsk 0:1063a091a062 718 * effect to Raw Interrupt Status flag.
igorsk 0:1063a091a062 719 **********************************************************************/
igorsk 0:1063a091a062 720 IntStatus SSP_GetRawIntStatus(LPC_SSP_TypeDef *SSPx, uint32_t RawIntType)
igorsk 0:1063a091a062 721 {
igorsk 0:1063a091a062 722 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 723 CHECK_PARAM(PARAM_SSP_INTSTAT_RAW(RawIntType));
igorsk 0:1063a091a062 724
igorsk 0:1063a091a062 725 return ((SSPx->RIS & RawIntType) ? SET : RESET);
igorsk 0:1063a091a062 726 }
igorsk 0:1063a091a062 727
igorsk 0:1063a091a062 728
igorsk 0:1063a091a062 729 /*********************************************************************//**
igorsk 0:1063a091a062 730 * @brief Check whether the specified interrupt status flag is
igorsk 0:1063a091a062 731 * set or not
igorsk 0:1063a091a062 732 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 733 * @param[in] IntType Raw Interrupt Type, should be:
igorsk 0:1063a091a062 734 * - SSP_INTSTAT_ROR: Receive Overrun interrupt
igorsk 0:1063a091a062 735 * - SSP_INTSTAT_RT: Receive Time out interrupt
igorsk 0:1063a091a062 736 * - SSP_INTSTAT_RX: RX FIFO is at least half full interrupt
igorsk 0:1063a091a062 737 * - SSP_INTSTAT_TX: TX FIFO is at least half empty interrupt
igorsk 0:1063a091a062 738 * @return New State of specified interrupt status flag in SSP peripheral
igorsk 0:1063a091a062 739 * Note: Enabling/Disabling specified interrupt in SSP peripheral effects
igorsk 0:1063a091a062 740 * to Interrupt Status flag.
igorsk 0:1063a091a062 741 **********************************************************************/
igorsk 0:1063a091a062 742 IntStatus SSP_GetIntStatus (LPC_SSP_TypeDef *SSPx, uint32_t IntType)
igorsk 0:1063a091a062 743 {
igorsk 0:1063a091a062 744 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 745 CHECK_PARAM(PARAM_SSP_INTSTAT(IntType));
igorsk 0:1063a091a062 746
igorsk 0:1063a091a062 747 return ((SSPx->MIS & IntType) ? SET :RESET);
igorsk 0:1063a091a062 748 }
igorsk 0:1063a091a062 749
igorsk 0:1063a091a062 750
igorsk 0:1063a091a062 751
igorsk 0:1063a091a062 752 /*********************************************************************//**
igorsk 0:1063a091a062 753 * @brief Clear specified interrupt pending in SSP peripheral
igorsk 0:1063a091a062 754 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 755 * @param[in] IntType Interrupt pending to clear, should be:
igorsk 0:1063a091a062 756 * - SSP_INTCLR_ROR: clears the "frame was received when
igorsk 0:1063a091a062 757 * RxFIFO was full" interrupt.
igorsk 0:1063a091a062 758 * - SSP_INTCLR_RT: clears the "Rx FIFO was not empty and
igorsk 0:1063a091a062 759 * has not been read for a timeout period" interrupt.
igorsk 0:1063a091a062 760 * @return None
igorsk 0:1063a091a062 761 **********************************************************************/
igorsk 0:1063a091a062 762 void SSP_ClearIntPending(LPC_SSP_TypeDef *SSPx, uint32_t IntType)
igorsk 0:1063a091a062 763 {
igorsk 0:1063a091a062 764 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 765 CHECK_PARAM(PARAM_SSP_INTCLR(IntType));
igorsk 0:1063a091a062 766
igorsk 0:1063a091a062 767 SSPx->ICR = IntType;
igorsk 0:1063a091a062 768 }
igorsk 0:1063a091a062 769
igorsk 0:1063a091a062 770 /*********************************************************************//**
igorsk 0:1063a091a062 771 * @brief Enable/Disable DMA function for SSP peripheral
igorsk 0:1063a091a062 772 * @param[in] SSPx SSP peripheral selected, should be SSP0 or SSP1
igorsk 0:1063a091a062 773 * @param[in] DMAMode Type of DMA, should be:
igorsk 0:1063a091a062 774 * - SSP_DMA_TX: DMA for the transmit FIFO
igorsk 0:1063a091a062 775 * - SSP_DMA_RX: DMA for the Receive FIFO
igorsk 0:1063a091a062 776 * @param[in] NewState New State of DMA function on SSP peripheral,
igorsk 0:1063a091a062 777 * should be:
igorsk 0:1063a091a062 778 * - ENALBE: Enable this function
igorsk 0:1063a091a062 779 * - DISABLE: Disable this function
igorsk 0:1063a091a062 780 * @return None
igorsk 0:1063a091a062 781 **********************************************************************/
igorsk 0:1063a091a062 782 void SSP_DMACmd(LPC_SSP_TypeDef *SSPx, uint32_t DMAMode, FunctionalState NewState)
igorsk 0:1063a091a062 783 {
igorsk 0:1063a091a062 784 CHECK_PARAM(PARAM_SSPx(SSPx));
igorsk 0:1063a091a062 785 CHECK_PARAM(PARAM_SSP_DMA(DMAMode));
igorsk 0:1063a091a062 786 CHECK_PARAM(PARAM_FUNCTIONALSTATE(NewState));
igorsk 0:1063a091a062 787
igorsk 0:1063a091a062 788 if (NewState == ENABLE)
igorsk 0:1063a091a062 789 {
igorsk 0:1063a091a062 790 SSPx->DMACR |= DMAMode;
igorsk 0:1063a091a062 791 }
igorsk 0:1063a091a062 792 else
igorsk 0:1063a091a062 793 {
igorsk 0:1063a091a062 794 SSPx->DMACR &= (~DMAMode) & SSP_DMA_BITMASK;
igorsk 0:1063a091a062 795 }
igorsk 0:1063a091a062 796 }
igorsk 0:1063a091a062 797
igorsk 0:1063a091a062 798 /**
igorsk 0:1063a091a062 799 * @brief Standard SSP0 Interrupt handler
igorsk 0:1063a091a062 800 * @param[in] None
igorsk 0:1063a091a062 801 * @return None
igorsk 0:1063a091a062 802 */
igorsk 0:1063a091a062 803 void SSP0_StdIntHandler(void)
igorsk 0:1063a091a062 804 {
igorsk 0:1063a091a062 805 // Call relevant handler
igorsk 0:1063a091a062 806 sspdat[0].inthandler(LPC_SSP0);
igorsk 0:1063a091a062 807 }
igorsk 0:1063a091a062 808
igorsk 0:1063a091a062 809 /**
igorsk 0:1063a091a062 810 * @brief Standard SSP1 Interrupt handler
igorsk 0:1063a091a062 811 * @param[in] None
igorsk 0:1063a091a062 812 * @return None
igorsk 0:1063a091a062 813 */
igorsk 0:1063a091a062 814 void SSP1_StdIntHandler(void)
igorsk 0:1063a091a062 815 {
igorsk 0:1063a091a062 816 // Call relevant handler
igorsk 0:1063a091a062 817 sspdat[1].inthandler(LPC_SSP1);
igorsk 0:1063a091a062 818 }
igorsk 0:1063a091a062 819
igorsk 0:1063a091a062 820 /**
igorsk 0:1063a091a062 821 * @}
igorsk 0:1063a091a062 822 */
igorsk 0:1063a091a062 823
igorsk 0:1063a091a062 824 #endif /* _SSP */
igorsk 0:1063a091a062 825
igorsk 0:1063a091a062 826 /**
igorsk 0:1063a091a062 827 * @}
igorsk 0:1063a091a062 828 */
igorsk 0:1063a091a062 829
igorsk 0:1063a091a062 830 /* --------------------------------- End Of File ------------------------------ */
igorsk 0:1063a091a062 831