Publish and subscribe over wss://livekit.uni-wh.de:7800 and refuse cleartext ws://. Conference room is uwh-telhai. Includes the uncommitted encoded H.264 publish path, Rally hairpin, and KMS wall overlay.
73 lines
1.8 KiB
Python
73 lines
1.8 KiB
Python
"""Split Annex-B H.264 into access units."""
|
|
from __future__ import annotations
|
|
|
|
|
|
def _start_at(buf: bytes, i: int) -> int:
|
|
n = len(buf)
|
|
while i + 2 < n:
|
|
if buf[i] == 0 and buf[i + 1] == 0:
|
|
if buf[i + 2] == 1:
|
|
return i
|
|
if i + 3 < n and buf[i + 2] == 0 and buf[i + 3] == 1:
|
|
return i
|
|
i += 1
|
|
return -1
|
|
|
|
|
|
def nal_unit_type(nal: bytes) -> int:
|
|
"""First NAL type in an AU (5 = IDR)."""
|
|
i = _start_at(nal, 0)
|
|
if i < 0:
|
|
return 0
|
|
hdr = i + (4 if i + 3 < len(nal) and nal[i + 2] == 0 else 3)
|
|
if hdr >= len(nal):
|
|
return 0
|
|
return nal[hdr] & 0x1F
|
|
|
|
|
|
def is_keyframe(au: bytes) -> bool:
|
|
i = 0
|
|
n = len(au)
|
|
while True:
|
|
s = _start_at(au, i)
|
|
if s < 0:
|
|
return False
|
|
hdr = s + (4 if s + 3 < n and au[s + 2] == 0 else 3)
|
|
if hdr >= n:
|
|
return False
|
|
ntype = au[hdr] & 0x1F
|
|
if ntype == 5:
|
|
return True
|
|
i = hdr + 1
|
|
|
|
|
|
class AnnexBSplitter:
|
|
"""Feed byte-stream; yield complete AUs (including start codes)."""
|
|
|
|
def __init__(self) -> None:
|
|
self._buf = bytearray()
|
|
|
|
def push(self, data: bytes) -> list[bytes]:
|
|
if data:
|
|
self._buf.extend(data)
|
|
out: list[bytes] = []
|
|
buf = self._buf
|
|
first = _start_at(bytes(buf), 0)
|
|
if first < 0:
|
|
if len(buf) > 1_000_000:
|
|
del buf[: len(buf) - 8]
|
|
return out
|
|
if first:
|
|
del buf[:first]
|
|
pos = 0
|
|
while True:
|
|
nxt = _start_at(bytes(buf), pos + 3)
|
|
if nxt < 0:
|
|
break
|
|
au = bytes(buf[:nxt])
|
|
if au:
|
|
out.append(au)
|
|
del buf[:nxt]
|
|
pos = 0
|
|
return out
|