From bbfb03f98a3bdb32d5e062e74b86d573f5f0a126 Mon Sep 17 00:00:00 2001 From: l Date: Thu, 19 Mar 2020 14:36:56 +0800 Subject: [PATCH 1/4] =?UTF-8?q?=E4=BF=AE=E5=A4=8Dsrs=5Fwrite=5Flarge=5Fiov?= =?UTF-8?q?s=E4=B8=ADnwrite=E6=9C=AA=E7=B4=AF=E5=8A=A0=E7=9A=84=E9=94=99?= =?UTF-8?q?=E8=AF=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- trunk/src/protocol/srs_protocol_utility.cpp | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/trunk/src/protocol/srs_protocol_utility.cpp b/trunk/src/protocol/srs_protocol_utility.cpp index 28141f625..56294defb 100644 --- a/trunk/src/protocol/srs_protocol_utility.cpp +++ b/trunk/src/protocol/srs_protocol_utility.cpp @@ -342,15 +342,19 @@ srs_error_t srs_write_large_iovs(ISrsProtocolReadWriter* skt, iovec* iovs, int s } return err; } - + // send in multiple times. int cur_iov = 0; + ssize_t nwrite = 0; while (cur_iov < size) { int cur_count = srs_min(limits, size - cur_iov); - if ((err = skt->writev(iovs + cur_iov, cur_count, pnwrite)) != srs_success) { + if ((err = skt->writev(iovs + cur_iov, cur_count, &nwrite)) != srs_success) { return srs_error_wrap(err, "writev"); } cur_iov += cur_count; + if (pnwrite) { + *pnwrite += nwrite; + } } return err; From f89b4b3b26bec6b25bd56d7505d7fb831b173b9e Mon Sep 17 00:00:00 2001 From: winlin Date: Sat, 21 Mar 2020 20:20:40 +0800 Subject: [PATCH 2/4] For #1651, fix return pnwrite of srs_write_large_iovs. 3.0.135 --- README.md | 2 + trunk/src/core/srs_core_version3.hpp | 2 +- trunk/src/protocol/srs_protocol_utility.cpp | 2 +- trunk/src/utest/srs_utest_protocol.cpp | 64 ++++++++++++++++++++- 4 files changed, 66 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index b56e9edaf..2cd74f917 100755 --- a/README.md +++ b/README.md @@ -146,6 +146,7 @@ For previous versions, please read: ## V3 changes +* v3.0, 2020-03-21, For [#1651][bug #1651], fix return pnwrite of srs_write_large_iovs. 3.0.135 * v3.0, 2020-03-18, [3.0 beta3(3.0.134)][r3.0b3] released. 122509 lines. * v3.0, 2020-03-12, For [#1635][bug #1635], inotify watch ConfigMap for reload. 3.0.134 * v3.0, 2020-03-12, For [#1635][bug #1635], support auto reaload config by inotify. 3.0.129 @@ -1676,6 +1677,7 @@ Winlin [bug #1594]: https://github.com/ossrs/srs/issues/1594 [bug #1630]: https://github.com/ossrs/srs/issues/1630 [bug #1635]: https://github.com/ossrs/srs/issues/1635 +[bug #1651]: https://github.com/ossrs/srs/issues/1651 [bug #yyyyyyyyyyyyy]: https://github.com/ossrs/srs/issues/yyyyyyyyyyyyy [exo #828]: https://github.com/google/ExoPlayer/pull/828 diff --git a/trunk/src/core/srs_core_version3.hpp b/trunk/src/core/srs_core_version3.hpp index 5ff02aa5a..85bd342c0 100644 --- a/trunk/src/core/srs_core_version3.hpp +++ b/trunk/src/core/srs_core_version3.hpp @@ -24,6 +24,6 @@ #ifndef SRS_CORE_VERSION3_HPP #define SRS_CORE_VERSION3_HPP -#define SRS_VERSION3_REVISION 134 +#define SRS_VERSION3_REVISION 135 #endif diff --git a/trunk/src/protocol/srs_protocol_utility.cpp b/trunk/src/protocol/srs_protocol_utility.cpp index 56294defb..2582a0c1a 100644 --- a/trunk/src/protocol/srs_protocol_utility.cpp +++ b/trunk/src/protocol/srs_protocol_utility.cpp @@ -336,7 +336,7 @@ srs_error_t srs_write_large_iovs(ISrsProtocolReadWriter* skt, iovec* iovs, int s #endif // send in a time. - if (size < limits) { + if (size <= limits) { if ((err = skt->writev(iovs, size, pnwrite)) != srs_success) { return srs_error_wrap(err, "writev"); } diff --git a/trunk/src/utest/srs_utest_protocol.cpp b/trunk/src/utest/srs_utest_protocol.cpp index 0e952cf68..2535b6fd2 100644 --- a/trunk/src/utest/srs_utest_protocol.cpp +++ b/trunk/src/utest/srs_utest_protocol.cpp @@ -230,8 +230,6 @@ srs_error_t MockBufferIO::writev(const iovec *iov, int iov_size, ssize_t* nwrite total += writen; } - sbytes += total; - if (nwrite) { *nwrite = total; } @@ -6412,3 +6410,65 @@ VOID TEST(ProtocolKbpsTest, RAWStatistic) } } +VOID TEST(ProtocolKbpsTest, WriteLargeIOVs) +{ + srs_error_t err; + + if (true) { + iovec iovs[1]; + iovs[0].iov_base = (char*)"Hello"; + iovs[0].iov_len = 5; + + MockBufferIO io; + ssize_t nn = 0; + HELPER_EXPECT_SUCCESS(srs_write_large_iovs(&io, iovs, 1, &nn)); + EXPECT_EQ(5, nn); + EXPECT_EQ(5, io.sbytes); + } + + if (true) { + iovec iovs[1024]; + int nn_iovs = (int)(sizeof(iovs)/sizeof(iovec)); + for (int i = 0; i < nn_iovs; i++) { + iovs[i].iov_base = (char*)"Hello"; + iovs[i].iov_len = 5; + } + + MockBufferIO io; + ssize_t nn = 0; + HELPER_EXPECT_SUCCESS(srs_write_large_iovs(&io, iovs, nn_iovs, &nn)); + EXPECT_EQ(5 * nn_iovs, nn); + EXPECT_EQ(5 * nn_iovs, io.sbytes); + } + + if (true) { + iovec iovs[1025]; + int nn_iovs = (int)(sizeof(iovs)/sizeof(iovec)); + for (int i = 0; i < nn_iovs; i++) { + iovs[i].iov_base = (char*)"Hello"; + iovs[i].iov_len = 5; + } + + MockBufferIO io; + ssize_t nn = 0; + HELPER_EXPECT_SUCCESS(srs_write_large_iovs(&io, iovs, nn_iovs, &nn)); + EXPECT_EQ(5 * nn_iovs, nn); + EXPECT_EQ(5 * nn_iovs, io.sbytes); + } + + if (true) { + iovec iovs[4096]; + int nn_iovs = (int)(sizeof(iovs)/sizeof(iovec)); + for (int i = 0; i < nn_iovs; i++) { + iovs[i].iov_base = (char*)"Hello"; + iovs[i].iov_len = 5; + } + + MockBufferIO io; + ssize_t nn = 0; + HELPER_EXPECT_SUCCESS(srs_write_large_iovs(&io, iovs, nn_iovs, &nn)); + EXPECT_EQ(5 * nn_iovs, nn); + EXPECT_EQ(5 * nn_iovs, io.sbytes); + } +} + From 850a4bbf205c4b603a2c6331e1eb65c4a354f0af Mon Sep 17 00:00:00 2001 From: winlin Date: Sat, 21 Mar 2020 20:41:37 +0800 Subject: [PATCH 3/4] Fix #1619, configure without utest by default. 3.0.136 --- .circleci/config.yml | 4 ++-- README.md | 2 ++ trunk/auto/options.sh | 6 +++--- trunk/src/core/srs_core_version3.hpp | 2 +- 4 files changed, 8 insertions(+), 6 deletions(-) diff --git a/.circleci/config.yml b/.circleci/config.yml index 9fa2e06e3..48d678850 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -5,13 +5,13 @@ jobs: - image: ossrs/srs:dev steps: - checkout - - run: cd trunk && ./configure && make + - run: cd trunk && ./configure --with-utest && make test: docker: - image: ossrs/srs:dev steps: - checkout - - run: cd trunk && ./configure --gcov && make && ./objs/srs_utest && bash auto/coverage.sh + - run: cd trunk && ./configure --with-utest --gcov && make && ./objs/srs_utest && bash auto/coverage.sh workflows: version: 2 build_and_test: diff --git a/README.md b/README.md index 2cd74f917..f25438e0a 100755 --- a/README.md +++ b/README.md @@ -146,6 +146,7 @@ For previous versions, please read: ## V3 changes +* v3.0, 2020-03-21, For [#1619][bug #1619], configure without utest by default. 3.0.136 * v3.0, 2020-03-21, For [#1651][bug #1651], fix return pnwrite of srs_write_large_iovs. 3.0.135 * v3.0, 2020-03-18, [3.0 beta3(3.0.134)][r3.0b3] released. 122509 lines. * v3.0, 2020-03-12, For [#1635][bug #1635], inotify watch ConfigMap for reload. 3.0.134 @@ -1678,6 +1679,7 @@ Winlin [bug #1630]: https://github.com/ossrs/srs/issues/1630 [bug #1635]: https://github.com/ossrs/srs/issues/1635 [bug #1651]: https://github.com/ossrs/srs/issues/1651 +[bug #1619]: https://github.com/ossrs/srs/issues/1619 [bug #yyyyyyyyyyyyy]: https://github.com/ossrs/srs/issues/yyyyyyyyyyyyy [exo #828]: https://github.com/google/ExoPlayer/pull/828 diff --git a/trunk/auto/options.sh b/trunk/auto/options.sh index 7bf4f209c..4c6bc58ca 100755 --- a/trunk/auto/options.sh +++ b/trunk/auto/options.sh @@ -20,7 +20,7 @@ SRS_NGINX=NO SRS_FFMPEG_TOOL=NO SRS_LIBRTMP=NO SRS_RESEARCH=NO -SRS_UTEST=YES +SRS_UTEST=NO SRS_GPERF=NO # Performance test: tcmalloc SRS_GPERF_MC=NO # Performance test: gperf memory check SRS_GPERF_MD=NO # Performance test: gperf memory defence @@ -386,7 +386,7 @@ function apply_user_presets() { SRS_HDS=YES SRS_LIBRTMP=YES SRS_RESEARCH=NO - SRS_UTEST=YES + SRS_UTEST=NO SRS_STATIC=NO fi @@ -413,7 +413,7 @@ function apply_user_presets() { SRS_HDS=YES SRS_LIBRTMP=YES SRS_RESEARCH=NO - SRS_UTEST=YES + SRS_UTEST=NO SRS_STATIC=NO fi diff --git a/trunk/src/core/srs_core_version3.hpp b/trunk/src/core/srs_core_version3.hpp index 85bd342c0..e6022c5df 100644 --- a/trunk/src/core/srs_core_version3.hpp +++ b/trunk/src/core/srs_core_version3.hpp @@ -24,6 +24,6 @@ #ifndef SRS_CORE_VERSION3_HPP #define SRS_CORE_VERSION3_HPP -#define SRS_VERSION3_REVISION 135 +#define SRS_VERSION3_REVISION 136 #endif From 0dd6c31487c2d4adc163d0b136d3c5976c7e2a7d Mon Sep 17 00:00:00 2001 From: winlin Date: Sat, 21 Mar 2020 22:41:25 +0800 Subject: [PATCH 4/4] Fix #1629, fix kickoff FLV client bug. 3.0.137 --- README.md | 2 ++ trunk/src/app/srs_app_http_conn.cpp | 38 ++++++++++++++++++++------- trunk/src/app/srs_app_http_conn.hpp | 3 +++ trunk/src/app/srs_app_http_stream.cpp | 12 ++++----- trunk/src/core/srs_core_version3.hpp | 2 +- 5 files changed, 40 insertions(+), 17 deletions(-) diff --git a/README.md b/README.md index f25438e0a..e7b88dcbf 100755 --- a/README.md +++ b/README.md @@ -146,6 +146,7 @@ For previous versions, please read: ## V3 changes +* v3.0, 2020-03-21, For [#1629][bug #1629], fix kickoff FLV client bug. 3.0.137 * v3.0, 2020-03-21, For [#1619][bug #1619], configure without utest by default. 3.0.136 * v3.0, 2020-03-21, For [#1651][bug #1651], fix return pnwrite of srs_write_large_iovs. 3.0.135 * v3.0, 2020-03-18, [3.0 beta3(3.0.134)][r3.0b3] released. 122509 lines. @@ -1680,6 +1681,7 @@ Winlin [bug #1635]: https://github.com/ossrs/srs/issues/1635 [bug #1651]: https://github.com/ossrs/srs/issues/1651 [bug #1619]: https://github.com/ossrs/srs/issues/1619 +[bug #1629]: https://github.com/ossrs/srs/issues/1629 [bug #yyyyyyyyyyyyy]: https://github.com/ossrs/srs/issues/yyyyyyyyyyyyy [exo #828]: https://github.com/google/ExoPlayer/pull/828 diff --git a/trunk/src/app/srs_app_http_conn.cpp b/trunk/src/app/srs_app_http_conn.cpp index fc1831aa4..8f9429cbc 100644 --- a/trunk/src/app/srs_app_http_conn.cpp +++ b/trunk/src/app/srs_app_http_conn.cpp @@ -198,19 +198,32 @@ srs_error_t SrsResponseOnlyHttpConn::pop_message(ISrsHttpMessage** preq) srs_error_t err = srs_success; SrsStSocket skt; - + if ((err = skt.initialize(stfd)) != srs_success) { return srs_error_wrap(err, "init socket"); } - - if ((err = parser->parse_message(&skt, preq)) != srs_success) { - return srs_error_wrap(err, "parse message"); + + // Check user interrupt by interval. + skt.set_recv_timeout(3 * SRS_UTIME_SECONDS); + + // drop all request body. + char body[4096]; + while (true) { + if ((err = trd->pull()) != srs_success) { + return srs_error_wrap(err, "timeout"); + } + + if ((err = skt.read(body, 4096, NULL)) != srs_success) { + // Because we use timeout to check trd state, so we should ignore any timeout. + if (srs_error_code(err) == ERROR_SOCKET_TIMEOUT) { + srs_freep(err); + continue; + } + + return srs_error_wrap(err, "read response"); + } } - // Attach owner connection to message. - SrsHttpMessage* hreq = (SrsHttpMessage*)(*preq); - hreq->set_connection(this); - return err; } @@ -219,12 +232,12 @@ srs_error_t SrsResponseOnlyHttpConn::on_got_http_message(ISrsHttpMessage* msg) srs_error_t err = srs_success; ISrsHttpResponseReader* br = msg->body_reader(); - + // when not specified the content length, ignore. if (msg->content_length() == -1) { return err; } - + // drop all request body. char body[4096]; while (!br->eof()) { @@ -236,6 +249,11 @@ srs_error_t SrsResponseOnlyHttpConn::on_got_http_message(ISrsHttpMessage* msg) return err; } +void SrsResponseOnlyHttpConn::expire() +{ + SrsHttpConn::expire(); +} + SrsHttpServer::SrsHttpServer(SrsServer* svr) { server = svr; diff --git a/trunk/src/app/srs_app_http_conn.hpp b/trunk/src/app/srs_app_http_conn.hpp index f3de6659e..7529cfc5b 100644 --- a/trunk/src/app/srs_app_http_conn.hpp +++ b/trunk/src/app/srs_app_http_conn.hpp @@ -101,6 +101,9 @@ public: virtual srs_error_t pop_message(ISrsHttpMessage** preq); public: virtual srs_error_t on_got_http_message(ISrsHttpMessage* msg); +public: + // Set connection to expired. + virtual void expire(); }; // The http server, use http stream or static server to serve requests. diff --git a/trunk/src/app/srs_app_http_stream.cpp b/trunk/src/app/srs_app_http_stream.cpp index fb7bd54b3..815561e1e 100755 --- a/trunk/src/app/srs_app_http_stream.cpp +++ b/trunk/src/app/srs_app_http_stream.cpp @@ -592,10 +592,15 @@ srs_error_t SrsLiveStream::do_serve_http(ISrsHttpResponseWriter* w, ISrsHttpMess SrsAutoFree(SrsPithyPrint, pprint); SrsMessageArray msgs(SRS_PERF_MW_MSGS); + + // Use receive thread to accept the close event to avoid FD leak. + // @see https://github.com/ossrs/srs/issues/636#issuecomment-298208427 + SrsHttpMessage* hr = dynamic_cast(r); + SrsResponseOnlyHttpConn* hc = dynamic_cast(hr->connection()); // update the statistic when source disconveried. SrsStatistic* stat = SrsStatistic::instance(); - if ((err = stat->on_client(_srs_context->get_id(), req, NULL, SrsRtmpConnPlay)) != srs_success) { + if ((err = stat->on_client(_srs_context->get_id(), req, hc, SrsRtmpConnPlay)) != srs_success) { return srs_error_wrap(err, "stat on client"); } @@ -613,11 +618,6 @@ srs_error_t SrsLiveStream::do_serve_http(ISrsHttpResponseWriter* w, ISrsHttpMess } SrsFlvStreamEncoder* ffe = dynamic_cast(enc); - - // Use receive thread to accept the close event to avoid FD leak. - // @see https://github.com/ossrs/srs/issues/636#issuecomment-298208427 - SrsHttpMessage* hr = dynamic_cast(r); - SrsResponseOnlyHttpConn* hc = dynamic_cast(hr->connection()); // Set the socket options for transport. bool tcp_nodelay = _srs_config->get_tcp_nodelay(req->vhost); diff --git a/trunk/src/core/srs_core_version3.hpp b/trunk/src/core/srs_core_version3.hpp index e6022c5df..95a9c694d 100644 --- a/trunk/src/core/srs_core_version3.hpp +++ b/trunk/src/core/srs_core_version3.hpp @@ -24,6 +24,6 @@ #ifndef SRS_CORE_VERSION3_HPP #define SRS_CORE_VERSION3_HPP -#define SRS_VERSION3_REVISION 136 +#define SRS_VERSION3_REVISION 137 #endif