AnsweredAssumed Answered

EIM in iMX7D in Multiplexed synchronous Read/Write mode

Question asked by bipin kumar on Apr 15, 2019
Latest reply on Apr 16, 2019 by igorpadykov

Hi,

I am trying to run the EIM interface in 16 bit Multiplexed synchronous(Burst) mode( to interface EIM with FPGA ). Please find the source code below:

  1. // WEIM clock root and clock gate registers
  2. #define CCM_BASE_ADDRESS    0x30380000
  3. #define CCM_CCGR22          0x30384160
  4. #define CCM_TARGET_ROOT83   0x3038A980
  5.  
  6. /* WEIM registers */
  7. typedef struct
  8. {
  9.      UINT32 EIM_CS0GCR1;
  10.      UINT32 EIM_CS0GCR2;
  11.      UINT32 EIM_CS0RCR1;
  12.      UINT32 EIM_CS0RCR2;
  13.      UINT32 EIM_CS0WCR1;
  14.      UINT32 EIM_CS0WCR2;
  15.      UINT32 EIM_CS1GCR1;
  16.      UINT32 EIM_CS1GCR2;
  17.      UINT32 EIM_CS1RCR1;
  18.      UINT32 EIM_CS1RCR2;
  19.      UINT32 EIM_CS1WCR1;
  20.      UINT32 EIM_CS1WCR2;
  21.      UINT32 EIM_CS2GCR1;
  22.      UINT32 EIM_CS2GCR2;
  23.      UINT32 EIM_CS2RCR1;
  24.      UINT32 EIM_CS2RCR2;
  25.      UINT32 EIM_CS2WCR1;
  26.      UINT32 EIM_CS2WCR2;
  27.      UINT32 EIM_CS3GCR1;
  28.      UINT32 EIM_CS3GCR2;
  29.      UINT32 EIM_CS3RCR1;
  30.      UINT32 EIM_CS3RCR2;
  31.      UINT32 EIM_CS3WCR1;
  32.      UINT32 EIM_CS3WCR2;
  33.      UINT32 EIM_CS4GCR1;
  34.      UINT32 EIM_CS4GCR2;
  35.      UINT32 EIM_CS4RCR1;
  36.      UINT32 EIM_CS4RCR2;
  37.      UINT32 EIM_CS4WCR1;
  38.      UINT32 EIM_CS4WCR2;
  39.      UINT32 EIM_CS5GCR1;
  40.      UINT32 EIM_CS5GCR2;
  41.      UINT32 EIM_CS5RCR1;
  42.      UINT32 EIM_CS5RCR2;
  43.      UINT32 EIM_CS5WCR1;
  44.      UINT32 EIM_CS5WCR2;
  45.      UINT32 EIM_WCR;
  46.      UINT32 EIM_DCR;
  47.      UINT32 EIM_DSR;
  48.      UINT32 EIM_WIAR;
  49.      UINT32 EIM_EAR;
  50. }tEIM_CSP_WEIM_REGS, *ptEIM_CSP_WEIM_REGS;
  51.  
  52. //-----------------------------------------------------------------------------
  53. // Configure the IOs for the iMX7 EIM bus
  54. /// @param[in] hGpio    handle received from Gpio_Init()
  55. /// @retval     TRUE       Success
  56. /// @retval     FALSE      Failure
  57. BOOL Eim_ConfigureIos(HANDLE hGpio)
  58. {
  59.      int i;
  60.      BOOL fSuccess = TRUE;
  61.  
  62.      const uIo eimIo[] =
  63.      {
  64.          COLIBRI_PIN( 89),   // RW
  65.          COLIBRI_PIN( 91),   // OE
  66.          COLIBRI_PIN(105),   // CS0_B
  67.          COLIBRI_PIN(150),   // LBA_B
  68.          COLIBRI_PIN(152),   // BCLK
  69.          COLIBRI_PIN(111),   // AD0
  70.          COLIBRI_PIN(113),   // AD1
  71.          COLIBRI_PIN(115),   // AD2
  72.          COLIBRI_PIN(117),   // AD3
  73.          COLIBRI_PIN(119),   // AD4
  74.          COLIBRI_PIN(121),   // AD5
  75.          COLIBRI_PIN(123),   // AD6
  76.          COLIBRI_PIN(125),   // AD7
  77.          COLIBRI_PIN(110),   // AD8
  78.          COLIBRI_PIN(112),   // AD9
  79.          COLIBRI_PIN(114),   // AD10
  80.          COLIBRI_PIN(116),   // AD11
  81.          COLIBRI_PIN(118),   // AD12
  82.          COLIBRI_PIN(120),   // AD13
  83.          COLIBRI_PIN(122),   // AD14
  84.          COLIBRI_PIN(124)    // AD15
  85.      };
  86.  
  87.      /// The EIM functionality is on Alternate Function 4 for all EIM pins.
  88.      for (i = 0; i < _countof(eimIo); i++)
  89.          fSuccess &= Imx7Gpio_SetConfigString(hGpio, eimIo[i], NULL, L"AltFn=4", StoreVolatile);
  90.  
  91.      return fSuccess;
  92. }
  93.  
  94. //*****************************************************************************
  95. /// Main function
  96. /// @param[in]  argc    number of command line arguments
  97. /// @param[in]  argv    array containing command line arguments
  98. /// @retval     1       Success
  99. /// @retval     0       Failure
  100. int wmain(int argc, _TCHAR* argv[])
  101. {
  102.      BOOL   fSuccess = TRUE;
  103.      HANDLE hMap;
  104.      HANDLE hGpio;
  105.  
  106.      volatile ptEIM_CSP_WEIM_REGS pEimReg;
  107.      volatile DWORD *clkRegs;
  108.      volatile DWORD  tmp;
  109.      volatile UINT16 *extBus;
  110.      volatile DWORD *targetAddr;
  111.      UINT16 i;
  112.      UINT16 buff[ ] = { 0xAA,0x11,0x22,0x77,0x33,0x44,0x55,0x66 };
  113.  
  114.      // Enable EIM Clock,
  115.      hMap = Map_Init();
  116.      clkRegs  = (DWORD* )Map_MapMemory(CCM_BASE_ADDRESS, 0x10000);
  117.      targetAddr =  clkRegs + (CCM_CCGR22 - CCM_BASE_ADDRESS)/4;
  118.      *targetAddr &= ~0xFFFFFFFF;
  119.      targetAddr = clkRegs + (CCM_TARGET_ROOT83 - CCM_BASE_ADDRESS)/4;
  120.      *targetAddr |= 0x16030000;    //  125MHz/4
  121.      targetAddr = clkRegs + (CCM_CCGR22 - CCM_BASE_ADDRESS)/4;
  122.      *targetAddr |= 0x03;
  123.  
  124.      // configure EIM GPIOs
  125.      hGpio = Imx7Gpio_Init(NULL);
  126.      fSuccess &= Eim_ConfigureIos(hGpio);
  127.      fSuccess &= Imx7Gpio_Deinit(hGpio);
  128.  
  129.      // Configure CS0 properties for multiplexed, asynchronous operation
  130.      pEimReg = (ptEIM_CSP_WEIM_REGS)Map_MapMemory(0x30BC0000, 0x1000);
  131.      pEimReg->EIM_WIAR &=    ~( 1 << 4 );
  132.      pEimReg->EIM_CS0GCR1 = 0x0011013F; 
  133.      pEimReg->EIM_CS0GCR2 = 0x00001000; 
  134.      pEimReg->EIM_CS0RCR1 = 0x01000000;
  135.      pEimReg->EIM_CS0RCR2 = 0x00000000; 
  136.      pEimReg->EIM_CS0WCR1 = 0x01000000; 
  137.      pEimReg->EIM_CS0WCR2 = 0x00000000;   
  138.      pEimReg->EIM_WCR |=        ( 1 << 3 );
  139.      pEimReg->EIM_WIAR |=    ( 1 << 4 );
  140.      printf("CSxGCR1 main reg: 0x%08X\n",pEimReg->EIM_CS0GCR1);
  141.      printf("CSxGCR2 main reg: 0x%08X\n",pEimReg->EIM_CS0GCR2);
  142.      printf("CSxRCR1 main reg: 0x%08X\n",pEimReg->EIM_CS0RCR1);
  143.      printf("CSxRCR2 main reg: 0x%08X\n",pEimReg->EIM_CS0RCR2);
  144.      printf("CSxWCR1 main reg: 0x%08X\n",pEimReg->EIM_CS0WCR1);
  145.      printf("CSxWCR2 main reg: 0x%08X\n",pEimReg->EIM_CS0WCR2);
  146.      printf("WCR main reg: 0x%08X\n",pEimReg->EIM_WCR);
  147.      printf("WIAR main reg: 0x%08X\n",pEimReg->EIM_WIAR);
  148.      printf("DCR main reg: 0x%08X\n",pEimReg->EIM_DCR);
  149.      printf("DSR main reg: 0x%08X\n",pEimReg->EIM_DSR);
  150.  
  151.  
  152.      // Access memory at CS0 address.
  153.      // The address range for nCS0 is 0x28000000 to 0x28FFFFFF (128MB).
  154.      // However, we map only 64kB here.
  155.      extBus =(UINT16* )Map_MapMemory(0x28000000, 0x5000);
  156.     
  157.      while(1)
  158.      {   
  159.          memcpy( (UINT16*)extBus, buff, sizeof( buff ) );       
  160.     
  161.      }
  162.  
  163.      return 1;
  164. }

As per my understanding when using burst mode with every address assertion an address and then a burst of data(8 Words in my case) will be sent on EIM bus and then process repeats as I am running a while loop. However this is not a happening in my case. I am not able to see this behaviour. Data is not coming in burst and Address, CS and RW signals are not as per configuration.

There are few queries for better understanding of the interface:

1. Is there difference between Synchronous mode and Burst mode ?

2. Is there any initialisation sequence for continuous BCLK Multiplexed synchronous mode ?

3. In case of fix latency mode all the wait states are ignored( like WWSC/RWSC) ?

4. Start address of CS0 is 0x28000000, I haven't found it in iMX7D reference guide, From where i can find the addresses of all the chip selects ?

Regards

Bipin Kumar

Outcomes