Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 :
21 : #include "rtlproto.hxx"
22 : #include "sbdiagnose.hxx"
23 :
24 : #include "basic/sbstar.hxx"
25 :
26 : #include <tools/debug.hxx>
27 : #include <comphelper/flagguard.hxx>
28 :
29 : #ifdef DBG_UTIL
30 :
31 : static DbgChannelId nRestoreChannelId = 0;
32 : static DbgChannelId nAssertionChannelId = 0;
33 : static StarBASICRef xAssertionChannelBasic;
34 : static OUString sCaptureFunctionName;
35 : static bool bReportingAssertion = false;
36 :
37 : void ResetCapturedAssertions()
38 : {
39 : if ( nRestoreChannelId != 0 )
40 : {
41 : DBG_INSTOUTERROR( nRestoreChannelId );
42 : }
43 : nRestoreChannelId = 0;
44 : xAssertionChannelBasic = NULL;
45 : sCaptureFunctionName = OUString();
46 : bReportingAssertion = false;
47 : }
48 :
49 : void DbgReportAssertion( const sal_Char* i_assertionMessage )
50 : {
51 : if ( !xAssertionChannelBasic )
52 : {
53 : ResetCapturedAssertions();
54 : return;
55 : }
56 :
57 : // prevent infinite recursion
58 : if ( bReportingAssertion )
59 : {
60 : return;
61 : }
62 : ::comphelper::FlagRestorationGuard aGuard( bReportingAssertion, true );
63 :
64 : SbxArrayRef const xArguments( new SbxArray( SbxVARIANT ) );
65 : SbxVariableRef const xMessageText = new SbxVariable( SbxSTRING );
66 : xMessageText->PutString( rtl::OUString::createFromAscii(i_assertionMessage) );
67 : xArguments->Put( xMessageText, 1 );
68 :
69 : ErrCode const nError = xAssertionChannelBasic->Call( sCaptureFunctionName, xArguments );
70 : if ( ( nError & SbERR_METHOD_NOT_FOUND ) != 0 )
71 : {
72 : ResetCapturedAssertions();
73 : }
74 : }
75 :
76 : #endif
77 :
78 : /// capture assertions, route them to the given given Basic function
79 0 : RTLFUNC(CaptureAssertions)
80 : {
81 : (void)bWrite;
82 :
83 : // need exactly one argument
84 0 : if ( rPar.Count() != 2 )
85 : {
86 0 : StarBASIC::Error( SbERR_BAD_ARGUMENT );
87 0 : return;
88 : }
89 :
90 : #ifdef DBG_UTIL
91 : DBG_TESTSOLARMUTEX();
92 :
93 : OUString const sFunctionName = rPar.Get(1)->GetOUString();
94 : if ( sFunctionName.isEmpty() )
95 : {
96 : ResetCapturedAssertions();
97 : return;
98 : }
99 :
100 : if ( nAssertionChannelId == 0 )
101 : {
102 : // TODO: should we register a named channel at the VCL API, instead of an unnamed channel at the tools API?
103 : // A named channel would mean it would appear in the nonpro-debug-options dialog
104 : nAssertionChannelId = DbgRegisterUserChannel( &DbgReportAssertion );
105 : }
106 :
107 : DbgChannelId const nCurrentChannelId = (DbgChannelId)DbgGetErrorOut();
108 : if ( nCurrentChannelId != nAssertionChannelId )
109 : {
110 : // remember the current channel
111 : nRestoreChannelId = nCurrentChannelId;
112 :
113 : // set the new channel
114 : DBG_INSTOUTERROR( nAssertionChannelId );
115 :
116 : // ensure OSL assertions are captured, too
117 : DbgData aData( *DbgGetData() );
118 : aData.bHookOSLAssert = sal_True;
119 : DbgUpdateOslHook( &aData );
120 : }
121 :
122 : xAssertionChannelBasic = pBasic;
123 : sCaptureFunctionName = sFunctionName;
124 : #else
125 : (void)pBasic;
126 : (void)rPar;
127 : (void)bWrite;
128 : #endif
129 84 : }
130 :
131 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|