00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040 #include "board.h"
00041
00042 #include <string.h>
00043 #include <stdio.h>
00044
00045 #ifdef BOARD_LCD_ILI9488
00046
00047
00048
00049
00050
00051 static const Pin lcd_ebi_cds_pin = BOARD_EBI_LCD_PIN_CDS;
00052
00053 COMPILER_ALIGNED(32) static sIli9488Dma ili9488EbiDma;
00054 static volatile sIli9488DmaCtl ili9488DmaCtlInEbiMode;
00055
00056
00057
00058
00059
00060
00061
00062 static void _ILI9488_ConfigureSmc(void)
00063 {
00064
00065 PMC_EnablePeripheral(ID_SMC);
00066
00067
00068
00069 SMC->SMC_CS_NUMBER[SMC_EBI_LCD_CS].SMC_SETUP = SMC_SETUP_NWE_SETUP(2)
00070 | SMC_SETUP_NCS_WR_SETUP(0)
00071 | SMC_SETUP_NRD_SETUP(0)
00072 | SMC_SETUP_NCS_RD_SETUP(0);
00073
00074 SMC->SMC_CS_NUMBER[SMC_EBI_LCD_CS].SMC_PULSE = SMC_PULSE_NWE_PULSE(6)
00075 | SMC_PULSE_NCS_WR_PULSE(0xA)
00076 | SMC_PULSE_NRD_PULSE(0xA)
00077 | SMC_PULSE_NCS_RD_PULSE(0xA);
00078
00079 SMC->SMC_CS_NUMBER[SMC_EBI_LCD_CS].SMC_CYCLE = SMC_CYCLE_NWE_CYCLE(0xA)
00080 | SMC_CYCLE_NRD_CYCLE(0xA);
00081
00082 SMC->SMC_CS_NUMBER[SMC_EBI_LCD_CS].SMC_MODE = SMC_MODE_READ_MODE
00083 | SMC_MODE_WRITE_MODE
00084 | SMC_MODE_DBW_16_BIT
00085 | SMC_MODE_EXNW_MODE_DISABLED
00086 | SMC_MODE_TDF_CYCLES(0xF);
00087 }
00088
00089
00090
00091
00092 static void _ILI9488_Ebi_Rx_CB(void)
00093 {
00094 if (!ili9488DmaCtlInEbiMode.cmdOrDataFlag)
00095 ili9488DmaCtlInEbiMode.rxDoneFlag = 1;
00096 }
00097
00098
00099
00100
00101 static void _ILI9488_Ebi_Tx_CB(void)
00102 {
00103 volatile uint32_t i;
00104
00105 if (ili9488DmaCtlInEbiMode.cmdOrDataFlag) {
00106 for (i = 0; i < 0xF; i++);
00107
00108 PIO_Set(&lcd_ebi_cds_pin);
00109 ili9488DmaCtlInEbiMode.cmdOrDataFlag = 0;
00110 }
00111
00112 ili9488DmaCtlInEbiMode.txDoneFlag = 1;
00113 }
00114
00115
00116
00117
00118
00119 static void _ILI9488_EbiDmaInitialize(sXdmad *dmad)
00120 {
00121 ili9488DmaCtlInEbiMode.cmdOrDataFlag = 1;
00122 ili9488DmaCtlInEbiMode.rxDoneFlag = 0;
00123 ili9488DmaCtlInEbiMode.txDoneFlag = 1;
00124
00125 ili9488EbiDma.xdmaD = dmad;
00126 ili9488EbiDma.xdmaD->pXdmacs = XDMAC;
00127 ili9488EbiDma.ili9488DmaTxChannel = 0;
00128 ili9488EbiDma.ili9488DmaRxChannel = 0;
00129 ili9488EbiDma.xdmaInt = 0;
00130 ili9488EbiDma.pSpiHw = 0;
00131 ili9488EbiDma.spiId = 0;
00132 }
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142 static uint8_t _ILI9488_EbiDmaConfigChannels(void)
00143 {
00144 uint32_t srcType, dstType;
00145
00146
00147 XDMAD_Initialize(ili9488EbiDma.xdmaD, 0);
00148
00149 XDMAD_FreeChannel(ili9488EbiDma.xdmaD, ili9488EbiDma.ili9488DmaTxChannel);
00150 XDMAD_FreeChannel(ili9488EbiDma.xdmaD, ili9488EbiDma.ili9488DmaRxChannel);
00151
00152 srcType = XDMAD_TRANSFER_MEMORY;
00153 dstType = XDMAD_TRANSFER_MEMORY;
00154
00155
00156 ili9488EbiDma.ili9488DmaTxChannel =
00157 XDMAD_AllocateChannel(ili9488EbiDma.xdmaD, srcType, dstType);
00158
00159 if (ili9488EbiDma.ili9488DmaTxChannel == XDMAD_ALLOC_FAILED)
00160 return ILI9488_ERROR_DMA_ALLOCATE_CHANNEL;
00161
00162
00163 ili9488EbiDma.ili9488DmaRxChannel =
00164 XDMAD_AllocateChannel(ili9488EbiDma.xdmaD, dstType, srcType);
00165
00166 if (ili9488EbiDma.ili9488DmaRxChannel == XDMAD_ALLOC_FAILED)
00167 return ILI9488_ERROR_DMA_ALLOCATE_CHANNEL;
00168
00169
00170 XDMAD_SetCallback(ili9488EbiDma.xdmaD, ili9488EbiDma.ili9488DmaRxChannel,
00171 (XdmadTransferCallback)_ILI9488_Ebi_Rx_CB, &ili9488EbiDma);
00172
00173 if (XDMAD_PrepareChannel(ili9488EbiDma.xdmaD,
00174 ili9488EbiDma.ili9488DmaRxChannel))
00175 return ILI9488_ERROR_DMA_ALLOCATE_CHANNEL;
00176
00177
00178 XDMAD_SetCallback(ili9488EbiDma.xdmaD, ili9488EbiDma.ili9488DmaTxChannel,
00179 (XdmadTransferCallback)_ILI9488_Ebi_Tx_CB, &ili9488EbiDma);
00180
00181 if (XDMAD_PrepareChannel(ili9488EbiDma.xdmaD,
00182 ili9488EbiDma.ili9488DmaTxChannel))
00183 return ILI9488_ERROR_DMA_ALLOCATE_CHANNEL;
00184
00185
00186 if (!(NVIC_GetActive(XDMAC_IRQn))) {
00187 NVIC_SetPriority(XDMAC_IRQn , 1);
00188
00189 NVIC_EnableIRQ(XDMAC_IRQn);
00190 }
00191
00192 return 0;
00193 }
00194
00195
00196
00197
00198
00199
00200 static uint8_t _ILI9488_EbiDmaConfigureRxTx(void)
00201 {
00202 uint32_t txAddress, rxAddress;
00203 sXdmad *pXdmad;
00204 pXdmad = ili9488EbiDma.xdmaD;
00205
00206 txAddress = rxAddress = (uint32_t)ILI9488_BASE_ADDRESS;
00207
00208
00209 ili9488EbiDma.xdmadTxCfg.mbr_sa = 0;
00210 ili9488EbiDma.xdmadTxCfg.mbr_da = txAddress;
00211 ili9488EbiDma.xdmadTxCfg.mbr_ubc = 0;
00212
00213 ili9488EbiDma.xdmadTxCfg.mbr_cfg =
00214 XDMAC_CC_TYPE_MEM_TRAN
00215 | XDMAC_CC_MBSIZE_SINGLE
00216 | XDMAC_CC_CSIZE_CHK_1
00217 | XDMAC_CC_DWIDTH_HALFWORD
00218 | XDMAC_CC_SIF_AHB_IF0
00219 | XDMAC_CC_DIF_AHB_IF1
00220 | XDMAC_CC_SAM_INCREMENTED_AM
00221 | XDMAC_CC_DAM_FIXED_AM;
00222
00223 ili9488EbiDma.xdmadTxCfg.mbr_bc = 0;
00224 ili9488EbiDma.xdmadTxCfg.mbr_sus = 0;
00225 ili9488EbiDma.xdmadTxCfg.mbr_dus = 0;
00226
00227
00228 ili9488EbiDma.xdmadRxCfg.mbr_ubc =
00229 XDMA_UBC_NVIEW_NDV0 | XDMA_UBC_NDE_FETCH_DIS ;
00230 ili9488EbiDma.xdmadRxCfg.mbr_da = 0;
00231 ili9488EbiDma.xdmadRxCfg.mbr_sa = rxAddress;
00232
00233 ili9488EbiDma.xdmadRxCfg.mbr_cfg =
00234 XDMAC_CC_TYPE_MEM_TRAN
00235 | XDMAC_CC_MBSIZE_SINGLE
00236 | XDMAC_CC_CSIZE_CHK_1
00237 | XDMAC_CC_DWIDTH_WORD
00238 | XDMAC_CC_SIF_AHB_IF1
00239 | XDMAC_CC_DIF_AHB_IF1
00240 | XDMAC_CC_SAM_FIXED_AM
00241 | XDMAC_CC_DAM_INCREMENTED_AM;
00242
00243 ili9488EbiDma.xdmadRxCfg.mbr_bc = 0;
00244 ili9488EbiDma.xdmadRxCfg.mbr_sus = 0;
00245 ili9488EbiDma.xdmadRxCfg.mbr_dus = 0;
00246
00247
00248 ili9488EbiDma.xdmaInt = (XDMAC_CIE_BIE
00249 | XDMAC_CIE_RBIE
00250 | XDMAC_CIE_WBIE
00251 | XDMAC_CIE_ROIE);
00252
00253 if (XDMAD_ConfigureTransfer(pXdmad, ili9488EbiDma.ili9488DmaRxChannel,
00254 &ili9488EbiDma.xdmadRxCfg, 0, 0, ili9488EbiDma.xdmaInt))
00255 return ILI9488_ERROR_DMA_CONFIGURE;
00256
00257 if (XDMAD_ConfigureTransfer(pXdmad, ili9488EbiDma.ili9488DmaTxChannel,
00258 &ili9488EbiDma.xdmadTxCfg, 0, 0, ili9488EbiDma.xdmaInt))
00259 return ILI9488_ERROR_DMA_CONFIGURE;
00260
00261 return 0;
00262 }
00263
00264
00265
00266
00267
00268
00269
00270
00271
00272
00273 static uint8_t _ILI9488_EbiDmaUpdateBuffer(uint16_t *pTxBuffer,
00274 uint32_t wTxSize,
00275 uint32_t *pRxBuffer, uint32_t wRxSize)
00276 {
00277 sXdmad *pXdmad;
00278 pXdmad = ili9488EbiDma.xdmaD;
00279
00280 ili9488EbiDma.xdmadTxCfg.mbr_sa = (uint32_t)pTxBuffer;
00281 ili9488EbiDma.xdmadTxCfg.mbr_ubc = wTxSize;
00282
00283 if (wRxSize) {
00284 ili9488EbiDma.xdmadRxCfg.mbr_da = (uint32_t)pRxBuffer;
00285 ili9488EbiDma.xdmadRxCfg.mbr_ubc = wRxSize;
00286
00287 if (XDMAD_ConfigureTransfer(pXdmad, ili9488EbiDma.ili9488DmaRxChannel,
00288 &ili9488EbiDma.xdmadRxCfg, 0, 0, ili9488EbiDma.xdmaInt))
00289 return ILI9488_ERROR_DMA_CONFIGURE;
00290 }
00291
00292 if (XDMAD_ConfigureTransfer(pXdmad, ili9488EbiDma.ili9488DmaTxChannel,
00293 &ili9488EbiDma.xdmadTxCfg, 0, 0, ili9488EbiDma.xdmaInt))
00294 return ILI9488_ERROR_DMA_CONFIGURE;
00295
00296 return 0;
00297 }
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308 uint8_t ILI9488_EbiInitializeWithDma(sXdmad *dmad)
00309 {
00310 _ILI9488_ConfigureSmc();
00311 _ILI9488_EbiDmaInitialize(dmad);
00312
00313 if (_ILI9488_EbiDmaConfigChannels()) return ILI9488_ERROR_DMA_ALLOCATE_CHANNEL;
00314
00315 if (_ILI9488_EbiDmaConfigureRxTx()) return ILI9488_ERROR_DMA_CONFIGURE;
00316
00317 return 0;
00318 }
00319
00320
00321
00322
00323
00324
00325
00326
00327 uint8_t ILI9488_EbiDmaTxTransfer(uint16_t *pTxBuffer, uint32_t wTxSize)
00328 {
00329 _ILI9488_EbiDmaUpdateBuffer(pTxBuffer, wTxSize, 0, 0);
00330
00331 SCB_CleanDCache_by_Addr((uint32_t *)pTxBuffer, wTxSize * 2);
00332
00333 if (XDMAD_StartTransfer(ili9488EbiDma.xdmaD,
00334 ili9488EbiDma.ili9488DmaTxChannel)) {
00335 printf("111");
00336 return ILI9488_ERROR_DMA_TRANSFER;
00337 }
00338
00339 while (!ili9488DmaCtlInEbiMode.txDoneFlag);
00340
00341 ili9488DmaCtlInEbiMode.txDoneFlag = 0;
00342
00343 return 0;
00344 }
00345
00346
00347
00348
00349
00350
00351
00352
00353 COMPILER_ALIGNED(32) static uint16_t dummyTxBuffer[5];
00354 uint8_t ILI9488_EbiDmaRxTransfer(uint32_t *pRxBuffer, uint32_t wRxSize)
00355 {
00356 SCB_CleanDCache_by_Addr((uint32_t *)pRxBuffer, wRxSize * 4);
00357 _ILI9488_EbiDmaUpdateBuffer(dummyTxBuffer, wRxSize, pRxBuffer, wRxSize);
00358
00359 if (XDMAD_StartTransfer(ili9488EbiDma.xdmaD,
00360 ili9488EbiDma.ili9488DmaRxChannel))
00361 return ILI9488_ERROR_DMA_TRANSFER;
00362
00363 return 0;
00364 }
00365
00366
00367
00368
00369
00370
00371
00372
00373
00374
00375 COMPILER_ALIGNED(32) static uint16_t command;
00376 uint8_t ILI9488_EbiSendCommand(uint16_t Instr, uint16_t *pTxData,
00377 uint32_t *pRxData, AccessIli_t ReadWrite, uint32_t size)
00378 {
00379 command = Instr;
00380
00381 if (ReadWrite == AccessInst) {
00382 PIO_Clear(&lcd_ebi_cds_pin);
00383 ili9488DmaCtlInEbiMode.cmdOrDataFlag = 1;
00384 return ILI9488_EbiDmaTxTransfer(&command, 1);
00385 } else if (ReadWrite == AccessWrite) {
00386 PIO_Clear(&lcd_ebi_cds_pin);
00387 ili9488DmaCtlInEbiMode.cmdOrDataFlag = 1;
00388 ILI9488_EbiDmaTxTransfer(&command, 1);
00389
00390 if (size == 0) return 0;
00391
00392 ILI9488_EbiDmaTxTransfer(pTxData, size);
00393 return 0;
00394 } else {
00395 ili9488DmaCtlInEbiMode.rxDoneFlag = 0;
00396 ILI9488_EbiDmaRxTransfer(pRxData, size);
00397
00398 while (!ili9488DmaCtlInEbiMode.rxDoneFlag);
00399 }
00400
00401 return 0;
00402 }
00403 #endif //BOARD_LCD_ILI9488