I have an AXI4 initiator that issues a 32-bit read request to an AXI target (memory) via a 64-bit wide data bus.
I set the ARSIZE parameter to 2.
The data in the target memory are the following:addr : data0x000: 64'h 77_66_55_44_33_22_11_000x100: 64'h 00_00_00_00_00_00_00_00
I am getting the following response data at the initiator interface:
In all cases, burst_type = INCR and burst_len = 0
case1: raddress = 'd0; ARSIZE= 'd2;rdata_rcvd: 64'h 77_66_55_44_33_22_11_00 rdata_expected = 64'h 77_66_55_44_33_22_11_00
case2: raddress = 'd4; ARSIZE= 'd2rdata_rcvd: 64'h 77_66_55_44_33_22_11_00 rdata_expected = 64'h xx_xx_xx_xx_77_66_55_44
case3: raddress = 'd5; ARSIZE= 'd2
rdata_rcvd: 64'h 77_66_55_44_33_22_11_00 rdata_expected = 64'h xx_xx_xx_xx_77_66_55_44
In case2 and case3, I expected that the slave aligns the 32-bit data on bits 0 to 32 of the 64-bit data bus.Does the slave behaves correct or my understanding of ARSIZE parameter is wrong?
The AXI protocol defines which byte lanes can be used for transfers based on the AxADDR, AxSIZE and AxBURST values. So where a transfer is narrower than the data bus, the data bytes will be transferred on these limited valid byte lanes, and not aligned to the LSBs of the data bus as you expected.
So for case 1 the start address is 0 (byte lane 0), and transfer width is 4 bytes, the valid data is 64'h xx_xx_xx_xx_33_22_11_00.
Case 2 you have a start address of 0x4 (byte lane 4) and transfer width 4 bytes, so the valid data is 64'h 77_66_55_44_xx_xx_xx_xx.
In case 3 you have a start address of 0x5 (byte lane 5) and transfer width 4 bytes. But the unaligned start address (not aligned to ARADDR) means that the allowed range of byte lanes is just 3 bytes (byte lanes 7 to 5), so the valid data is 64'h 77_66_55_xx_xx_xx_xx_xx (byte lane 4 is invalid because of the unaligned start address).
In this example the AXI target is ignoring ARSIZE and is just returning all 8 byte lanes, leaving it to the AXI initiator to look at the byte lanes it requested valid data on. Not a protocol issue, just probably keeping the AXI target design simpler.
Thank you. This answers my question.
So the initiator has to store the AxSIZE information of all pending requests. It will use this information to shift the received data and get the correct data. If the specification mandated that the target had to align the read data to the AxSIZE, the additional overhead for storing the size information in the initiator could have been avoided. Am I correct?
Your solution is one possible alternative solution, but something has to change the position of the data from the byte lanes corresponding to the address to the LSBs of the data bus. It is the initiator that requests the data, so it should be the one to do any data manipulation once received. The target should just provide the data bytes requested, and using the byte lanes corresponding to the address for the transfer.
There may be some obscure applications where the initiator WANTS the bytes to remain in the MSBs (or the correct byte lanes), perhaps it is performing a read/modify/write sequence, so it doesn't want the target to "manipulate" the data before returning it.
So best leave the initiator to do any data manipulation required as it is the module that knows what it wants to do with the data.
Ok. Thank you for the answer