📄 byte_align_be.uc
字号:
//----------------------------------------------------------------------
//
// I N T E L P R O P R I E T A R Y
//
// COPYRIGHT (c) 2001 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
//
//----------------------------------------------------------------------
//
// Filename : byte_align_be.uc
//
// Description: This macro byte aligns a 64 byte ethernet packet in
// big endian mode.
// It takes as input a 64 byte ethernet packet from RBUF,
// strips off the 14 byte ethernet header and byte aligns
// the contained IP packet in DRAM.
//
// History :
//
// Date Comment By
// --------------------------------------------------------------------
//
// 10/18/2001 Created. asv
// 01/21/2002 Removed code that was otherwise needed to avoid asv
// assembler warnings in earlier workbench versions.
// 10/14/2002 Cleaned up code. Added coding conventions. asv
//----------------------------------------------------------------------
#include "msf.uc"
// Defines starting address of RBUF (8KB : 0x2000 - 0x3FFF) in the
// MSF memory map. The ethernet packet will be in RBUF.
#define RBUF_TBUF_ADDR 0x2000
// Defines the DRAM address where the byte-aligned IP packet will
// be stored.
#define _DST_DRAM_ADDR 0x50
//----------------------------------------------------------------------
// _byte_align_be()
//
// Description: This macro byte aligns a 64 byte ethernet packet.
// It takes as input a 64 byte ethernet packet, strips
// off the 14-byte ethernet header and byte aligns the
// contained IP packet.
//
// Parameters:
// Inputs:
// in_rbuf_ele:
// RBUF element number containing ethernet packet.
// in_dst_dram_addr:
// DRAM address that will contain IP packet.
//
//----------------------------------------------------------------------
#macro _byte_align_be(in_rbuf_ele, in_dst_dram_addr)
.begin
// Declaring DRAM transfer registers that will be used.
.reg $$data0 $$data1 $$data2 $$data3 \
$$data4 $$data5 $$data6 $$data7 \
$$data8 $$data9 $$data10 $$data11 \
$$data12 $$data13 $$data14 $$data15
// Defines the ordering of DRAM transfer registers.
.xfer_order $$data0 $$data1 $$data2 $$data3 \
$$data4 $$data5 $$data6 $$data7 \
$$data8 $$data9 $$data10 $$data11 \
$$data12 $$data13 $$data14 $$data15
// Put zeroes in the upper 16 bits.
.reg last_word
immed[last_word, 0, <<16]
// Set byte shift as 2 - needed by the byte_align_be instruction.
// Setting a byte shift of 2 aligns the IP packet on a 4 byte
// boundary in DRAM. (see readme.txt)
// The local_csr_wr needs 3 nops or equivalent instructions.
local_csr_wr[byte_index, 2]
// Compute offset where the packet resides in RBUF.
// Shift by 6 for a 64-byte RBUF element.
.reg rbuf_offset
alu_shf[rbuf_offset, --, B, in_rbuf_ele, <<6]
// Store RBUF base address in a gpr.
.reg rbuf_addr
immed[rbuf_addr, RBUF_TBUF_ADDR]
// Read the 64 byte ethernet packet from RBUF into transfer
// registers $$data0-$$data15.
.sig msf_rd_sig
// Set ref cnt to 15 (to read 16 lw's) using indirect format.
// Also set the reference count override bit (bit 25).
alu[--, --, b, 0x1F, <<21]
msf[read, $$data0, rbuf_addr, rbuf_offset, max_16], indirect_ref, \
ctx_swap[msf_rd_sig]
// Discard the ethernet header (first 14 bytes), so start reading
// from the lower 16 bits of $$data3.
// Byte align the IP packet starting from the ls 16 bits of $$data3
// until the ms 16 bits of $$data15
// Store the result of the alignment in $$data0-$$data12
byte_align_be[--, $$data3]
byte_align_be[$$data0, $$data4]
byte_align_be[$$data1, $$data5]
byte_align_be[$$data2, $$data6]
byte_align_be[$$data3, $$data7]
byte_align_be[$$data4, $$data8]
byte_align_be[$$data5, $$data9]
byte_align_be[$$data6, $$data10]
byte_align_be[$$data7, $$data11]
byte_align_be[$$data8, $$data12]
byte_align_be[$$data9, $$data13]
byte_align_be[$$data10, $$data14]
byte_align_be[$$data11, $$data15]
// Byte align the ls 16 bits of $$data15 and pad the rest of the
// ouput with zeroes
byte_align_be[$$data12, last_word]
// This register is not used but since we can write to DRAM only
// in quad-words, it is used by the dram[write] instruction when
// writing 50 bytes (13 lw's or 7 qw's) to DRAM.
immed[$$data13, 0]
// Write the byte aligned IP packet to DRAM starting at location
// 'in_dst_dram_addr'
.sig dram_wr_sig
// Set ref cnt to 6 (to write 7 qw's) using indirect format.
// Also set the reference count override bit (bit 25).
alu[--, --, b, 0x16, <<21]
dram[write, $$data0, in_dst_dram_addr, 0, max_7], indirect_ref, \
sig_done[dram_wr_sig]
ctx_arb[dram_wr_sig]
.end
#endm
// Execution starts here.
// Run only on thread 0.
br=ctx[0, start#]
ctx_arb[kill]
start#:
// Signal used to indicate a packet has been received by the thread.
.sig volatile pkt_rx_sig
// Registers that contain information about the received packet.
// .set is needed since these registers are implicitly written to
// when a packet is received.
.reg $rsw0 $rsw1
.xfer_order $rsw0 $rsw1
.set $rsw0 $rsw1
// Register that contains information to add the thread to a
// freelist after it is done processing a received packet.
.reg freelist_gpr
// Initialize MSF to start receiving packets.
_msf_init(freelist_gpr)
// Wait until a packet is received.
ctx_arb[pkt_rx_sig]
// Get RBUF element number containing the packet.
.reg rbuf_ele
alu_shf[rbuf_ele, 0x7F, AND, $rsw0, >>24]
// Set dst address for packet in DRAM.
.reg dst_dram_addr
immed[dst_dram_addr, _DST_DRAM_ADDR]
// Byte align an ethernet packet in big endian mode.
_byte_align_be(rbuf_ele, dst_dram_addr)
// Free resources used while processing the packet.
_msf_reset(rbuf_ele, freelist_gpr)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -