Programmable Devices
CPLDs, FPGAs, SoC FPGAs, Configuration, and Transceivers
20680 Discussions

Access register User app level vs device driver level difference

Altera_Forum
Honored Contributor II
1,016 Views

Hello 

 

I've been using DE1-SoC board for certain project. 

 

The project I'm working on is transfer data from DDR SDRAM (HPS) to FPGA on-chip RAM (FPGA). 

 

As far as I know, in order to access SDRAM from FPGA part, some SDRAM controller setting is required. 

 

I've tried to follow the instruction from this link https://support.criticallink.com/redmine/projects/mityarm-5cs/wiki/important_note_about_fpgahps_sdram_bridge 

 

I neglect the bold warning in step3. But writing values to SDRAM register works in application program. but when I implement same method in device driver, It always crashes. 

 

I've succeeded to access SDRAM register in user application by using mmap system call.  

 

However, if I apply same method to device driver with only difference which is I used ioremap_nocache instead of mmap, the system crashes. 

 

I tested accessing PIO using ioremap_nocache, and controlling fpga LED works fine, which also means it is possible to access lwbridges.. but accessing to SDRAM register, which is other component of FPGA, doesn't work. So I concluded some components are accessible by using ioremap_nocache, but some are not. 

 

I wonder if there are some issue I overlooked when I using ioremap_nocach from device driver.. I attached some codes here.. 

 

Any idea will be really appreciated. Thanks in advance. 

 

 

<application code> // access SDRAM controller register by using mmap 

 

 

int main(void){ 

 

... 

fd = open( "/dev/mem", ( O_RDWR | O_SYNC ) 

... 

virtual_base = mmap( NULL, HW_REGS_SPAN, ( PROT_READ | PROT_WRITE ), MAP_SHARED, fd, HW_REGS_BASE ); 

... 

hps_sdram_portrst = virtual_base + ( ( unsigned long )( HW_SDRAM_PORTRST ) & ( unsigned long)( HW_REGS_MASK ) ); 

hps_sdram_staticcfg = virtual_base + ( ( unsigned long )( HW_SDRAM_STATICCFG ) & ( unsigned long)( HW_REGS_MASK ) ); 

... 

 

*((uint32_t *)hps_sdram_portrst) = 0x000; // all reset 

*((uint32_t *)hps_sdram_staticcfg) = 0x8; // applycfg 

*((uint32_t *)hps_sdram_portrst) = 0x1c7; // pulled out of reset 

 

 

 

<device driver cod> // access SDRAM controller register by using ioremap_nocache 

 

 

static int init(void){ 

 

... 

fpga_base = ioremap_nocache((unsigned long)(HW_REGS_BASE), HW_REGS_SPAN) 

 

fpga_pio = fpga_base + ( (unsigned long)(ALT_LWFPGASLVS_OFST + PIO_INSTR_ADDR_N_LEN_BASE) & (unsigned long)(HW_REGS_MASK) ); 

fpga_portrst = fpga_base + ( (unsigned long)(HW_SDRAM_PORTRST) & (unsigned long)(HW_REGS_MASK) ); 

fpga_static_cfg = fpga_base + ( (unsigned long)(HW_SDRAM_STATICCFG) & (unsigned long)(HW_REGS_MASK) ); 

 

*((unsigned long *)fpga_portrst) = 0x000; 

*((unsigned long *)fpga_static_cfg) = 0x8; 

*((unsigned long *)fpga_portrst) = 0x1f0f; 

 

... 

 

}
0 Kudos
0 Replies
Reply