mirror of
https://github.com/ossrs/srs.git
synced 2025-02-13 03:41:55 +00:00
Fix HLS segment close bug
This commit is contained in:
parent
138d1e3cad
commit
6380e8f1c0
4 changed files with 18 additions and 10 deletions
|
@ -242,15 +242,15 @@ void SrsFragmentWindow::clear_expired(bool delete_files)
|
|||
expired_fragments.clear();
|
||||
}
|
||||
|
||||
int64_t SrsFragmentWindow::max_duration()
|
||||
srs_utime_t SrsFragmentWindow::max_duration()
|
||||
{
|
||||
int64_t v = 0;
|
||||
srs_utime_t v = 0;
|
||||
|
||||
std::vector<SrsFragment*>::iterator it;
|
||||
|
||||
for (it = fragments.begin(); it != fragments.end(); ++it) {
|
||||
SrsFragment* fragment = *it;
|
||||
v = srs_max(v, srsu2ms(fragment->duration()));
|
||||
v = srs_max(v, fragment->duration());
|
||||
}
|
||||
|
||||
return v;
|
||||
|
|
|
@ -96,8 +96,8 @@ public:
|
|||
virtual void shrink(srs_utime_t window);
|
||||
// Clear the expired fragments.
|
||||
virtual void clear_expired(bool delete_files);
|
||||
// Get the max duration in ms of all fragments.
|
||||
virtual int64_t max_duration();
|
||||
// Get the max duration in srs_utime_t of all fragments.
|
||||
virtual srs_utime_t max_duration();
|
||||
public:
|
||||
virtual bool empty();
|
||||
virtual SrsFragment* first();
|
||||
|
|
|
@ -312,7 +312,7 @@ srs_error_t SrsHlsMuxer::update_config(SrsRequest* r, string entry_prefix,
|
|||
m3u8 = path + "/" + m3u8_url;
|
||||
|
||||
// when update config, reset the history target duration.
|
||||
max_td = (int)(fragment * _srs_config->get_hls_td_ratio(r->vhost));
|
||||
max_td = fragment * _srs_config->get_hls_td_ratio(r->vhost);
|
||||
|
||||
// create m3u8 dir once.
|
||||
m3u8_dir = srs_path_dirname(m3u8);
|
||||
|
@ -585,12 +585,19 @@ srs_error_t SrsHlsMuxer::segment_close()
|
|||
|
||||
// when close current segment, the current segment must not be NULL.
|
||||
srs_assert(current);
|
||||
|
||||
// We should always close the underlayer writer.
|
||||
if (current && current->writer) {
|
||||
current->writer->close();
|
||||
}
|
||||
|
||||
// valid, add to segments if segment duration is ok
|
||||
// when too small, it maybe not enough data to play.
|
||||
// when too large, it maybe timestamp corrupt.
|
||||
// make the segment more acceptable, when in [min, max_td * 2], it's ok.
|
||||
if (current->duration() >= SRS_AUTO_HLS_SEGMENT_MIN_DURATION && (int)srsu2msi(current->duration()) <= max_td * 2 * 1000) {
|
||||
bool matchMinDuration = current->duration() >= SRS_AUTO_HLS_SEGMENT_MIN_DURATION;
|
||||
bool matchMaxDuration = current->duration() <= max_td * 2 * 1000;
|
||||
if (matchMinDuration && matchMaxDuration) {
|
||||
// use async to call the http hooks, for it will cause thread switch.
|
||||
if ((err = async->execute(new SrsDvrAsyncCallOnHls(_srs_context->get_id(), req, current->fullpath(),
|
||||
current->uri, m3u8, m3u8_url, current->sequence_no, current->duration()))) != srs_success) {
|
||||
|
@ -607,6 +614,7 @@ srs_error_t SrsHlsMuxer::segment_close()
|
|||
|
||||
// rename from tmp to real path
|
||||
if ((err = current->rename()) != srs_success) {
|
||||
srs_freep(current);
|
||||
return srs_error_wrap(err, "rename");
|
||||
}
|
||||
|
||||
|
@ -744,8 +752,8 @@ srs_error_t SrsHlsMuxer::_refresh_m3u8(string m3u8_file)
|
|||
* typical target duration is 10 seconds.
|
||||
*/
|
||||
// @see https://github.com/ossrs/srs/issues/304#issuecomment-74000081
|
||||
int target_duration = (int)ceil(segments->max_duration() / 1000.0);
|
||||
target_duration = srs_max(target_duration, max_td);
|
||||
srs_utime_t max_duration = segments->max_duration();
|
||||
int target_duration = (int)ceil(srsu2msi(srs_max(max_duration, max_td)) / 1000.0);
|
||||
|
||||
ss << "#EXT-X-TARGETDURATION:" << target_duration << SRS_CONSTS_LF;
|
||||
|
||||
|
|
|
@ -168,7 +168,7 @@ private:
|
|||
SrsFileWriter *writer;
|
||||
private:
|
||||
int _sequence_no;
|
||||
int max_td;
|
||||
srs_utime_t max_td;
|
||||
std::string m3u8;
|
||||
std::string m3u8_url;
|
||||
private:
|
||||
|
|
Loading…
Reference in a new issue