snapshot of https://github.com/livekit/livekit.git @ 08c5433449c106943231037d0b892895f6e92d3b (2026-09-15)
This commit is contained in:
58
pkg/sfu/videolayerselector/framenumberwrapper.go
Normal file
58
pkg/sfu/videolayerselector/framenumberwrapper.go
Normal file
@@ -0,0 +1,58 @@
|
||||
// Copyright 2024 LiveKit, Inc.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package videolayerselector
|
||||
|
||||
import "github.com/livekit/protocol/logger"
|
||||
|
||||
type FrameNumberWrapper struct {
|
||||
offset uint64
|
||||
last uint64
|
||||
inited bool
|
||||
logger logger.Logger
|
||||
}
|
||||
|
||||
// UpdateAndGet returns the wrapped frame number from the given frame number, and updates the offset to
|
||||
// make sure the returned frame number is always inorder. Should only updateOffset if the new frame is a keyframe
|
||||
// because frame dependencies uses on the frame number diff so frames inside a GOP should have the same offset.
|
||||
func (f *FrameNumberWrapper) UpdateAndGet(new uint64, updateOffset bool) uint64 {
|
||||
if !f.inited {
|
||||
f.last = new
|
||||
f.inited = true
|
||||
return new
|
||||
}
|
||||
|
||||
if new <= f.last {
|
||||
return new + f.offset
|
||||
}
|
||||
|
||||
if updateOffset {
|
||||
new16 := uint16(new + f.offset)
|
||||
last16 := uint16(f.last + f.offset)
|
||||
// if new frame number wraps around and is considered as earlier by client, increase offset to make it later
|
||||
if diff := new16 - last16; diff > 0x8000 || (diff == 0x8000 && new16 < last16) {
|
||||
// increase offset by 6000, nearly 10 seconds for 30fps video with 3 spatial layers
|
||||
prevOffset := f.offset
|
||||
f.offset += uint64(65535 - diff + 6000)
|
||||
|
||||
f.logger.Debugw("wrap around frame number seen, update offset", "new", new, "last", f.last, "offset", f.offset, "prevOffset", prevOffset, "lastWrapFn", last16, "newWrapFn", new16)
|
||||
}
|
||||
}
|
||||
f.last = new
|
||||
return new + f.offset
|
||||
}
|
||||
|
||||
func (f *FrameNumberWrapper) LastOrigin() uint64 {
|
||||
return f.last
|
||||
}
|
||||
Reference in New Issue
Block a user