This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Copy ram data to flash via DMA (CC2541)

Other Parts Discussed in Thread: CC2541

Hi, I'm programming a CC2541 device and I need to copy the content of a part of the ram to the flash memory. I must do it without high level libraries (has HAL or OSAL) so I did this code:

/******************************************************************************
* INCLUDES
*/
#include <ioCC2541.h>
#include <stdlib.h> 

/******************************************************************************
* DEFINES
*/
#define INIT_RAM 0x0C00
#define INIT_FLASH 0xC000
#define COPY_LEN 512 // 256x8b = 4k = 4096b

//! Low nibble of 16bit variable
#define LOBYTE(w)           ((unsigned char)(w))
//! High nibble of 16bit variable
#define HIBYTE(w)           ((unsigned char)(((unsigned short)(w) >> 8) & 0xFF))


/******************************************************************************
* FUNCIONES     
*/
void programmer_init(void)
{
  // Switch programmer (a CC2530) to 32 MHz XOSC for max performance
  CLKCONCMD = 0x80;
  while (CLKCONSTA != 0x80);
}

/**************************************************************************//**
* @brief    Main function.
*
* @return   None.
******************************************************************************/
void main(void)
{
  asm("nop"); // For debugging.
  programmer_init();
  
  unsigned char * mem = (unsigned char *) INIT_RAM;
  mem[0]='H';
  mem[1]='E';
  mem[2]='L';
  mem[3]='L';
  mem[4]='O';
  
  
  MEMCTR = 0x08;
  
    //Start Flash Page 0xC1 erase.
    EA=0;
    FADDRH=HIBYTE(INIT_FLASH)+1; 
    FCTL|=0x01; //Erase with cache
    while (FCTL & 0x80);  // Wait until writing is done.
    
    //Start Flash Page 0xC0 erase.
    FADDRH=HIBYTE(INIT_FLASH); 
    FCTL|=0x01; //Erase with cache
    while (FCTL & 0x80);  // Wait until writing is done.
    EA=1;
  
  
  //SETUP DMA Controller.
  unsigned char * dma_desc_0 = (unsigned char *)0x1f00;
  dma_desc_0[7]=HIBYTE(INIT_RAM);           // src[15:8]
  dma_desc_0[6]=LOBYTE(INIT_RAM);           // src[7:0]
  dma_desc_0[5]=HIBYTE(FWDATA);           // dest[15:8]
  dma_desc_0[4]=LOBYTE(FWDATA);           // dest[7:0]
  dma_desc_0[3]=HIBYTE(COPY_LEN);            // len[12:8] 
  dma_desc_0[2]=LOBYTE(COPY_LEN);             // len[7:0]
  dma_desc_0[1]=0x12;                 
  dma_desc_0[0]=0x4A; 
  
  DMA0CFGH = HIBYTE(dma_desc_0); 
  DMA0CFGL = LOBYTE(dma_desc_0); 
  
  //SETUP Flash Controller.
  FADDRH=HIBYTE(INIT_FLASH); 
  FADDRL=LOBYTE(INIT_FLASH); 
  
  
  //ARM DMA Channel.
  DMAARM=1; //Arm Channel 0.
  
  //Arm Process takes 9 System Clocks.
  for(int i=0;i<11;i++){
    asm("nop");
  }
  
  //Start Flash Write.
  FCTL = 0x06; //FCTL |= 0x02;         // Trigger the DMA writes.
  
  // Wait until writing is done.
  
  while (FCTL & 0x80){
    asm("nop");
  }
 
  // Infinite loop
  while(1){
    asm("nop");
  }
}

I don't really know why it's not working because nothing is copied to flash. I've spent several hours trying to find out the mistake, and I need your help.

Thanks in advance.

Alfred.