This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Puzzled with the configuration between BAR and IB_BAR of TMS320C6670

Other Parts Discussed in Thread: TMS320C6670

Now, I am using TMS320C6670, and I am puzzled when use PCIESS. On page 39 of sprugs6c said:

 

“In 32-bit addressing, BAR0 is dedicated to Address Space 0 and BAR1-BAR5 are dedicated to Address Space 1. Regions 0~3 should be associated only with BAR1~BAR5”.

 

But when I use the PCIE boot_loader example of mcsdk_2_01_02_05, I find some codes are conflicted with it.

 

/* Configure IB_BAR0 to BAR0 for PCIE registers;

Configure IB_BAR1 to BAR1 for LL2 for core 0

Configure IB_BAR2 to BAR2 for MSMC;

  Configure IB_BAR3 to BAR3 for DDR */

for (i = 0; i < 4; i++)

{

                     iowrite32(i, ptrReg + IB_BAR(i)/4);    

                     iowrite32(PCIE_DEV->resource[i].start, ptrReg + IB_START_LO(i)/4);   

                     iowrite32(0, ptrReg + IB_START_HI(i)/4);

}    

              iowrite32(PCIE_BASE_ADDRESS, ptrReg + IB_OFFSET(0)/4);   

              iowrite32(LL2_START + (1 << 28), ptrReg + IB_OFFSET(1)/4);   

              iowrite32(MSMC_START, ptrReg + IB_OFFSET(2)/4); 

              iowrite32(DDR_START, ptrReg + IB_OFFSET(3)/4);

 

Is there something wrong with it?

