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

MAX10 RSU Project

EEren
Novice
1,655 Views

I'm looking at MAX10 RSU Project - an example how to download a binary image file to CFM1/2.

There is following lines

case 9: /*State 9: Start write into CFM1 with new image*/ for(address=CFM1StartAddress; address<=CFM1EndAddress; address=address+4) {   scanf("%2x%2x%2x%2x",&receivedHex[0],&receivedHex[1],&receivedHex[2],&receivedHex[3]); /*Get 4 bytes from UART Terminal*/ for(byte=0; byte<4; byte++) { receivedHex[byte] = (((receivedHex[byte] & 0xaa)>>1)|((receivedHex[byte] & 0x55)<<1)); /*Swap LSB with MSB before write into CFM*/ receivedHex[byte] = (((receivedHex[byte] & 0xcc)>>2)|((receivedHex[byte] & 0x33)<<2)); receivedHex[byte] = (((receivedHex[byte] & 0xf0)>>4)|((receivedHex[byte] & 0x0f)<<4)); }   word = (receivedHex[0]<<24)|(receivedHex[1]<<16)|(receivedHex[2]<<8)|(receivedHex[3]); /*Combine 4 bytes to become 1 word before write operation*/ IOWR_32DIRECT(ONCHIP_FLASH_0_DATA_BASE, address, word); /*Command to write into On-Chip Flash IP*/   and so on...

The first question - why the address incremented by 4 - for(address=CFM1StartAddress; address<=CFM1EndAddress; address=address+4) - every address holds 32 bits.

The second one - we get bytes from rpd file but lsb byte goes as msb byte in the address? word = (receivedHex[0]<<24)|(receivedHex[1]<<16)|(receivedHex[2]<<8)|(receivedHex[3]);

0 Kudos
5 Replies
sstrell
Honored Contributor III
1,320 Views

Avalon masters use byte addressing so the address has to be incremented by 4 each time for 32 bit data.

 

The endian swap is required for the bitstream data put into the CFM. See app note 741 for details:

 

https://www.intel.com/content/dam/www/programmable/us/en/pdfs/literature/an/an741.pdf

 

#iwork4intel

0 Kudos
JohnT_Intel
Employee
1,320 Views

Hi,

 

Avalon Master is using byte addressing so that it can handle different data width from 8bit to 64bit data.

 

The default rpd file generated is in little endian format while the On Chip Memory need Big Endian format. So if you are using little endian format rpd file then you will need to performed endian swap.

0 Kudos
EEren
Novice
1,320 Views

Why byte addressing? It says we writes words in ug-m10-ufm-16.0.pdf, so we create a word word = (receivedHex[0]<<24)|(receivedHex[1]<<16)|(receivedHex[2]<<8)|(receivedHex[3]); then write it to a specific address and then what? skip 4 addresses?

 

When I generate FLASH UPDATE IP in QSYS

component flash_update is

   port (

      clock                  : in std_logic                    := '0';            --   clk.clk

      avmm_csr_addr          : in std_logic                    := '0';            --   csr.address

      avmm_csr_read          : in std_logic                    := '0';            --      .read

      avmm_csr_writedata     : in std_logic_vector(31 downto 0) := (others => '0'); --      .writedata

      avmm_csr_write         : in std_logic                    := '0';            --      .write

      avmm_csr_readdata      : out std_logic_vector(31 downto 0);                   --      .readdata

      avmm_data_addr         : in std_logic_vector(18 downto 0) := (others => '0'); --  data.address

      avmm_data_read         : in std_logic                    := '0';            --      .read

      avmm_data_writedata    : in std_logic_vector(31 downto 0) := (others => '0'); --      .writedata

      avmm_data_write        : in std_logic                    := '0';            --      .write

      avmm_data_readdata     : out std_logic_vector(31 downto 0);                   --      .readdata

      avmm_data_waitrequest  : out std_logic;                                       --      .waitrequest

      avmm_data_readdatavalid : out std_logic;                                       --      .readdatavalid

      avmm_data_burstcount   : in std_logic_vector(3 downto 0) := (others => '0'); --      .burstcount

      reset_n                : in std_logic                    := '0'             -- nreset.reset_n

   );

end component;

 

as we can see data bus 32-bit and on every write I should increment avmm_data_addr by one as I understand.

 

When I create Altera On-Chip Flash IP I get the following addresses

sector 3 - 0x10000 - 0x6FFFF

sector 4 - 0x70000 - 0xB7FFF

sector 5 - 0xB8000 - 0x15FFFF

 

But when I Generate HDL

SECTOR3_START_ADDR            => 16384,

SECTOR3_END_ADDR                => 114687,

SECTOR4_START_ADDR            => 114688,

 SECTOR4_END_ADDR               => 188415,

 SECTOR5_START_ADDR           => 188416,

 SECTOR5_END_ADDR               => 360447,

 

So it's already divided by 4. Isn't it?

0 Kudos
JohnT_Intel
Employee
1,320 Views

Hi,

 

If you are refering to Avalon-MM Slave then it is addition by 1 on each avmm_data_addr or avmm_csr_addr.

 

0 Kudos
sstrell
Honored Contributor III
1,320 Views

As mentioned, Avalon masters use byte addressing and Avalon slaves use word addressing. The word size is typically the data width (32 in this case). So Avalon masters access the registers/memory locations for a slave at addresses 0x0, 0x4, 0x8, etc. For a 16 bit slave, the master would access the slave at 0x0, 0x2, 0x4, etc., though if the master itself is 32-bit, it would only need to access at 0x0, 0x4, etc. and could use byte enables for the appropriate bytes/words. See the Avalon spec for details:

 

https://www.intel.com/content/dam/www/programmable/us/en/pdfs/literature/manual/mnl_avalon_spec.pdf

 

Also check out online training:

 

https://www.intel.com/content/www/us/en/programmable/support/training/course/oqsys3000.html

 

#iwork4intel

0 Kudos
Reply