Dependencies: mbed NetServicesMin
main.cpp
- Committer:
- fernya
- Date:
- 2012-06-18
- Revision:
- 0:aa9ebbd3715f
File content as of revision 0:aa9ebbd3715f:
/* * Demonstrates sending a buffer repeatedly to the DAC using DMA. * Connect an oscilloscope to Mbed pin 18. This example doesn't * output anything else (nothing on any serial ports). */ #include "mbed.h" #include "MODDMA.h" #include "EthernetNetIf.h" #include "ipaddr.h" #include "UDPSocket.h" #include "fifo.h" #include "rtp.h" // Make the buffer size match the number of degrees // in a circle since we are going to output a sinewave. #define BUFFER_SIZE 300 // Set DAC output power mode. #define DAC_POWER_MODE (1 << 16) DigitalOut led1(LED1); DigitalOut led2(LED2); DigitalOut led3(LED3); DigitalOut led4(LED4); volatile int life_counter = 0; EthernetNetIf eth; UDPSocket data_sock; fifo circ_buf; char packet_buf[512] = {0}; struct rtp_header head; int play[2][40]; AnalogOut signal(p18); Timer timeout; MODDMA dma; MODDMA_Config *conf0, *conf1; void TC0_callback(void); void ERR0_callback(void); void TC1_callback(void); void ERR1_callback(void); int ethInit(void); int udpInit(void); void UDPReceive(UDPSocketEvent e); int main() { //serial initialization Serial pc(USBTX, USBRX); pc.baud(115200); //serial init done ethInit(); udpInit(); // Prepare the GPDMA system for buffer0. conf0 = new MODDMA_Config; conf0 ->channelNum ( MODDMA::Channel_0 ) ->srcMemAddr ( (uint32_t) &play[0] ) ->dstMemAddr ( MODDMA::DAC ) ->transferSize ( 40 ) ->transferType ( MODDMA::m2p ) ->dstConn ( MODDMA::DAC ) ->attach_tc ( &TC0_callback ) ->attach_err ( &ERR0_callback ) ; // config end // Prepare the GPDMA system for buffer1. conf1 = new MODDMA_Config; conf1 ->channelNum ( MODDMA::Channel_1 ) ->srcMemAddr ( (uint32_t) &play[1] ) ->dstMemAddr ( MODDMA::DAC ) ->transferSize ( 40 ) ->transferType ( MODDMA::m2p ) ->dstConn ( MODDMA::DAC ) ->attach_tc ( &TC1_callback ) ->attach_err ( &ERR1_callback ) ; // config end // Calculating the transfer frequency: // By default, the Mbed library sets the PCLK_DAC clock value // to 24MHz. LPC_DAC->DACCNTVAL = 3000; // 24e6/8000 // Prepare first configuration. if (!dma.Prepare( conf0 )) { error("Doh!"); } // Begin (enable DMA and counter). Note, don't enable // DBLBUF_ENA as we are using DMA double buffering. LPC_DAC->DACCTRL |= (3UL << 2); while (1) { // There's not a lot to do as DMA and interrupts are // now handling the buffer transfers. So we'll just // flash led1 to show the Mbed is alive and kicking. if (life_counter++ > 100000) { led1 = !led1; // Show some sort of life. life_counter = 0; Net::poll(); } } } // Configuration callback on TC void TC0_callback(void) { // Get configuration pointer. MODDMA_Config *config = dma.getConfig(); // Finish the DMA cycle by shutting down the channel. dma.Disable( (MODDMA::CHANNELS)config->channelNum() ); // Swap to buffer1 dma.Prepare( conf1 ); // Clear DMA IRQ flags. if (dma.irqType() == MODDMA::TcIrq) dma.clearTcIrq(); int i; for (i=0; i<40; i++) { circ_buf.get((uint32_t*)&play[0][i]); } } // Configuration callback on Error void ERR0_callback(void) { error("Oh no! My Mbed EXPLODED! :( Only kidding, go find the problem"); } // Configuration callback on TC void TC1_callback(void) { // Get configuration pointer. MODDMA_Config *config = dma.getConfig(); // Finish the DMA cycle by shutting down the channel. dma.Disable( (MODDMA::CHANNELS)config->channelNum() ); // Swap to buffer0 dma.Prepare( conf0 ); // Clear DMA IRQ flags. if (dma.irqType() == MODDMA::TcIrq) dma.clearTcIrq(); int i; for (i=0; i<40; i++) { circ_buf.get((uint32_t*)&play[1][i]); } } // Configuration callback on Error void ERR1_callback(void) { error("Oh no! My Mbed EXPLODED! :( Only kidding, go find the problem"); } int ethInit(void) { //Ethernet konfiguracio (DHCP) printf("Setting up...\r\n"); EthernetErr ethErr = eth.setup(); IpAddr ownIP = eth.getIp(); printf("My IP is: %d.%d.%d.%d\r\n",ownIP[0],ownIP[1],ownIP[2],ownIP[3]); if (ethErr) { printf("Error %d in Ethernet setup.\r\n", ethErr); return -1; } printf("Setup OK\r\n"); return 0; //Ethernet konfiguracio vege } int udpInit(void) { //UDP konfiguracio Host rtp_addr; data_sock.setOnEvent(&UDPReceive); UDPSocketErr sockErr = data_sock.bind(Host(IpAddr(), 5004)); printf("Ack\r\n"); if (sockErr) { printf("Error %d in socket setup.\r\n", sockErr); return -1; } return 0; //UDP konfiguracio vege } /**UDP recv callback */ void UDPReceive(UDPSocketEvent e) { short * data_ptr; int i,length; int tmp; switch (e) { case UDPSOCKET_READABLE: Host host; while ( int len = data_sock.recvfrom(packet_buf, 512, &host ) ) { if ( len <= 0 ) break; rtp_decompose(packet_buf, len, &head, (char**)&data_ptr); length = head.data_len/2; for ( i = 0; i < length; i++ ) { tmp = ntohs(data_ptr[i]); //network to host endianness tmp = ((tmp + 0x7FFF) & 0xFFC0) | (DAC_POWER_MODE); //format DAC register input (signed->unsigned conversion and masking) circ_buf.put( tmp ); //fill the circular buffer } } break; } }