From dbfde6ce82dc88d06581b785731bfbc9bca0e0fb Mon Sep 17 00:00:00 2001 From: luwenpeng Date: Thu, 25 May 2023 17:05:22 +0800 Subject: [PATCH] TSG-15278 bugfix: memleak --- platform/include/sce.h | 1 + platform/src/main.cpp | 66 ++++++++++++++++++++++++++++++++++---- platform/src/packet_io.cpp | 6 ++-- platform/src/sce.cpp | 6 ++++ platform/src/sf_status.cpp | 2 ++ 5 files changed, 73 insertions(+), 8 deletions(-) diff --git a/platform/include/sce.h b/platform/include/sce.h index 1a5a4af..e24a372 100644 --- a/platform/include/sce.h +++ b/platform/include/sce.h @@ -33,6 +33,7 @@ struct thread_ctx struct policy_enforcer *ref_enforcer; int session_table_need_reset; + int thread_is_runing; }; /****************************************************************************** diff --git a/platform/src/main.cpp b/platform/src/main.cpp index d6382d4..9d14bbb 100644 --- a/platform/src/main.cpp +++ b/platform/src/main.cpp @@ -13,6 +13,7 @@ #include "global_metrics.h" struct breakpad_instance *g_breakpad = NULL; +static int is_need_stop = 0; #ifdef SCE_GIT_VERSION static __attribute__((__used__)) const char *__sce_version = SCE_GIT_VERSION; @@ -25,7 +26,10 @@ static void usage(char *cmd) fprintf(stderr, "USAGE: %s [OPTIONS]\n", cmd); fprintf(stderr, " -v -- show version\n"); fprintf(stderr, " -h -- show help info\n\n"); - fprintf(stderr, "kill -s SIGHUP $PID -- reload zlog configure\n"); + fprintf(stderr, "kill -s SIGHUP $PID -- reload zlog configure\n"); + fprintf(stderr, "kill -s SIGINT $PID -- exit gracefully\n"); + fprintf(stderr, "kill -s SIGQUIT $PID -- exit gracefully\n"); + fprintf(stderr, "kill -s SIGTERM $PID -- exit gracefully\n"); } static void sig_handler(int signo) @@ -35,6 +39,24 @@ static void sig_handler(int signo) LOG_INFO("%s: recv SIGHUP, reload zlog.conf", LOG_TAG_SCE); LOG_RELOAD(); } + + if (signo == SIGINT) + { + LOG_ERROR("%s: recv SIGINT, exit !!!", LOG_TAG_SCE); + ATOMIC_SET(&is_need_stop, 1); + } + + if (signo == SIGQUIT) + { + LOG_ERROR("%s: recv SIGQUIT, exit !!!", LOG_TAG_SCE); + ATOMIC_SET(&is_need_stop, 1); + } + + if (signo == SIGTERM) + { + LOG_ERROR("%s: recv SIGTERM, exit !!!", LOG_TAG_SCE); + ATOMIC_SET(&is_need_stop, 1); + } } static void *worker_thread_cycle(void *arg) @@ -51,6 +73,7 @@ static void *worker_thread_cycle(void *arg) uint64_t sf_metrics_last_send_ts = timestamp_get_msec(ts); uint64_t sf_metrics_send_interval = sf_metrics_get_interval(thread_ctx->sf_metrics) * 1000; + ATOMIC_SET(&thread_ctx->thread_is_runing, 1); snprintf(thread_name, sizeof(thread_name), "sce:worker-%d", thread_ctx->thread_index); prctl(PR_SET_NAME, (unsigned long long)thread_name, NULL, NULL, NULL); @@ -61,7 +84,7 @@ static void *worker_thread_cycle(void *arg) LOG_INFO("%s: worker thread %d is running", LOG_TAG_SCE, thread_ctx->thread_index); - while (1) + while (!ATOMIC_READ(&is_need_stop)) { n_pkt_recv_from_nf = packet_io_thread_polling_nf(handle, thread_ctx); n_pkt_recv_from_endp = packet_io_thread_polling_endpoint(handle, thread_ctx); @@ -91,6 +114,7 @@ static void *worker_thread_cycle(void *arg) } error_out: + ATOMIC_SET(&thread_ctx->thread_is_runing, 0); LOG_ERROR("%s: worker thread %d exiting", LOG_TAG_SCE, thread_ctx->thread_index); return (void *)NULL; } @@ -129,6 +153,24 @@ int main(int argc, char **argv) LOG_CLOSE(); return -1; } + if (signal(SIGINT, sig_handler) == SIG_ERR) + { + LOG_ERROR("%s: unable to register SIGINT signal handler, error %d: %s", LOG_TAG_SCE, errno, strerror(errno)); + LOG_CLOSE(); + return -1; + } + if (signal(SIGQUIT, sig_handler) == SIG_ERR) + { + LOG_ERROR("%s: unable to register SIGQUIT signal handler, error %d: %s", LOG_TAG_SCE, errno, strerror(errno)); + LOG_CLOSE(); + return -1; + } + if (signal(SIGTERM, sig_handler) == SIG_ERR) + { + LOG_ERROR("%s: unable to register SIGTERM signal handler, error %d: %s", LOG_TAG_SCE, errno, strerror(errno)); + LOG_CLOSE(); + return -1; + } g_breakpad = breakpad_init(profile, "system", g_default_logger, __sce_version); @@ -169,7 +211,7 @@ int main(int argc, char **argv) g_metrics_last_send_ts = timestamp_get_msec(ctx->ts); g_metrics_send_interval = ctx->metrics->config.statsd_cycle * 1000; - while (1) + while (!ATOMIC_READ(&is_need_stop)) { if (timestamp_get_msec(ctx->ts) - g_metrics_last_send_ts >= g_metrics_send_interval) { @@ -184,9 +226,21 @@ int main(int argc, char **argv) error_out: for (int i = 0; i < ctx->nr_worker_threads; i++) { - struct thread_ctx *thread_ctx = &ctx->work_threads[i]; - session_table_destory(thread_ctx->session_table); - sf_metrics_destory(thread_ctx->sf_metrics); + while (1) + { + if (ATOMIC_READ(&(ctx->work_threads[i].thread_is_runing)) == 0) + { + struct thread_ctx *thread_ctx = &ctx->work_threads[i]; + session_table_destory(thread_ctx->session_table); + sf_metrics_destory(thread_ctx->sf_metrics); + break; + } + else + { + sleep(1); + LOG_ERROR("%s: wait thread %d exit", LOG_TAG_SCE, i); + } + } } sce_ctx_destory(ctx); diff --git a/platform/src/packet_io.cpp b/platform/src/packet_io.cpp index 12ca34c..43e2dac 100644 --- a/platform/src/packet_io.cpp +++ b/platform/src/packet_io.cpp @@ -1048,16 +1048,18 @@ static void handle_inject_packet(marsio_buff_t *rx_buff, struct thread_ctx *thre struct g_vxlan *g_vxlan_hdr = NULL; struct session_ctx *session_ctx = NULL; struct selected_chaining *chaining = NULL; + memset(&meta, 0, sizeof(struct metadata)); int sf_index = 0; int raw_len = marsio_buff_datalen(rx_buff); char *raw_data = marsio_buff_mtod(rx_buff); if (g_vxlan_decode(&g_vxlan_hdr, raw_data, raw_len) == -1) { - goto error_block; + throughput_metrics_inc(&(g_metrics->device.endpoint_drop), 1, raw_len); + action_err_block(rx_buff, &meta, NULL, thread_ctx); + return; } - memset(&meta, 0, sizeof(struct metadata)); meta.raw_data = (char *)g_vxlan_hdr + sizeof(struct g_vxlan); meta.raw_len = raw_len - sizeof(struct ethhdr) - sizeof(struct ip) - sizeof(struct udp_hdr) - sizeof(struct g_vxlan); meta.l7offset = 0; diff --git a/platform/src/sce.cpp b/platform/src/sce.cpp index 439b84b..1f2be19 100644 --- a/platform/src/sce.cpp +++ b/platform/src/sce.cpp @@ -98,6 +98,12 @@ void session_ctx_free(struct session_ctx *session_ctx) { if (session_ctx) { + if (session_ctx->session_addr) + { + free(session_ctx->session_addr); + session_ctx->session_addr = NULL; + } + if (session_ctx->decrypted_meta_i2e) { metadata_free(session_ctx->decrypted_meta_i2e); diff --git a/platform/src/sf_status.cpp b/platform/src/sf_status.cpp index 7308a38..c72e3af 100644 --- a/platform/src/sf_status.cpp +++ b/platform/src/sf_status.cpp @@ -138,6 +138,8 @@ void sf_status_delete(struct sf_status *handle, int sf_profile_id) handle->htable_elem_count--; LOG_DEBUG("%s: delete: sf_profile %d success, elem_num %lu", LOG_TAG_SF_STATUS, sf_profile_id, handle->htable_elem_count); HASH_DELETE(hh, handle->htable, temp); + free(temp); + temp = NULL; } else {