stp_process.c
来自「stp代码」· C语言 代码 · 共 1,383 行 · 第 1/3 页
C
1,383 行
/*
* Start Hello timer
*/
static void
start_hello_timer(spantree_t *stp)
{
stp->hello_timer.value = 0;
stp->hello_timer.active = True;
}
/*
* Stop Hello timer
*/
static void
stop_hello_timer(spantree_t *stp)
{
stp->hello_timer.active = False;
}
/*
* Is Hello timer expired
*/
static Boolean
hello_timer_expired(spantree_t *stp)
{
if (stp->hello_timer.active &&
(++(stp->hello_timer.value) >= stp->hello_time)) {
stp->hello_timer.active = False;
return(True);
}
return(False);
}
/*
* Start TCN timer
*/
static void
start_tcn_timer(spantree_t *stp)
{
stp->tcn_timer.value = 0;
stp->tcn_timer.active = True;
}
/*
* Start TCN timer
*/
static void
stop_tcn_timer(spantree_t *stp)
{
stp->tcn_timer.active = False;
}
/*
* Is TCN timer expired
*/
static Boolean
tcn_timer_expired(spantree_t *stp)
{
if (stp->tcn_timer.active &&
(++(stp->tcn_timer.value) >= stp->bridge_hello_time)) {
stp->tcn_timer.active = False;
return(True);
}
return(False);
}
/*
* Start topology change timer
*/
static void
start_tc_timer(spantree_t *stp)
{
stp->tc_timer.value = 0;
stp->tc_timer.active = True;
}
/*
* Stop topology change timer
*/
static void
stop_tc_timer(spantree_t *stp)
{
stp->tc_timer.active = False;
}
/*
* Is topology change timer expired
*/
static Boolean
tc_timer_expired(spantree_t *stp)
{
if (stp->tc_timer.active &&
((++(stp->tc_timer.value) >= stp->topology_change_time))) {
stp->tc_timer.active = False;
return(True);
}
return (False);
}
/*
* Start message age timer
*/
static void
start_message_age_timer(spantree_t *stp, stp_port_t *port, uint16 message_age)
{
port->message_age_timer.value = message_age;
port->message_age_timer.active = True;
}
/*
* Stop message age timer
*/
static void
stop_message_age_timer(spantree_t *stp, stp_port_t *port)
{
port->message_age_timer.active = False;
}
/*
* Is message age timer expired
*/
static Boolean
message_age_timer_expired(spantree_t *stp, stp_port_t *port)
{
if (port->message_age_timer.active &&
(++(port->message_age_timer.value) >= stp->max_age)) {
port->message_age_timer.active = False;
return(True);
}
return(False);
}
/*
* Start forward delay timer
*/
static void
start_forward_delay_timer(spantree_t *stp, stp_port_t *port)
{
port->forward_delay_timer.value = 0;
port->forward_delay_timer.active = True;
}
/*
* Stop forward delay timer
*/
static void
stop_forward_delay_timer(spantree_t *stp, stp_port_t *port)
{
port->forward_delay_timer.active = False;
}
/*
* Is forward delay timer expired
*/
static Boolean
forward_delay_timer_expired(spantree_t *stp, stp_port_t *port)
{
if (port->forward_delay_timer.active &&
(++port->forward_delay_timer.value >= stp->forward_delay)) {
port->forward_delay_timer.active = False;
return(True);
}
return(False);
}
/*
* Start HOLD timer
*/
static void
start_hold_timer(spantree_t *stp, stp_port_t *port)
{
port->hold_timer.value = 0;
port->hold_timer.active = True;
}
/*
* Stop HOLD timer
*/
static void
stop_hold_timer(spantree_t *stp, stp_port_t *port)
{
port->hold_timer.active = False;
}
/*
* Is HOLD timer expired
*/
static Boolean
hold_timer_expired(spantree_t *stp, stp_port_t *port)
{
if (port->hold_timer.active &&
((++(port->hold_timer.value) >= stp->hold_time))) {
port->hold_timer.active = False;
return(True);
}
return(False);
}
/*
* A single thread to handle multiple spanning tree algorithm
*/
static void
stp_main_process(void *arg)
{
spantree_t *stp;
int i;
/* Run forever */
while (!stp_exit) {
i = 0;
FOR_ALL_STP(stp) {
sal_usleep(5000);
if (stp->running) {
stp_lock_link();
stp_tick(stp);
stp_unlock_link();
}
i++;
}
sal_usleep(1000000 - (5000 * i));
}
stp_thread_id = NULL;
sal_thread_exit(0);
}
/*
* Start up the STP process
*/
int
start_stp_process(void)
{
stp_exit = 0;
if (stp_thread_id == NULL) {
stp_thread_id = sal_thread_create("spantree", SAL_THREAD_STKSZ*2, 50,
stp_main_process, NULL);
if (stp_thread_id == SAL_THREAD_ERROR) {
stp_thread_id = NULL;
printf("start stp process failure\n");
return -1;
}
printf("Start stp sucess.\n");
}
return 0;
}
/*
* Kill the STP process
*/
void
stp_process_teardown(void)
{
if (stp_instance_q != NULL) {
return;
}
debugk(DK_STP,"stp process exit.\n");
stp_exit = 1;
/* while(stp_thread_id != NULL);*/
}
/*------------------------------------------------------------------------------
* FUNCTION:set_all_port_to_forward
* DESCRIPTION:设置交换机的所有活动端口的为转发状态。
*
* AUTHOR:ZHOUGUIS
-------------------------------------------------------------------------------*/
void set_all_port_to_forward(void)
{
int unit,port,link=0,pport;
for(unit =0;unit<soc_ndev_attached;unit++)
{
#if BOARD_TYPE==RHS8012GE_3T8F
for(port = RHG_MIN_GEPORT+2;port <= RHG_MAX_GEPORT; port++)
{ pport = port - 2;
if (bcm_port_link_status_get(unit, pport, &link) < 0) {
printL("bcm_port_link_status_get error\n","");
continue;
}
if(link)
{
bcm_stg_stp_set(unit, 1, pport, STP_FORWARDING);
}
}
#else
for(port = RHG_MIN_GEPORT;port <= RHG_MAX_GEPORT; port ++)
{
pport = port - 1;
if (bcm_port_link_status_get(unit, pport, &link) < 0) {
printL("bcm_port_link_status_get error\n","");
continue;
}
if(link)
{
bcm_stg_stp_set(unit, 1,pport, STP_FORWARDING);
}
}
#endif
}
}
/*------------------------------------------------------------------------------
* FUNCTION:stp_thread_shutdown
* DESCRIPTION:关闭生成树功能。正常退出spantree进程和stp_pkt进程。
*
* AUTHOR:ZHOUGUIS
-------------------------------------------------------------------------------*/
void stp_thread_shutdown(void)
{
/* empty stp list; */
stp_exit_all = 1;
stp_sys_cleanup();
debugk(DK_STP,"stp system clean up.\n");
stk_pakq_release();
debugk(DK_STP,"stp packet precess exit.\n");
stp_shutdown();
debugk(DK_STP,"stp spanning tree clean up.\n");
/* mstp globe flag */
stp_close_mstp_flag_valued();
stp_exit_all = 0;
}
/*------------------------------------------------------------------------------
* FUNCTION:stp_get_stop_method
* DESCRIPTION:通过全局变量判断是删除一棵生成树还是删除所有的生成树。
* 删除一棵生成树:把当前生成树活动端口移到缺省生成树,跟vlan匹配。
* 删除所有的生成树:删除所有的资源,退出生成树进程和收发包进程。
* AUTHOR:ZHOUGUIS
-------------------------------------------------------------------------------*/
int stp_get_stop_method(void)
{
return stp_exit_all;
}
/*------------------------------------------------------------------------------
* FUNCTION:edgeport_make_forwarding
* DESCRIPTION:如果是边缘端口,则直接置为转发状态。
*
* AUTHOR:ZHOUGUIS
-------------------------------------------------------------------------------*/
static void
edgeport_make_forwarding(spantree_t *stp, stp_port_t *port)
{
set_port_state(stp, port, STP_FORWARDING);
}
/*------------------------------------------------------------------------------
* FUNCTION:check_config_port_to_forwarding
* DESCRIPTION:检查当前所设置的边缘端口是否为UP状态。如果UP则直接置为转发状态。
*
* AUTHOR:ZHOUGUIS
-------------------------------------------------------------------------------*/
void check_config_port_to_forwarding(int unit,int ingport,int lport)
{
spantree_t *stp,*stptemp;
stp_port_t *sport;
int gport;
FOR_ALL_STP(stp)
{
if(stp == NULL)
{
/* debugk(DK_STP,"Port is not up!\n");*/
return;
}
stptemp = stp;
/*printL("PORT STATE\n","");*/
sport = stp->port_list.next ;
while (sport != &stp->port_list)
{
gport = get_global_port(sport->unit,sport->port);
if(gport == ingport)
{
/* debugk(DK_STP,"Found sport %d in stp %d\n",gport,stp->external_id);*/
make_forwarding(stp, sport);
return;
}
sport = sport->next;
}
}
}
/*------------------------------------------------------------------------------
* FUNCTION:port_changed_cause_state_selection
* DESCRIPTION:端口状态改变要重新计算生成树。
*
* AUTHOR:ZHOUGUIS
-------------------------------------------------------------------------------*/
void port_changed_cause_state_selection(spantree_t *stp)
{
port_state_selection(stp);
}
/*------------------------------------------------------------------------------
* FUNCTION:stp_make_all_active_port_forwarding
* DESCRIPTION:等待系统所有的活动端口状态变迁完成。。
*
* AUTHOR:ZHOUGUIS
-------------------------------------------------------------------------------*/
void stp_make_all_active_port_forwarding(void)
{
spantree_t *stp;
stp_port_t *sport;
int flag = 1;
printL("Waiting state change: \n","");
FOR_ALL_STP(stp)
{
if(stp == NULL)
{
return;
}
sport = stp->port_list.next;
while (sport != &stp->port_list)
{
flag = 1;
while(flag)
{
if((sport->state == STP_BLOCKING)||(sport->state == STP_FORWARDING))
{
flag = 0;
}
else
{
printL(".","");
taskDelay(sysClkRateGet()*1);
}
}
sport = sport->next;
}
}
printL("Over.\n","");
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?