Thank you very much!

  • Xiang,

    As mentioned in the PCIe user guide, the BAR0 is fixed mapping to PCIe application registers. It is not necessary to associate inbound transaction to BAR0.

    The demo code will be updated in the later release of MCSDK. In the current demo code, you can ignore IB_BAR0 since it does not affect BAR0 usage on PCIe module. Or you can update the code yourself to free up IB_BAR0 for other usage.

  • Hi,

        " iowrite32(i, ptrReg + IB_BAR(i)/4);

         ....

        ......"

        why does ' IB_BAR(i) ' divide 4 ?  

  • I think it is because "ptrReg" is defined as 32-bit pointer as below:

    uint32_t *ptrReg = 0; 

    "ptrReg+1" means ptrReg move forward 32-bit (4-byte).

    But "IB_BAR(n)" is defined in byte, so you need to divide it by 4 to get the correct index for that register address to work with "ptrReg".

    You can also do some experiments to verify if "ptrReg+IB_BAR(i)/4" is pointing to the correct register address as well.

  • Hi,

        Thanks a lot, I get it.

        Here is another question : why " uint32_t *prtReg = 0" is right ?  I thought a pointer should point to a actual address.         

        Does it also means " uint32_t *ptrReg = 0x0000 0000 " ?

  • I think it is just some initial value for this pointer and it will be re-assigned to the real PCIe application register address before actually using it, as follows in the code:

    /* Pointing to the beginning of the application registers */
    ptrReg = (uint32_t *)regVirt;

  • Hi,

        Gotcha, thanks !

         Now I am facing a very seriously problem to me : The OS of my computer is Win7 64bit, In our project there are some      data located in the main memory(PC) that needed to be calculated in the core of c6678, take the efficiency into                consideration, I need to use the DMA in the CPU(PC) to transfer these data(about 6MB size) via PCIe. So I need to        configurate the DMA.

        My questions are :

              1. Can I use global address of c6678 when I define the destination address?

              2. The data flows from CPU(PC) to DSP or from DSP to CPU(PC), which situation I can use EDMA3 to transfer                these data ? Or neither can ?

              3. Do I need to configurate PCIe inbound or outbound address translate registers ?

        Can you please tell me more details about this kind of problem or what kind of problem I should avoid?

  • 1. I am not quite sure about how PCIe is working with Win7 OS. You may refer to the PCIe driver manual in your OS or other related documents. If it is similar as C6678 DSP, the CPU/DMA needs to use the PCIe data space (starting from 0x60000000 in C6678) as destination address, in order to write or read those packets via PCIe link. And the PCIe address of those packets will be the same as destination address. If you are using PCIe in PC as RC and PCIe in DSP as EP, you need to setup BARs in EP to match the PCIe address of those incoming packets in order to receive them correctly. 

    2. For PCIe, there are outbound transactions (local device initiates the transfer) and inbound transactions (remote device initiates the transfer). In this case, you can use EDAM3 in DSP to generate both outbound write (write packets from DSP to PC) and outbound read (read packets from PC to DSP) to PCIe slave port in DSP. 

    3. For DSP inbound transfer, the remote device (PC) will transfer the packets to PCIe master port of DSP via PCIe link. And the PCIe master port in DSP will distribute those packets to the target DSP memory based on the PCIe address with those packets received. If those PCIe address are targeted to the DSP memory address already (such as 0x80000000 for DDR, 0x0C000000 for MSMC SRAM, etc), you do not need to enable inbound address translation.

    But some of the time, the PCIe address with those packets are not matching the DSP memory address directly or your need to transfer those packets to other locations, the inbound address translation could be enabled to help in this situation. Please take  a look at the section "2.7 Address Translation" in PCIe user guide and PCIe use case application note for examples.

    Basically you need to know what is the PCIe address coming out of RC or EP and what is the memory location the packets are targeted to. Then you can setup the BAR or inbound/outbound translations in RC and/or EP to make sure the transfer could be completed correctly.

    It will also be good to open new thread for new questions for us to keep track of those threads and make it easier for later reference. Thanks.

  • Hi, Steven ji:

    I am trying to perform a data transfer from FPGA(K7) to C6678 over DMA, C6678 as RC, FPGA as EP.

    FPGA load a xilinx PCIE DMA CORE, communicate with C6678 directly, and RefClock= 100M, linkSpeed=2.5G, lane num = 1.

    Firstly, I initial the C6678 PCIE follow the example: "C:\ti\pdk_C6678_1_1_2_6\packages\ti\drv\pcie\example\sample\pcie_sample.c".

    The configuration is as follows:

    gpPCIE_RC_regs->BAR[1]= 0x90000000;

    gpPCIE_app_regs->INBOUND_TRANSLATION[0].IB_BAR = 1;

    gpPCIE_app_regs->INBOUND_TRANSLATION[0].IB_START_LO = 0x90000000;

    gpPCIE_app_regs->INBOUND_TRANSLATION[0].IB_START_HI = 0x00000000;

    gpPCIE_app_regs->INBOUND_TRANSLATION[0].IB_OFFSET = 0x00000000;

    gpPCIE_app_regs->CMD_STATUS |= (CSL_PCIESS_APP_CMD_STATUS_IB_XLT_EN_MASK);



    gpPCIE_app_regs->OUTBOUND_TRANSLATION[0].OB_OFFSET_INDEX = 0x70000001;

    gpPCIE_app_regs->OUTBOUND_TRANSLATION[0].OB_OFFSET_HI = 0x0;

    gpPCIE_app_regs->CMD_STATUS |= (CSL_PCIESS_APP_CMD_STATUS_OB_XLT_EN_MASK);

    And, PCIE link training successfully with FPGA, and I can read the FPGA configuration space too.

    Then, I config the FPGA's configuration space as follow:

    gpPCIE_remote_EP_regs->BAR[0] = 0x70000000;
    gpPCIE_remote_EP_regs->STATUS_COMMAND |= 0x00000006;

    And, C6678 can read & write FPGA MEMORY SPACE successfully by PCIE.

    Finally, I config the FPGA DMA CORE throught PCIE, such as: ADDR(0x00801000),SIZE(63),COUNT(129), then START DMA.

    I can see The FPGA send the TLP packets successfully by ChipScope, However, I can't read the correct values in ADDR(0x00801000).

    What's the matter? Do I miss any thing?

    Does the C6678 need to start EDMA?

    Who can help me?The project is very urgent.

    Looking forward to your reply.



    many Thanks

    btyang