@blockcast/mmt-base 0.1.0 → 0.3.0-main.d9354616fdf2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +16 -2
- package/dist/fec-block-profile.d.ts +55 -0
- package/dist/fec-block-profile.d.ts.map +1 -0
- package/dist/fec-block-profile.js +128 -0
- package/dist/fec-block-profile.js.map +1 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +5 -0
- package/dist/index.js.map +1 -1
- package/dist/mmtp.d.ts +77 -56
- package/dist/mmtp.d.ts.map +1 -1
- package/dist/mmtp.js +260 -216
- package/dist/mmtp.js.map +1 -1
- package/dist/net-constants.d.ts +18 -0
- package/dist/net-constants.d.ts.map +1 -0
- package/dist/net-constants.js +18 -0
- package/dist/net-constants.js.map +1 -0
- package/dist/ntp-short.d.ts +47 -0
- package/dist/ntp-short.d.ts.map +1 -0
- package/dist/ntp-short.js +54 -0
- package/dist/ntp-short.js.map +1 -0
- package/dist/serial-number.d.ts +57 -0
- package/dist/serial-number.d.ts.map +1 -0
- package/dist/serial-number.js +98 -0
- package/dist/serial-number.js.map +1 -0
- package/dist/signalling.d.ts +312 -0
- package/dist/signalling.d.ts.map +1 -0
- package/dist/signalling.js +637 -0
- package/dist/signalling.js.map +1 -0
- package/package.json +9 -4
- package/src/fec-block-profile.ts +145 -0
- package/src/index.ts +5 -0
- package/src/mmtp.ts +334 -188
- package/src/net-constants.ts +17 -0
- package/src/ntp-short.ts +67 -0
- package/src/serial-number.ts +107 -0
- package/src/signalling.ts +862 -0
- package/src/alfec.test.ts +0 -176
- package/src/mmtp.test.ts +0 -769
package/README.md
CHANGED
|
@@ -57,9 +57,23 @@ MPU `payload_length` is interpreted strictly as ISO's length-after-field value:
|
|
|
57
57
|
| `extractFecPayloadId` | function | `{ ssId }` from a source packet's FEC payload id (or `null`) |
|
|
58
58
|
| `extractRepairFecPayloadId` | function | Repair-flow FEC payload id (13-byte, `REPAIR_FEC_PID_SIZE`) |
|
|
59
59
|
| `parseMoqRepairFrame` | function | Strictly parse a mode-0 MMTP Annex C repair frame → `MoqRepairFrame` |
|
|
60
|
-
| `
|
|
61
|
-
| `MoqRepairFrame`, `AlFecConfig` | type | Repair-frame / AL-FEC config shapes |
|
|
60
|
+
| `MoqRepairFrame` | type | Repair-frame shape |
|
|
62
61
|
| `ALFEC_MESSAGE_ID` (0x0203), `FEC_CODE_XOR` (1), `FEC_CODE_RAPTORQ` (2), `REPAIR_FEC_PID_SIZE` (13) | const | AL-FEC signaling + payload-id constants |
|
|
62
|
+
| `MMTP_SIGNALING_PACKET_ID` (0), `MMTP_PACKET_ID_MAX` (0xffff) | const | Signaling-flow `packet_id` (never a track's) and the 16-bit `packet_id` ceiling; a track's `packet_id` is 1..65535 |
|
|
63
|
+
|
|
64
|
+
### Signalling messages (`signalling.ts`, packet_id 0)
|
|
65
|
+
|
|
66
|
+
Total parsers (malformed or unsupported input → `null`, never a throw), per
|
|
67
|
+
ISO/IEC 23008-1:2023 9.3.4.2, 10.2-10.3, 10.6 and Annex C Table C.3 as
|
|
68
|
+
replaced by Amd 1:2025.
|
|
69
|
+
|
|
70
|
+
| Symbol | Kind | Purpose |
|
|
71
|
+
|--------|------|---------|
|
|
72
|
+
| `parseSignallingPayload` | function | Split a signalling packet into complete messages; reports the payload form: `iso-9.3.4.2` (Figure 15 header) or `legacy-bare-alfec` (message 0x0203 directly after the MMTP header, recognised by its exact `0x02 0x03` peek) |
|
|
73
|
+
| `parseSignallingPacket` | function | Decode every message of a signalling packet → `al-fec` / `pa` / `mpt` / `other` |
|
|
74
|
+
| `parseAlFecMessage`, `parseAlFecMessageBody` | function | Every FEC flow of an AL-FEC message: all asset packet_ids, one-stage / two-stage / LA-FEC repair flows, private fields → `AlFecMessage` |
|
|
75
|
+
| `alFecRaptorQFlowConfig` | function | One flow's decoder geometry under the Blockcast one-stage RaptorQ profile (private field = OTI + interleave depth) → `AlFecRaptorQFlowConfig` |
|
|
76
|
+
| `parsePaMessageBody`, `parseMptMessageBody`, `parseMpTable`, `mpAssetPacketIds` | function | PA / MPT messages and the MP table: asset → packet_id mapping |
|
|
63
77
|
|
|
64
78
|
### ALTA trailer (re-exported from `@blockcast/mmt-alta-parse`)
|
|
65
79
|
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
/** The two block profiles a catalog `fec.blockProfile` may name. */
|
|
2
|
+
export type FecBlockProfile = 'k-padded-v1' | 'iso-ssbg1-v1';
|
|
3
|
+
/** Every accepted `fec.blockProfile` token, legacy first. */
|
|
4
|
+
export declare const FEC_BLOCK_PROFILES: readonly FecBlockProfile[];
|
|
5
|
+
/** True for a known block-profile token. */
|
|
6
|
+
export declare function isFecBlockProfile(value: unknown): value is FecBlockProfile;
|
|
7
|
+
/**
|
|
8
|
+
* Read a required `fec.blockProfile`. Throws on an absent or unknown token:
|
|
9
|
+
* there is no default and nothing is inferred, because the two profiles carry
|
|
10
|
+
* identical wire tuples whose repair math differs.
|
|
11
|
+
*
|
|
12
|
+
* @param where the catalog path of the field, for the error message.
|
|
13
|
+
*/
|
|
14
|
+
export declare function parseFecBlockProfile(value: unknown, where: string): FecBlockProfile;
|
|
15
|
+
/** ISO/IEC 23008-1 C.3.3 ssbg_mode1: the two-octet packet length field. */
|
|
16
|
+
export declare const SSBG1_LENGTH_FIELD_BYTES = 2;
|
|
17
|
+
/** The largest protected packet an ssbg_mode1 symbol of size T can carry. */
|
|
18
|
+
export declare function ssbg1MaxPacketLength(symbolSize: number): number;
|
|
19
|
+
/** Whether a protected packet of `packetLength` bytes fits one T-byte ssbg_mode1 symbol. */
|
|
20
|
+
export declare function ssbg1FitsSymbol(packetLength: number, symbolSize: number): boolean;
|
|
21
|
+
/**
|
|
22
|
+
* Build one ssbg_mode1 source symbol (C.3.3): the protected packet's length
|
|
23
|
+
* in two octets, network byte order, then the packet, then zero octets up to
|
|
24
|
+
* T. The protected packet is the MMTP packet before its Source FEC Payload ID
|
|
25
|
+
* is appended (C.4.2).
|
|
26
|
+
*
|
|
27
|
+
* @throws when `length + 2 > T`: the packet cannot be protected under this
|
|
28
|
+
* profile, and silently truncating it would corrupt every repair symbol.
|
|
29
|
+
*/
|
|
30
|
+
export declare function buildSsbg1SourceSymbol(packet: Uint8Array, symbolSize: number): Uint8Array;
|
|
31
|
+
/**
|
|
32
|
+
* Recover the protected packet from one ssbg_mode1 source symbol: the bytes
|
|
33
|
+
* the length field names. Returns null, never a guess, when the length field
|
|
34
|
+
* points past the symbol or any padding octet is non-zero (C.3.3 padding is
|
|
35
|
+
* all 00h), since either means the recovered symbol is not what was sent.
|
|
36
|
+
*/
|
|
37
|
+
export declare function trimSsbg1SourceSymbol(symbol: Uint8Array): Uint8Array | null;
|
|
38
|
+
/** The SS_ID after the last source symbol of `[ssStart, ssStart + ssbLength)`. */
|
|
39
|
+
export declare function isoBlockEnd(ssStart: number, ssbLength: number): number;
|
|
40
|
+
/**
|
|
41
|
+
* Range membership (C.5.2, C.5.3): whether `ssId` is one of the
|
|
42
|
+
* `ssbLength` consecutive SS_IDs starting at `ssStart`, modulo 2^32.
|
|
43
|
+
*/
|
|
44
|
+
export declare function isoBlockContains(ssStart: number, ssbLength: number, ssId: number): boolean;
|
|
45
|
+
/**
|
|
46
|
+
* A lower bound on how many blocks the block starting at `a` lies behind the
|
|
47
|
+
* one starting at `b` (0 when `a` does not precede `b`). An iso-ssbg1-v1
|
|
48
|
+
* block holds at most `kMax` source symbols (the catalog `sourceSymbols`, the
|
|
49
|
+
* AL-FEC maximum_k_for_repair_flow), so `n * kMax` SS_IDs always span at least
|
|
50
|
+
* `n` blocks. Every interleave horizon in the receiver (decoder retention,
|
|
51
|
+
* worker retirement, ordered-relay settlement) uses this one bound, so the
|
|
52
|
+
* manager's horizon can never fall inside the decoder's.
|
|
53
|
+
*/
|
|
54
|
+
export declare function isoBlocksBehindLowerBound(a: number, b: number, kMax: number): number;
|
|
55
|
+
//# sourceMappingURL=fec-block-profile.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"fec-block-profile.d.ts","sourceRoot":"","sources":["../src/fec-block-profile.ts"],"names":[],"mappings":"AAwBA,oEAAoE;AACpE,MAAM,MAAM,eAAe,GAAG,aAAa,GAAG,cAAc,CAAA;AAE5D,6DAA6D;AAC7D,eAAO,MAAM,kBAAkB,EAAE,SAAS,eAAe,EAGvD,CAAA;AAEF,4CAA4C;AAC5C,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,eAAe,CAE1E;AAED;;;;;;GAMG;AACH,wBAAgB,oBAAoB,CAAC,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,GAAG,eAAe,CAUnF;AAED,2EAA2E;AAC3E,eAAO,MAAM,wBAAwB,IAAI,CAAA;AAEzC,6EAA6E;AAC7E,wBAAgB,oBAAoB,CAAC,UAAU,EAAE,MAAM,GAAG,MAAM,CAE/D;AAED,4FAA4F;AAC5F,wBAAgB,eAAe,CAAC,YAAY,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,OAAO,CAOjF;AAED;;;;;;;;GAQG;AACH,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,UAAU,EAAE,UAAU,EAAE,MAAM,GAAG,UAAU,CAczF;AAED;;;;;GAKG;AACH,wBAAgB,qBAAqB,CAAC,MAAM,EAAE,UAAU,GAAG,UAAU,GAAG,IAAI,CAS3E;AAED,kFAAkF;AAClF,wBAAgB,WAAW,CAAC,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,MAAM,CAEtE;AAED;;;GAGG;AACH,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAE1F;AAED;;;;;;;;GAQG;AACH,wBAAgB,yBAAyB,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,CAKpF"}
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* FEC block profile (BLO-35597, ISO/IEC 23008-1 Annex C).
|
|
3
|
+
*
|
|
4
|
+
* Every catalog `fec` object that declares an FEC instance names exactly one
|
|
5
|
+
* block profile in `fec.blockProfile`. A receiver applies all of a profile's
|
|
6
|
+
* rules or none of them, so the token is the one explicit per-stream
|
|
7
|
+
* discriminator: it is never defaulted and never inferred from the wire.
|
|
8
|
+
*
|
|
9
|
+
* - `k-padded-v1` (legacy, Blockcast-private): a source symbol is the
|
|
10
|
+
* protected MMTP packet zero-padded to T with no length field; every block
|
|
11
|
+
* is a K-symbol RaptorQ block whose ESIs `SSB_length..K-1` are implicit
|
|
12
|
+
* zero padding; `SS_ID = SBN*K + ESI`, so `SS_Start = SBN*K`; repair
|
|
13
|
+
* ESI = K + RS_ID; the MoQ repair group id is the SBN.
|
|
14
|
+
* - `iso-ssbg1-v1`: ssbg_mode1 (C.3.3): a source symbol is
|
|
15
|
+
* `u16 length || protected packet || zero padding` to T; a block is a
|
|
16
|
+
* K' = SSB_length RaptorQ block (C.5.3) and repair ESI = SSB_length + RS_ID;
|
|
17
|
+
* SS_ID increments by one per FEC source packet and wraps at 2^32 (C.5.2),
|
|
18
|
+
* so a block is located by membership in `[SS_Start, SS_Start + SSB_length)`
|
|
19
|
+
* under RFC 1982 serial arithmetic; the MoQ repair group id is the 62-bit
|
|
20
|
+
* wrap-epoch-extended SS_Start. The AL-FEC coding byte for this profile is
|
|
21
|
+
* 0x14 (one-stage, ssbg_mode1, fec_payload_id_mode 0, Amd 1:2025 Table C.3).
|
|
22
|
+
*/
|
|
23
|
+
import { serial32Add, serial32Distance, serial32Precedes } from './serial-number.js';
|
|
24
|
+
/** Every accepted `fec.blockProfile` token, legacy first. */
|
|
25
|
+
export const FEC_BLOCK_PROFILES = Object.freeze([
|
|
26
|
+
'k-padded-v1',
|
|
27
|
+
'iso-ssbg1-v1',
|
|
28
|
+
]);
|
|
29
|
+
/** True for a known block-profile token. */
|
|
30
|
+
export function isFecBlockProfile(value) {
|
|
31
|
+
return value === 'k-padded-v1' || value === 'iso-ssbg1-v1';
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* Read a required `fec.blockProfile`. Throws on an absent or unknown token:
|
|
35
|
+
* there is no default and nothing is inferred, because the two profiles carry
|
|
36
|
+
* identical wire tuples whose repair math differs.
|
|
37
|
+
*
|
|
38
|
+
* @param where the catalog path of the field, for the error message.
|
|
39
|
+
*/
|
|
40
|
+
export function parseFecBlockProfile(value, where) {
|
|
41
|
+
if (isFecBlockProfile(value))
|
|
42
|
+
return value;
|
|
43
|
+
if (value === undefined) {
|
|
44
|
+
throw new Error(`${where} is required: name the FEC block profile ("k-padded-v1" or "iso-ssbg1-v1")`);
|
|
45
|
+
}
|
|
46
|
+
throw new Error(`${where} must be "k-padded-v1" or "iso-ssbg1-v1" (got ${JSON.stringify(value)})`);
|
|
47
|
+
}
|
|
48
|
+
/** ISO/IEC 23008-1 C.3.3 ssbg_mode1: the two-octet packet length field. */
|
|
49
|
+
export const SSBG1_LENGTH_FIELD_BYTES = 2;
|
|
50
|
+
/** The largest protected packet an ssbg_mode1 symbol of size T can carry. */
|
|
51
|
+
export function ssbg1MaxPacketLength(symbolSize) {
|
|
52
|
+
return symbolSize - SSBG1_LENGTH_FIELD_BYTES;
|
|
53
|
+
}
|
|
54
|
+
/** Whether a protected packet of `packetLength` bytes fits one T-byte ssbg_mode1 symbol. */
|
|
55
|
+
export function ssbg1FitsSymbol(packetLength, symbolSize) {
|
|
56
|
+
return (Number.isSafeInteger(packetLength) &&
|
|
57
|
+
packetLength >= 0 &&
|
|
58
|
+
packetLength <= ssbg1MaxPacketLength(symbolSize) &&
|
|
59
|
+
packetLength <= 0xffff);
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Build one ssbg_mode1 source symbol (C.3.3): the protected packet's length
|
|
63
|
+
* in two octets, network byte order, then the packet, then zero octets up to
|
|
64
|
+
* T. The protected packet is the MMTP packet before its Source FEC Payload ID
|
|
65
|
+
* is appended (C.4.2).
|
|
66
|
+
*
|
|
67
|
+
* @throws when `length + 2 > T`: the packet cannot be protected under this
|
|
68
|
+
* profile, and silently truncating it would corrupt every repair symbol.
|
|
69
|
+
*/
|
|
70
|
+
export function buildSsbg1SourceSymbol(packet, symbolSize) {
|
|
71
|
+
if (!Number.isSafeInteger(symbolSize) || symbolSize <= SSBG1_LENGTH_FIELD_BYTES) {
|
|
72
|
+
throw new Error(`ssbg_mode1 symbol size must exceed ${SSBG1_LENGTH_FIELD_BYTES} (got ${symbolSize})`);
|
|
73
|
+
}
|
|
74
|
+
if (!ssbg1FitsSymbol(packet.byteLength, symbolSize)) {
|
|
75
|
+
throw new Error(`ssbg_mode1 source symbol needs ${packet.byteLength} + ${SSBG1_LENGTH_FIELD_BYTES} bytes but T is ${symbolSize}`);
|
|
76
|
+
}
|
|
77
|
+
const symbol = new Uint8Array(symbolSize);
|
|
78
|
+
symbol[0] = (packet.byteLength >>> 8) & 0xff;
|
|
79
|
+
symbol[1] = packet.byteLength & 0xff;
|
|
80
|
+
symbol.set(packet, SSBG1_LENGTH_FIELD_BYTES);
|
|
81
|
+
return symbol;
|
|
82
|
+
}
|
|
83
|
+
/**
|
|
84
|
+
* Recover the protected packet from one ssbg_mode1 source symbol: the bytes
|
|
85
|
+
* the length field names. Returns null, never a guess, when the length field
|
|
86
|
+
* points past the symbol or any padding octet is non-zero (C.3.3 padding is
|
|
87
|
+
* all 00h), since either means the recovered symbol is not what was sent.
|
|
88
|
+
*/
|
|
89
|
+
export function trimSsbg1SourceSymbol(symbol) {
|
|
90
|
+
if (symbol.byteLength < SSBG1_LENGTH_FIELD_BYTES)
|
|
91
|
+
return null;
|
|
92
|
+
const length = (symbol[0] << 8) | symbol[1];
|
|
93
|
+
const end = SSBG1_LENGTH_FIELD_BYTES + length;
|
|
94
|
+
if (end > symbol.byteLength)
|
|
95
|
+
return null;
|
|
96
|
+
for (let i = end; i < symbol.byteLength; i++) {
|
|
97
|
+
if (symbol[i] !== 0)
|
|
98
|
+
return null;
|
|
99
|
+
}
|
|
100
|
+
return symbol.subarray(SSBG1_LENGTH_FIELD_BYTES, end);
|
|
101
|
+
}
|
|
102
|
+
/** The SS_ID after the last source symbol of `[ssStart, ssStart + ssbLength)`. */
|
|
103
|
+
export function isoBlockEnd(ssStart, ssbLength) {
|
|
104
|
+
return serial32Add(ssStart, ssbLength);
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* Range membership (C.5.2, C.5.3): whether `ssId` is one of the
|
|
108
|
+
* `ssbLength` consecutive SS_IDs starting at `ssStart`, modulo 2^32.
|
|
109
|
+
*/
|
|
110
|
+
export function isoBlockContains(ssStart, ssbLength, ssId) {
|
|
111
|
+
return serial32Distance(ssStart, ssId) < ssbLength;
|
|
112
|
+
}
|
|
113
|
+
/**
|
|
114
|
+
* A lower bound on how many blocks the block starting at `a` lies behind the
|
|
115
|
+
* one starting at `b` (0 when `a` does not precede `b`). An iso-ssbg1-v1
|
|
116
|
+
* block holds at most `kMax` source symbols (the catalog `sourceSymbols`, the
|
|
117
|
+
* AL-FEC maximum_k_for_repair_flow), so `n * kMax` SS_IDs always span at least
|
|
118
|
+
* `n` blocks. Every interleave horizon in the receiver (decoder retention,
|
|
119
|
+
* worker retirement, ordered-relay settlement) uses this one bound, so the
|
|
120
|
+
* manager's horizon can never fall inside the decoder's.
|
|
121
|
+
*/
|
|
122
|
+
export function isoBlocksBehindLowerBound(a, b, kMax) {
|
|
123
|
+
if (!Number.isSafeInteger(kMax) || kMax <= 0) {
|
|
124
|
+
throw new Error(`iso-ssbg1-v1 block horizon needs a positive maximum K (got ${kMax})`);
|
|
125
|
+
}
|
|
126
|
+
return serial32Precedes(a, b) ? Math.floor(serial32Distance(a, b) / kMax) : 0;
|
|
127
|
+
}
|
|
128
|
+
//# sourceMappingURL=fec-block-profile.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"fec-block-profile.js","sourceRoot":"","sources":["../src/fec-block-profile.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
CHANGED
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAA"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAA;AACzB,cAAc,oBAAoB,CAAA;AAClC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,iBAAiB,CAAA;AAC/B,cAAc,oBAAoB,CAAA;AAClC,cAAc,wBAAwB,CAAA"}
|
package/dist/index.js
CHANGED
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAA"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAA;AACzB,cAAc,oBAAoB,CAAA;AAClC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,iBAAiB,CAAA;AAC/B,cAAc,oBAAoB,CAAA;AAClC,cAAc,wBAAwB,CAAA"}
|
package/dist/mmtp.d.ts
CHANGED
|
@@ -74,12 +74,32 @@ export declare const PACKET_TYPE_MPU = 0;
|
|
|
74
74
|
export declare const PACKET_TYPE_SIGNALING = 2;
|
|
75
75
|
export declare const PACKET_TYPE_REPAIR = 3;
|
|
76
76
|
export declare const ALFEC_MESSAGE_ID = 515;
|
|
77
|
+
/**
|
|
78
|
+
* MMTP `packet_id` of the signaling flow, which carries PACKET_TYPE_SIGNALING
|
|
79
|
+
* packets such as the AL-FEC message (ALFEC_MESSAGE_ID). The FFmpeg `moq_mmt`
|
|
80
|
+
* muxer sends that message on this packet_id into the same multicast group as
|
|
81
|
+
* the media, and moqcast-draft (PR #44) makes advertising it for a track a
|
|
82
|
+
* MUST NOT. A track's packet_id is therefore 1..MMTP_PACKET_ID_MAX.
|
|
83
|
+
*/
|
|
84
|
+
export declare const MMTP_SIGNALING_PACKET_ID = 0;
|
|
85
|
+
/** Largest value of the 16-bit MMTP `packet_id` header field. */
|
|
86
|
+
export declare const MMTP_PACKET_ID_MAX = 65535;
|
|
77
87
|
export declare const FEC_CODE_XOR = 1;
|
|
78
88
|
export declare const FEC_CODE_RAPTORQ = 2;
|
|
79
89
|
/**
|
|
80
90
|
* Parse MMTP header from buffer
|
|
81
91
|
*/
|
|
82
92
|
export declare function parseMMTPHeader(buffer: Uint8Array): MMTPHeader;
|
|
93
|
+
/**
|
|
94
|
+
* The MMTP `packet_id` of `buffer`, or null exactly when parseMMTPHeader would
|
|
95
|
+
* throw for it (short buffer, V != 0, truncated packet_counter or header
|
|
96
|
+
* extension).
|
|
97
|
+
*
|
|
98
|
+
* This is the per-packet filter a receiver runs before any other work, so it
|
|
99
|
+
* builds no header object, DataView or BigInt timestamp (BLO-36599). Use
|
|
100
|
+
* parseMMTPHeader when any other header field is needed.
|
|
101
|
+
*/
|
|
102
|
+
export declare function readMMTPPacketId(buffer: Uint8Array): number | null;
|
|
83
103
|
/**
|
|
84
104
|
* Unwrap MMTP packet to extract payload
|
|
85
105
|
*/
|
|
@@ -96,6 +116,18 @@ export declare function unwrapMMTP(buffer: Uint8Array): MMTPPacket;
|
|
|
96
116
|
*/
|
|
97
117
|
export declare function parseMPUHeader(payload: Uint8Array): MPUHeader;
|
|
98
118
|
export declare function parseTimedMfuDuHeader(payload: Uint8Array, offset: number): MFUDuHeader | null;
|
|
119
|
+
/**
|
|
120
|
+
* Why `extractMFUPayload` refused a packet.
|
|
121
|
+
*
|
|
122
|
+
* These identifiers are part of the public contract: callers surface them in
|
|
123
|
+
* diagnostics, so renaming one is a breaking change.
|
|
124
|
+
*/
|
|
125
|
+
export type MFURejectionGate = 'packet-shorter-than-mmtp-plus-mpu-header' | 'mmtp-header-unparseable' | 'not-an-mpu-packet' | 'payload-shorter-than-mpu-header' | 'aggregation-flag-set' | 'mpu-payload-length-below-header-remainder' | 'mpu-declared-end-exceeds-payload' | 'mfu-offset-at-or-past-declared-end' | 'source-fec-payload-id-width-mismatch' | 'declared-trailers-unresolved';
|
|
126
|
+
export interface MFURejection {
|
|
127
|
+
gate: MFURejectionGate;
|
|
128
|
+
/** Human-readable detail, including the byte arithmetic that decided it. */
|
|
129
|
+
detail: string;
|
|
130
|
+
}
|
|
99
131
|
/**
|
|
100
132
|
* Extract NAL unit payload from MMTP packet
|
|
101
133
|
*/
|
|
@@ -120,29 +152,31 @@ export interface MFUExtraction {
|
|
|
120
152
|
} | null;
|
|
121
153
|
}
|
|
122
154
|
/**
|
|
123
|
-
*
|
|
124
|
-
*
|
|
125
|
-
* Handles all the byte arithmetic for:
|
|
126
|
-
* - MMTP header (12 bytes)
|
|
127
|
-
* - MPU sub-header (8 bytes, payloadLength field)
|
|
128
|
-
* - MFU DU header (14 bytes timed / 4 bytes non-timed, only for FI ≤ 1)
|
|
129
|
-
* - Source FEC Payload ID (4 bytes at end, only when `FEC_type == 1`)
|
|
155
|
+
* Report why `extractMFUPayload` would refuse this packet, or null if it would
|
|
156
|
+
* accept it.
|
|
130
157
|
*
|
|
131
|
-
* `
|
|
132
|
-
*
|
|
133
|
-
*
|
|
134
|
-
*
|
|
135
|
-
*
|
|
136
|
-
* @param options.skipFecId When true, do NOT subtract the 4-byte Source FEC Payload ID
|
|
137
|
-
* from the payload boundary, even if fecType >= 1 in the MMTP header. Use this for
|
|
138
|
-
* FEC-recovered symbols where the FEC PID was already stripped before WASM decoding
|
|
139
|
-
* but the fecType bits in byte 0 still reflect the original packet (FEC Type=1 per
|
|
140
|
-
* draft-ramadan-moq-mmt-00 §3.1).
|
|
141
|
-
* @returns Extracted MFU data + metadata, or null if packet is too small
|
|
158
|
+
* `extractMFUPayload` returns bare `null` on ten distinct conditions, which
|
|
159
|
+
* makes a producer/consumer framing disagreement indistinguishable from a
|
|
160
|
+
* publisher that never started — both render as silence. Use this wherever
|
|
161
|
+
* that distinction matters: diagnostics, contract tests, and operator-facing
|
|
162
|
+
* logs.
|
|
142
163
|
*/
|
|
164
|
+
export declare function explainMFURejection(mmtpPacket: Uint8Array, options?: {
|
|
165
|
+
skipFecId?: boolean;
|
|
166
|
+
}): MFURejection | null;
|
|
143
167
|
export declare function extractMFUPayload(mmtpPacket: Uint8Array, options?: {
|
|
144
168
|
skipFecId?: boolean;
|
|
145
169
|
}): MFUExtraction | null;
|
|
170
|
+
/**
|
|
171
|
+
* extractMFUPayload for a caller that already holds this packet's parsed MMTP
|
|
172
|
+
* header, so the header is not parsed a second time (BLO-36599).
|
|
173
|
+
*
|
|
174
|
+
* `header` must be `parseMMTPHeader(mmtpPacket)` of this same packet; the
|
|
175
|
+
* result is then identical to `extractMFUPayload(mmtpPacket, options)`.
|
|
176
|
+
*/
|
|
177
|
+
export declare function extractMFUPayloadWithHeader(mmtpPacket: Uint8Array, header: MMTPHeader, options?: {
|
|
178
|
+
skipFecId?: boolean;
|
|
179
|
+
}): MFUExtraction | null;
|
|
146
180
|
/**
|
|
147
181
|
* Extract timestamp from MMTP packet
|
|
148
182
|
*/
|
|
@@ -157,9 +191,10 @@ export declare function isFecRepairPacket(mmtpPacket: Uint8Array): boolean;
|
|
|
157
191
|
* source packet per ISO/IEC 23008-1:2023 Section C.5.2 Figure C.10.
|
|
158
192
|
*
|
|
159
193
|
* SS_ID is a flat 32-bit monotonic counter (incremented by 1 per packet
|
|
160
|
-
* for ssbg_mode0 and ssbg_mode1).
|
|
161
|
-
*
|
|
162
|
-
*
|
|
194
|
+
* for ssbg_mode0 and ssbg_mode1). Block membership and ESI use the
|
|
195
|
+
* configured K; repair SS_Start identifies the first SS_ID of the block and
|
|
196
|
+
* SSB_length records the authored source-symbol count:
|
|
197
|
+
* SBN = floor(SS_ID / K), ESI = SS_ID % K
|
|
163
198
|
* SS_Start = SBN * K (first SS_ID of the block)
|
|
164
199
|
*
|
|
165
200
|
* This matches FFmpeg moqenc_mmt.c, the drafts (draft-ramadan-moq-fec §6.2),
|
|
@@ -173,6 +208,18 @@ export declare function extractFecPayloadId(mmtpPacket: Uint8Array): {
|
|
|
173
208
|
* payload contains a four-byte Source FEC Payload ID.
|
|
174
209
|
*/
|
|
175
210
|
export declare function hasSourceFecPayloadId(mmtpPacket: Uint8Array): boolean;
|
|
211
|
+
/**
|
|
212
|
+
* The Source FEC Payload ID of a packet whose MMTP header the caller already
|
|
213
|
+
* parsed, or null when the packet carries none: present only when FEC_type=1
|
|
214
|
+
* and the exact suffix after the ISO-declared MPU payload holds the four-byte
|
|
215
|
+
* ID (ISO/IEC 23008-1 §C.5.2). Same answer as extractFecPayloadId, without a
|
|
216
|
+
* second header parse (BLO-36599).
|
|
217
|
+
*
|
|
218
|
+
* `header` must be `parseMMTPHeader(mmtpPacket)` of this same packet.
|
|
219
|
+
*/
|
|
220
|
+
export declare function sourceFecPayloadIdOf(mmtpPacket: Uint8Array, header: MMTPHeader): {
|
|
221
|
+
ssId: number;
|
|
222
|
+
} | null;
|
|
176
223
|
/**
|
|
177
224
|
* MMTP header-extension ext_type assigned to the detached ALTA authenticator
|
|
178
225
|
* trailer (Path 2 / 08-07). Carried in an `[ext_type][ext_length][auth]`
|
|
@@ -212,7 +259,7 @@ export interface MoqRepairFrame {
|
|
|
212
259
|
rsbLength: number;
|
|
213
260
|
/** RS_ID (24 bits): repair symbol index (0-based) */
|
|
214
261
|
rsId: number;
|
|
215
|
-
/** SSB_length (24 bits):
|
|
262
|
+
/** SSB_length (24 bits): authored source-symbol count (1..=configured K) */
|
|
216
263
|
ssbLength: number;
|
|
217
264
|
/** Repair symbol data after the dynamic MMTP header and 13-byte FEC payload ID. */
|
|
218
265
|
symbolData: Uint8Array;
|
|
@@ -225,7 +272,7 @@ export interface MoqRepairFrame {
|
|
|
225
272
|
* then SS_Start (4 bytes) → block identifier
|
|
226
273
|
* then RSB_length (3 bytes) → P
|
|
227
274
|
* then RS_ID (3 bytes) → ESI = K + RS_ID
|
|
228
|
-
* then SSB_length (3 bytes) → K
|
|
275
|
+
* then SSB_length (3 bytes) → authored source-symbol count (1..=K)
|
|
229
276
|
* then Repair Symbol Data (T bytes)
|
|
230
277
|
*
|
|
231
278
|
* @param frame - Raw MoQ repair frame bytes
|
|
@@ -233,39 +280,13 @@ export interface MoqRepairFrame {
|
|
|
233
280
|
*/
|
|
234
281
|
export declare function parseMoqRepairFrame(frame: Uint8Array): MoqRepairFrame | null;
|
|
235
282
|
/**
|
|
236
|
-
*
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
fecPayloadIdMode: 0;
|
|
241
|
-
repairSymbolSize: number;
|
|
242
|
-
maximumK: number;
|
|
243
|
-
maximumP: number;
|
|
244
|
-
interleaveDepth: number;
|
|
245
|
-
oti: Uint8Array;
|
|
246
|
-
}
|
|
247
|
-
/**
|
|
248
|
-
* Parse AL-FEC signaling message from a full MMTP signaling packet.
|
|
249
|
-
*
|
|
250
|
-
* Wire format (ISO/IEC 23008-1:2023 Table C.3, Amendment 1:2025):
|
|
251
|
-
* [12-byte MMTP header (packet_type=0x02)]
|
|
252
|
-
* message_id(2) = 0x0203
|
|
253
|
-
* version(1)
|
|
254
|
-
* message_length(2) = length of remaining payload
|
|
255
|
-
* flags(1) = fec_flag(1) | private_fec_flag(1) | reserved(6)
|
|
256
|
-
* fec_flow_descriptor:
|
|
257
|
-
* length(2)
|
|
258
|
-
* num_flows(1)
|
|
259
|
-
* per flow:
|
|
260
|
-
* fec_flow_id(1), source_flow_id(1), num_assets(1), packet_ids(2*N),
|
|
261
|
-
* coding_params(1), repair_symbol_size(2),
|
|
262
|
-
* [one-stage]: repair_flow_id(2), fec_code_id(1),
|
|
263
|
-
* [private_fec_flag]: private_header(1){flag(1)|len(7)},
|
|
264
|
-
* current RaptorQ profile OTI(12) + interleave_depth(1)
|
|
265
|
-
* max_k(3), max_p(3), protection_window_time(4), protection_window_size(4)
|
|
283
|
+
* parseMoqRepairFrame for a caller that already holds this frame's parsed MMTP
|
|
284
|
+
* header, so the header is not parsed a second time (BLO-36599). The router's
|
|
285
|
+
* multicast repair branch uses it: one repair packet in every K + P otherwise
|
|
286
|
+
* paid two header parses.
|
|
266
287
|
*
|
|
267
|
-
*
|
|
268
|
-
*
|
|
288
|
+
* `header` must be `parseMMTPHeader(frame)` of this same frame; the result is
|
|
289
|
+
* then identical to `parseMoqRepairFrame(frame)`.
|
|
269
290
|
*/
|
|
270
|
-
export declare function
|
|
291
|
+
export declare function parseMoqRepairFrameWithHeader(frame: Uint8Array, header: MMTPHeader): MoqRepairFrame | null;
|
|
271
292
|
//# sourceMappingURL=mmtp.d.ts.map
|
package/dist/mmtp.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"mmtp.d.ts","sourceRoot":"","sources":["../src/mmtp.ts"],"names":[],"mappings":"AAAA,OAAO,EAGL,kBAAkB,IAAI,uBAAuB,EAC7C,KAAK,WAAW,IAAI,gBAAgB,EACrC,MAAM,2BAA2B,CAAA;AAElC;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,MAAM,WAAW,UAAU;IACzB,OAAO,EAAE,MAAM,CAAA;IACf,yDAAyD;IACzD,UAAU,EAAE,MAAM,CAAA;IAClB,QAAQ,EAAE,MAAM,CAAA;IAChB,SAAS,EAAE,MAAM,CAAA;IACjB,cAAc,EAAE,MAAM,CAAA;IACtB,aAAa,EAAE,MAAM,CAAA;IACrB,OAAO,EAAE,MAAM,CAAA;IACf,sDAAsD;IACtD,iBAAiB,EAAE,OAAO,CAAA;IAC1B,aAAa,CAAC,EAAE,MAAM,CAAA;IACtB,4DAA4D;IAC5D,aAAa,EAAE,OAAO,CAAA;IACtB,SAAS,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,UAAU,CAAA;KAAE,CAAA;IAC9C,oDAAoD;IACpD,YAAY,EAAE,MAAM,CAAA;IACpB,gFAAgF;IAChF,OAAO,EAAE,OAAO,CAAA;CACjB;AAED,MAAM,WAAW,SAAS;IACxB,iBAAiB,EAAE,MAAM,CAAA;IACzB,sBAAsB,EAAE,MAAM,CAAA;IAC9B,8CAA8C;IAC9C,eAAe,EAAE,MAAM,CAAA;IACvB,iFAAiF;IACjF,SAAS,EAAE,MAAM,CAAA;IACjB,wEAAwE;IACxE,eAAe,EAAE,OAAO,CAAA;IACxB;sEACkE;IAClE,aAAa,EAAE,MAAM,CAAA;CACtB;AAED,MAAM,WAAW,WAAW;IAC1B,2BAA2B,EAAE,MAAM,CAAA;IACnC,YAAY,EAAE,MAAM,CAAA;IACpB,MAAM,EAAE,MAAM,CAAA;IACd,QAAQ,EAAE,MAAM,CAAA;IAChB,iBAAiB,EAAE,MAAM,CAAA;CAC1B;AAED,MAAM,WAAW,UAAU;IACzB,MAAM,EAAE,UAAU,CAAA;IAClB,OAAO,EAAE,UAAU,CAAA;CACpB;AAED,eAAO,MAAM,gBAAgB,KAAK,CAAA;AAClC,eAAO,MAAM,eAAe,IAAI,CAAA;AAChC,eAAO,MAAM,wBAAwB,KAAK,CAAA;AAC1C,eAAO,MAAM,2BAA2B,IAAI,CAAA;AAO5C,eAAO,MAAM,eAAe,IAAO,CAAA;AACnC,eAAO,MAAM,qBAAqB,IAAO,CAAA;AACzC,eAAO,MAAM,kBAAkB,IAAO,CAAA;AAGtC,eAAO,MAAM,gBAAgB,MAAS,CAAA;
|
|
1
|
+
{"version":3,"file":"mmtp.d.ts","sourceRoot":"","sources":["../src/mmtp.ts"],"names":[],"mappings":"AAAA,OAAO,EAGL,kBAAkB,IAAI,uBAAuB,EAC7C,KAAK,WAAW,IAAI,gBAAgB,EACrC,MAAM,2BAA2B,CAAA;AAElC;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,MAAM,WAAW,UAAU;IACzB,OAAO,EAAE,MAAM,CAAA;IACf,yDAAyD;IACzD,UAAU,EAAE,MAAM,CAAA;IAClB,QAAQ,EAAE,MAAM,CAAA;IAChB,SAAS,EAAE,MAAM,CAAA;IACjB,cAAc,EAAE,MAAM,CAAA;IACtB,aAAa,EAAE,MAAM,CAAA;IACrB,OAAO,EAAE,MAAM,CAAA;IACf,sDAAsD;IACtD,iBAAiB,EAAE,OAAO,CAAA;IAC1B,aAAa,CAAC,EAAE,MAAM,CAAA;IACtB,4DAA4D;IAC5D,aAAa,EAAE,OAAO,CAAA;IACtB,SAAS,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,UAAU,CAAA;KAAE,CAAA;IAC9C,oDAAoD;IACpD,YAAY,EAAE,MAAM,CAAA;IACpB,gFAAgF;IAChF,OAAO,EAAE,OAAO,CAAA;CACjB;AAED,MAAM,WAAW,SAAS;IACxB,iBAAiB,EAAE,MAAM,CAAA;IACzB,sBAAsB,EAAE,MAAM,CAAA;IAC9B,8CAA8C;IAC9C,eAAe,EAAE,MAAM,CAAA;IACvB,iFAAiF;IACjF,SAAS,EAAE,MAAM,CAAA;IACjB,wEAAwE;IACxE,eAAe,EAAE,OAAO,CAAA;IACxB;sEACkE;IAClE,aAAa,EAAE,MAAM,CAAA;CACtB;AAED,MAAM,WAAW,WAAW;IAC1B,2BAA2B,EAAE,MAAM,CAAA;IACnC,YAAY,EAAE,MAAM,CAAA;IACpB,MAAM,EAAE,MAAM,CAAA;IACd,QAAQ,EAAE,MAAM,CAAA;IAChB,iBAAiB,EAAE,MAAM,CAAA;CAC1B;AAED,MAAM,WAAW,UAAU;IACzB,MAAM,EAAE,UAAU,CAAA;IAClB,OAAO,EAAE,UAAU,CAAA;CACpB;AAED,eAAO,MAAM,gBAAgB,KAAK,CAAA;AAClC,eAAO,MAAM,eAAe,IAAI,CAAA;AAChC,eAAO,MAAM,wBAAwB,KAAK,CAAA;AAC1C,eAAO,MAAM,2BAA2B,IAAI,CAAA;AAO5C,eAAO,MAAM,eAAe,IAAO,CAAA;AACnC,eAAO,MAAM,qBAAqB,IAAO,CAAA;AACzC,eAAO,MAAM,kBAAkB,IAAO,CAAA;AAGtC,eAAO,MAAM,gBAAgB,MAAS,CAAA;AAEtC;;;;;;GAMG;AACH,eAAO,MAAM,wBAAwB,IAAI,CAAA;AAEzC,iEAAiE;AACjE,eAAO,MAAM,kBAAkB,QAAS,CAAA;AAGxC,eAAO,MAAM,YAAY,IAAI,CAAA;AAC7B,eAAO,MAAM,gBAAgB,IAAI,CAAA;AAEjC;;GAEG;AACH,wBAAgB,eAAe,CAAC,MAAM,EAAE,UAAU,GAAG,UAAU,CAuE9D;AAED;;;;;;;;GAQG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,UAAU,GAAG,MAAM,GAAG,IAAI,CAelE;AAED;;GAEG;AACH,wBAAgB,UAAU,CAAC,MAAM,EAAE,UAAU,GAAG,UAAU,CAKzD;AAED;;;;;;;;;GASG;AACH,wBAAgB,cAAc,CAAC,OAAO,EAAE,UAAU,GAAG,SAAS,CA+B7D;AAED,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,UAAU,EAAE,MAAM,EAAE,MAAM,GAAG,WAAW,GAAG,IAAI,CAU7F;AAED;;;;;GAKG;AACH,MAAM,MAAM,gBAAgB,GACxB,0CAA0C,GAC1C,yBAAyB,GACzB,mBAAmB,GACnB,iCAAiC,GACjC,sBAAsB,GACtB,2CAA2C,GAC3C,kCAAkC,GAClC,oCAAoC,GACpC,sCAAsC,GACtC,8BAA8B,CAAA;AAElC,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,gBAAgB,CAAA;IACtB,4EAA4E;IAC5E,MAAM,EAAE,MAAM,CAAA;CACf;AA4GD;;GAEG;AACH,wBAAgB,cAAc,CAAC,UAAU,EAAE,UAAU,GAAG,UAAU,CAIjE;AAED,2DAA2D;AAC3D,MAAM,WAAW,aAAa;IAC5B,yBAAyB;IACzB,MAAM,EAAE,UAAU,CAAA;IAClB,wBAAwB;IACxB,GAAG,EAAE,SAAS,CAAA;IACd,+DAA+D;IAC/D,YAAY,EAAE,MAAM,CAAA;IACpB,8EAA8E;IAC9E,IAAI,EAAE,UAAU,CAAA;IAChB,8DAA8D;IAC9D,WAAW,EAAE,WAAW,GAAG,IAAI,CAAA;IAC/B,kEAAkE;IAClE,MAAM,EAAE,MAAM,GAAG,IAAI,CAAA;IACrB,kEAAkE;IAClE,YAAY,EAAE;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAA;CACtC;AA0ID;;;;;;;;;GASG;AACH,wBAAgB,mBAAmB,CACjC,UAAU,EAAE,UAAU,EACtB,OAAO,CAAC,EAAE;IAAE,SAAS,CAAC,EAAE,OAAO,CAAA;CAAE,GAChC,YAAY,GAAG,IAAI,CAGrB;AAED,wBAAgB,iBAAiB,CAC/B,UAAU,EAAE,UAAU,EACtB,OAAO,CAAC,EAAE;IAAE,SAAS,CAAC,EAAE,OAAO,CAAA;CAAE,GAChC,aAAa,GAAG,IAAI,CAEtB;AAED;;;;;;GAMG;AACH,wBAAgB,2BAA2B,CACzC,UAAU,EAAE,UAAU,EACtB,MAAM,EAAE,UAAU,EAClB,OAAO,CAAC,EAAE;IAAE,SAAS,CAAC,EAAE,OAAO,CAAA;CAAE,GAChC,aAAa,GAAG,IAAI,CAEtB;AAqCD;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,UAAU,EAAE,UAAU,GAAG,MAAM,CAG/D;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,UAAU,EAAE,UAAU,GAAG,OAAO,CAIjE;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,mBAAmB,CAAC,UAAU,EAAE,UAAU,GAAG;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAGnF;AAED;;;GAGG;AACH,wBAAgB,qBAAqB,CAAC,UAAU,EAAE,UAAU,GAAG,OAAO,CAGrE;AAWD;;;;;;;;GAQG;AACH,wBAAgB,oBAAoB,CAClC,UAAU,EAAE,UAAU,EACtB,MAAM,EAAE,UAAU,GACjB;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAqBzB;AAED;;;;;;;GAOG;AAIH,eAAO,MAAM,uBAAuB,QAAgC,CAAA;AACpE,eAAO,MAAM,4BAA4B,IAAqC,CAAA;AAC9E,MAAM,MAAM,WAAW,GAAG,gBAAgB,CAAA;AAC1C,eAAO,MAAM,kBAAkB,gCAA0B,CAAA;AAEzD,sEAAsE;AACtE,eAAO,MAAM,mBAAmB,KAAK,CAAA;AA2CrC;;;;;;;;GAQG;AACH,wBAAgB,yBAAyB,CAAC,UAAU,EAAE,UAAU,GAAG;IACjE,OAAO,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CACpE,GAAG,IAAI,CASP;AAED,wEAAwE;AACxE,MAAM,WAAW,cAAc;IAC7B,4EAA4E;IAC5E,QAAQ,EAAE,MAAM,CAAA;IAChB,gEAAgE;IAChE,OAAO,EAAE,MAAM,CAAA;IACf,yDAAyD;IACzD,SAAS,EAAE,MAAM,CAAA;IACjB,qDAAqD;IACrD,IAAI,EAAE,MAAM,CAAA;IACZ,4EAA4E;IAC5E,SAAS,EAAE,MAAM,CAAA;IACjB,mFAAmF;IACnF,UAAU,EAAE,UAAU,CAAA;CACvB;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,UAAU,GAAG,cAAc,GAAG,IAAI,CAE5E;AAED;;;;;;;;GAQG;AACH,wBAAgB,6BAA6B,CAC3C,KAAK,EAAE,UAAU,EACjB,MAAM,EAAE,UAAU,GACjB,cAAc,GAAG,IAAI,CAEvB"}
|