📄 sys_loopback_pl_eg_rx.uc
字号:
/* sys_loopback_eg_rx.uc
*
* This file receives CSIX packets and stores them in DRAM. If the number
* of expected packets is received, it signals the XScale through the
* mailbox register. If it has not received the expected number of packets,
* it writes to scratch to infrom the transmit ME that there is a packet in
* DRAM to be transmitted.
*
*---------------------------------------------------------------------------
*
* I N T E L P R O P R I E T A R Y
*
* COPYRIGHT (c) 2002 BY INTEL CORPORATION. ALL RIGHTS
* RESERVED. NO PART OF THIS PROGRAM OR PUBLICATION MAY
* BE REPRODUCED, TRANSMITTED, TRANSCRIBED, STORED IN A
* RETRIEVAL SYSTEM, OR TRANSLATED INTO ANY LANGUAGE OR COMPUTER
* LANGUAGE IN ANY FORM OR BY ANY MEANS, ELECTRONIC, MECHANICAL,
* MAGNETIC, OPTICAL, CHEMICAL, MANUAL, OR OTHERWISE, WITHOUT
* THE PRIOR WRITTEN PERMISSION OF :
*
* INTEL CORPORATION
*
* 2200 MISSION COLLEGE BLVD
*
* SANTA CLARA, CALIFORNIA 95052-8119
*
*---------------------------------------------------------------------------
*
*
* system: IXDP2400
* subsystem: DIAG
* author: dalsraja, April, 2002
* revisions: dalsraja, May 8, 2002
*
*
* --------------------------------------------------------------------------
*/
#include "common_uc.h"
#define RX_SINGLE_PHY MSF_SINGLE_PHY
#define RX_WIDTH MSF_WIDTH_1x32
#define RX_ENABLE_MASK 0x1
#define RX_MODE MSF_CSIX
#define RX_ELEMENT_SIZE MSF_ELEMENTSIZE_128
#define RBUF_ELEM_COUNT (1 << (7 - RX_ELEMENT_SIZE)) // Tot. elements
#define RBUF_DATA_ELEM_COUNT ((RBUF_ELEM_COUNT >> 2) * 3) // (Tot. elements / 4) * 3
#define RBUF_ADDR_SHF (6 + RX_ELEMENT_SIZE)
#define RX_ELEMENTSIZE_BYTE (1 << RBUF_ADDR_SHF)
#define RX_TRANSFER_THREAD &$TransferReg00
#define RX_SIGNAL_THREAD &rx_sig
#define ME_NUMBER_RX 0
#define ME_NUMBER_TX 1
#define TX_THD_NUM 0
#define INTERTHD_SIG_NUM 15
#define MESSAGE_ADDR 0x200
#define DRAM_PCKT_BASE 0x2000000
#define TOTAL_NUM_PACKETS 36
.reg tmp0 tmp1 temp
.reg sopbit eopbit port_num
.reg RxThreadList
.reg bytecnt elem packet_count ring_num dram_addr packet_num packet_size pkt_buff_addr
.reg RxConfigData0
.reg rbuf Rbufoffset
.reg MsfAddress MsfAddress0 MsfAddress1
.reg $temp0 $temp1 $scratch_data
.reg $TransferReg00 $TransferReg01
.reg RxConfigData $RxConfigData0
.reg scratch_addr dramPacketBase
.reg $prepend_data0 $prepend_data1
.sig MSF_SIG scratch1 rx_sig sig_dram_xfer1 cap_sig scratch_sig
.xfer_order $TransferReg00 $TransferReg01
.xfer_order $prepend_data0 $prepend_data1
.set_sig rx_sig
.set $TransferReg00 $TransferReg01
br=ctx[0, Init_Value#]
ctx_arb[kill]
Init_Value#:
immed[packet_count, 0]
immed[packet_num, 0]
immed[packet_size, 0]
immed[pkt_buff_addr, 0]
immed[scratch_addr, MESSAGE_ADDR]
alu[ring_num, --, B, RING_5, <<2] // ring number in a register
immed[dramPacketBase, (DRAM_PCKT_BASE & MASK_16BIT)]
immed_w1[dramPacketBase, ((DRAM_PCKT_BASE >> 16) & MASK_16BIT)]
//****************************************
// Configure for ctx0
//***************************************
immed[MsfAddress0, RX_THREAD_FREELIST_0]
immed[MsfAddress1, RBUF_ELEMENT_DONE]
immed[RBuf, RBUF_TBUF ]
immed[RxThreadList, ((RX_SIGNAL_THREAD << 12) | (ME_NUMBER_RX << 7) | (0 << 4))]
alu[RxConfigData, RxThreadList, OR , RX_TRANSFER_THREAD]
alu[RxConfigData, --, B, RxConfigData, <<16]
//****************************************************
// Configure RX/TX Control
//****************************************************
immed[RxConfigData0, ((0 << 9) | (RX_ELEMENT_SIZE << 2))] //put control and data into diff freelist
immed_w1[RxConfigData0, ((RX_MODE << 6) | (RX_WIDTH << 4) | (RX_SINGLE_PHY << 3) | (0<<1)|(1<<0))]
alu[$RxConfigData0, --, B, RxConfigData0]
immed[MsfAddress, MSF_RX_CONTROL]
msf[write, $RxConfigData0, MsfAddress, 0, 1], ctx_swap[MSF_SIG]
immed[MsfAddress, CSIX_TYPE_MAP]
alu[$temp1, --, B, MSF_CSIX_RBUF_DATA, <<BIT_SHF_UNICAST]
msf[write, $temp1, MsfAddress, 0, 1], ctx_swap[MSF_SIG]
//******************************************************
// Initialize RBUF Freelist to add elements to the list
//******************************************************
.begin
.reg temp_reg temp
immed[temp_reg, 0]
init_RBUF#:
alu[temp, --, B, temp_reg, <<16]
msf[fast_wr, --, temp, RBUF_ELEMENT_DONE]
alu[temp_reg, temp_reg, +, 1]
alu[--, RBUF_ELEM_COUNT, -, temp_reg]
bne[init_RBUF#]
.end
//****************************************************
// Configure RX/TX Control
//****************************************************
immed[MsfAddress, MSF_RX_CONTROL]
immed[RxConfigData0, ((0 << 9) | (RX_ELEMENT_SIZE << 2))] //put control and data into diff freelist
immed_w1[RxConfigData0, ((RX_ENABLE_MASK << 12) | (RX_MODE << 6) | (RX_WIDTH << 4) | (RX_SINGLE_PHY << 3) | (0<<1)|(1<<0))]
alu[$RxConfigData0, --, B, RxConfigData0]
msf[write, $RxConfigData0, MsfAddress, 0, 1], ctx_swap[MSF_SIG]
//**************************************************
// Configure Scratch Ring
//**************************************************
.begin
.reg $scratch_base $scratch_head $scratch_tail tmp_data
.sig scratch_sig1 scratch_sig2 scratch_sig3
// immed[$scratch_base,0x200]
immed[$scratch_head,0]
immed[$scratch_tail,0]
alu[$scratch_base, --, B, 0, <<9] // Use ring size of 128 lw and base 0x0
cap[write,$scratch_base,SCRATCH_RING_BASE_0],sig_done[scratch_sig1]
cap[write,$scratch_head,SCRATCH_RING_HEAD_0],sig_done[scratch_sig2]
cap[write,$scratch_tail,SCRATCH_RING_TAIL_0],sig_done[scratch_sig3]
ctx_arb[scratch_sig1, scratch_sig2, scratch_sig3]
alu[$scratch_base, --, B, 1, <<9] // Use ring size of 128 lw and base 0x200
cap[write,$scratch_base,SCRATCH_RING_BASE_1],sig_done[scratch_sig1]
cap[write,$scratch_head,SCRATCH_RING_HEAD_1],sig_done[scratch_sig2]
cap[write,$scratch_tail,SCRATCH_RING_TAIL_1],sig_done[scratch_sig3]
ctx_arb[scratch_sig1, scratch_sig2, scratch_sig3]
alu[$scratch_base, --, B, 2, <<9] // Use ring size of 128 lw and base 0x400
cap[write,$scratch_base,SCRATCH_RING_BASE_2],sig_done[scratch_sig1]
cap[write,$scratch_head,SCRATCH_RING_HEAD_2],sig_done[scratch_sig2]
cap[write,$scratch_tail,SCRATCH_RING_TAIL_2],sig_done[scratch_sig3]
ctx_arb[scratch_sig1, scratch_sig2, scratch_sig3]
alu[$scratch_base, --, B, 3, <<9] // Use ring size of 128 lw and base 0x600
cap[write,$scratch_base,SCRATCH_RING_BASE_3],sig_done[scratch_sig1]
cap[write,$scratch_head,SCRATCH_RING_HEAD_3],sig_done[scratch_sig2]
cap[write,$scratch_tail,SCRATCH_RING_TAIL_3],sig_done[scratch_sig3]
ctx_arb[scratch_sig1, scratch_sig2, scratch_sig3]
alu[$scratch_base, --, B, 4, <<9] // Use ring size of 128 lw and base 0x800
cap[write,$scratch_base,SCRATCH_RING_BASE_4],sig_done[scratch_sig1]
cap[write,$scratch_head,SCRATCH_RING_HEAD_4],sig_done[scratch_sig2]
cap[write,$scratch_tail,SCRATCH_RING_TAIL_4],sig_done[scratch_sig3]
ctx_arb[scratch_sig1, scratch_sig2, scratch_sig3]
alu[$scratch_base, --, B, 5, <<9] // Use ring size of 128 lw and base 0xA00
cap[write,$scratch_base,SCRATCH_RING_BASE_5],sig_done[scratch_sig1]
cap[write,$scratch_head,SCRATCH_RING_HEAD_5],sig_done[scratch_sig2]
cap[write,$scratch_tail,SCRATCH_RING_TAIL_5],sig_done[scratch_sig3]
ctx_arb[scratch_sig1, scratch_sig2, scratch_sig3]
.end
context_enable_csr_config#:
//**********************************************************
// Program CSR Context Enables, used by the context arbiter
//**********************************************************
// Initialize CTX_Enables CSR (Put into 8 CTX mode)
// Bit 31: In-Use contexts: 0 = 8 ctx mode, 1 = 4 ctx mode
// Bit 20: Next Neighbour registers are written from this ME
// Bit 17, 1=LM_ADDR_1 is GLOBAL, 0=LM_ADDR_1 is context_relative
// Bit 16, 1=LM_ADDR_0 is GLOBAL, 0=LM_ADDR_0 is context_relative
// Bits [15:8] CTX enables for contexts 7:0
#define In_Use_Contexts 0
#define Control_Store_Parity_Error 0
#define Control_Store_Parity_Enable 0
#define Breakpoint 0
#define NN_Mode 1
#define NN_Ring_Empty 0
#define LM_ADDR_1_Global 0
#define LM_ADDR_0_Global 0
#define Enable 0xff
//*******************************************
// Configure Ctx_Enables
//*******************************************
.begin
.reg CtxEnableData
immed[CtxEnableData, (Enable << 8)]
immed_w1[CtxEnableData, ((In_Use_Contexts << 15)|(Control_Store_Parity_Error << 13)|(Control_Store_Parity_Enable << 12)|(Breakpoint << 11)|(NN_Mode << 4)|(NN_Ring_Empty << 2)|(LM_ADDR_1_Global << 1)|(LM_ADDR_0_Global << 0))]
local_csr_wr[CTX_Enables, CtxEnableData]
.end
immed[temp, ((ME_NUMBER_TX << 7) | (TX_THD_NUM << 4) | (INTERTHD_SIG_NUM << 0))]
alu[--, --, B, temp]
cap[fast_wr, ALU, interthread_sig]
//********************************************************
// Start of Receive
//********************************************************
ReceivePacket#:
.set_sig rx_sig
msf[fast_wr, --, MsfAddress0, RxConfigData] // add thread to freelist
ctx_arb[rx_sig]
// RSW should be in xfer register
// Transfer RBUF data to sram_in transfer registers
//***************************************
// Extract RSW
//****************************************
RSW#:
alu[elem, 0x7f, AND, $TransferReg00, >>24] // get element number
alu[bytecnt, 0xff, AND, $TransferReg00, >>16] // get pkt len
alu[bytecnt, bytecnt, -, PREPEND_LENGTH] // calculate packet length without prepend
//*********************************
// Transfer from ME to DRAM
//*********************************
.begin
.reg cur_rbuf_addr refcnt
alu[cur_rbuf_addr, rbuf, OR, elem, <<RBUF_ADDR_SHF]
msf[read64, $prepend_data0, cur_rbuf_addr, 0, 1], ctx_swap[msf_sig]
alu[sopbit, 1, AND, $prepend_data1, >>1]
alu[eopbit, 1, AND, $prepend_data1]
alu[port_num, --, B, $prepend_data1, >>16]
.if (packet_size == 0)
alu[pkt_buff_addr, dramPacketBase, OR, packet_num, <<8]
.endif
alu[cur_rbuf_addr, cur_rbuf_addr, +, PREPEND_LENGTH]
alu[cur_rbuf_addr, --, B, cur_rbuf_addr, <<5]
alu[cur_rbuf_addr, cur_rbuf_addr, OR, 1, <<4] // set the overwrite bit for the RBUF addr
alu[refcnt, --, B, bytecnt, >>3]
alu[--, bytecnt, AND, 0x7]
beq[cont1#]
alu[refcnt, refcnt, +, 1] // Calculate the refcnt for indirect ref
cont1#:
.if (refcnt > 15) // This is assuming that the RBUF Element are always 128 bytes
immed[refcnt, 15]
.endif
alu[refcnt, --, B, refcnt, <<21] // Shift to appropriate bit
alu[refcnt, refcnt, OR, 1, <<25] // Set the overwrite bit for refcnt
alu[--, cur_rbuf_addr, OR, refcnt] // indirect ref
dram[rbuf_rd, --, pkt_buff_addr, packet_size, 8], indirect_ref, sig_done[sig_dram_xfer1]
ctx_arb[sig_dram_xfer1]
.end
/*
.begin
.reg scratch_add $s_xfer
.sig scratch_sig
alu[packet_count, packet_count, +, 1]
immed[scratch_add, 0x400]
alu[$s_xfer, --, B, packet_count]
scratch[write, $s_xfer, scratch_add, 0, 1], ctx_swap[scratch_sig]
.end
*/
/*
//*****************************************************************
// Write to MAILBOX0 register to signal completion to XScale code
//*****************************************************************
#ifndef WORKBENCH_SIM
.begin
.reg pci_base pci_offset
.reg $pci_rw
.sig pci_sig
immed[pci_base, (PCI_LOCAL_CSR_BASE & MASK_16BIT)]
immed_w1[pci_base, ((PCI_LOCAL_CSR_BASE >> 16) & MASK_16BIT)]
immed[pci_offset, MAILBOX0_OFFSET]
alu[$pci_rw, --, B, bytecnt]
pci[write, $pci_rw, pci_base, pci_offset, 1], ctx_swap[pci_sig]
.end
#endif
*/
//**************************************************************
// Free up Element by writing to RBUF_ELEMENT_DONE{Channel}
//**************************************************************
alu[$temp0, --, B, elem]
msf[write, $temp0, MsfAddress1, 0, 1], ctx_swap[msf_sig]
alu[packet_size, packet_size, +, bytecnt]
.if (eopbit == 0)
br[next_packet#]
.endif
.local temp
alu[temp, packet_size, OR, port_num, <<8]
alu[$scratch_data, temp, OR, packet_num, <<16]
.endlocal
fill#:
br_inp_state[SCR_Ring1_Full, fill#]
scratch[put, $scratch_data, ring_num, 0, 1], ctx_swap[scratch_sig]
immed[packet_size, 0]
alu[packet_num, packet_num, +, 1]
.if (packet_num == TOTAL_NUM_PACKETS)
immed[packet_num, 0]
.endif
next_packet#:
br[ReceivePacket#]
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -