Make ~Window more robust

...in cases where the Window(WindowType) ctor did not call Window::ImplInit, so
many members are null; if then a derived class's ctor throws an exception,
~Window must be careful not to dereference those null members.

Change-Id: I12c4b1b5d7f3633387b85acf9da6d57c42e793b4
This commit is contained in:
Stephan Bergmann
2012-11-26 12:48:26 +01:00
parent a1ba48f312
commit f902bcda6e
2 changed files with 50 additions and 39 deletions

View File

@@ -268,19 +268,22 @@ void UnoWrapper::WindowDestroyed( Window* pWindow )
// ::com::sun::star::chaos::System-Windows suchen...
Window* pOverlap = pWindow->GetWindow( WINDOW_OVERLAP );
pOverlap = pOverlap->GetWindow( WINDOW_FIRSTOVERLAP );
while ( pOverlap )
if ( pOverlap )
{
Window* pNextOverlap = pOverlap->GetWindow( WINDOW_NEXT );
Window* pClient = pOverlap->GetWindow( WINDOW_CLIENT );
if ( pClient->GetWindowPeer() && lcl_ImplIsParent( pWindow, pClient ) )
pOverlap = pOverlap->GetWindow( WINDOW_FIRSTOVERLAP );
while ( pOverlap )
{
::com::sun::star::uno::Reference< ::com::sun::star::lang::XComponent > xComp( pClient->GetComponentInterface( sal_False ), ::com::sun::star::uno::UNO_QUERY );
xComp->dispose();
}
Window* pNextOverlap = pOverlap->GetWindow( WINDOW_NEXT );
Window* pClient = pOverlap->GetWindow( WINDOW_CLIENT );
pOverlap = pNextOverlap;
if ( pClient->GetWindowPeer() && lcl_ImplIsParent( pWindow, pClient ) )
{
::com::sun::star::uno::Reference< ::com::sun::star::lang::XComponent > xComp( pClient->GetComponentInterface( sal_False ), ::com::sun::star::uno::UNO_QUERY );
xComp->dispose();
}
pOverlap = pNextOverlap;
}
}
Window* pParent = pWindow->GetParent();

View File

@@ -1105,11 +1105,11 @@ void Window::ImplRemoveWindow( sal_Bool bRemoveFrameData )
{
if ( mpWindowImpl->mpPrev )
mpWindowImpl->mpPrev->mpWindowImpl->mpNext = mpWindowImpl->mpNext;
else
else if ( mpWindowImpl->mpParent )
mpWindowImpl->mpParent->mpWindowImpl->mpFirstChild = mpWindowImpl->mpNext;
if ( mpWindowImpl->mpNext )
mpWindowImpl->mpNext->mpWindowImpl->mpPrev = mpWindowImpl->mpPrev;
else
else if ( mpWindowImpl->mpParent )
mpWindowImpl->mpParent->mpWindowImpl->mpLastChild = mpWindowImpl->mpPrev;
}
@@ -4368,29 +4368,33 @@ Window::~Window()
{
rtl::OStringBuffer aErrorStr;
sal_Bool bError = sal_False;
Window* pTempWin = mpWindowImpl->mpFrameData->mpFirstOverlap;
while ( pTempWin )
Window* pTempWin;
if (mpWindowImpl->mpFrameData != 0)
{
if ( ImplIsRealParentPath( pTempWin ) )
pTempWin = mpWindowImpl->mpFrameData->mpFirstOverlap;
while ( pTempWin )
{
bError = sal_True;
aErrorStr.append(lcl_createWindowInfo(*pTempWin));
if ( ImplIsRealParentPath( pTempWin ) )
{
bError = sal_True;
aErrorStr.append(lcl_createWindowInfo(*pTempWin));
}
pTempWin = pTempWin->mpWindowImpl->mpNextOverlap;
}
if ( bError )
{
rtl::OStringBuffer aTempStr;
aTempStr.append(RTL_CONSTASCII_STRINGPARAM("Window ("));
aTempStr.append(rtl::OUStringToOString(GetText(),
RTL_TEXTENCODING_UTF8));
aTempStr.append(RTL_CONSTASCII_STRINGPARAM(
") with living SystemWindow(s) destroyed: "));
aTempStr.append(aErrorStr.toString());
OSL_FAIL(aTempStr.getStr());
// abort in non-pro version, this must be fixed!
GetpApp()->Abort(rtl::OStringToOUString(
aTempStr.makeStringAndClear(), RTL_TEXTENCODING_UTF8));
}
pTempWin = pTempWin->mpWindowImpl->mpNextOverlap;
}
if ( bError )
{
rtl::OStringBuffer aTempStr;
aTempStr.append(RTL_CONSTASCII_STRINGPARAM("Window ("));
aTempStr.append(rtl::OUStringToOString(GetText(),
RTL_TEXTENCODING_UTF8));
aTempStr.append(RTL_CONSTASCII_STRINGPARAM(
") with living SystemWindow(s) destroyed: "));
aTempStr.append(aErrorStr.toString());
OSL_FAIL(aTempStr.getStr());
// abort in non-pro version, this must be fixed!
GetpApp()->Abort(rtl::OStringToOUString(
aTempStr.makeStringAndClear(), RTL_TEXTENCODING_UTF8));
}
bError = sal_False;
@@ -4562,7 +4566,8 @@ Window::~Window()
}
if ( pOverlapWindow->mpWindowImpl->mpLastFocusWindow == this )
if ( pOverlapWindow != 0 &&
pOverlapWindow->mpWindowImpl->mpLastFocusWindow == this )
pOverlapWindow->mpWindowImpl->mpLastFocusWindow = NULL;
// reset hint for DefModalDialogParent
@@ -4570,12 +4575,15 @@ Window::~Window()
pSVData->maWinData.mpActiveApplicationFrame = NULL;
// reset marked windows
if ( mpWindowImpl->mpFrameData->mpFocusWin == this )
mpWindowImpl->mpFrameData->mpFocusWin = NULL;
if ( mpWindowImpl->mpFrameData->mpMouseMoveWin == this )
mpWindowImpl->mpFrameData->mpMouseMoveWin = NULL;
if ( mpWindowImpl->mpFrameData->mpMouseDownWin == this )
mpWindowImpl->mpFrameData->mpMouseDownWin = NULL;
if ( mpWindowImpl->mpFrameData != 0 )
{
if ( mpWindowImpl->mpFrameData->mpFocusWin == this )
mpWindowImpl->mpFrameData->mpFocusWin = NULL;
if ( mpWindowImpl->mpFrameData->mpMouseMoveWin == this )
mpWindowImpl->mpFrameData->mpMouseMoveWin = NULL;
if ( mpWindowImpl->mpFrameData->mpMouseDownWin == this )
mpWindowImpl->mpFrameData->mpMouseDownWin = NULL;
}
// reset Deactivate-Window
if ( pSVData->maWinData.mpLastDeacWin == this )