Color Oled(SSD1331) connect to STMicroelectronics Nucleo-F466

Dependencies:   ssd1331

Committer:
kadonotakashi
Date:
Wed Oct 10 00:33:53 2018 +0000
Revision:
0:8fdf9a60065b
how to make mbed librry

Who changed what in which revision?

UserRevisionLine numberNew contents of line
kadonotakashi 0:8fdf9a60065b 1 /* mbed Microcontroller Library
kadonotakashi 0:8fdf9a60065b 2 * Copyright (c) 2015-2016 Nuvoton
kadonotakashi 0:8fdf9a60065b 3 *
kadonotakashi 0:8fdf9a60065b 4 * Licensed under the Apache License, Version 2.0 (the "License");
kadonotakashi 0:8fdf9a60065b 5 * you may not use this file except in compliance with the License.
kadonotakashi 0:8fdf9a60065b 6 * You may obtain a copy of the License at
kadonotakashi 0:8fdf9a60065b 7 *
kadonotakashi 0:8fdf9a60065b 8 * http://www.apache.org/licenses/LICENSE-2.0
kadonotakashi 0:8fdf9a60065b 9 *
kadonotakashi 0:8fdf9a60065b 10 * Unless required by applicable law or agreed to in writing, software
kadonotakashi 0:8fdf9a60065b 11 * distributed under the License is distributed on an "AS IS" BASIS,
kadonotakashi 0:8fdf9a60065b 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
kadonotakashi 0:8fdf9a60065b 13 * See the License for the specific language governing permissions and
kadonotakashi 0:8fdf9a60065b 14 * limitations under the License.
kadonotakashi 0:8fdf9a60065b 15 */
kadonotakashi 0:8fdf9a60065b 16
kadonotakashi 0:8fdf9a60065b 17 #include "dma_api.h"
kadonotakashi 0:8fdf9a60065b 18 #include "string.h"
kadonotakashi 0:8fdf9a60065b 19 #include "cmsis.h"
kadonotakashi 0:8fdf9a60065b 20 #include "mbed_assert.h"
kadonotakashi 0:8fdf9a60065b 21 #include "PeripheralNames.h"
kadonotakashi 0:8fdf9a60065b 22 #include "nu_modutil.h"
kadonotakashi 0:8fdf9a60065b 23 #include "nu_bitutil.h"
kadonotakashi 0:8fdf9a60065b 24 #include "dma.h"
kadonotakashi 0:8fdf9a60065b 25
kadonotakashi 0:8fdf9a60065b 26 #define NU_PDMA_CH_MAX PDMA_CH_MAX /* Specify maximum channels of PDMA */
kadonotakashi 0:8fdf9a60065b 27 #define NU_PDMA_CH_Pos 0 /* Specify first channel number of PDMA */
kadonotakashi 0:8fdf9a60065b 28 #define NU_PDMA_CH_Msk (((1 << NU_PDMA_CH_MAX) - 1) << NU_PDMA_CH_Pos)
kadonotakashi 0:8fdf9a60065b 29
kadonotakashi 0:8fdf9a60065b 30 struct nu_dma_chn_s {
kadonotakashi 0:8fdf9a60065b 31 void (*handler)(uint32_t, uint32_t);
kadonotakashi 0:8fdf9a60065b 32 uint32_t id;
kadonotakashi 0:8fdf9a60065b 33 uint32_t event;
kadonotakashi 0:8fdf9a60065b 34 };
kadonotakashi 0:8fdf9a60065b 35
kadonotakashi 0:8fdf9a60065b 36 static int dma_inited = 0;
kadonotakashi 0:8fdf9a60065b 37 static uint32_t dma_chn_mask = 0;
kadonotakashi 0:8fdf9a60065b 38 static struct nu_dma_chn_s dma_chn_arr[NU_PDMA_CH_MAX];
kadonotakashi 0:8fdf9a60065b 39
kadonotakashi 0:8fdf9a60065b 40 static void pdma_vec(void);
kadonotakashi 0:8fdf9a60065b 41 static const struct nu_modinit_s dma_modinit = {DMA_0, PDMA_MODULE, 0, 0, PDMA_RST, PDMA_IRQn, (void *) pdma_vec};
kadonotakashi 0:8fdf9a60065b 42
kadonotakashi 0:8fdf9a60065b 43
kadonotakashi 0:8fdf9a60065b 44 void dma_init(void)
kadonotakashi 0:8fdf9a60065b 45 {
kadonotakashi 0:8fdf9a60065b 46 if (dma_inited) {
kadonotakashi 0:8fdf9a60065b 47 return;
kadonotakashi 0:8fdf9a60065b 48 }
kadonotakashi 0:8fdf9a60065b 49
kadonotakashi 0:8fdf9a60065b 50 dma_inited = 1;
kadonotakashi 0:8fdf9a60065b 51 dma_chn_mask = ~NU_PDMA_CH_Msk;
kadonotakashi 0:8fdf9a60065b 52 memset(dma_chn_arr, 0x00, sizeof (dma_chn_arr));
kadonotakashi 0:8fdf9a60065b 53
kadonotakashi 0:8fdf9a60065b 54 // Reset this module
kadonotakashi 0:8fdf9a60065b 55 SYS_ResetModule(dma_modinit.rsetidx);
kadonotakashi 0:8fdf9a60065b 56
kadonotakashi 0:8fdf9a60065b 57 // Enable IP clock
kadonotakashi 0:8fdf9a60065b 58 CLK_EnableModuleClock(dma_modinit.clkidx);
kadonotakashi 0:8fdf9a60065b 59
kadonotakashi 0:8fdf9a60065b 60 PDMA_Open(0);
kadonotakashi 0:8fdf9a60065b 61
kadonotakashi 0:8fdf9a60065b 62 NVIC_SetVector(dma_modinit.irq_n, (uint32_t) dma_modinit.var);
kadonotakashi 0:8fdf9a60065b 63 NVIC_EnableIRQ(dma_modinit.irq_n);
kadonotakashi 0:8fdf9a60065b 64 }
kadonotakashi 0:8fdf9a60065b 65
kadonotakashi 0:8fdf9a60065b 66 int dma_channel_allocate(uint32_t capabilities)
kadonotakashi 0:8fdf9a60065b 67 {
kadonotakashi 0:8fdf9a60065b 68 if (! dma_inited) {
kadonotakashi 0:8fdf9a60065b 69 dma_init();
kadonotakashi 0:8fdf9a60065b 70 }
kadonotakashi 0:8fdf9a60065b 71
kadonotakashi 0:8fdf9a60065b 72 int i = nu_cto(dma_chn_mask);
kadonotakashi 0:8fdf9a60065b 73 if (i != 32) {
kadonotakashi 0:8fdf9a60065b 74 dma_chn_mask |= 1 << i;
kadonotakashi 0:8fdf9a60065b 75 memset(dma_chn_arr + i - NU_PDMA_CH_Pos, 0x00, sizeof (struct nu_dma_chn_s));
kadonotakashi 0:8fdf9a60065b 76 return i;
kadonotakashi 0:8fdf9a60065b 77 }
kadonotakashi 0:8fdf9a60065b 78
kadonotakashi 0:8fdf9a60065b 79 // No channel available
kadonotakashi 0:8fdf9a60065b 80 return DMA_ERROR_OUT_OF_CHANNELS;
kadonotakashi 0:8fdf9a60065b 81 }
kadonotakashi 0:8fdf9a60065b 82
kadonotakashi 0:8fdf9a60065b 83 int dma_channel_free(int channelid)
kadonotakashi 0:8fdf9a60065b 84 {
kadonotakashi 0:8fdf9a60065b 85 if (channelid != DMA_ERROR_OUT_OF_CHANNELS) {
kadonotakashi 0:8fdf9a60065b 86 dma_chn_mask &= ~(1 << channelid);
kadonotakashi 0:8fdf9a60065b 87 }
kadonotakashi 0:8fdf9a60065b 88
kadonotakashi 0:8fdf9a60065b 89 return 0;
kadonotakashi 0:8fdf9a60065b 90 }
kadonotakashi 0:8fdf9a60065b 91
kadonotakashi 0:8fdf9a60065b 92 void dma_set_handler(int channelid, uint32_t handler, uint32_t id, uint32_t event)
kadonotakashi 0:8fdf9a60065b 93 {
kadonotakashi 0:8fdf9a60065b 94 MBED_ASSERT(dma_chn_mask & (1 << channelid));
kadonotakashi 0:8fdf9a60065b 95
kadonotakashi 0:8fdf9a60065b 96 dma_chn_arr[channelid - NU_PDMA_CH_Pos].handler = (void (*)(uint32_t, uint32_t)) handler;
kadonotakashi 0:8fdf9a60065b 97 dma_chn_arr[channelid - NU_PDMA_CH_Pos].id = id;
kadonotakashi 0:8fdf9a60065b 98 dma_chn_arr[channelid - NU_PDMA_CH_Pos].event = event;
kadonotakashi 0:8fdf9a60065b 99
kadonotakashi 0:8fdf9a60065b 100 // Set interrupt vector if someone has removed it.
kadonotakashi 0:8fdf9a60065b 101 NVIC_SetVector(dma_modinit.irq_n, (uint32_t) dma_modinit.var);
kadonotakashi 0:8fdf9a60065b 102 NVIC_EnableIRQ(dma_modinit.irq_n);
kadonotakashi 0:8fdf9a60065b 103 }
kadonotakashi 0:8fdf9a60065b 104
kadonotakashi 0:8fdf9a60065b 105 PDMA_T *dma_modbase(void)
kadonotakashi 0:8fdf9a60065b 106 {
kadonotakashi 0:8fdf9a60065b 107 return (PDMA_T *) NU_MODBASE(dma_modinit.modname);
kadonotakashi 0:8fdf9a60065b 108 }
kadonotakashi 0:8fdf9a60065b 109
kadonotakashi 0:8fdf9a60065b 110 static void pdma_vec(void)
kadonotakashi 0:8fdf9a60065b 111 {
kadonotakashi 0:8fdf9a60065b 112 uint32_t intsts = PDMA_GET_INT_STATUS();
kadonotakashi 0:8fdf9a60065b 113
kadonotakashi 0:8fdf9a60065b 114 // Abort
kadonotakashi 0:8fdf9a60065b 115 if (intsts & PDMA_INTSTS_ABTIF_Msk) {
kadonotakashi 0:8fdf9a60065b 116 uint32_t abtsts = PDMA_GET_ABORT_STS();
kadonotakashi 0:8fdf9a60065b 117 // Clear all Abort flags
kadonotakashi 0:8fdf9a60065b 118 PDMA_CLR_ABORT_FLAG(abtsts);
kadonotakashi 0:8fdf9a60065b 119
kadonotakashi 0:8fdf9a60065b 120 while (abtsts) {
kadonotakashi 0:8fdf9a60065b 121 int chn_id = nu_ctz(abtsts) - PDMA_ABTSTS_ABTIFn_Pos + NU_PDMA_CH_Pos;
kadonotakashi 0:8fdf9a60065b 122 if (dma_chn_mask & (1 << chn_id)) {
kadonotakashi 0:8fdf9a60065b 123 struct nu_dma_chn_s *dma_chn = dma_chn_arr + chn_id - NU_PDMA_CH_Pos;
kadonotakashi 0:8fdf9a60065b 124 if (dma_chn->handler && (dma_chn->event & DMA_EVENT_ABORT)) {
kadonotakashi 0:8fdf9a60065b 125 dma_chn->handler(dma_chn->id, DMA_EVENT_ABORT);
kadonotakashi 0:8fdf9a60065b 126 }
kadonotakashi 0:8fdf9a60065b 127 }
kadonotakashi 0:8fdf9a60065b 128 abtsts &= ~(1 << (chn_id - NU_PDMA_CH_Pos + PDMA_ABTSTS_ABTIFn_Pos));
kadonotakashi 0:8fdf9a60065b 129 }
kadonotakashi 0:8fdf9a60065b 130 }
kadonotakashi 0:8fdf9a60065b 131
kadonotakashi 0:8fdf9a60065b 132 // Transfer done
kadonotakashi 0:8fdf9a60065b 133 if (intsts & PDMA_INTSTS_TDIF_Msk) {
kadonotakashi 0:8fdf9a60065b 134 uint32_t tdsts = PDMA_GET_TD_STS();
kadonotakashi 0:8fdf9a60065b 135 // Clear all transfer done flags
kadonotakashi 0:8fdf9a60065b 136 PDMA_CLR_TD_FLAG(tdsts);
kadonotakashi 0:8fdf9a60065b 137
kadonotakashi 0:8fdf9a60065b 138 while (tdsts) {
kadonotakashi 0:8fdf9a60065b 139 int chn_id = nu_ctz(tdsts) - PDMA_TDSTS_TDIFn_Pos + NU_PDMA_CH_Pos;
kadonotakashi 0:8fdf9a60065b 140 if (dma_chn_mask & (1 << chn_id)) {
kadonotakashi 0:8fdf9a60065b 141 struct nu_dma_chn_s *dma_chn = dma_chn_arr + chn_id - NU_PDMA_CH_Pos;
kadonotakashi 0:8fdf9a60065b 142 if (dma_chn->handler && (dma_chn->event & DMA_EVENT_TRANSFER_DONE)) {
kadonotakashi 0:8fdf9a60065b 143 dma_chn->handler(dma_chn->id, DMA_EVENT_TRANSFER_DONE);
kadonotakashi 0:8fdf9a60065b 144 }
kadonotakashi 0:8fdf9a60065b 145 }
kadonotakashi 0:8fdf9a60065b 146 tdsts &= ~(1 << (chn_id - NU_PDMA_CH_Pos + PDMA_TDSTS_TDIFn_Pos));
kadonotakashi 0:8fdf9a60065b 147 }
kadonotakashi 0:8fdf9a60065b 148 }
kadonotakashi 0:8fdf9a60065b 149
kadonotakashi 0:8fdf9a60065b 150 // Table empty
kadonotakashi 0:8fdf9a60065b 151 if (intsts & PDMA_INTSTS_TEIF_Msk) {
kadonotakashi 0:8fdf9a60065b 152 uint32_t scatsts = PDMA_GET_EMPTY_STS();
kadonotakashi 0:8fdf9a60065b 153 // Clear all table empty flags
kadonotakashi 0:8fdf9a60065b 154 PDMA_CLR_EMPTY_FLAG(scatsts);
kadonotakashi 0:8fdf9a60065b 155 }
kadonotakashi 0:8fdf9a60065b 156
kadonotakashi 0:8fdf9a60065b 157 // Timeout
kadonotakashi 0:8fdf9a60065b 158 uint32_t reqto = intsts & PDMA_INTSTS_REQTOFn_Msk;
kadonotakashi 0:8fdf9a60065b 159 if (reqto) {
kadonotakashi 0:8fdf9a60065b 160 // Clear all Timeout flags
kadonotakashi 0:8fdf9a60065b 161 PDMA->INTSTS = reqto;
kadonotakashi 0:8fdf9a60065b 162
kadonotakashi 0:8fdf9a60065b 163 while (reqto) {
kadonotakashi 0:8fdf9a60065b 164 int chn_id = nu_ctz(reqto) - PDMA_INTSTS_REQTOFn_Pos + NU_PDMA_CH_Pos;
kadonotakashi 0:8fdf9a60065b 165 if (dma_chn_mask & (1 << chn_id)) {
kadonotakashi 0:8fdf9a60065b 166 struct nu_dma_chn_s *dma_chn = dma_chn_arr + chn_id - NU_PDMA_CH_Pos;
kadonotakashi 0:8fdf9a60065b 167 if (dma_chn->handler && (dma_chn->event & DMA_EVENT_TIMEOUT)) {
kadonotakashi 0:8fdf9a60065b 168 dma_chn->handler(dma_chn->id, DMA_EVENT_TIMEOUT);
kadonotakashi 0:8fdf9a60065b 169 }
kadonotakashi 0:8fdf9a60065b 170 }
kadonotakashi 0:8fdf9a60065b 171 reqto &= ~(1 << (chn_id - NU_PDMA_CH_Pos + PDMA_INTSTS_REQTOFn_Pos));
kadonotakashi 0:8fdf9a60065b 172 }
kadonotakashi 0:8fdf9a60065b 173 }
kadonotakashi 0:8fdf9a60065b 174 }