remotion-dev/remotion · error · Error
Invalid sync byte
Error message
Invalid sync byte
What it means
Thrown by parsePacket() when the first byte of a 188-byte MPEG-TS packet is not 0x47 (the MPEG-TS sync byte). Every TS packet must start with 0x47; any other value means the data is not aligned to a TS packet boundary or is not MPEG-TS at all.
Source
Thrown at packages/media-parser/src/containers/transport-stream/parse-packet.ts:23
import {parsePat, parseSdt} from './parse-pat';
import {parsePes} from './parse-pes';
import {parsePmt} from './parse-pmt';
import {parseStream} from './parse-stream-packet';
import {getProgramForId, getStreamForId} from './traversal';
export const parsePacket = ({
iterator,
structure,
transportStream,
}: {
iterator: BufferIterator;
structure: TransportStreamStructure;
transportStream: TransportStreamState;
}): TransportStreamBox | null => {
const offset = iterator.counter.getOffset();
const syncByte = iterator.getUint8();
if (syncByte !== 0x47) {
throw new Error('Invalid sync byte');
}
iterator.startReadingBits();
iterator.getBits(1); // transport error indicator
const payloadUnitStartIndicator = iterator.getBits(1);
iterator.getBits(1); // transport priority
const programId = iterator.getBits(13);
iterator.getBits(2); // transport scrambling control
const adaptationFieldControl1 = iterator.getBits(1); // adaptation field control 1
iterator.getBits(1); // adaptation field control 2
iterator.getBits(4); // continuity counter
iterator.stopReadingBits();
if (adaptationFieldControl1 === 1) {
iterator.startReadingBits();
const adaptationFieldLength = iterator.getBits(8);
const headerOffset = iterator.counter.getOffset();
if (adaptationFieldLength > 0) {
iterator.getBits(1); // discontinuity indicatorView on GitHub (pinned to 78fe4bb3fd)
Solutions
- Resync by scanning forward for the next 0x47 at a 188-byte stride before parsing.
- Verify the file is MPEG-TS (ffprobe -show_format).
- Re-mux the TS to repair alignment: ffmpeg -i in.ts -c copy out.ts.
Example fix
// before
const syncByte = iterator.getUint8();
if (syncByte !== 0x47) throw new Error('Invalid sync byte');
// after: resync to next 0x47
while (iterator.bytesRemaining() > 0 && iterator.getUint8() !== 0x47) { /* advance */ } Defensive patterns
Strategy: validation
Validate before calling
// Verify the 0x47 sync byte at each 188-byte boundary before parsing.
function isTsSyncByte(b: number): boolean {
return b === 0x47;
}
if (!isTsSyncByte(iterator.getUint8())) {
// resync: scan forward for 0x47 at 188-byte stride
} Type guard
function isTsSyncByte(b: number): boolean {
return b === 0x47;
} Try / catch
try {
parsePacket({iterator, structure, transportStream});
} catch (err) {
if (err instanceof Error && err.message === 'Invalid sync byte') {
// resync to next 0x47 and continue
} else throw err;
} Prevention
- Resync on 0x47 at 188-byte stride after any corrupt packet.
- Confirm the file is MPEG-TS with ffprobe before parsing.
- Capture TS from the start so packet alignment is intact.
When it happens
Trigger: Misaligned TS data (the reader is not at a packet boundary), corrupt TS, or non-TS data routed to the TS parser. Common after a dropped/corrupt packet throws alignment off by N bytes.
Common situations: See trigger scenarios.
Related errors
- Unknown packet identifier
- Invalid ADTS header
- Only supporting MPEG-4 for .ts
- Only supporting layer 0 for .ts
- Invalid ADTS header - too short
AI-assisted analysis of remotion-dev/remotion@78fe4bb3fd (2026-08-12).
Data as JSON: /api/errors/09f02749b78565a5.
Report an issue: GitHub.