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.

6678 SRIO维护的问题



        6678通过交换芯片CPS1848与FPGA相连通信,现在已经实现了1x 2.5G的通信。

        但是每一次改动DSP程序,重新load之后,必须先重新load交换芯片和FPGA的程序才能够再次实现通信。如果不load FPGA和交换芯片的程序,即使一开始port ok,发送一个数据包之后port的状态也会进入错误(根据err_stat寄存器的值得到)。

        而且如果是FPGA和DSP双向发送接收的话,每一次按照顺序load完程序(交换芯片,FPGA,最后DSP),DSP程序尚未运行即可以收到FPGA传送过来的数据,但是一旦程序运行,运行完函数Keystone_SRIO_Init(&srio_cfg);之后,接收即终止了,之后也没办法继续接收FPGA传输的数据。而此时DSP可以正常向FPGA传输数据。

        不知道是不是因为没有添加维护函数Keystone_SRIO_match_ACK_ID(0, FPGA_SRIO_BASE_ID, 2);的原因?

        但是在初始化函数之后添加该维护函数之后,我却一直没办法运行通过该函数,停在了函数的while循环之中如下:

do
 {  
  //set the remote OUTBOUND_ACKID to be same as local INBOUND_ACKID
  uiLocal_In_ACK_ID= (srioRegs->RIO_SP[uiLocalPort].RIO_SP_ACKID_STAT&CSL_SRIO_RIO_SP_ACKID_STAT_INB_ACKID_MASK)>>
   CSL_SRIO_RIO_SP_ACKID_STAT_INB_ACKID_SHIFT;

  uiMaintenanceValue= ((uiRemote_In_ACK_ID+1)<<
   CSL_SRIO_RIO_SP_ACKID_STAT_INB_ACKID_SHIFT)|uiLocal_In_ACK_ID;

  //set the remote ACK_ID through maintenance packet
  uiResult= Keystone_SRIO_Maintenance(uiLocalPort, uiLocalPort, uiDestID,
    0x148+(0x20*uiRemotePort), GLOBAL_ADDR(&uiMaintenanceValue),
     SRIO_PKT_TYPE_MTN_WRITE);

  if(flag_maintenance == 0)
   break;
  if(uiResult)  //fail
   continue; 
  
  //readback the remote ID
  uiResult= Keystone_SRIO_Maintenance(uiLocalPort, uiLocalPort,
   uiDestID, 0x148+(0x20*uiRemotePort), GLOBAL_ADDR(&uiMaintenanceValue),
   SRIO_PKT_TYPE_MTN_READ);
  uiRemote_out_ACK_ID= uiMaintenanceValue&
   CSL_SRIO_RIO_SP_ACKID_STAT_OUTB_ACKID_MASK;
  }while(uiResult|(uiLocal_In_ACK_ID+1 != uiRemote_out_ACK_ID));

uiResult的值是能够返回0的,也就是读写都成功了?但是uiMaintenanceValue的值在读之后一直是0,导致无法退出循环。

请问该维护函数是DSP和交换芯片之间的读写嘛?还是DSP和FPGA之间的读写?

维护函数始终无法通过是否是因为DSP是小端而交换芯片是大端的原因?

还有始终要load交换芯片和FPGA程序是否是因为没有维护函数的原因?

  • 1 是读写成功的

    2  退出循环的条件是 除了 读写成功,且uiLocal_inACK_ID+1要等于 uiRemote_out_ACK_ID

    3   这里程序本身是看link partner,,  在您的场景中, 是DSP和交换芯片的

    4    如果DSP配置成little endian模式,由于RAPID IO协议是基于 big endian传输的,所以在程序中要把维护包的数据值进行反序


    uiCompletionCode= KeyStone_SRIO_wait_LSU_completion(uiLSU_No,
    lsuTransfer.transactionID, lsuTransfer.contextBit);

    #ifdef _LITTLE_ENDIAN
    Uint32 * uipData = (Uint32 *)uiLocalAddress;

    //swap maintenance value for little endian
    *uipData= _swap4(_packlh2(*uipData, *uipData));
    #endif

    5 重新load才能正常运行的原因一般是ACK ID 没有匹配上,也就是您的测试中,始终没有退出while循环

  • Thomas Yang1 说:

    1 是读写成功的

    2  退出循环的条件是 除了 读写成功,且uiLocal_inACK_ID+1要等于 uiRemote_out_ACK_ID

    3   这里程序本身是看link partner,,  在您的场景中, 是DSP和交换芯片的

    4    如果DSP配置成little endian模式,由于RAPID IO协议是基于 big endian传输的,所以在程序中要把维护包的数据值进行反序


    uiCompletionCode= KeyStone_SRIO_wait_LSU_completion(uiLSU_No,
    lsuTransfer.transactionID, lsuTransfer.contextBit);

    #ifdef _LITTLE_ENDIAN
    Uint32 * uipData = (Uint32 *)uiLocalAddress;

    //swap maintenance value for little endian
    *uipData= _swap4(_packlh2(*uipData, *uipData));
    #endif

    5 重新load才能正常运行的原因一般是ACK ID 没有匹配上,也就是您的测试中,始终没有退出while循环

    感谢你的回复。

    还想请问一下,在维护函数中Keystone_SRIO_match_ACK_ID(0, FPGA_SRIO_BASE_ID, 2);第二个参数是对方的deviceID,在我这种应用场景下,该设备ID应该是交换芯片的设备ID?还是应该是FPGA的?

    因为始终没有找到交换芯片的deviceID,所以一直使用的是FPGA的deviceID,但是也能读写成功,即返回值为0.

    谢谢。

  • SWITCH 应该也有自己的DEVICE ID的,试试呢?

  • Thomas Yang1 说:

    SWITCH 应该也有自己的DEVICE ID的,试试呢?

    你好,还想请教你一下。

    在调试中,第一次上电我们按照交换芯片,FPGA,DSP这样的顺序来load程序,结果可以正常的收发。

    之后重新load了交换芯片和FPGA的程序,没有load DSP的程序,DSP端就只能够接收FPGA的数据而不能发送出去,此时端口状态寄存器err_stat显示端口错误,最低字节为6.

    然后load了DSP的程序并对DSP进行重新初始化,跑完SRIO的初始化程序之后,端口状态OK,即err_stat寄存器最低字节为2.但此时DSP不能接收数据只能发送数据,这个时候观测交换芯片对应的端口的寄存器,发现端口状态出错,最低字节为6。

    请问

    1.是否可以这么理解,交换芯片和FPGA重新load程序之后,DSP的SRIO仍然处于已初始化的状态,所以可以直接和交换芯片连接上接收数据,但是为何端口状态会是错误,从而无法发送数据?

    2.为何DSP重新进行一次初始化之后,交换芯片那一端的端口状态就变为了错误,导致这个时候DSP只能发送不能接收?

    3.出现这些错误的原因是没有进行维护吗?

    4.一边端口出错的情况下,应该使用maintenance函数进行维护吗?还是端口出错maintenance函数在这种情况下就没有作用了?

    5.如果不是使用maintenance函数,那么这个错误应该怎么解决啊?

    谢谢

  • 你好,请问你的问题是否解决,我也遇到了跟你类似的问题!