Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
example4.h
00001 /* 00002 * Demonstrates sending a buffer repeatedly to the DAC using DMA. 00003 * Connect an oscilloscope to Mbed pin 18. This example doesn't 00004 * output anything else (nothing on any serial ports). 00005 */ 00006 #include "mbed.h" 00007 #include "MODDMA.h" 00008 00009 // Make the buffer size match the number of degrees 00010 00011 // in a circle since we are going to output a sinewave. 00012 #define BUFFER_SIZE 360 00013 00014 // Set DAC output power mode. 00015 00016 #define DAC_POWER_MODE (1 << 16) 00017 00018 DigitalOut led1(LED1); 00019 DigitalOut led3(LED3); 00020 DigitalOut led4(LED4); 00021 00022 int buffer[2][BUFFER_SIZE]; 00023 00024 AnalogOut signal(p18); 00025 00026 MODDMA dma; 00027 MODDMA_Config* conf0, *conf1; 00028 00029 void TC0_callback(void); 00030 void ERR0_callback(void); 00031 00032 void TC1_callback(void); 00033 void ERR1_callback(void); 00034 00035 /** 00036 * @brief 00037 * @note 00038 * @param 00039 * @retval 00040 */ 00041 int main() 00042 { 00043 volatile int life_counter = 0; 00044 00045 // Create a sinewave buffer for testing. 00046 for (int i = 0; i <= 90; i++) 00047 buffer[0][i] = (512 * sin(3.14159 / 180.0 * i)) + 512; 00048 for (int i = 91; i <= 180; i++) 00049 buffer[0][i] = buffer[0][180 - i]; 00050 for (int i = 181; i <= 270; i++) 00051 buffer[0][i] = 512 - (buffer[0][i - 180] - 512); 00052 for (int i = 271; i < 360; i++) 00053 buffer[0][i] = 512 - (buffer[0][360 - i] - 512); 00054 00055 // Adjust the sinewave buffer for use with DAC hardware. 00056 for (int i = 0; i < 360; i++) { 00057 buffer[0][i] = DAC_POWER_MODE | ((buffer[0][i] << 6) & 0xFFC0); 00058 buffer[1][i] = buffer[0][i]; // Just create a copy of buffer0 to continue sinewave. 00059 } 00060 00061 // Prepare the GPDMA system for buffer0. 00062 conf0 = new MODDMA_Config; 00063 conf0->channelNum(MODDMA::Channel_0); 00064 conf0->srcMemAddr((uint32_t) & buffer[0]); 00065 conf0->dstMemAddr(MODDMA::DAC); 00066 conf0->transferSize(360); 00067 conf0->transferType(MODDMA::m2p); 00068 conf0->dstConn(MODDMA::DAC); 00069 conf0->attach_tc(&TC0_callback); 00070 conf0->attach_err(&ERR0_callback); 00071 00072 // Prepare the GPDMA system for buffer1. 00073 conf1 = new MODDMA_Config; 00074 conf1->channelNum(MODDMA::Channel_1); 00075 conf1->srcMemAddr((uint32_t) & buffer[1]); 00076 conf1->dstMemAddr(MODDMA::DAC); 00077 conf1->transferSize(360); 00078 conf1->transferType(MODDMA::m2p); 00079 conf1->dstConn(MODDMA::DAC); 00080 conf1->attach_tc(&TC1_callback); 00081 conf1->attach_err(&ERR1_callback); 00082 00083 // Calculating the transfer frequency: 00084 // By default, the Mbed library sets the PCLK_DAC clock value 00085 // to 24MHz. One complete sinewave cycle in each buffer is 360 00086 // points long. So, for a 1Hz wave we would need to transfer 360 00087 // values per second. That would be 24000000/360 which is approx 00088 // 66,666. But that's no good! The count val is only 16bits in size 00089 // so bare this in mind. If you need to go slower you will need to 00090 // alter PCLK_DAC from CCLK/4 to CCLK/8. 00091 // For our demo we are going to have the sinewave run at 1kHz. 00092 // That's 24000000/360000 which is approx 66. Experimentation 00093 // however showed 65 to get closer to 1kHz (on my Mbed and scope 00094 // at least). 00095 LPC_DAC->DACCNTVAL = 65; // 6500 for 10Hz 00096 00097 // Prepare first configuration. 00098 if (!dma.Prepare(conf0)) { 00099 error("Doh!"); 00100 } 00101 00102 // Begin (enable DMA and counter). Note, don't enable 00103 // DBLBUF_ENA as we are using DMA double buffering. 00104 LPC_DAC->DACCTRL |= (3UL << 2); 00105 00106 while (1) { 00107 00108 // There's not a lot to do as DMA and interrupts are 00109 // now handling the buffer transfers. So we'll just 00110 // flash led1 to show the Mbed is alive and kicking. 00111 if (life_counter++ > 1000000) { 00112 led1 = !led1; // Show some sort of life. 00113 life_counter = 0; 00114 } 00115 } 00116 } 00117 00118 // Configuration callback on TC 00119 void TC0_callback(void) 00120 { 00121 // Just show sending buffer0 complete. 00122 led3 = !led3; 00123 00124 // Get configuration pointer. 00125 MODDMA_Config* config = dma.getConfig(); 00126 00127 // Finish the DMA cycle by shutting down the channel. 00128 dma.Disable((MODDMA::CHANNELS) config->channelNum()); 00129 00130 // Swap to buffer1 00131 dma.Prepare(conf1); 00132 00133 // Clear DMA IRQ flags. 00134 if (dma.irqType() == MODDMA::TcIrq) 00135 dma.clearTcIrq(); 00136 } 00137 00138 // Configuration callback on Error 00139 void ERR0_callback(void) 00140 { 00141 error("Oh no! My Mbed EXPLODED! :( Only kidding, go find the problem"); 00142 } 00143 00144 // Configuration callback on TC 00145 void TC1_callback(void) 00146 { 00147 // Just show sending buffer1 complete. 00148 led4 = !led4; 00149 00150 // Get configuration pointer. 00151 MODDMA_Config* config = dma.getConfig(); 00152 00153 // Finish the DMA cycle by shutting down the channel. 00154 dma.Disable((MODDMA::CHANNELS) config->channelNum()); 00155 00156 // Swap to buffer0 00157 dma.Prepare(conf0); 00158 00159 // Clear DMA IRQ flags. 00160 if (dma.irqType() == MODDMA::TcIrq) 00161 dma.clearTcIrq(); 00162 } 00163 00164 // Configuration callback on Error 00165 void ERR1_callback(void) 00166 { 00167 error("Oh no! My Mbed EXPLODED! :( Only kidding, go find the problem"); 00168 }
Generated on Mon Dec 12 2022 15:08:43 by
1.7.2