xref: /aoo41x/main/uui/source/secmacrowarnings.cxx (revision cdf0e10c)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 #include <com/sun/star/xml/crypto/XSecurityEnvironment.hpp>
29 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
30 #include <com/sun/star/security/XDocumentDigitalSignatures.hpp>
31 #include <comphelper/sequence.hxx>
32 #include "comphelper/documentconstants.hxx"
33 #include <comphelper/processfactory.hxx>
34 
35 #include <vcl/msgbox.hxx>
36 #include <com/sun/star/security/NoPasswordException.hpp>
37 
38 using namespace ::com::sun::star::security;
39 
40 #include "ids.hrc"
41 #include "secmacrowarnings.hxx"
42 #include "secmacrowarnings.hrc"
43 
44 #ifdef _MSC_VER
45 #pragma warning (disable : 4355)	// 4355: this used in initializer-list
46 #endif
47 
48 using namespace ::com::sun::star;
49 using namespace ::com::sun::star;
50 
51 
52 // HACK!!! copied from xmlsecurity/source/dialog/resourcemanager.cxx
53 
54 namespace
55 {
56 	String GetContentPart( const String& _rRawString, const String& _rPartId )
57 	{
58 		String		s;
59 
60 		xub_StrLen	nContStart = _rRawString.Search( _rPartId );
61 		if( nContStart != STRING_NOTFOUND )
62 		{
63 			nContStart = nContStart + _rPartId.Len();
64 			++nContStart;					// now it's start of content, directly after Id
65 
66 			xub_StrLen	nContEnd = _rRawString.Search( sal_Unicode( ',' ), nContStart );
67 
68 			s = String( _rRawString, nContStart, nContEnd - nContStart );
69 		}
70 
71 		return s;
72 	}
73 }
74 
75 
76 MacroWarning::MacroWarning( Window* _pParent, bool _bWithSignatures, ResMgr& rResMgr )
77 	:ModalDialog			( _pParent, ResId( RID_XMLSECDLG_MACROWARN, rResMgr ) )
78 	,mpInfos				( NULL )
79 	,maSymbolImg			( this, ResId( IMG_SYMBOL, rResMgr ) )
80 	,maDocNameFI			( this, ResId( FI_DOCNAME, rResMgr ) )
81 	,maDescr1aFI			( this, ResId( FI_DESCR1A, rResMgr ) )
82 	,maDescr1bFI			( this, ResId( FI_DESCR1B, rResMgr ) )
83 	,maSignsFI				( this, ResId( FI_SIGNS, rResMgr ) )
84 	,maViewSignsBtn			( this, ResId( PB_VIEWSIGNS, rResMgr ) )
85 	,maDescr2FI				( this, ResId( FI_DESCR2, rResMgr ) )
86 	,maAlwaysTrustCB		( this, ResId( CB_ALWAYSTRUST, rResMgr ) )
87 	,maBottomSepFL			( this, ResId( FL_BOTTOM_SEP, rResMgr ) )
88 	,maEnableBtn			( this, ResId( PB_ENABLE, rResMgr ) )
89 	,maDisableBtn			( this, ResId( PB_DISABLE, rResMgr ) )
90 	,maHelpBtn				( this, ResId( BTN_HELP, rResMgr ) )
91 	,mbSignedMode			( true )
92     ,mbShowSignatures       ( _bWithSignatures )
93 	,mnActSecLevel			( 0 )
94 {
95 	FreeResource();
96 
97     InitControls();
98 
99     maDisableBtn.SetClickHdl( LINK( this, MacroWarning, DisableBtnHdl ) );
100 	maEnableBtn.SetClickHdl( LINK( this, MacroWarning, EnableBtnHdl ) );
101     maDisableBtn.GrabFocus(); // Default button, but focus is on view button
102 }
103 
104 MacroWarning::~MacroWarning()
105 {
106 }
107 
108 short MacroWarning::Execute()
109 {
110     FitControls();
111     return ModalDialog::Execute();
112 }
113 
114 void MacroWarning::SetDocumentURL( const String& rDocURL )
115 {
116     maDocNameFI.SetText( rDocURL );
117 }
118 
119 IMPL_LINK( MacroWarning, ViewSignsBtnHdl, void*, EMPTYARG )
120 {
121 	DBG_ASSERT( mxCert.is(), "*MacroWarning::ViewSignsBtnHdl(): no certificate set!" );
122 
123     uno::Sequence< uno::Any > aArgs( 1 );
124     aArgs[0] = uno::makeAny( maODFVersion );
125 	uno::Reference< security::XDocumentDigitalSignatures > xD(
126 		comphelper::getProcessServiceFactory()->createInstanceWithArguments( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM ( "com.sun.star.security.DocumentDigitalSignatures" ) ), aArgs ), uno::UNO_QUERY );
127 	if( xD.is() )
128 	{
129 		if( mxCert.is() )
130 			xD->showCertificate( mxCert );
131 		else if( mxStore.is() )
132 			xD->showScriptingContentSignatures( mxStore, uno::Reference< io::XInputStream >() );
133 	}
134 
135     return 0;
136 }
137 
138 IMPL_LINK( MacroWarning, EnableBtnHdl, void*, EMPTYARG )
139 {
140 	if( mbSignedMode && maAlwaysTrustCB.IsChecked() )
141 	{	// insert path into trusted path list
142         uno::Sequence< uno::Any > aArgs( 1 );
143         aArgs[0] = uno::makeAny( maODFVersion );
144         uno::Reference< security::XDocumentDigitalSignatures > xD(
145             comphelper::getProcessServiceFactory()->createInstanceWithArguments( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM ( "com.sun.star.security.DocumentDigitalSignatures" ) ), aArgs ), uno::UNO_QUERY );
146 		if( xD.is() )
147 		{
148 			if( mxCert.is() )
149 				xD->addAuthorToTrustedSources( mxCert );
150 			else if( mxStore.is() )
151 			{
152 				DBG_ASSERT( mpInfos, "-MacroWarning::EnableBtnHdl(): no infos, search in nirvana..." );
153 
154 				sal_Int32	nCnt = mpInfos->getLength();
155 				for( sal_Int32 i = 0 ; i < nCnt ; ++i )
156 					xD->addAuthorToTrustedSources( (*mpInfos)[ i ].Signer );
157 			}
158 		}
159 	}
160 
161 	EndDialog( RET_OK );
162     return 0;
163 }
164 
165 IMPL_LINK( MacroWarning, DisableBtnHdl, void*, EMPTYARG )
166 {
167 	EndDialog( RET_CANCEL );
168     return 0;
169 }
170 
171 IMPL_LINK( MacroWarning, AlwaysTrustCheckHdl, void*, EMPTYARG )
172 {
173 	bool bEnable = ( mnActSecLevel < 2 || maAlwaysTrustCB.IsChecked() );
174 	maEnableBtn.Enable( bEnable );
175 	maDisableBtn.Enable( !maAlwaysTrustCB.IsChecked() );
176 
177 	return 0;
178 }
179 
180 void MacroWarning::InitControls()
181 {
182     // set warning image
183     Image aImg( WarningBox::GetStandardImage() );
184     maSymbolImg.SetImage( aImg );
185     maSymbolImg.SetSizePixel( aImg.GetSizePixel() );
186     // set bold font and path ellipsis for docname fixedtext
187     Font aTmpFont = maDocNameFI.GetControlFont();
188     aTmpFont.SetWeight( WEIGHT_BOLD );
189     maDocNameFI.SetControlFont( aTmpFont );
190     WinBits nStyle = maDocNameFI.GetStyle();
191     nStyle |= WB_PATHELLIPSIS;
192     maDocNameFI.SetStyle( nStyle );
193     // show signature controls?
194     if( mbShowSignatures )
195     {
196         maDescr1bFI.Hide();
197         maViewSignsBtn.SetClickHdl( LINK( this, MacroWarning, ViewSignsBtnHdl ) );
198         maViewSignsBtn.Disable();   // default
199         maAlwaysTrustCB.SetClickHdl( LINK( this, MacroWarning, AlwaysTrustCheckHdl ) );
200 
201         mnActSecLevel = SvtSecurityOptions().GetMacroSecurityLevel();
202         if ( mnActSecLevel >= 2 )
203             maEnableBtn.Disable();
204     }
205     else
206     {
207         maDescr1aFI.Hide();
208         maSignsFI.Hide();
209         maViewSignsBtn.Hide();
210         maAlwaysTrustCB.Hide();
211 
212         // move hint up to position of signer list
213         maDescr2FI.SetPosPixel( maSignsFI.GetPosPixel() );
214     }
215     // without signature controls could be smaller
216     if ( !mbShowSignatures )
217     {
218         Point aPos = maDescr2FI.GetPosPixel();
219         aPos.Y() += maDescr2FI.GetSizePixel().Height();
220         aPos.Y() += LogicToPixel( Size( 3, 3 ) ).Height();
221         long nDelta = maBottomSepFL.GetPosPixel().Y() - aPos.Y();
222         Window* pWins[] =
223         {
224             &maBottomSepFL, &maEnableBtn, &maDisableBtn, &maHelpBtn
225         };
226         Window** pCurrent = pWins;
227         for ( sal_uInt32 i = 0; i < sizeof( pWins ) / sizeof( pWins[ 0 ] ); ++i, ++pCurrent )
228         {
229             Point aNewPos = (*pCurrent)->GetPosPixel();
230             aNewPos.Y() -= nDelta;
231             (*pCurrent)->SetPosPixel( aNewPos );
232         }
233 
234         Size aDlgSz = GetSizePixel();
235         aDlgSz.Height() -= nDelta;
236         SetSizePixel( aDlgSz );
237     }
238 
239     // check if some buttontexts are to wide
240     String sText = maViewSignsBtn.GetText();
241     long nTxtW = maViewSignsBtn.GetTextWidth( sText );
242     const long nOffset = 12;
243     if ( sText.Search( '~' ) == STRING_NOTFOUND )
244         nTxtW += nOffset;
245     long nBtnW = maViewSignsBtn.GetSizePixel().Width();
246     if ( nTxtW >= nBtnW )
247     {
248         // broaden the button
249         long nDelta = Max( nTxtW - nBtnW, nOffset/3 );
250         Size aNewSize = maViewSignsBtn.GetSizePixel();
251         aNewSize.Width() += nDelta;
252         maViewSignsBtn.SetSizePixel( aNewSize );
253         // and give it a new position
254         Point aNewPos = maViewSignsBtn.GetPosPixel();
255         aNewPos.X() -= nDelta;
256         maViewSignsBtn.SetPosPixel( aNewPos );
257         // the the left fixedtext must be smaller
258         aNewSize = maSignsFI.GetSizePixel();
259         aNewSize.Width() -= nDelta;
260         maSignsFI.SetSizePixel( aNewSize );
261     }
262     // if the button text (we compare with the longest of both) is too wide, then broaden the buttons
263     String sText1 = maEnableBtn.GetText();
264     long nTxtW1 = maEnableBtn.GetTextWidth( sText1 );
265     if ( sText1.Search( '~' ) == STRING_NOTFOUND )
266         nTxtW1 += nOffset;
267     String sText2 = maDisableBtn.GetText();
268     long nTxtW2 = maDisableBtn.GetTextWidth( sText2 );
269     if ( sText2.Search( '~' ) == STRING_NOTFOUND )
270         nTxtW2 += nOffset;
271     nTxtW = Max( nTxtW1, nTxtW2 );
272     nBtnW = maEnableBtn.GetSizePixel().Width();
273     if ( nTxtW > nBtnW )
274     {
275         // broaden both buttons
276         long nDelta = nTxtW - nBtnW;
277         Size aNewSize = maEnableBtn.GetSizePixel();
278         aNewSize.Width() += nDelta;
279         maEnableBtn.SetSizePixel( aNewSize );
280         maDisableBtn.SetSizePixel( aNewSize );
281         // and give them a new position
282         Point aNewPos = maEnableBtn.GetPosPixel();
283         aNewPos.X() -= (2*nDelta);
284         maEnableBtn.SetPosPixel( aNewPos );
285         aNewPos = maDisableBtn.GetPosPixel();
286         aNewPos.X() -= nDelta;
287         maDisableBtn.SetPosPixel( aNewPos );
288     }
289 }
290 
291 void MacroWarning::FitControls()
292 {
293     Size a3Size = LogicToPixel( Size( 3, 3 ), MAP_APPFONT );
294     Size aNewSize, aMinSize;
295     long nTxtH = 0;
296     long nCtrlH = 0;
297     long nDelta = 0;
298 
299     if ( mbShowSignatures )
300     {
301         aMinSize = maSignsFI.CalcMinimumSize( maSignsFI.GetSizePixel().Width() );
302         nTxtH = Max( aMinSize.Height(), maViewSignsBtn.GetSizePixel().Height() );
303         nTxtH += a3Size.Height() / 2;
304         nCtrlH = maSignsFI.GetSizePixel().Height();
305         nDelta = Max( nCtrlH - nTxtH, static_cast< long >( -100 ) ); // not too large
306         aNewSize = maSignsFI.GetSizePixel();
307         aNewSize.Height() -= nDelta;
308         maSignsFI.SetSizePixel( aNewSize );
309     }
310 
311     aMinSize = maDescr2FI.CalcMinimumSize( maDescr2FI.GetSizePixel().Width() );
312     nTxtH = aMinSize.Height();
313     nCtrlH = maDescr2FI.GetSizePixel().Height();
314     long nDelta2 = ( nCtrlH - nTxtH );
315     aNewSize = maDescr2FI.GetSizePixel();
316     aNewSize.Height() -= nDelta2;
317     maDescr2FI.SetSizePixel( aNewSize );
318 
319     // new position for the succeeding windows
320     Window* pWins[] =
321     {
322         &maDescr2FI, &maAlwaysTrustCB, &maBottomSepFL, &maEnableBtn, &maDisableBtn, &maHelpBtn
323     };
324     Window** pCurrent = pWins;
325     for ( sal_uInt32 i = 0; i < sizeof( pWins ) / sizeof( pWins[ 0 ] ); ++i, ++pCurrent )
326     {
327         Point aNewPos = (*pCurrent)->GetPosPixel();
328         aNewPos.Y() -= nDelta;
329         (*pCurrent)->SetPosPixel( aNewPos );
330 
331         if ( *pCurrent == &maDescr2FI )
332             nDelta += nDelta2;
333     }
334 
335     // new size of the dialog
336     aNewSize = GetSizePixel();
337     aNewSize.Height() -= nDelta;
338     SetSizePixel( aNewSize );
339 }
340 
341 void MacroWarning::SetStorage( const cssu::Reference < css::embed::XStorage >& rxStore,
342                                const ::rtl::OUString& aODFVersion,
343                                const cssu::Sequence< security::DocumentSignatureInformation >& rInfos )
344 {
345 	mxStore = rxStore;
346     maODFVersion = aODFVersion;
347 	sal_Int32	nCnt = rInfos.getLength();
348 	if( mxStore.is() && nCnt > 0 )
349 	{
350 		mpInfos = &rInfos;
351 		String		aCN_Id( String::CreateFromAscii( "CN" ) );
352 		String		s;
353 		s = GetContentPart( rInfos[ 0 ].Signer->getSubjectName(), aCN_Id );
354 
355 		for( sal_Int32 i = 1 ; i < nCnt ; ++i )
356 		{
357 			s.AppendAscii( "\n" );
358 			s += GetContentPart( rInfos[ i ].Signer->getSubjectName(), aCN_Id );
359 		}
360 
361         maSignsFI.SetText( s );
362 		maViewSignsBtn.Enable();
363 	}
364 }
365 
366 void MacroWarning::SetCertificate( const cssu::Reference< css::security::XCertificate >& _rxCert )
367 {
368 	mxCert = _rxCert;
369 	if( mxCert.is() )
370 	{
371 		String	aCN_Id( String::CreateFromAscii( "CN" ) );
372 		String	s;
373 		s = GetContentPart( mxCert->getSubjectName(), aCN_Id );
374         maSignsFI.SetText( s );
375 		maViewSignsBtn.Enable();
376 	}
377 }
378 
379