Nios® V/II Embedded Design Suite (EDS)
Support for Embedded Development Tools, Processors (SoCs and Nios® V/II processor), Embedded Development Suites (EDSs), Boot and Configuration, Operating Systems, C and C++
12615 Discussions

HPS t o FPGA access time measuring

Honored Contributor II

Hi everybody, 


I am currently playing around with the Cyclone V SoC Development board. 

I have a QSys system running resembling the Golden system reference design apart from the fact that the h2f_axi_clock is controlled by a PLL residing on FPGA side. 

The h2f_axi_clock is 50 MHz in my case.  


I have an IP test (with many registers) up and running according to the GSRD and connected directly to H2F_axi_master. I used the Linux example to run a Linux (3.7) application on the HPS. From within the application I can write to and read from my IP test in the FPGA, the memory address range is mmaped to the linux user space for this purpose. 

Now the question: 

The time taken to lauch 2 read (or write ) access from an application to my IP registers was mush more than expected (we should have a bandwith of 3.5 GHZ/s I think) : 

According to signal tap (by tracking the chipselect signal): 1 read access takes only 40ns , (1 write, 20ns) whereas between 2 read access there is a 320 ns (same as for write access) . And my application is simple: mmap IP address writes 32-bit values to 10 registers and read back results at the end (by storing them in an array of uint32_t : uint32_t IP_reg[10]). 


read instruction: IP_regs[0]= *((unsigned long *) (map_base + (target & MAP_MASK)+24  ));// (10 accesses such as this one) 

write instruction: *((unsigned long *) (map_base + (target & MAP_MASK) +24  )) = 1;// (10 accesses such as this one) 


How can I accelerate several read write accesses to FPGA IPs from the HPS ? 

Thanks in advance, 



My IP interface: mm_avalon 

Processor : 925 MHz, ARM cortex A9 dual core 

Board: Altera cyclone V SX SoC
0 Kudos
1 Reply
Honored Contributor II

Hi Sam16, 

I appreciate that this is a late reply, but thought a reply might be better than nothing. 


I found I would get better access using commands like memcpy rather than individual reads, but I haven't done as careful timing as you. 

Other options would include setting a pointer, eg 

ip_regs_base = *((unsigned long *)(map_base + ....); 

and then you can do: 

IP_regs[0] = ip_regs_base[0]; 

and ip_regs_base[0] = 1; 

to simplify what the compiler might generate. But memcpy is tailored to moving memory quickly and efficiently, so it will use minimal instructions to do the job. 



0 Kudos