BrowseBox: Don’t set last column width to LONG_MAX when win is invisible

BrowseBox::AutoSizeLastColumn calls SetColumnWidth with the width set to
LONG_MAX. SetColumnWidth then tries to limit the actual width to the
remaining space for the last column. However, this was only done when
the window is visible, presumably because the remaining space
calculations might not work otherwise. This width is later used to
calculate a rectangle starting from the column’s X position. This of
course ends up overflowing the Long variable so it could be counted as
undefined behaviour. Instead, let’s just bail out early from the
function when the window isn’t visible and leave the width as it was.
The actual width will be recalculated when the window becomes visible
anyway because Window::Show calls Resize.

This was picked up by Stephan Bergmann with UBSAN and it was discussed
in the comments for this patch:

https://gerrit.libreoffice.org/c/core/+/193174

Change-Id: Ic2922a3d98c8ebc2e7f2d04c8c59105fdbd4e666
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/193268
Reviewed-by: Stephan Bergmann <stephan.bergmann@collabora.com>
Tested-by: Jenkins
This commit is contained in:
Neil Roberts
2025-11-01 08:10:34 +01:00
committed by Stephan Bergmann
parent 18d82f37ee
commit 87270edb1b
+16 -5
View File
@@ -593,15 +593,26 @@ void BrowseBox::SetColumnWidth( sal_uInt16 nItemId, tools::Long nWidth )
tools::Long nOldWidth = mvCols[ nItemPos ]->Width();
// adjust last column, if necessary
if ( IsVisible() && nItemPos == mvCols.size() - 1 )
if ( nItemPos == mvCols.size() - 1 )
{
tools::Long nMaxWidth = pDataWin->GetSizePixel().Width();
nMaxWidth -= pDataWin->bAutoSizeLastCol
if ( IsVisible() )
{
tools::Long nMaxWidth = pDataWin->GetSizePixel().Width();
nMaxWidth -= pDataWin->bAutoSizeLastCol
? GetFieldRect(nItemId).Left()
: GetFrozenWidth();
if ( pDataWin->bAutoSizeLastCol || nWidth > nMaxWidth )
if ( pDataWin->bAutoSizeLastCol || nWidth > nMaxWidth )
{
nWidth = nMaxWidth > 16 ? nMaxWidth : nOldWidth;
}
}
else if ( nWidth == LONG_MAX )
{
nWidth = nMaxWidth > 16 ? nMaxWidth : nOldWidth;
// If we can’t calculate the maximum width because the window isn’t visible then it’s
// better to leave the width as it is than to set it to LONG_MAX. The last column width
// will be recalculated when the window is shown anyway because the window will be
// resized.
return;
}
}