//###################### P U B L I C   F U N C T I O N S ####################### 
void initEMC(void)
{
    //Power up lcd peripheral
    CLKPWR_ConfigPPWR (CLKPWR_PCONP_PCEMC, true);
    configureEMCPins();
    
    //Disable all dynamic memory features
    LPC_EMC->DynamicControl = 0;
    
    LPC_EMC->Control = 0; //Disable peripheral
        
    //Set little endian format
    LPC_EMC->Config = 0;    
        
    //Use half clock as CPU 60 MHz
    LPC_SC->EMCCLKSEL = 1;
    //Disable automatic address shifting
    //LPC_SC->SCS |=  (1 << 0);
    configureEMCForStaticMemory(&extProgFlash);
   
    LPC_EMC->Control |= 1; //Enable the EMC 
    
    for(volatile uint32_t i = 0; i < 99999; i++) {}
}
//##################### P R I V A T E   F U N C T I O N S ###################### 
static void configureEMCForStaticMemory(const EmcStaticMemoryConfig* conf)
{
    //Set Extende wait  time out
    //0x0 = 16 clock cycles.
    //0x1 - 0x3FF = (n+1) x16 clock cycles.    
    if(conf->extWait == EMC_MEM_EXTENDED_WAIT_ENABLE)
        LPC_EMC->StaticExtendedWait = 0;    
     
    *statMemChanReg[conf->chan].StaticConfig = conf->memWidth;
    *statMemChanReg[conf->chan].StaticConfig |= conf->pageMode;
    *statMemChanReg[conf->chan].StaticConfig |= conf->chipSel;
    *statMemChanReg[conf->chan].StaticConfig |= conf->laneState;
    *statMemChanReg[conf->chan].StaticConfig |= conf->extWait;
    *statMemChanReg[conf->chan].StaticConfig |= conf->buffer;
    *statMemChanReg[conf->chan].StaticConfig |= conf->wrProt;
    
    //Write enable delay: chip select -> write enable.
    //0x0 = One EMCCLK cycle delay between assertion of chip select and we
    //0x1 - 0xF = (n + 1) * EMCCLK cycle delay.
    *statMemChanReg[conf->chan].StaticWaitWen = conf->writeEnableDelay;
    //Output enable delay: chip select or address change, whichever is later,
    //                     to the output enable.    
    //0x0 = No delay (POR reset value).
    //0x1 - 0xF = n cycle delay. The delay is WAITOEN x tEMCCLK.    
    *statMemChanReg[conf->chan].StaticWaitOen = conf->readEnableDelay;
    
    //Read delay: chip select -> read access
    //first read only: 0x0 - 0x1E = (n + 1) * EMCCLK cycles for read accesses.
    //For non-sequential reads, the wait state time is (WAITRD + 1) x tEMCCLK.
    //0x1F = 32 EMCCLK cycles for read accesses.
    *statMemChanReg[conf->chan].StaticWaitRd = conf->readDataDelay;
    
    //Page Mode ready delay:
    //0x0 - 0x1E = (n + 1) * EMCCLK cycle read access time
    //0x1F = 32 EMCCLK cycle read access time.
    *statMemChanReg[conf->chan].StaticWaitPage = conf->pageModeDelay;
    
    //Write delay:  chip select -> write access
    //0x0 - 0x1E = (n + 2) * EMCCLK cycle write access time.
    //0x1F = 33 EMCCLK cycle write access time.
    *statMemChanReg[conf->chan].StaticWaitWr = conf->writeDataDelay; 
    
    ////Turn round delay: number of bus turnaround cycles
    //0x0 - 0xE = (n + 1) * EMCCLK turn-around cycles.
    //0xF = 16 EMCCLK turn-around cycles.
    *statMemChanReg[conf->chan].StaticWaitTurn = conf->waitTurnDelay;
}
static void configureEMCPins(void)
{
    //OE
    PINSEL_ConfigPin(4, 24, 1);
    
    //WE
    PINSEL_ConfigPin(4, 25, 1);
    
    //BLE
    PINSEL_ConfigPin(4, 26, 1);
    
    //BHE
    PINSEL_ConfigPin(4, 27, 1);
    
    //CS0
    PINSEL_ConfigPin(4, 30, 1);
    
    //CS1
    PINSEL_ConfigPin(4, 31, 1);
    
    //D0_15
    for(uint8_t dataPin = 0; dataPin < 16; dataPin ++)
        PINSEL_ConfigPin(3, dataPin, 1);
    
    //A0_21
    for(uint8_t addrPin = 0; addrPin < 23; addrPin ++)
        PINSEL_ConfigPin(4, addrPin, 1);
}      |