Better bounds-checking in CFDE_TextOut::ReloadLinePiece().
Re-write the loops to ensure `iPieceIndex` is checked before trying
to get a given piece.
Bug: chromium:1147125
Change-Id: I25a08edbf3c35fabfc955bee38a5654e8c4e8d61
Reviewed-on: https://pdfium-review.googlesource.com/c/pdfium/+/76371
Commit-Queue: Tom Sepez <tsepez@chromium.org>
Reviewed-by: Daniel Hosseinian <dhoss@chromium.org>
diff --git a/xfa/fde/cfde_textout.cpp b/xfa/fde/cfde_textout.cpp
index dbc54f0..ce7a1d2 100644
--- a/xfa/fde/cfde_textout.cpp
+++ b/xfa/fde/cfde_textout.cpp
@@ -451,32 +451,29 @@
}
}
-void CFDE_TextOut::ReloadLinePiece(Line* pLine, const CFX_RectF& rect) {
+void CFDE_TextOut::ReloadLinePiece(Line* line, const CFX_RectF& rect) {
pdfium::span<const wchar_t> text_span = m_wsText.span();
- size_t iPieceIndex = 0;
- size_t iPieceCount = pLine->GetSize();
- const Piece* pPiece = pLine->GetPieceAtIndex(0);
- size_t start_char = pPiece->start_char;
- int32_t iPieceWidths = 0;
- CFX_BreakType dwBreakStatus = CFX_BreakType::kNone;
- m_fLinePos = pPiece->bounds.top;
- while (iPieceIndex < iPieceCount) {
- size_t start = start_char;
- size_t end = pPiece->char_count + start;
- while (start < end) {
- dwBreakStatus = m_pTxtBreak->AppendChar(text_span[start]);
- if (!CFX_BreakTypeNoneOrPiece(dwBreakStatus))
- RetrievePieces(dwBreakStatus, true, rect, &start_char, &iPieceWidths);
-
- ++start;
+ size_t start_char = 0;
+ size_t piece_count = line->GetSize();
+ int32_t piece_widths = 0;
+ CFX_BreakType break_status = CFX_BreakType::kNone;
+ for (size_t piece_index = 0; piece_index < piece_count; ++piece_index) {
+ const Piece* piece = line->GetPieceAtIndex(piece_index);
+ if (piece_index == 0) {
+ start_char = piece->start_char;
+ m_fLinePos = piece->bounds.top;
}
- ++iPieceIndex;
- pPiece = pLine->GetPieceAtIndex(iPieceIndex);
+ size_t end = start_char + piece->char_count;
+ for (size_t start = start_char; start < end; ++start) {
+ break_status = m_pTxtBreak->AppendChar(text_span[start]);
+ if (!CFX_BreakTypeNoneOrPiece(break_status))
+ RetrievePieces(break_status, true, rect, &start_char, &piece_widths);
+ }
}
- dwBreakStatus = m_pTxtBreak->EndBreak(CFX_BreakType::kParagraph);
- if (!CFX_BreakTypeNoneOrPiece(dwBreakStatus))
- RetrievePieces(dwBreakStatus, true, rect, &start_char, &iPieceWidths);
+ break_status = m_pTxtBreak->EndBreak(CFX_BreakType::kParagraph);
+ if (!CFX_BreakTypeNoneOrPiece(break_status))
+ RetrievePieces(break_status, true, rect, &start_char, &piece_widths);
m_pTxtBreak->Reset();
}