mirror of
https://github.com/zoriya/Kyoo.git
synced 2025-07-09 03:04:20 -04:00
Fix master playlist & keyframes deadlock
This commit is contained in:
parent
c3ef7bc0e1
commit
ca6b581c85
@ -88,6 +88,7 @@ func (fs *FileStream) GetMaster() string {
|
||||
master += "CHANNELS=\"2\","
|
||||
master += fmt.Sprintf("URI=\"./audio/%d/index.m3u8\"\n", audio.Index)
|
||||
}
|
||||
master += "\n"
|
||||
|
||||
// codec is the prefix + the level, the level is not part of the codec we want to compare for the same_codec check bellow
|
||||
transmux_prefix := "avc1.6400"
|
||||
@ -108,9 +109,10 @@ func (fs *FileStream) GetMaster() string {
|
||||
if def_video != nil {
|
||||
qualities := Filter(Qualities, func(quality Quality) bool {
|
||||
same_codec := def_video.MimeCodec != nil && strings.HasPrefix(*def_video.MimeCodec, transmux_prefix)
|
||||
return quality.Height() < def_video.Quality().Height() ||
|
||||
(quality.Height() == def_video.Quality().Height() && !same_codec)
|
||||
return quality.Height() < def_video.Height ||
|
||||
(quality.Height() == def_video.Height && !same_codec)
|
||||
})
|
||||
qualities = append(qualities, Original)
|
||||
|
||||
for _, quality := range qualities {
|
||||
for _, video := range fs.Info.Videos {
|
||||
@ -126,13 +128,14 @@ func (fs *FileStream) GetMaster() string {
|
||||
} else {
|
||||
master += fmt.Sprintf("NAME=\"Video %d\",", video.Index)
|
||||
}
|
||||
if &video == def_video {
|
||||
master += "DEFAULT=YES"
|
||||
if video == *def_video {
|
||||
master += "DEFAULT=YES\n"
|
||||
} else {
|
||||
master += fmt.Sprintf("URI=\"./%d/%s/index.m3u8\"\n", video.Index, quality)
|
||||
}
|
||||
}
|
||||
}
|
||||
master += "\n"
|
||||
|
||||
// original stream
|
||||
{
|
||||
@ -152,7 +155,7 @@ func (fs *FileStream) GetMaster() string {
|
||||
aspectRatio := float32(def_video.Width) / float32(def_video.Height)
|
||||
|
||||
for i, quality := range qualities {
|
||||
if i == 0 {
|
||||
if i == len(qualities)-1 {
|
||||
// skip the original stream that already got handled
|
||||
continue
|
||||
}
|
||||
@ -164,7 +167,7 @@ func (fs *FileStream) GetMaster() string {
|
||||
master += fmt.Sprintf("CODECS=\"%s\",", strings.Join([]string{transmux_codec, audio_codec}, ","))
|
||||
master += "AUDIO=\"audio\","
|
||||
master += "CLOSED-CAPTIONS=NONE\n"
|
||||
master += fmt.Sprintf("./%s/index.m3u8\n", quality)
|
||||
master += fmt.Sprintf("./%d/%s/index.m3u8\n", def_video.Index, quality)
|
||||
}
|
||||
}
|
||||
|
||||
@ -172,17 +175,11 @@ func (fs *FileStream) GetMaster() string {
|
||||
}
|
||||
|
||||
func (fs *FileStream) getVideoStream(idx uint32, quality Quality) (*VideoStream, error) {
|
||||
var err error
|
||||
stream, _ := fs.videos.GetOrCreate(VideoKey{idx, quality}, func() *VideoStream {
|
||||
var ret *VideoStream
|
||||
ret, err = fs.transcoder.NewVideoStream(fs, idx, quality)
|
||||
ret, _ := fs.transcoder.NewVideoStream(fs, idx, quality)
|
||||
return ret
|
||||
})
|
||||
if err != nil {
|
||||
fs.videos.Remove(VideoKey{idx, quality})
|
||||
return nil, err
|
||||
}
|
||||
stream.ready.Wait()
|
||||
stream.keyframes.info.ready.Wait()
|
||||
return stream, nil
|
||||
}
|
||||
|
||||
@ -203,17 +200,11 @@ func (fs *FileStream) GetVideoSegment(idx uint32, quality Quality, segment int32
|
||||
}
|
||||
|
||||
func (fs *FileStream) getAudioStream(audio uint32) (*AudioStream, error) {
|
||||
var err error
|
||||
stream, _ := fs.audios.GetOrCreate(audio, func() *AudioStream {
|
||||
var ret *AudioStream
|
||||
ret, err = fs.transcoder.NewAudioStream(fs, audio)
|
||||
ret, _ := fs.transcoder.NewAudioStream(fs, audio)
|
||||
return ret
|
||||
})
|
||||
if err != nil {
|
||||
fs.audios.Remove(audio)
|
||||
return nil, err
|
||||
}
|
||||
stream.ready.Wait()
|
||||
stream.keyframes.info.ready.Wait()
|
||||
return stream, nil
|
||||
}
|
||||
|
||||
|
@ -31,7 +31,6 @@ type StreamHandle interface {
|
||||
|
||||
type Stream struct {
|
||||
handle StreamHandle
|
||||
ready sync.WaitGroup
|
||||
file *FileStream
|
||||
keyframes *Keyframe
|
||||
segments []Segment
|
||||
@ -70,27 +69,31 @@ func NewStream(file *FileStream, keyframes *Keyframe, handle StreamHandle, ret *
|
||||
ret.keyframes = keyframes
|
||||
ret.heads = make([]Head, 0)
|
||||
|
||||
length, is_done := keyframes.Length()
|
||||
ret.segments = make([]Segment, length, max(length, 2000))
|
||||
for seg := range ret.segments {
|
||||
ret.segments[seg].channel = make(chan struct{})
|
||||
}
|
||||
go func() {
|
||||
keyframes.info.ready.Wait()
|
||||
|
||||
if !is_done {
|
||||
keyframes.AddListener(func(keyframes []float64) {
|
||||
ret.lock.Lock()
|
||||
defer ret.lock.Unlock()
|
||||
old_length := len(ret.segments)
|
||||
if cap(ret.segments) > len(keyframes) {
|
||||
ret.segments = ret.segments[:len(keyframes)]
|
||||
} else {
|
||||
ret.segments = append(ret.segments, make([]Segment, len(keyframes)-old_length)...)
|
||||
}
|
||||
for seg := old_length; seg < len(keyframes); seg++ {
|
||||
ret.segments[seg].channel = make(chan struct{})
|
||||
}
|
||||
})
|
||||
}
|
||||
length, is_done := keyframes.Length()
|
||||
ret.segments = make([]Segment, length, max(length, 2000))
|
||||
for seg := range ret.segments {
|
||||
ret.segments[seg].channel = make(chan struct{})
|
||||
}
|
||||
|
||||
if !is_done {
|
||||
keyframes.AddListener(func(keyframes []float64) {
|
||||
ret.lock.Lock()
|
||||
defer ret.lock.Unlock()
|
||||
old_length := len(ret.segments)
|
||||
if cap(ret.segments) > len(keyframes) {
|
||||
ret.segments = ret.segments[:len(keyframes)]
|
||||
} else {
|
||||
ret.segments = append(ret.segments, make([]Segment, len(keyframes)-old_length)...)
|
||||
}
|
||||
for seg := old_length; seg < len(keyframes); seg++ {
|
||||
ret.segments[seg].channel = make(chan struct{})
|
||||
}
|
||||
})
|
||||
}
|
||||
}()
|
||||
}
|
||||
|
||||
// Remember to lock before calling this.
|
||||
|
Loading…
x
Reference in New Issue
Block a user