Skip to content

Conversation

@Gaurang-5
Copy link

Fixes #20439

Summary

Fixes an infinite loop issue when decoding JBIG2 images with more than 4 referred-to segments.

Details

The bug had two parts:

  1. Incorrect condition check: The code was checking the entire referredFlags byte (referredFlags === 7) instead of checking the extracted referredToCount value (the top 3 bits: referredToCount === 7)

  2. Incorrect byte count calculation: The calculation for retention flags bytes was (referredToCount + 7) >> 3 when it should be (referredToCount + 8) >> 3

According to the JBIG2 specification, retention flags require (referredToCount + 1) bits total: 1 bit for the segment itself plus 1 bit for each referred segment. The correct byte count is ceil((referredToCount + 1) / 8) which equals (referredToCount + 8) >> 3.

This issue was causing the parser to read incorrect positions, resulting in an infinite loop in the readSegments function.

Testing

  • Tested with the provided PDF from the issue (hmm.pdf)
  • All existing unit tests pass (1065 specs, 0 failures)
  • Fix aligns with solutions in other PDF renderers (SerenityOS, PDFium)

Fixes issue mozilla#20439 where pdf.js would hang on JBIG2 images with more
than 4 referred-to segments.

The bug had two parts:
1. Checking the entire referredFlags byte (=== 7) instead of the
   extracted referredToCount value (top 3 bits)
2. Incorrect byte count calculation for retention flags, missing the
   +1 for the segment's own retention bit

According to the JBIG2 spec, retention flags need (referredToCount + 1)
bits total: 1 for the segment itself plus 1 for each referred segment.
The correct byte count is ceil((referredToCount + 1) / 8) which equals
(referredToCount + 8) >> 3.
@timvandermeij
Copy link
Contributor

Please add a test case (see e.g. https://github.com/mozilla/pdf.js/pull/20270/files for how to do that) which serves as a regression test. After that we can trigger the tests here.

@nico
Copy link

nico commented Nov 16, 2025

Feel free to use the file attached to the issue :)

@calixteman
Copy link
Contributor

@nico, it's super easy to add the test yourself:

  • copy your file in test/pdfs/
  • add an entry in test_manifest.json very similar to:
    "id": "tracemonkey-eq",
    "file": "pdfs/tracemonkey.pdf",
    "md5": "9a192d8b1a7dc652a19835f6f08098bd",
    "rounds": 1,
    "type": "eq"

commit and push.

Add regression test for issue mozilla#20439 to ensure that JBIG2 images
with more than 4 referred-to segments are handled correctly.
@Gaurang-5
Copy link
Author

@timvandermeij
I've added a regression test for this issue. The test uses the PDF file from the bug report and verifies that it can be decoded without hanging. All tests pass locally.

The test file is located at:

  • test/pdfs/issue20439.pdf
  • Entry added to test/test_manifest.json

Please let me know if you need any changes!
Thanks

Copy link
Contributor

@timvandermeij timvandermeij left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me like this, with the comment addressed, the commits squashed into one and passing tests. Thanks!

@calixteman
Copy link
Contributor

/botio test

@moz-tools-bot
Copy link
Collaborator

From: Bot.io (Windows)


Received

Command cmd_test from @calixteman received. Current queue size: 0

Live output at: http://54.193.163.58:8877/73e7f20e09be864/output.txt

@moz-tools-bot
Copy link
Collaborator

From: Bot.io (Linux m4)


Received

Command cmd_test from @calixteman received. Current queue size: 0

Live output at: http://54.241.84.105:8877/5a1410188c64b28/output.txt

@moz-tools-bot
Copy link
Collaborator

From: Bot.io (Linux m4)


Failed

Full output at http://54.241.84.105:8877/5a1410188c64b28/output.txt

Total script time: 40.08 mins

  • Unit tests: Passed
  • Integration Tests: FAILED
  • Regression tests: FAILED
  different ref/snapshot: 1

Image differences available at: http://54.241.84.105:8877/5a1410188c64b28/reftest-analyzer.html#web=eq.log

@moz-tools-bot
Copy link
Collaborator

From: Bot.io (Windows)


Failed

Full output at http://54.193.163.58:8877/73e7f20e09be864/output.txt

Total script time: 75.00 mins

  • Unit tests: FAILED
  • Integration Tests: FAILED
  • Regression tests: FAILED
  different ref/snapshot: 1

Image differences available at: http://54.193.163.58:8877/73e7f20e09be864/reftest-analyzer.html#web=eq.log

@timvandermeij
Copy link
Contributor

Could you squash the commits into one so we have a single commit for the change (see https://github.com/mozilla/pdf.js/wiki/Squashing-Commits if you're not familiar with how to do that)? This should be good to merge then.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug]: pdf.js busy-loops forever on JBIG2 image with > 4 referred-to segments

5 participants