From ab5079909d4bc7a8c7bac10e9728c2800a411cd0 Mon Sep 17 00:00:00 2001 From: winlin Date: Sun, 31 Oct 2021 18:16:33 +0800 Subject: [PATCH] For #2369, #1708, #1941: Check errno when close fd or stop thread --- trunk/src/app/srs_app_st.cpp | 11 ++++++++- trunk/src/core/srs_core.hpp | 2 ++ trunk/src/protocol/srs_service_st.cpp | 13 +++++++++-- trunk/src/utest/srs_utest_reload.hpp | 2 +- trunk/src/utest/srs_utest_service.cpp | 33 +++++++++++++++++++++++++++ 5 files changed, 57 insertions(+), 4 deletions(-) diff --git a/trunk/src/app/srs_app_st.cpp b/trunk/src/app/srs_app_st.cpp index 3d439c12ae..04de607c7e 100755 --- a/trunk/src/app/srs_app_st.cpp +++ b/trunk/src/app/srs_app_st.cpp @@ -202,7 +202,16 @@ void SrsFastCoroutine::stop() if (trd) { void* res = NULL; int r0 = st_thread_join((st_thread_t)trd, &res); - srs_assert(!r0); + if (r0) { + // By st_thread_join + if (errno == EINVAL) srs_assert(!r0); + if (errno == EDEADLK) srs_assert(!r0); + // By st_cond_timedwait + if (errno == EINTR) srs_assert(!r0); + if (errno == ETIME) srs_assert(!r0); + // Others + srs_assert(!r0); + } srs_error_t err_res = (srs_error_t)res; if (err_res != srs_success) { diff --git a/trunk/src/core/srs_core.hpp b/trunk/src/core/srs_core.hpp index 4fe1dc0c07..ceecdd0796 100644 --- a/trunk/src/core/srs_core.hpp +++ b/trunk/src/core/srs_core.hpp @@ -54,7 +54,9 @@ #endif #include +#ifndef srs_assert #define srs_assert(expression) assert(expression) +#endif #include #include diff --git a/trunk/src/protocol/srs_service_st.cpp b/trunk/src/protocol/srs_service_st.cpp index 577c1204b5..a64283340b 100644 --- a/trunk/src/protocol/srs_service_st.cpp +++ b/trunk/src/protocol/srs_service_st.cpp @@ -74,8 +74,17 @@ void srs_close_stfd(srs_netfd_t& stfd) { if (stfd) { // we must ensure the close is ok. - int err = st_netfd_close((st_netfd_t)stfd); - srs_assert(err != -1); + int r0 = st_netfd_close((st_netfd_t)stfd); + if (r0) { + // By _st_epoll_fd_close or _st_kq_fd_close + if (errno == EBUSY) srs_assert(!r0); + // By close + if (errno == EBADF) srs_assert(!r0); + if (errno == EINTR) srs_assert(!r0); + if (errno == EIO) srs_assert(!r0); + // Others + srs_assert(!r0); + } stfd = NULL; } } diff --git a/trunk/src/utest/srs_utest_reload.hpp b/trunk/src/utest/srs_utest_reload.hpp index b803f35da7..ab19fc1cad 100644 --- a/trunk/src/utest/srs_utest_reload.hpp +++ b/trunk/src/utest/srs_utest_reload.hpp @@ -10,7 +10,7 @@ /* #include */ -#include +#include #include #include diff --git a/trunk/src/utest/srs_utest_service.cpp b/trunk/src/utest/srs_utest_service.cpp index 97baae8b70..c9d13ac3ec 100644 --- a/trunk/src/utest/srs_utest_service.cpp +++ b/trunk/src/utest/srs_utest_service.cpp @@ -24,6 +24,7 @@ using namespace std; #include #include #include +#include MockSrsConnection::MockSrsConnection() { @@ -1452,3 +1453,35 @@ VOID TEST(TCPServerTest, ContextUtility) } } +class MockStopSelfThread : public ISrsCoroutineHandler +{ +public: + int r0; + int r1; + SrsFastCoroutine trd; + MockStopSelfThread() : trd("mock", this), r0(0), r1(0) { + } + virtual ~MockStopSelfThread() { + } + srs_error_t start() { + return trd.start(); + } + void stop() { + trd.stop(); + } + virtual srs_error_t cycle() { + r0 = st_thread_join((st_thread_t)trd.trd, NULL); + r1 = errno; + return srs_success; + } +}; + +VOID TEST(StopSelfThreadTest, ShouldFailWhenStopSelf) +{ + MockStopSelfThread trd; + trd.start(); + srs_usleep(0); + EXPECT_EQ(-1, trd.r0); + EXPECT_EQ(EDEADLK, trd.r1); +} +