Commit 26cac626 authored by Tomasz Wlostowski's avatar Tomasz Wlostowski

userspace: removed test_rtu (obsolute and not compatibile with newer RTU implementations)

parent 7a62875c
CC=$(CROSS_COMPILE)gcc
WR_INSTALL_ROOT ?= $(WRS_OUTPUT_DIR)/images/wr
OBJS = rtu_sim.o rtu_hw.o rtu_test.o rtu_common.o \
rtu_test_data.o rtu_test_main.o
LDFLAGS = -L$(WR_INSTALL_ROOT)/lib -lswitchhw
CFLAGS = -I. -O2 -I../include -DDEBUG
BINARY = rtu_sim
all: $(OBJS)
${CC} -o $(BINARY) $(OBJS) $(LDFLAGS)
clean:
rm -f $(BINARY) *.o *~
install:
install -d $(WR_INSTALL_ROOT)/bin
install $(BINARY) $(WR_INSTALL_ROOT)/bin
#!/bin/sh
. ../../../settings
t=`pwd`
cd ../../libswitchhw
./build.sh clean
./build.sh
cd $t
make CROSS_COMPILE=$CC_CPU $1 $2 $3 $4
/*
-------------------------------------------------------------------------------
-- Title : Routing Table Unit Common (for SIM & HW) Functions
-- Project : White Rabbit Switch
-------------------------------------------------------------------------------
-- File : rtu_common.c
-- Authors : Maciej Lipinski (maciej.lipinski@cern.ch)
-- Company : CERN BE-CO-HT
-- Created : 2010-06-30
-- Last update: 2010-06-30
-- Description: This file contain functions which interface H/W
*/
#include <stdio.h>
#include <inttypes.h>
#include "rtu_sim.h"
#define POLYNOMIAL SIM_POLYNOMIAL_CCITT
/*
================================================================================
HASH COMPUTATION
================================================================================
*/
/*
==================================================================================
hash function presented below, produces hash which correspondes to hash produced
by VHDL generated on this page :generated with: http://outputlogic.com/
==================================================================================
-------------------------------------------------------------------------------
-- SOME EXPLANATION REGARDING VHDL vs C CRC IMPLEMENTATION BY ML
-------------------------------------------------------------------------------
-- C code to produce exactly the same CRC as VHDL generated
-- with http://outputlogic.com/ .
-- it uses naive method, it's not optimal at all
-- but it's good enough to chech whether VHDL works OK
-- It was made (by maciej.lipinski@cern.ch) modifying source from here:
-- http://www.netrino.com/Embedded-Systems/How-To/CRC-Calculation-C-Code
-- the website provides explanation of CRC
--
-- To get the hex representation of POLY to be used with the C function, which is different
-- than hex representation of polly used to generate VHDL code (i.e.:0x1021 <->0x88108),
-- here is the trick:
--
-- 1) we are using the following poly equation: 1+x^5+x^12+x^16;
-- 2) it translates to binary: (1) 0001 0000 0010 0001 = 0x1021
-- | |
-- | this is default | this you can find in
-- |-> it's the 16th bit |-> the wiki as description
-- of the polly equation
--
-- 3) we include the "default" bit into the polly and add zeroes at the end
-- creating 20 bit polly, like this
-- (1) 0001 0000 0010 0001 => 1000 1000 0001 0000 1000 = 0x88108
--
--------------------------------------------------------------------------------
--| name | polly equation | polly (hex) | our polly | tested |
--------------------------------------------------------------------------------
--| CRC-16-CCITT | 1+x^5+x^12+x^16 | 0x1021 | 0x88108 | yes |
--| CRC-16-IBM | 1+x^2+x^15+x^16 | 0x8005 | 0xC0028 | yes |
--| CRC-16-DECT | 1+x^3+x^7+x^8+x^10+x^16 | 0x0589 | 0x82C48 | yes |
--------------------------------------------------------------------------------
--
*/
uint16_t
crcNaive16_2(uint16_t const message, uint16_t const init_crc)
{
uint32_t remainder;
int bit;
/*
* Initially, the dividend is the remainder.
*/
remainder = message^init_crc;// (message << 4) | 0x000;
//remainder = 0xFF ^ message;
/*
* For each bit position in the message....
*/
for (bit = 20; bit > 0; --bit)
{
/*
* If the uppermost bit is a 1...
*/
if (remainder & 0x80000)
{
/*
* XOR the previous remainder with the divisor.
*/
if(CFG.hash_poly == SIM_POLYNOMIAL_DECT || CFG.hash_poly == SIM_POLYNOMIAL_CCITT || CFG.hash_poly == SIM_POLYNOMIAL_IBM)
remainder ^= CFG.hash_poly;
else
remainder ^= POLYNOMIAL;
}
/*
* Shift the next bit of the message into the remainder.
*/
remainder = (remainder << 1);
}
/*
* Return only the relevant bits of the remainder as CRC.
*/
return (remainder >> 4);
return remainder;
} /* crcNaive() */
uint16_t
hash(uint16_t mac_hi, uint32_t mac_lo, uint8_t fid)
{
uint16_t tmp;
tmp = crcNaive16_2((0x0000 | fid) ,0xFFFF);
tmp = crcNaive16_2(mac_hi ,tmp);
tmp = crcNaive16_2((0xFFFF & (mac_lo >> 16 )),tmp);
tmp = crcNaive16_2((0xFFFF & mac_lo) ,tmp);
return (0x7FF & tmp);
}
uint32_t zbt_addr_get(/*int bank,*/ int bucket, uint16_t mac_hi, uint32_t mac_lo, uint8_t fid)
{
uint16_t tmp;
tmp = hash(mac_hi, mac_lo, fid);
uint32_t ret = 0xFFFF & ((tmp << 5) | ((0x3 & bucket) << 3) | 0x0);
return ret;
/*
if(bank)
return ret;
else
return (0xFFFF & ret);
*/
}
This diff is collapsed.
/*
-------------------------------------------------------------------------------
-- Title : Routing Table Unit Hardware Access Functions
-- Project : White Rabbit Switch
-------------------------------------------------------------------------------
-- File : rtu_hw.h
-- Authors : Maciej Lipinski (maciej.lipinski@cern.ch)
-- Company : CERN BE-CO-HT
-- Created : 2010-06-30
-- Last update: 2010-06-30
-- Description: Some usefull addresses in FPGA defined here
*/
#define HW_POLYNOMIAL_DECT 0x0589
#define HW_POLYNOMIAL_CCITT 0x1021
#define HW_POLYNOMIAL_IBM 0x8005
#define FPGA_BASE_RTU 0x60000
#define FPGA_BASE_PORT0 0x80000
#define FPGA_BASE_PORT1 0xa0000
#define FPGA_BASE_PORT2 0xc0000
#define FPGA_BASE_PORT3 0xe0000
#define FPGA_BASE_PORT4 0x100000
#define FPGA_BASE_PORT5 0x120000
#define FPGA_BASE_PORT6 0x140000
#define FPGA_BASE_PORT7 0x160000
#define FPGA_BASE_PORT8 0x180000
#define FPGA_BASE_PORT9 0x1a0000
#define FPGA_RTU_GCR 0x0
#define FPGA_RTU_AGR_HCAM 0x4
//global RTU settings
#define FPGA_RTU_GCR_HT_BASEL_0 0x0
#define FPGA_RTU_GCR_HT_BASEL_1 0x1
#define FPGA_RTU_GCR_HCAM_BSEL_0 0x0
#define FPGA_RTU_GCR_HCAM_BSEL_1 0x2
#define FPGA_RTU_GCR_G_ENA 0x4
#define FPGA_RTU_GCR_G_DIS 0x0
//port settings
#define FPGA_RTU_PCR_LEARN_EN 0x1
#define FPGA_RTU_PCR_PASS_ALL 0x2
#define FPGA_RTU_PCR_PASS_BPDU 0x4
#define FPGA_RTU_PCR_FIX_PRIO 0x8
#define FPGA_RTU_PCR_B_UNREC 0x80
#define FPGA_RTU_PCR0 0x8
#define FPGA_RTU_PCR1 0xC
#define FPGA_RTU_PCR2 0x10
#define FPGA_RTU_PCR3 0x14
#define FPGA_RTU_PCR4 0x18
#define FPGA_RTU_PCR5 0x1C
#define FPGA_RTU_PCR6 0x20
#define FPGA_RTU_PCR7 0x24
#define FPGA_RTU_PCR8 0x28
#define FPGA_RTU_PCR9 0x2C
#define FPGA_RTU_EIC_IDR 0x40
#define FPGA_RTU_EIC_IER 0x44
#define FPGA_RTU_EIC_IMR 0x48
#define FPGA_RTU_EIC_ISR 0x4C
//DMAC
#define FPGA_RTU_UFIFO_R0 0x50
#define FPGA_RTU_UFIFO_R1 0x54
//SMAC
#define FPGA_RTU_UFIFO_R2 0x58
#define FPGA_RTU_UFIFO_R3 0x5c
//other staff
#define FPGA_RTU_UFIFO_R4 0x60
//control/status
#define FPGA_RTU_UFIFO_CSR 0x64
//ad_sel
#define FPGA_RTU_MFIFO_R0 0x68
//ad_value
#define FPGA_RTU_MFIFO_R1 0x6c
//control/status
#define FPGA_RTU_MFIFO_CSR 0x70
#define FPGA_RTU_HCAM 0x4000
#define FPGA_RTU_ARAM_MAIN 0x8000
#define FPGA_RTU_VLAN_TAB 0xc000
This diff is collapsed.
/*
-------------------------------------------------------------------------------
-- Title : Routing Table Unit Software Simulation
-- Project : White Rabbit Switch
-------------------------------------------------------------------------------
-- File : rtu_sim.h
-- Authors : Tomasz Wlostowski
-- Company : CERN BE-CO-HT
-- Created : 2010-04-27
-- Last update: 2010-06-30
-- Description: Definitions of data used for simulations
--
--
*/
#ifndef RTU_SIM
#define RTU_SIM
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <inttypes.h>
#include "rtu_test_main.h"
//#define CAM_ENTRIES 128
// number of entries for each bank
#define CAM_ENTRIES 32
#define MAX_VLANS 4096
#define RTU_ENTRIES 16384
#define RTU_BUCKETS 4
//#define RTU_NUM_PORTS 10
#define RTU_NUM_PORTS PORT_NUMBER
#define MAX_FIFO_SIZE 128
//added by ML
#define ARAM_WORDS 256
#define SIM_POLYNOMIAL_DECT 0x82C48
#define SIM_POLYNOMIAL_CCITT 0x88108
#define SIM_POLYNOMIAL_IBM 0xC0028
#include "rtu_hw.h"
//////////////
#define MAX_REQUEST_NUMBER 1000
typedef uint8_t mac_addr_t [6];
// RTU request: input for the RTU
typedef struct {
char short_comment[100];
int port_id; // physical port identifier
mac_addr_t src; // source MAC address
mac_addr_t dst; // destitation MAC address
uint16_t src_high; // source MAC address
uint32_t src_low; // source MAC address
uint16_t dst_high; // destitation MAC address
uint32_t dst_low; // destitation MAC address
uint16_t vid; // VLAN ID from the packet header
int has_vid; // non-zero: VLAN id is present, 0: untagged packet (VID = 0)
uint8_t prio; // packet priority (either assigned by the port or extracted from packet header)
int has_prio; // non-zero: priority present, 0: no priority defined
} rtu_request_t ;
// RTU response: output from the RTU
typedef struct {
int port_id;
uint32_t port_mask; // Port mask: bits set to 1 indicate ports to which the packet must be routed
int drop; // drop flag: non-zero: drop packet
uint8_t prio; // final packet priority, assigned by RTU or taken from the port/packet header (depending on the configuration)
} rtu_response_t;
// MAC table entry
typedef struct {
int valid; // bit: 1 = entry is valid, 0: entry is invalid (empty)
int end_of_bucket; // bit: 1 = last entry in current bucket, stop search at this point
int is_bpdu; // bit: 1 = BPDU (or other non-STP-dependent packet)
mac_addr_t mac; // MAC address (for searching the bucketed hashtable)
uint8_t fid; // Filtering database ID (for searching the bucketed hashtable)
uint32_t port_mask_src; // port mask for source MAC addresses. Bits set to 1 indicate that
// packet having this MAC address can be forwarded from these corresponding ports. Ports having
// their bits set to 0 shall drop the packet.
uint32_t port_mask_dst; // port mask for destination MAC address. Bits set to 1 indicate to which physical ports the packet with matching destination
// MAC address shall be routed
int drop_when_source; // bit: 1 = drop the packet when source address matches
int drop_when_dest; // bit: 1 = drop the packet when destination address matches
int drop_unmatched_src_ports; //bit: 1 = drop the packet when it comes from source port different than specified in port_mask_src
uint32_t last_access_t; // time of last access to the rule (for aging)
uint8_t prio_src; // priority (src MAC)
int has_prio_src; // priority value valid
int prio_override_src; // priority override (force per-MAC priority)
uint8_t prio_dst; // priority (dst MAC)
int has_prio_dst; // priority value valid
int prio_override_dst; // priority override (force per-MAC priority)
int go_to_cam; // 1 : there are more entries outside the bucket
uint8_t cam_addr ; // address of the first entry in CAM memory
} mac_table_entry_t;
typedef struct {
uint32_t port_mask; // VLAN port mask: 1 = ports assigned to thisVLAN
uint8_t fid; // Filtering Database Index
uint8_t prio; // VLAN priority
int has_prio; // priority defined;
int prio_override; // priority override (force per-VLAN priority)
int drop; // 1: drop the packet (VLAN not registered)
} vlan_table_entry_t;
typedef struct {
int forward_bpdu_only; // forward BPDU/PTP packets only (when the port is in BLOCKING or LEARNING state)
// works regardless of **pass_all** value - forward_bpdu_only overrides it
// it allows only bpdu packages to be passed
int learning_enabled; // enable learning
int pass_all; // in other words: enable this port
//int pass_bpdu; // BPDU packets (with dst MAC 01:80:c2:00:00:00) are passed according to RT rules. This setting overrides
int fixed_prio_ena; //fixed prio set on this port
int fixed_prio_val; //value of the fixed prio
int b_unrec; //Unrecognized request behaviour
//Sets the port behaviour for all unrecognized requests:
// 0: packet is dropped
// 1: packet is broadcast
} rtu_port_config_t;
typedef struct {
int rtu_bank; // active MAC table bank
int cam_bank; // active CAM bank
int global_enable; // global enable of RTU
uint32_t hash_poly; //POLY_VAL [read/write]: Hash Poly
//Determines the polynomial used for hash computation.
//Currently available: 0x1021, 0x8005, 0x0589
rtu_port_config_t port_cfg[RTU_NUM_PORTS];
} rtu_config_t;
typedef struct {
// MAC address table, organized as hash table with 4-entry buckets.
mac_table_entry_t buckets[RTU_ENTRIES/4][4];
} mac_table_t;
typedef struct {
rtu_request_t data[MAX_FIFO_SIZE];
int head, tail, count;
} request_fifo_t;
///// these variables must be accessible (RW) from the Wishbone
// MAC address table (2 banks)
mac_table_t rtu_tab[2];
// CAM lookup table (2 banks) - for RTU entries with more than 4 matches
// for the same hash value
mac_table_entry_t rtu_cam[2][CAM_ENTRIES];
// VLAN table
vlan_table_entry_t vlan_tab[MAX_VLANS];
request_fifo_t learning_queue;
rtu_config_t CFG;
//added by ML
uint32_t rtu_agr_htab[ARAM_WORDS];
uint32_t rtu_agr_hcam;
typedef struct {
uint32_t word;
int address;
} changed_aging_htab_word_t;
int number_of_found_entries;
int hash_addresses[RTU_ENTRIES];
int hash_address_writen_cnt;
// nasty global for number of entries writen
// to hcam (separately for each bank
int cam_address[2];
#endif
\ No newline at end of file
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
/*
TODO:
- upgrade to newest version of main (with versioning)
- merge constarings, do constraings properly
- fix two know bugs which cause ~20% of tests to fail
- implement normal and continous work of RTU, which means:
1) write requetrs/mems
2) read responses/ufifo
3) write more requests mems
4) switch banks
5) read more requets/ufifos
5) go to 1)
- prepare some good solution when the CAM is full (due
to error, the fill_in_data function considered CAM
to be full and did not fill it - this caused error)
-
*/
/****************************************
decide on data kind
****************************************/
/*
uncomment to use a predefined
data, only very few examples
*/
//#define PREDEFINED_DATA
/*
uncomment to have random data
filled in htab, vlan, hcam
and have requets generated
randomly
*/
#define RANDOM_DATA
/*
uncomment to have settings
generated randomly
*/
#define RANDOM_SETTINGS
/*
uncomment to base the seed of rand()
function on the time - each time
test app is run, data is different
if commented, always the same random
data is generated
*/
#define TIME_DRIVEN_RANDOM
/*
In order to test that CAM works fine,
in case that the randome data does not
produce CAM entries, it is possible to
enforce some entires to be "CAM entries"
this is done by taking few percent of
request MACs from CAM (rtu_test_data.c).
if the define is commented, it's not very
likely there are meny (if any) CAM entires
since the MACs are taken from the htab entires
*/
#define ENFORCE_DATA_ENTRIES
/****************************************
define hw/sim run mode
****************************************/
/*
if commented, the "flooding mode""
is on
*/
//#define HW_TEST_ONE_BY_ONE
/****************************************
test mode (choose one define only)
****************************************/
/*
mode of operation: single test
it runs only one full test which includes:
- clean memories (htab, vlan)
- fill in memories(htab, vlan)
- set settings
- create requests (based on data in mems)
- run hw/sim
- compare results
- output results (errors if occure)
*/
//#define SINGALE_TEST
/*
mode of operation: single loop test
it runs TEST_ITERATIONS times hw/sim run without
cleaing mems:
- clean memories
- fill in memories
- repeat:
* fill in new settings
* create requests (based on data in mems)
* run hw/sim
* compare results
* add more entries to htab
- output results (errors if occure)
*/
//#define SINGLE_LOOP_TEST
/*
mode of operation: multi loop test
it runs :
MULTI_LOOP_TEST_NUMBER times loop with
TEST_ITERATIONS times hw/sim run without
cleaing mems:
- clean memories
- fill in memories
- repeat (MULTI_LOOP_TEST_NUMBER times):
-> repeat (TEST_ITERATIONS times):
* fill in new settings
* create requests (based on data in mems)
* run hw/sim
* compare results
* add more entries to htab
-> clean aging memories
-> clean tab storing hashes of filled in htab entries
-> fill in vlan
-> fill in htab
- output results (errors if occure)
*/
#define MULTI_LOOP_TEST
//#define CONTINUOUS_TEST
/****************************************
decide on hash polynomial
****************************************/
/*
DECT
*/
//#define USE_POLYNOMIAL 0x0589
/*
CCITT
*/
#define USE_POLYNOMIAL 0x1021
/*
IBM
*/
//#define USE_POLYNOMIAL 0x8005
/****************************************
test parameters
****************************************/
#define ACTIVE_BANK 1
/*
Sets how many requests will be send to RTU
during the test.
Due to limited learning queue (UFIFO.size=128),
setting more than 100 requests may result in
UFIFO being filled and errors will be reported.
It is suggested not to set more than 100 reqs
*/
#define TEST_REQS 100
/*
Number of ports depends on the FPGA settings
*/
#define PORT_NUMBER 8
/*
Number of test iterations per
application run during continous mode
*/
#define TEST_ITERATIONS 20
#define MULTI_LOOP_TEST_NUMBER 1000000
/*
for "#define CONTINUOUS_MODE"
Not finished yet
*/
#define TEST_ITERATIONS_PER_LOOP 3
/*
Enables to set custom SEED.
It is usefull if an error is report
during a test. in such case the seed
with which the test was run, should be
noted (it is printed at the beginnig
of the test.
To repeat the test to fix the bug,
the appropriate seed should be defined
here.
*/
//#define CUSTOME_SEED 496
//#define CUSTOME_SEED 176
/****************************************
If we want the test app to start talking
here are a few options for that
****************************************/
//#define VERBOSE_MODE
//#define DEBUG_HTAB
//#define DEBUG_VLAN
//#define DEBUG_REQUEST
//#define DEBUG_RESULTS
//#define DEBUG_HCAM
//#define DEBUG_SIMULATION
//#define DEBUG_READING_RESPONSES
//#define ML_DBG
/****************************************
bug fixing playground
(restricted area for civils)
****************************************/
//resolved
//#define DST_HAS_PRIO_PROBLEM
//resolved
//#define AGING_PROBLEM
// not resolved yet :(
//#define CAM_DROP_PROBLEM
//
//#define CAM_DROP_PROBLEM_2
/*
out of 14 trials in 3 errors occured
seeds that cause problems:
---- this seeds work with #define RANDOM_SETTINGS commented
seems to be algorith issue:
seed:176,
16
228
ok seeds:
1) seed = 6685
repeating tests:
while [ 1 ]; do ./build.sh run T=192.168.1.5; done > test_results
*/
\ No newline at end of file
This diff is collapsed.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment