mediabunny 1.9.0 → 1.9.2

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 CHANGED
@@ -28,6 +28,14 @@ Mediabunny is a JavaScript library for reading, writing, and converting media fi
28
28
  </a>
29
29
  </div>
30
30
 
31
+ ### Bronze sponsors
32
+
33
+ <div align="center">
34
+ <a href="https://www.reactvideoeditor.com/" target="_blank">
35
+ <img src="./docs/public/sponsors/rve.svg" width="40" height="40" alt="React Video Editor">
36
+ </a>
37
+ </div>
38
+
31
39
  [Sponsor Mediabunny's development](https://github.com/sponsors/Vanilagy)
32
40
 
33
41
  ## Features
@@ -1766,6 +1766,7 @@ var Mediabunny = (() => {
1766
1766
  async addEncodedAudioPacket(track, packet, meta) {
1767
1767
  const release = await this.mutex.acquire();
1768
1768
  try {
1769
+ this.validateAndNormalizeTimestamp(track, packet.timestamp, packet.type === "key");
1769
1770
  if (!this.audioSpecificConfig) {
1770
1771
  validateAudioChunkMetadata(meta);
1771
1772
  const description = meta?.decoderConfig?.description;
@@ -5462,8 +5463,6 @@ var Mediabunny = (() => {
5462
5463
  408125543 /* Segment */
5463
5464
  ];
5464
5465
  var LEVEL_1_EBML_IDS = [
5465
- 17138 /* EBMLMaxIDLength */,
5466
- 17139 /* EBMLMaxSizeLength */,
5467
5466
  290298740 /* SeekHead */,
5468
5467
  357149030 /* Info */,
5469
5468
  524531317 /* Cluster */,
@@ -5827,6 +5826,23 @@ var Mediabunny = (() => {
5827
5826
  }
5828
5827
  return null;
5829
5828
  }
5829
+ /** Searches for the next occurrence of an element ID using a naive byte-wise search. */
5830
+ async resync(ids, until) {
5831
+ const loadChunkSize = 2 ** 20;
5832
+ const idsSet = new Set(ids);
5833
+ while (this.pos <= until - MIN_HEADER_SIZE) {
5834
+ if (!this.reader.rangeIsLoaded(this.pos, Math.min(this.pos + MAX_HEADER_SIZE, until))) {
5835
+ await this.reader.loadRange(this.pos, Math.min(this.pos + loadChunkSize, until));
5836
+ }
5837
+ const elementStartPos = this.pos;
5838
+ const elementId = this.readElementId();
5839
+ if (elementId !== null && idsSet.has(elementId)) {
5840
+ return elementStartPos;
5841
+ }
5842
+ this.pos = elementStartPos + 1;
5843
+ }
5844
+ return null;
5845
+ }
5830
5846
  };
5831
5847
  var CODEC_STRING_MAP = {
5832
5848
  "avc": "V_MPEG4/ISO/AVC",
@@ -12458,11 +12474,15 @@ ${cue.notes ?? ""}`;
12458
12474
  this.metadataReader.pos = sourceSize - 4;
12459
12475
  const lastWord = this.metadataReader.readU32();
12460
12476
  const potentialMfraPos = sourceSize - lastWord;
12461
- if (potentialMfraPos >= 0 && potentialMfraPos < sourceSize) {
12462
- await this.metadataReader.reader.loadRange(potentialMfraPos, sourceSize);
12477
+ if (potentialMfraPos >= 0 && potentialMfraPos <= sourceSize - MAX_BOX_HEADER_SIZE) {
12478
+ await this.metadataReader.reader.loadRange(potentialMfraPos, potentialMfraPos + 2 ** 16);
12463
12479
  this.metadataReader.pos = potentialMfraPos;
12464
12480
  const boxInfo = this.metadataReader.readBoxHeader();
12465
12481
  if (boxInfo.name === "mfra") {
12482
+ await this.metadataReader.reader.loadRange(
12483
+ potentialMfraPos,
12484
+ potentialMfraPos + boxInfo.totalSize
12485
+ );
12466
12486
  this.readContiguousBoxes(boxInfo.contentSize);
12467
12487
  }
12468
12488
  }
@@ -14414,6 +14434,7 @@ ${cue.notes ?? ""}`;
14414
14434
  { id: 374648427 /* Tracks */, flag: "tracksSeen" },
14415
14435
  { id: 475249515 /* Cues */, flag: "cuesSeen" }
14416
14436
  ];
14437
+ var MAX_RESYNC_LENGTH = 10 * 2 ** 20;
14417
14438
  var MatroskaDemuxer = class extends Demuxer {
14418
14439
  constructor(input) {
14419
14440
  super(input);
@@ -14523,8 +14544,18 @@ ${cue.notes ?? ""}`;
14523
14544
  );
14524
14545
  const elementStartPos = this.metadataReader.pos;
14525
14546
  const header = this.metadataReader.readElementHeader();
14526
- if (!header) {
14527
- break;
14547
+ if (!header || !LEVEL_1_EBML_IDS.includes(header.id)) {
14548
+ this.metadataReader.pos = elementStartPos;
14549
+ const nextPos = await this.metadataReader.resync(
14550
+ LEVEL_1_EBML_IDS,
14551
+ Math.min(this.currentSegment.elementEndPos, this.metadataReader.pos + MAX_RESYNC_LENGTH)
14552
+ );
14553
+ if (nextPos) {
14554
+ this.metadataReader.pos = nextPos;
14555
+ continue;
14556
+ } else {
14557
+ break;
14558
+ }
14528
14559
  }
14529
14560
  const { id, size } = header;
14530
14561
  const dataStartPos = this.metadataReader.pos;
@@ -14541,6 +14572,9 @@ ${cue.notes ?? ""}`;
14541
14572
  this.currentSegment.clusterSeekStartPos = elementStartPos;
14542
14573
  }
14543
14574
  }
14575
+ if (size !== null) {
14576
+ this.metadataReader.pos = dataStartPos + size;
14577
+ }
14544
14578
  if (this.currentSegment.infoSeen && this.currentSegment.tracksSeen && this.currentSegment.cuesSeen) {
14545
14579
  break;
14546
14580
  }
@@ -14564,8 +14598,12 @@ ${cue.notes ?? ""}`;
14564
14598
  if (size === null) {
14565
14599
  break;
14566
14600
  }
14567
- this.metadataReader.pos = dataStartPos + size;
14568
- if (!clusterEncountered) {
14601
+ }
14602
+ if (!clusterEncountered) {
14603
+ const seekEntry = this.currentSegment.seekEntries.find((entry) => entry.id === 524531317 /* Cluster */);
14604
+ if (seekEntry) {
14605
+ this.currentSegment.clusterSeekStartPos = segmentDataStart + seekEntry.segmentPosition;
14606
+ } else {
14569
14607
  this.currentSegment.clusterSeekStartPos = this.metadataReader.pos;
14570
14608
  }
14571
14609
  }
@@ -15613,8 +15651,18 @@ ${cue.notes ?? ""}`;
15613
15651
  await metadataReader.reader.loadRange(metadataReader.pos, metadataReader.pos + MAX_HEADER_SIZE);
15614
15652
  const elementStartPos = metadataReader.pos;
15615
15653
  const elementHeader = metadataReader.readElementHeader();
15616
- if (!elementHeader) {
15617
- break;
15654
+ if (!elementHeader || !LEVEL_1_EBML_IDS.includes(elementHeader.id)) {
15655
+ metadataReader.pos = elementStartPos;
15656
+ const nextPos = await metadataReader.resync(
15657
+ LEVEL_1_EBML_IDS,
15658
+ Math.min(segment.elementEndPos, metadataReader.pos + MAX_RESYNC_LENGTH)
15659
+ );
15660
+ if (nextPos) {
15661
+ metadataReader.pos = nextPos;
15662
+ continue;
15663
+ } else {
15664
+ break;
15665
+ }
15618
15666
  }
15619
15667
  const id = elementHeader.id;
15620
15668
  let size = elementHeader.size;