From eec659a8cb772a5e1f68ba1373e9c73ce265a767 Mon Sep 17 00:00:00 2001 From: sKyissKy Date: Sat, 9 Mar 2024 01:49:36 +0800 Subject: [PATCH] Add rejoin option as ugly hack to allow send IGMP/MLD leave+join every X seconds (#7) Co-authored-by: Rozhuk Ivan --- README.md | 2 +- conf/msd_lite.conf | 1 + src/msd_lite.c | 35 +++++++++++++++++++++++++++++------ src/stream_sys.c | 15 ++++++++++++++- src/stream_sys.h | 4 +++- 5 files changed, 48 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 9637c9e..9b07feb 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,7 @@ [![Build-Ubuntu-latest Actions Status](https://github.com/rozhuk-im/msd_lite/workflows/build-ubuntu-latest/badge.svg)](https://github.com/rozhuk-im/msd_lite/actions) -Rozhuk Ivan 2011 - 2021 +Rozhuk Ivan 2011 - 2023 msd_lite - Multi stream daemon lite. This lightweight version of Multi Stream daemon (msd) diff --git a/conf/msd_lite.conf b/conf/msd_lite.conf index 6c14783..8712a22 100644 --- a/conf/msd_lite.conf +++ b/conf/msd_lite.conf @@ -73,6 +73,7 @@ available. vlan777 + 0 diff --git a/src/msd_lite.c b/src/msd_lite.c index d50119d..24a8d1d 100644 --- a/src/msd_lite.c +++ b/src/msd_lite.c @@ -1,5 +1,5 @@ /*- - * Copyright (c) 2012 - 2021 Rozhuk Ivan + * Copyright (c) 2012-2023 Rozhuk Ivan * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -115,7 +115,8 @@ int msd_http_srv_hub_attach(http_srv_cli_p cli, uint8_t *hub_name, size_t hub_name_size, str_src_conn_params_p src_conn_params); uint32_t msd_http_req_url_parse(http_srv_req_p req, - struct sockaddr_storage *ssaddr, uint32_t *if_index, + struct sockaddr_storage *ssaddr, + uint32_t *if_index, uint32_t *rejoin_time, uint8_t *hub_name, size_t hub_name_size, size_t *hub_name_size_ret); @@ -264,6 +265,9 @@ msd_src_conn_profile_load(const uint8_t *data, size_t data_size, void *conn) { if_name[MIN(IFNAMSIZ, tm)] = 0; ((str_src_conn_mc_p)conn)->if_index = if_nametoindex(if_name); } + xml_get_val_uint32_args(data, data_size, NULL, + &((str_src_conn_mc_p)conn)->rejoin_time, + (const uint8_t*)"multicast", "rejoinTime", NULL); return (0); } @@ -521,11 +525,11 @@ msd_http_srv_hub_attach(http_srv_cli_p cli, uint8_t *hub_name, size_t hub_name_s uint32_t msd_http_req_url_parse(http_srv_req_p req, struct sockaddr_storage *ssaddr, - uint32_t *if_index, + uint32_t *if_index, uint32_t *rejoin_time, uint8_t *hub_name, size_t hub_name_size, size_t *hub_name_size_ret) { const uint8_t *ptm; size_t tm; - uint32_t ifindex; + uint32_t ifindex, rejointime; char straddr[STR_ADDR_LEN], ifname[(IFNAMSIZ + 1)]; struct sockaddr_storage ss; @@ -562,6 +566,19 @@ msd_http_req_url_parse(http_srv_req_p req, struct sockaddr_storage *ssaddr, if_indextoname(ifindex, ifname); } + /* rejoin_time. */ + if (0 == http_query_val_get(req->line.query, + req->line.query_size, (const uint8_t*)"rejoin_time", 11, + &ptm, &tm)) { + rejointime = ustr2u32(ptm, tm); + } else { /* Default value. */ + if (NULL != if_index) { + rejointime = (*rejoin_time); + } else { + rejointime = 0; + } + } + if (0 != sa_addr_port_to_str(&ss, straddr, sizeof(straddr), NULL)) return (400); tm = (size_t)snprintf((char*)hub_name, hub_name_size, @@ -572,6 +589,9 @@ msd_http_req_url_parse(http_srv_req_p req, struct sockaddr_storage *ssaddr, if (NULL != if_index) { (*if_index) = ifindex; } + if (NULL != rejoin_time) { + (*rejoin_time) = rejointime; + } if (NULL != hub_name_size_ret) { (*hub_name_size_ret) = tm; } @@ -641,8 +661,11 @@ msd_http_srv_on_req_rcv_cb(http_srv_cli_p cli, void *udata __unused, /* Default value. */ memcpy(&src_conn_params, &g_data.src_conn_params, sizeof(str_src_conn_mc_t)); /* Get multicast address, ifindex, hub name. */ - resp->status_code = msd_http_req_url_parse(req, &src_conn_params.udp.addr, - &src_conn_params.mc.if_index, buf, sizeof(buf), &buf_size); + resp->status_code = msd_http_req_url_parse(req, + &src_conn_params.udp.addr, + &src_conn_params.mc.if_index, + &src_conn_params.mc.rejoin_time, + buf, sizeof(buf), &buf_size); if (200 != resp->status_code) return (HTTP_SRV_CB_CONTINUE); if (HTTP_REQ_METHOD_HEAD == req->line.method_code) { diff --git a/src/stream_sys.c b/src/stream_sys.c index d4b5441..d47af3d 100644 --- a/src/stream_sys.c +++ b/src/stream_sys.c @@ -1,5 +1,5 @@ /*- - * Copyright (c) 2012 - 2021 Rozhuk Ivan + * Copyright (c) 2012-2023 Rozhuk Ivan * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -168,6 +168,7 @@ str_src_conn_def(str_src_conn_params_p src_conn_params) { return; mem_bzero(src_conn_params, sizeof(str_src_conn_params_t)); src_conn_params->mc.if_index = STR_SRC_CONN_DEF_IFINDEX; + src_conn_params->mc.rejoin_time = 0; } @@ -376,6 +377,7 @@ str_hubs_bckt_stat_summary(str_hubs_bckt_p shbskt, str_hubs_stat_p stat) { void str_hubs_bckt_timer_service(str_hubs_bckt_p shbskt, str_hub_p str_hub, str_hubs_stat_p stat) { + int error; str_src_settings_p src_params = &shbskt->src_params; struct timespec *tp = &shbskt->tp_last_tmr_next; uint64_t tm64; @@ -415,6 +417,17 @@ str_hubs_bckt_timer_service(str_hubs_bckt_p shbskt, str_hub_p str_hub, return; } } + /* Re join multicast group timer. */ + if (0 != str_hub->src_conn_params.mc.rejoin_time && + str_hub->next_rejoin_time < tp->tv_sec) { + str_hub->next_rejoin_time = (tp->tv_sec + (time_t)str_hub->src_conn_params.mc.rejoin_time); + for (int join = 0; join < 2; join ++) { + error = skt_mc_join(tp_task_ident_get(str_hub->tptask), join, + str_hub->src_conn_params.mc.if_index, + &str_hub->src_conn_params.mc.udp.addr); + LOG_ERR(error, "skt_mc_join()"); + } + } } static void str_hubs_bckt_timer_msg_cb(tpt_p tpt, void *udata) { diff --git a/src/stream_sys.h b/src/stream_sys.h index 7515c48..4af8176 100644 --- a/src/stream_sys.h +++ b/src/stream_sys.h @@ -1,5 +1,5 @@ /*- - * Copyright (c) 2012 - 2021 Rozhuk Ivan + * Copyright (c) 2012-2023 Rozhuk Ivan * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -114,6 +114,7 @@ typedef struct str_src_conn_udp_s { typedef struct str_src_conn_mc_s { str_src_conn_udp_t udp; uint32_t if_index; + uint32_t rejoin_time; } str_src_conn_mc_t, *str_src_conn_mc_p; #define STR_SRC_CONN_DEF_IFINDEX ((uint32_t)-1) @@ -160,6 +161,7 @@ typedef struct str_hub_s { #ifdef __linux__ /* Linux specific code. */ size_t r_buf_rcvd; /* Ring buf LOWAT emulator. */ #endif /* Linux specific code. */ + time_t next_rejoin_time; /* Next time to send leave+join. */ tpt_p tpt; /* Thread data for all IO operations. */ str_src_conn_params_t src_conn_params; /* Point to str_src_conn_XXX */