Skip to content

Fix heap buffer overflow in opj_j2k_read_sod#1621

Merged
rouault merged 1 commit into
uclouvain:masterfrom
PGZXB:dev-fix-1620
Feb 10, 2026
Merged

Fix heap buffer overflow in opj_j2k_read_sod#1621
rouault merged 1 commit into
uclouvain:masterfrom
PGZXB:dev-fix-1620

Conversation

@PGZXB

@PGZXB PGZXB commented Feb 6, 2026

Copy link
Copy Markdown
Contributor

Fixes #1620

This change adds a bounds check before writing to tp_index. It checks that tp_index is not NULL and that l_current_tile_part is less than nb_tps. If the condition fails, the writes are skipped.

Verification Before Fix

Running the PoC triggers AddressSanitizer error:

[INFO] Start to read j2k main header (0).
[INFO] Main header has been correctly decoded.
[INFO] No decoded area parameters, set the decoded area to the whole image
=================================================================
==1625==ERROR: AddressSanitizer: heap-buffer-overflow on address 0x503000000030 at pc 0x5588a8aaa54d bp 0x7ffca913bbe0 sp 0x7ffca913bbd8
WRITE of size 8 at 0x503000000030 thread T0
    #0 0x5588a8aaa54c in opj_j2k_read_sod /src/openjpeg/src/lib/openjp2/j2k.c:5086:13
    #1 0x5588a8aa644c in opj_j2k_read_tile_header /src/openjpeg/src/lib/openjp2/j2k.c:9912:19
    #2 0x5588a8add663 in opj_j2k_decode_tiles /src/openjpeg/src/lib/openjp2/j2k.c:12079:19
    #3 0x5588a8aa33b8 in opj_j2k_exec /src/openjpeg/src/lib/openjp2/j2k.c:9181:33
    #4 0x5588a8ab6a70 in opj_j2k_decode /src/openjpeg/src/lib/openjp2/j2k.c:12425:11
    #5 0x5588a8a8b490 in opj_decode /src/openjpeg/src/lib/openjp2/openjpeg.c:526:16
    #6 0x5588a8a46a7e in main /src/openjpeg/src/bin/jp2/opj_decompress.c:1582:19
    #7 0x7f6a6b440082 in __libc_start_main /build/glibc-B3wQXB/glibc-2.31/csu/../csu/libc-start.c:308:16
    #8 0x5588a896b4dd in _start (/src/openjpeg/build/bin/opj_decompress+0x424dd)

0x503000000030 is located 8 bytes after 24-byte region [0x503000000010,0x503000000028)
allocated by thread T0 here:
    #0 0x5588a8a046b9 in calloc /src/llvm-project/compiler-rt/lib/asan/asan_malloc_linux.cpp:75:3
    #1 0x5588a8a8ddaf in opj_calloc /src/openjpeg/src/lib/openjp2/opj_malloc.c:204:12
    #2 0x5588a8ac3d6f in opj_j2k_build_tp_index_from_tlm /src/openjpeg/src/lib/openjp2/j2k.c:8939:57
    #3 0x5588a8abf7f8 in opj_j2k_read_header_procedure /src/openjpeg/src/lib/openjp2/j2k.c:9152:5
    #4 0x5588a8aa33b8 in opj_j2k_exec /src/openjpeg/src/lib/openjp2/j2k.c:9181:33
    #5 0x5588a8aa2f71 in opj_j2k_read_header /src/openjpeg/src/lib/openjp2/j2k.c:8526:11
    #6 0x5588a8a8b1df in opj_read_header /src/openjpeg/src/lib/openjp2/openjpeg.c:475:16
    #7 0x5588a8a4672a in main /src/openjpeg/src/bin/jp2/opj_decompress.c:1520:15
    #8 0x7f6a6b440082 in __libc_start_main /build/glibc-B3wQXB/glibc-2.31/csu/../csu/libc-start.c:308:16

SUMMARY: AddressSanitizer: heap-buffer-overflow /src/openjpeg/src/lib/openjp2/j2k.c:5086:13 in opj_j2k_read_sod
Shadow bytes around the buggy address:
  0x502ffffffd80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x502ffffffe00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x502ffffffe80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x502fffffff00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x502fffffff80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
=>0x503000000000: fa fa 00 00 00 fa[fa]fa 00 00 00 fa fa fa fa fa
  0x503000000080: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x503000000100: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x503000000180: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x503000000200: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x503000000280: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
Shadow byte legend (one shadow byte represents 8 application bytes):
  Addressable:           00
  Partially addressable: 01 02 03 04 05 06 07 
  Heap left redzone:       fa
  Freed heap region:       fd
  Stack left redzone:      f1
  Stack mid redzone:       f2
  Stack right redzone:     f3
  Stack after return:      f5
  Stack use after scope:   f8
  Global redzone:          f9
  Global init order:       f6
  Poisoned by user:        f7
  Container overflow:      fc
  Array cookie:            ac
  Intra object redzone:    bb
  ASan internal:           fe
  Left alloca redzone:     ca
  Right alloca redzone:    cb
==1625==ABORTING

Verification After Fix

Running the PoC:

[INFO] Start to read j2k main header (0).
[INFO] Main header has been correctly decoded.
[INFO] No decoded area parameters, set the decoded area to the whole image
[INFO] Header of tile 2 / 2 has been read.
[INFO] Tile 2/2 has been decoded.
[INFO] Image data has been updated with tile 2.

[INFO] Header of tile 1 / 2 has been read.
[INFO] Tile 1/2 has been decoded.
[INFO] Image data has been updated with tile 1.

[INFO] Generated Outfile /tmp/out.tif
decode time: 0 ms

@PGZXB

PGZXB commented Feb 10, 2026

Copy link
Copy Markdown
Contributor Author

Hi @rouault,

I’ve submitted this PR to address #1620. The currently allowed checks have passed.

I’m not sure who would be the appropriate reviewer, and I hope I’m not disturbing you. Could you please review the changes?

Thank you very much for your time and help!

@rouault

rouault commented Feb 10, 2026

Copy link
Copy Markdown
Collaborator

@PGZXB can you fix the code formatting issues as indicated at the end of https://github.com/uclouvain/openjpeg/actions/runs/21762807205/job/63137787264?pr=1621 ?

@PGZXB

PGZXB commented Feb 10, 2026

Copy link
Copy Markdown
Contributor Author

@PGZXB can you fix the code formatting issues as indicated at the end of https://github.com/uclouvain/openjpeg/actions/runs/21762807205/job/63137787264?pr=1621 ?

I updated this PR to fix the code formatting issues by using scripts/prepare-commit.sh (change

@rouault rouault merged commit d33cbec into uclouvain:master Feb 10, 2026
15 of 22 checks passed
jef-n added a commit to jef-n/OSGeo4W that referenced this pull request Apr 21, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Heap buffer overlfow in opj_j2k_read_sod

2 participants