-
Notifications
You must be signed in to change notification settings - Fork 513
fix DTVCC: Heap Buffer Overflow & Out-of-Bounds Read #1968
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fix DTVCC: Heap Buffer Overflow & Out-of-Bounds Read #1968
Conversation
dfa3fe2 to
028ce9d
Compare
cfsmp3
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As I said in a different PR, I don't think we should be spending time here - all of this is going to be Rust soon.
But if you do it, checks needs to be really needed, otherwise it's just bloat - if you need to know if you are guarding against possible out of range accesses and things like that, not just look for maximums that can't be reached because something prevents it.
src/lib_ccx/avc_functions.c
Outdated
| while (tbuf < seiend - 1) // Use -1 because of trailing marker | ||
| { | ||
| tbuf = sei_message(ctx, tbuf, seiend - 1); | ||
| if (!tbuf) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is unnecessary. sei_message never returns NULLs.
| int anchor_point = data[4] >> 4; | ||
| int col_count = (data[5] & 0x3f) + 1; // according to CEA-708-D | ||
|
|
||
| if (row_count > CCX_DTVCC_MAX_ROWS || col_count > CCX_DTVCC_MAX_COLUMNS) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this even possible, considering that we are doing a mask with 0xf?
cfsmp3
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for working on these security fixes. Many of the changes are valid, but some checks are unnecessary - they guard against conditions that are mathematically impossible given the code structure.
Dead Code - Please Remove
1. dtvcc_window_copy_to_screen - "secondary safety guard" (lines ~595-598 in your diff)
if (copyrows > window->row_count)
copyrows = window->row_count;
if (copycols > window->col_count)
copycols = window->col_count;This can NEVER trigger. Given:
int copyrows = top + window->row_count >= SCREENGRID_ROWS ? SCREENGRID_ROWS - top : window->row_count;- Case 1:
copyrows = SCREENGRID_ROWS - top→ We're in the branch wheretop + row_count >= SCREENGRID_ROWS, which meansrow_count >= SCREENGRID_ROWS - top, socopyrows <= row_count. Never triggers. - Case 2:
copyrows = row_count→copyrows > row_countis trivially false.
Please remove this dead code.
2. dtvcc_process_character - pen bounds check
if (window->pen_row < 0 || window->pen_row >= CCX_DTVCC_MAX_ROWS ||
window->pen_column < 0 || window->pen_column >= CCX_DTVCC_MAX_COLUMNS)These conditions are impossible:
pen_row < 0: pen_row is initialized to 0, only decremented withif (pen_row > 0) pen_row--, and SetPenLocation parses it fromdata[1] & 0xf(always 0-15)pen_row >= MAX_ROWS: Your DefineWindow validation ensuresrow_count <= MAX_ROWS, and your SetPenLocation validation ensuresrow < row_count, so pen_row is bounded
Please remove this redundant check.
3. dtvcc_window_copy_to_screen - redundant invariant check
if (window->row_count > CCX_DTVCC_MAX_ROWS || window->col_count > CCX_DTVCC_MAX_COLUMNS)This is redundant since you're adding the same validation in dtvcc_handle_DFx_DefineWindow. If DefineWindow rejects invalid sizes, they can never reach this function.
Please remove this redundant check.
Valid Changes ✓
These are good and should stay:
- SEI bounds checks in
avc_functions.c - DefineWindow size validation
- SetPenLocation bounds validation
- VBI early return on undersized buffer
- Teletext size checks
- PSI buffer overflow check
- Extended header bounds check
- DTVCC packet length checks
Note
I'm closing #1960, #1962, #1964, #1966 since this PR includes all their commits.
|
Thanks for the detailed review @cfsmp3 I’ve updated the PR to remove all the redundant and unreachable checks you pointed out: The changes are now strictly limited to eliminating dead code without altering behavior. |
CCExtractor CI platform finished running the test files on linux. Below is a summary of the test results, when compared to test for commit f5dc1cf...:
Your PR breaks these cases:
Congratulations: Merging this PR would fix the following tests:
It seems that not all tests were passed completely. This is an indication that the output of some files is not as expected (but might be according to you). Check the result page for more info. |
CCExtractor CI platform finished running the test files on windows. Below is a summary of the test results, when compared to test for commit f5dc1cf...:
Congratulations: Merging this PR would fix the following tests:
All tests passed completely. Check the result page for more info. |
In raising this pull request, I confirm the following (please check boxes):
My familiarity with the project is as follows (check one):
Description
fixed critical vulnerabilities in the DTVCC (CEA-708) decoder
Issues Fixed:
Heap Buffer Overflow in
dtvcc_process_dataCCX_DTVCC_MAX_PACKET_LENGTH.Out-of-Bounds Read in
dtvcc_process_current_packetImpact if unpatched:
Testing:
CCX_DTVCC_MAX_PACKET_LENGTHare safely ignored.fixed #1966