1e1f63238SAndrew Rist /**************************************************************
2cdf0e10cSrcweir *
3e1f63238SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one
4e1f63238SAndrew Rist * or more contributor license agreements. See the NOTICE file
5e1f63238SAndrew Rist * distributed with this work for additional information
6e1f63238SAndrew Rist * regarding copyright ownership. The ASF licenses this file
7e1f63238SAndrew Rist * to you under the Apache License, Version 2.0 (the
8e1f63238SAndrew Rist * "License"); you may not use this file except in compliance
9e1f63238SAndrew Rist * with the License. You may obtain a copy of the License at
10e1f63238SAndrew Rist *
11e1f63238SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0
12e1f63238SAndrew Rist *
13e1f63238SAndrew Rist * Unless required by applicable law or agreed to in writing,
14e1f63238SAndrew Rist * software distributed under the License is distributed on an
15e1f63238SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16e1f63238SAndrew Rist * KIND, either express or implied. See the License for the
17e1f63238SAndrew Rist * specific language governing permissions and limitations
18e1f63238SAndrew Rist * under the License.
19e1f63238SAndrew Rist *
20e1f63238SAndrew Rist *************************************************************/
21e1f63238SAndrew Rist
22e1f63238SAndrew Rist
23cdf0e10cSrcweir
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_basic.hxx"
26cdf0e10cSrcweir #include <basic/sbx.hxx>
27cdf0e10cSrcweir #include "sbcomp.hxx"
28cdf0e10cSrcweir #include <com/sun/star/script/ModuleType.hpp>
29cdf0e10cSrcweir
30cdf0e10cSrcweir struct SbiParseStack { // "Stack" fuer Statement-Blocks
31cdf0e10cSrcweir SbiParseStack* pNext; // Chain
32cdf0e10cSrcweir SbiExprNode* pWithVar; // Variable fuer WITH
33cdf0e10cSrcweir SbiToken eExitTok; // Exit-Token
34cdf0e10cSrcweir sal_uInt32 nChain; // JUMP-Chain
35cdf0e10cSrcweir };
36cdf0e10cSrcweir
37cdf0e10cSrcweir struct SbiStatement {
38cdf0e10cSrcweir SbiToken eTok;
39cdf0e10cSrcweir void( SbiParser::*Func )(); // Verarbeitungsroutine
40cdf0e10cSrcweir sal_Bool bMain; // sal_True: ausserhalb SUBs OK
41cdf0e10cSrcweir sal_Bool bSubr; // sal_True: in SUBs OK
42cdf0e10cSrcweir };
43cdf0e10cSrcweir
44cdf0e10cSrcweir #define Y sal_True
45cdf0e10cSrcweir #define N sal_False
46cdf0e10cSrcweir
47cdf0e10cSrcweir static SbiStatement StmntTable [] = {
48cdf0e10cSrcweir { CALL, &SbiParser::Call, N, Y, }, // CALL
49cdf0e10cSrcweir { CLOSE, &SbiParser::Close, N, Y, }, // CLOSE
50cdf0e10cSrcweir { _CONST_, &SbiParser::Dim, Y, Y, }, // CONST
51cdf0e10cSrcweir { DECLARE, &SbiParser::Declare, Y, N, }, // DECLARE
52cdf0e10cSrcweir { DEFBOOL, &SbiParser::DefXXX, Y, N, }, // DEFBOOL
53cdf0e10cSrcweir { DEFCUR, &SbiParser::DefXXX, Y, N, }, // DEFCUR
54cdf0e10cSrcweir { DEFDATE, &SbiParser::DefXXX, Y, N, }, // DEFDATE
55cdf0e10cSrcweir { DEFDBL, &SbiParser::DefXXX, Y, N, }, // DEFDBL
56cdf0e10cSrcweir { DEFERR, &SbiParser::DefXXX, Y, N, }, // DEFERR
57cdf0e10cSrcweir { DEFINT, &SbiParser::DefXXX, Y, N, }, // DEFINT
58cdf0e10cSrcweir { DEFLNG, &SbiParser::DefXXX, Y, N, }, // DEFLNG
59cdf0e10cSrcweir { DEFOBJ, &SbiParser::DefXXX, Y, N, }, // DEFOBJ
60cdf0e10cSrcweir { DEFSNG, &SbiParser::DefXXX, Y, N, }, // DEFSNG
61cdf0e10cSrcweir { DEFSTR, &SbiParser::DefXXX, Y, N, }, // DEFSTR
62cdf0e10cSrcweir { DEFVAR, &SbiParser::DefXXX, Y, N, }, // DEFVAR
63cdf0e10cSrcweir { DIM, &SbiParser::Dim, Y, Y, }, // DIM
64cdf0e10cSrcweir { DO, &SbiParser::DoLoop, N, Y, }, // DO
65cdf0e10cSrcweir { ELSE, &SbiParser::NoIf, N, Y, }, // ELSE
66cdf0e10cSrcweir { ELSEIF, &SbiParser::NoIf, N, Y, }, // ELSEIF
67cdf0e10cSrcweir { ENDIF, &SbiParser::NoIf, N, Y, }, // ENDIF
68cdf0e10cSrcweir { END, &SbiParser::Stop, N, Y, }, // END
69cdf0e10cSrcweir { ENUM, &SbiParser::Enum, Y, N, }, // TYPE
70cdf0e10cSrcweir { ERASE, &SbiParser::Erase, N, Y, }, // ERASE
71cdf0e10cSrcweir { _ERROR_, &SbiParser::ErrorStmnt, N, Y, }, // ERROR
72cdf0e10cSrcweir { EXIT, &SbiParser::Exit, N, Y, }, // EXIT
73cdf0e10cSrcweir { FOR, &SbiParser::For, N, Y, }, // FOR
74cdf0e10cSrcweir { FUNCTION, &SbiParser::SubFunc, Y, N, }, // FUNCTION
75cdf0e10cSrcweir { GOSUB, &SbiParser::Goto, N, Y, }, // GOSUB
76cdf0e10cSrcweir { GLOBAL, &SbiParser::Dim, Y, N, }, // GLOBAL
77cdf0e10cSrcweir { GOTO, &SbiParser::Goto, N, Y, }, // GOTO
78cdf0e10cSrcweir { IF, &SbiParser::If, N, Y, }, // IF
79cdf0e10cSrcweir { IMPLEMENTS, &SbiParser::Implements, Y, N, }, // IMPLEMENTS
80cdf0e10cSrcweir { INPUT, &SbiParser::Input, N, Y, }, // INPUT
81cdf0e10cSrcweir { LET, &SbiParser::Assign, N, Y, }, // LET
82cdf0e10cSrcweir { LINE, &SbiParser::Line, N, Y, }, // LINE, -> LINE INPUT (#i92642)
83cdf0e10cSrcweir { LINEINPUT,&SbiParser::LineInput, N, Y, }, // LINE INPUT
84cdf0e10cSrcweir { LOOP, &SbiParser::BadBlock, N, Y, }, // LOOP
85cdf0e10cSrcweir { LSET, &SbiParser::LSet, N, Y, }, // LSET
86cdf0e10cSrcweir { NAME, &SbiParser::Name, N, Y, }, // NAME
87cdf0e10cSrcweir { NEXT, &SbiParser::BadBlock, N, Y, }, // NEXT
88cdf0e10cSrcweir { ON, &SbiParser::On, N, Y, }, // ON
89cdf0e10cSrcweir { OPEN, &SbiParser::Open, N, Y, }, // OPEN
90cdf0e10cSrcweir { OPTION, &SbiParser::Option, Y, N, }, // OPTION
91cdf0e10cSrcweir { PRINT, &SbiParser::Print, N, Y, }, // PRINT
92cdf0e10cSrcweir { PRIVATE, &SbiParser::Dim, Y, N, }, // PRIVATE
93cdf0e10cSrcweir { PROPERTY, &SbiParser::SubFunc, Y, N, }, // FUNCTION
94cdf0e10cSrcweir { PUBLIC, &SbiParser::Dim, Y, N, }, // PUBLIC
95cdf0e10cSrcweir { REDIM, &SbiParser::ReDim, N, Y, }, // DIM
96cdf0e10cSrcweir { RESUME, &SbiParser::Resume, N, Y, }, // RESUME
97cdf0e10cSrcweir { RETURN, &SbiParser::Return, N, Y, }, // RETURN
98cdf0e10cSrcweir { RSET, &SbiParser::RSet, N, Y, }, // RSET
99cdf0e10cSrcweir { SELECT, &SbiParser::Select, N, Y, }, // SELECT
100cdf0e10cSrcweir { SET, &SbiParser::Set, N, Y, }, // SET
101cdf0e10cSrcweir { STATIC, &SbiParser::Static, Y, Y, }, // STATIC
102cdf0e10cSrcweir { STOP, &SbiParser::Stop, N, Y, }, // STOP
103cdf0e10cSrcweir { SUB, &SbiParser::SubFunc, Y, N, }, // SUB
104cdf0e10cSrcweir { TYPE, &SbiParser::Type, Y, N, }, // TYPE
105cdf0e10cSrcweir { UNTIL, &SbiParser::BadBlock, N, Y, }, // UNTIL
106cdf0e10cSrcweir { WHILE, &SbiParser::While, N, Y, }, // WHILE
107cdf0e10cSrcweir { WEND, &SbiParser::BadBlock, N, Y, }, // WEND
108cdf0e10cSrcweir { WITH, &SbiParser::With, N, Y, }, // WITH
109cdf0e10cSrcweir { WRITE, &SbiParser::Write, N, Y, }, // WRITE
110cdf0e10cSrcweir
111cdf0e10cSrcweir { NIL, NULL, N, N }
112cdf0e10cSrcweir };
113cdf0e10cSrcweir
114cdf0e10cSrcweir
115cdf0e10cSrcweir #ifdef _MSC_VER
116cdf0e10cSrcweir // 'this' : used in base member initializer list
117cdf0e10cSrcweir #pragma warning( disable: 4355 )
118cdf0e10cSrcweir #endif
119cdf0e10cSrcweir
SbiParser(StarBASIC * pb,SbModule * pm)120cdf0e10cSrcweir SbiParser::SbiParser( StarBASIC* pb, SbModule* pm )
121cdf0e10cSrcweir : SbiTokenizer( pm->GetSource32(), pb ),
122cdf0e10cSrcweir aGblStrings( this ),
123cdf0e10cSrcweir aLclStrings( this ),
124cdf0e10cSrcweir aGlobals( aGblStrings, SbGLOBAL ),
125cdf0e10cSrcweir aPublics( aGblStrings, SbPUBLIC ),
126cdf0e10cSrcweir aRtlSyms( aGblStrings, SbRTL ),
127cdf0e10cSrcweir aGen( *pm, this, 1024 )
128cdf0e10cSrcweir {
129cdf0e10cSrcweir pBasic = pb;
130cdf0e10cSrcweir eCurExpr = SbSYMBOL;
131cdf0e10cSrcweir eEndTok = NIL;
132cdf0e10cSrcweir pProc = NULL;
133cdf0e10cSrcweir pStack = NULL;
134cdf0e10cSrcweir pWithVar = NULL;
135cdf0e10cSrcweir nBase = 0;
136cdf0e10cSrcweir bText =
137cdf0e10cSrcweir bGblDefs =
138cdf0e10cSrcweir bNewGblDefs =
139cdf0e10cSrcweir bSingleLineIf =
140cdf0e10cSrcweir bExplicit = sal_False;
141cdf0e10cSrcweir bClassModule = ( pm->GetModuleType() == com::sun::star::script::ModuleType::CLASS );
142cdf0e10cSrcweir OSL_TRACE("Parser - %s, bClassModule %d", rtl::OUStringToOString( pm->GetName(), RTL_TEXTENCODING_UTF8 ).getStr(), bClassModule );
143cdf0e10cSrcweir pPool = &aPublics;
144cdf0e10cSrcweir for( short i = 0; i < 26; i++ )
145cdf0e10cSrcweir eDefTypes[ i ] = SbxVARIANT; // Kein expliziter Defaulttyp
146cdf0e10cSrcweir
147cdf0e10cSrcweir aPublics.SetParent( &aGlobals );
148cdf0e10cSrcweir aGlobals.SetParent( &aRtlSyms );
149cdf0e10cSrcweir
150cdf0e10cSrcweir // Die globale Chainkette faengt bei Adresse 0 an:
151cdf0e10cSrcweir nGblChain = aGen.Gen( _JUMP, 0 );
152cdf0e10cSrcweir
153cdf0e10cSrcweir rTypeArray = new SbxArray; // Array fuer Benutzerdefinierte Typen
154cdf0e10cSrcweir rEnumArray = new SbxArray; // Array for Enum types
155cdf0e10cSrcweir bVBASupportOn = pm->IsVBACompat();
156cdf0e10cSrcweir if ( bVBASupportOn )
157cdf0e10cSrcweir EnableCompatibility();
158cdf0e10cSrcweir
159cdf0e10cSrcweir }
160cdf0e10cSrcweir
161cdf0e10cSrcweir
162cdf0e10cSrcweir // Ist Teil der Runtime-Library?
CheckRTLForSym(const String & rSym,SbxDataType eType)163cdf0e10cSrcweir SbiSymDef* SbiParser::CheckRTLForSym( const String& rSym, SbxDataType eType )
164cdf0e10cSrcweir {
165cdf0e10cSrcweir SbxVariable* pVar = GetBasic()->GetRtl()->Find( rSym, SbxCLASS_DONTCARE );
166cdf0e10cSrcweir SbiSymDef* pDef = NULL;
167cdf0e10cSrcweir if( pVar )
168cdf0e10cSrcweir {
169cdf0e10cSrcweir if( pVar->IsA( TYPE(SbxMethod) ) )
170cdf0e10cSrcweir {
171cdf0e10cSrcweir SbiProcDef* pProc_ = aRtlSyms.AddProc( rSym );
172*22a7caf0STsutomu Uchino SbxMethod* pMethod = (SbxMethod*) pVar;
173*22a7caf0STsutomu Uchino if ( pMethod && pMethod->IsRuntimeFunction() )
174*22a7caf0STsutomu Uchino {
175*22a7caf0STsutomu Uchino pProc_->SetType( pMethod->GetRuntimeFunctionReturnType() );
176*22a7caf0STsutomu Uchino }
177*22a7caf0STsutomu Uchino else
178*22a7caf0STsutomu Uchino {
179*22a7caf0STsutomu Uchino pProc_->SetType( pVar->GetType() );
180*22a7caf0STsutomu Uchino }
181cdf0e10cSrcweir pDef = pProc_;
182cdf0e10cSrcweir }
183cdf0e10cSrcweir else
184cdf0e10cSrcweir {
185cdf0e10cSrcweir pDef = aRtlSyms.AddSym( rSym );
186cdf0e10cSrcweir pDef->SetType( eType );
187cdf0e10cSrcweir }
188cdf0e10cSrcweir }
189cdf0e10cSrcweir return pDef;
190cdf0e10cSrcweir }
191cdf0e10cSrcweir
192cdf0e10cSrcweir // Globale Chainkette schliessen
193cdf0e10cSrcweir
HasGlobalCode()194cdf0e10cSrcweir sal_Bool SbiParser::HasGlobalCode()
195cdf0e10cSrcweir {
196cdf0e10cSrcweir if( bGblDefs && nGblChain )
197cdf0e10cSrcweir {
198cdf0e10cSrcweir aGen.BackChain( nGblChain );
199cdf0e10cSrcweir aGen.Gen( _LEAVE );
200cdf0e10cSrcweir // aGen.Gen( _STOP );
201cdf0e10cSrcweir nGblChain = 0;
202cdf0e10cSrcweir }
203cdf0e10cSrcweir return bGblDefs;
204cdf0e10cSrcweir }
205cdf0e10cSrcweir
OpenBlock(SbiToken eTok,SbiExprNode * pVar)206cdf0e10cSrcweir void SbiParser::OpenBlock( SbiToken eTok, SbiExprNode* pVar )
207cdf0e10cSrcweir {
208cdf0e10cSrcweir SbiParseStack* p = new SbiParseStack;
209cdf0e10cSrcweir p->eExitTok = eTok;
210cdf0e10cSrcweir p->nChain = 0;
211cdf0e10cSrcweir p->pWithVar = pWithVar;
212cdf0e10cSrcweir p->pNext = pStack;
213cdf0e10cSrcweir pStack = p;
214cdf0e10cSrcweir pWithVar = pVar;
215cdf0e10cSrcweir
216cdf0e10cSrcweir // #29955 for-Schleifen-Ebene pflegen
217cdf0e10cSrcweir if( eTok == FOR )
218cdf0e10cSrcweir aGen.IncForLevel();
219cdf0e10cSrcweir }
220cdf0e10cSrcweir
CloseBlock()221cdf0e10cSrcweir void SbiParser::CloseBlock()
222cdf0e10cSrcweir {
223cdf0e10cSrcweir if( pStack )
224cdf0e10cSrcweir {
225cdf0e10cSrcweir SbiParseStack* p = pStack;
226cdf0e10cSrcweir
227cdf0e10cSrcweir // #29955 for-Schleifen-Ebene pflegen
228cdf0e10cSrcweir if( p->eExitTok == FOR )
229cdf0e10cSrcweir aGen.DecForLevel();
230cdf0e10cSrcweir
231cdf0e10cSrcweir aGen.BackChain( p->nChain );
232cdf0e10cSrcweir pStack = p->pNext;
233cdf0e10cSrcweir pWithVar = p->pWithVar;
234cdf0e10cSrcweir delete p;
235cdf0e10cSrcweir }
236cdf0e10cSrcweir }
237cdf0e10cSrcweir
238cdf0e10cSrcweir // EXIT ...
239cdf0e10cSrcweir
Exit()240cdf0e10cSrcweir void SbiParser::Exit()
241cdf0e10cSrcweir {
242cdf0e10cSrcweir SbiToken eTok = Next();
243cdf0e10cSrcweir for( SbiParseStack* p = pStack; p; p = p->pNext )
244cdf0e10cSrcweir {
245cdf0e10cSrcweir SbiToken eExitTok = p->eExitTok;
246cdf0e10cSrcweir if( eTok == eExitTok ||
247cdf0e10cSrcweir (eTok == PROPERTY && (eExitTok == GET || eExitTok == LET) ) ) // #i109051
248cdf0e10cSrcweir {
249cdf0e10cSrcweir p->nChain = aGen.Gen( _JUMP, p->nChain );
250cdf0e10cSrcweir return;
251cdf0e10cSrcweir }
252cdf0e10cSrcweir }
253cdf0e10cSrcweir if( pStack )
254cdf0e10cSrcweir Error( SbERR_EXPECTED, pStack->eExitTok );
255cdf0e10cSrcweir else
256cdf0e10cSrcweir Error( SbERR_BAD_EXIT );
257cdf0e10cSrcweir }
258cdf0e10cSrcweir
TestSymbol(sal_Bool bKwdOk)259cdf0e10cSrcweir sal_Bool SbiParser::TestSymbol( sal_Bool bKwdOk )
260cdf0e10cSrcweir {
261cdf0e10cSrcweir Peek();
262cdf0e10cSrcweir if( eCurTok == SYMBOL || ( bKwdOk && IsKwd( eCurTok ) ) )
263cdf0e10cSrcweir {
264cdf0e10cSrcweir Next(); return sal_True;
265cdf0e10cSrcweir }
266cdf0e10cSrcweir Error( SbERR_SYMBOL_EXPECTED );
267cdf0e10cSrcweir return sal_False;
268cdf0e10cSrcweir }
269cdf0e10cSrcweir
270cdf0e10cSrcweir // Testen auf ein bestimmtes Token
271cdf0e10cSrcweir
TestToken(SbiToken t)272cdf0e10cSrcweir sal_Bool SbiParser::TestToken( SbiToken t )
273cdf0e10cSrcweir {
274cdf0e10cSrcweir if( Peek() == t )
275cdf0e10cSrcweir {
276cdf0e10cSrcweir Next(); return sal_True;
277cdf0e10cSrcweir }
278cdf0e10cSrcweir else
279cdf0e10cSrcweir {
280cdf0e10cSrcweir Error( SbERR_EXPECTED, t );
281cdf0e10cSrcweir return sal_False;
282cdf0e10cSrcweir }
283cdf0e10cSrcweir }
284cdf0e10cSrcweir
285cdf0e10cSrcweir // Testen auf Komma oder EOLN
286cdf0e10cSrcweir
TestComma()287cdf0e10cSrcweir sal_Bool SbiParser::TestComma()
288cdf0e10cSrcweir {
289cdf0e10cSrcweir SbiToken eTok = Peek();
290cdf0e10cSrcweir if( IsEoln( eTok ) )
291cdf0e10cSrcweir {
292cdf0e10cSrcweir Next();
293cdf0e10cSrcweir return sal_False;
294cdf0e10cSrcweir }
295cdf0e10cSrcweir else if( eTok != COMMA )
296cdf0e10cSrcweir {
297cdf0e10cSrcweir Error( SbERR_EXPECTED, COMMA );
298cdf0e10cSrcweir return sal_False;
299cdf0e10cSrcweir }
300cdf0e10cSrcweir Next();
301cdf0e10cSrcweir return sal_True;
302cdf0e10cSrcweir }
303cdf0e10cSrcweir
304cdf0e10cSrcweir // Testen, ob EOLN vorliegt
305cdf0e10cSrcweir
TestEoln()306cdf0e10cSrcweir void SbiParser::TestEoln()
307cdf0e10cSrcweir {
308cdf0e10cSrcweir if( !IsEoln( Next() ) )
309cdf0e10cSrcweir {
310cdf0e10cSrcweir Error( SbERR_EXPECTED, EOLN );
311cdf0e10cSrcweir while( !IsEoln( Next() ) ) {}
312cdf0e10cSrcweir }
313cdf0e10cSrcweir }
314cdf0e10cSrcweir
315cdf0e10cSrcweir // Parsing eines Statement-Blocks
316cdf0e10cSrcweir // Das Parsing laeuft bis zum Ende-Token.
317cdf0e10cSrcweir
StmntBlock(SbiToken eEnd)318cdf0e10cSrcweir void SbiParser::StmntBlock( SbiToken eEnd )
319cdf0e10cSrcweir {
320cdf0e10cSrcweir SbiToken xe = eEndTok;
321cdf0e10cSrcweir eEndTok = eEnd;
322cdf0e10cSrcweir while( !bAbort && Parse() ) {}
323cdf0e10cSrcweir eEndTok = xe;
324cdf0e10cSrcweir if( IsEof() )
325cdf0e10cSrcweir {
326cdf0e10cSrcweir Error( SbERR_BAD_BLOCK, eEnd );
327cdf0e10cSrcweir bAbort = sal_True;
328cdf0e10cSrcweir }
329cdf0e10cSrcweir }
330cdf0e10cSrcweir
331cdf0e10cSrcweir // Die Hauptroutine. Durch wiederholten Aufrufs dieser Routine wird
332cdf0e10cSrcweir // die Quelle geparst. Returnwert sal_False bei Ende/Fehlern.
333cdf0e10cSrcweir
Parse()334cdf0e10cSrcweir sal_Bool SbiParser::Parse()
335cdf0e10cSrcweir {
336cdf0e10cSrcweir if( bAbort ) return sal_False;
337cdf0e10cSrcweir
338cdf0e10cSrcweir EnableErrors();
339cdf0e10cSrcweir
340cdf0e10cSrcweir bErrorIsSymbol = false;
341cdf0e10cSrcweir Peek();
342cdf0e10cSrcweir bErrorIsSymbol = true;
343cdf0e10cSrcweir // Dateiende?
344cdf0e10cSrcweir if( IsEof() )
345cdf0e10cSrcweir {
346cdf0e10cSrcweir // AB #33133: Falls keine Sub angelegt wurde, muss hier
347cdf0e10cSrcweir // der globale Chain abgeschlossen werden!
348cdf0e10cSrcweir // AB #40689: Durch die neue static-Behandlung kann noch
349cdf0e10cSrcweir // ein nGblChain vorhanden sein, daher vorher abfragen
350cdf0e10cSrcweir if( bNewGblDefs && nGblChain == 0 )
351cdf0e10cSrcweir nGblChain = aGen.Gen( _JUMP, 0 );
352cdf0e10cSrcweir return sal_False;
353cdf0e10cSrcweir }
354cdf0e10cSrcweir
355cdf0e10cSrcweir // Leerstatement?
356cdf0e10cSrcweir if( IsEoln( eCurTok ) )
357cdf0e10cSrcweir {
358cdf0e10cSrcweir Next(); return sal_True;
359cdf0e10cSrcweir }
360cdf0e10cSrcweir
361cdf0e10cSrcweir if( !bSingleLineIf && MayBeLabel( sal_True ) )
362cdf0e10cSrcweir {
363cdf0e10cSrcweir // Ist ein Label
364cdf0e10cSrcweir if( !pProc )
365cdf0e10cSrcweir Error( SbERR_NOT_IN_MAIN, aSym );
366cdf0e10cSrcweir else
367cdf0e10cSrcweir pProc->GetLabels().Define( aSym );
368cdf0e10cSrcweir Next(); Peek();
369cdf0e10cSrcweir // Leerstatement?
370cdf0e10cSrcweir if( IsEoln( eCurTok ) )
371cdf0e10cSrcweir {
372cdf0e10cSrcweir Next(); return sal_True;
373cdf0e10cSrcweir }
374cdf0e10cSrcweir }
375cdf0e10cSrcweir
376cdf0e10cSrcweir // Ende des Parsings?
377cdf0e10cSrcweir if( eCurTok == eEndTok ||
378cdf0e10cSrcweir ( bVBASupportOn && // #i109075
379cdf0e10cSrcweir (eCurTok == ENDFUNC || eCurTok == ENDPROPERTY || eCurTok == ENDSUB) &&
380cdf0e10cSrcweir (eEndTok == ENDFUNC || eEndTok == ENDPROPERTY || eEndTok == ENDSUB) ) )
381cdf0e10cSrcweir {
382cdf0e10cSrcweir Next();
383cdf0e10cSrcweir if( eCurTok != NIL )
384cdf0e10cSrcweir aGen.Statement();
385cdf0e10cSrcweir return sal_False;
386cdf0e10cSrcweir }
387cdf0e10cSrcweir
388cdf0e10cSrcweir // Kommentar?
389cdf0e10cSrcweir if( eCurTok == REM )
390cdf0e10cSrcweir {
391cdf0e10cSrcweir Next(); return sal_True;
392cdf0e10cSrcweir }
393cdf0e10cSrcweir
394cdf0e10cSrcweir // Kommt ein Symbol, ist es entweder eine Variable( LET )
395cdf0e10cSrcweir // oder eine SUB-Prozedur( CALL ohne Klammern )
396cdf0e10cSrcweir // DOT fuer Zuweisungen im WITH-Block: .A=5
397cdf0e10cSrcweir if( eCurTok == SYMBOL || eCurTok == DOT )
398cdf0e10cSrcweir {
399cdf0e10cSrcweir if( !pProc )
400cdf0e10cSrcweir Error( SbERR_EXPECTED, SUB );
401cdf0e10cSrcweir else
402cdf0e10cSrcweir {
403cdf0e10cSrcweir // Damit Zeile & Spalte stimmen...
404cdf0e10cSrcweir Next();
405cdf0e10cSrcweir Push( eCurTok );
406cdf0e10cSrcweir aGen.Statement();
407cdf0e10cSrcweir Symbol();
408cdf0e10cSrcweir }
409cdf0e10cSrcweir }
410cdf0e10cSrcweir else
411cdf0e10cSrcweir {
412cdf0e10cSrcweir Next();
413cdf0e10cSrcweir
414cdf0e10cSrcweir // Hier folgen nun die Statement-Parser.
415cdf0e10cSrcweir
416cdf0e10cSrcweir SbiStatement* p;
417cdf0e10cSrcweir for( p = StmntTable; p->eTok != NIL; p++ )
418cdf0e10cSrcweir if( p->eTok == eCurTok )
419cdf0e10cSrcweir break;
420cdf0e10cSrcweir if( p->eTok != NIL )
421cdf0e10cSrcweir {
422cdf0e10cSrcweir if( !pProc && !p->bMain )
423cdf0e10cSrcweir Error( SbERR_NOT_IN_MAIN, eCurTok );
424cdf0e10cSrcweir else if( pProc && !p->bSubr )
425cdf0e10cSrcweir Error( SbERR_NOT_IN_SUBR, eCurTok );
426cdf0e10cSrcweir else
427cdf0e10cSrcweir {
428cdf0e10cSrcweir // globalen Chain pflegen
429cdf0e10cSrcweir // AB #41606/#40689: Durch die neue static-Behandlung kann noch
430cdf0e10cSrcweir // ein nGblChain vorhanden sein, daher vorher abfragen
431cdf0e10cSrcweir if( bNewGblDefs && nGblChain == 0 &&
432cdf0e10cSrcweir ( eCurTok == SUB || eCurTok == FUNCTION || eCurTok == PROPERTY ) )
433cdf0e10cSrcweir {
434cdf0e10cSrcweir nGblChain = aGen.Gen( _JUMP, 0 );
435cdf0e10cSrcweir bNewGblDefs = sal_False;
436cdf0e10cSrcweir }
437cdf0e10cSrcweir // Statement-Opcode bitte auch am Anfang einer Sub
438cdf0e10cSrcweir if( ( p->bSubr && (eCurTok != STATIC || Peek() == SUB || Peek() == FUNCTION ) ) ||
439cdf0e10cSrcweir eCurTok == SUB || eCurTok == FUNCTION )
440cdf0e10cSrcweir aGen.Statement();
441cdf0e10cSrcweir (this->*( p->Func ) )();
442cdf0e10cSrcweir SbxError nSbxErr = SbxBase::GetError();
443cdf0e10cSrcweir if( nSbxErr )
444cdf0e10cSrcweir SbxBase::ResetError(), Error( (SbError)nSbxErr );
445cdf0e10cSrcweir }
446cdf0e10cSrcweir }
447cdf0e10cSrcweir else
448cdf0e10cSrcweir Error( SbERR_UNEXPECTED, eCurTok );
449cdf0e10cSrcweir }
450cdf0e10cSrcweir
451cdf0e10cSrcweir // Test auf Ende des Statements:
452cdf0e10cSrcweir // Kann auch ein ELSE sein, da vor dem ELSE kein : stehen muss!
453cdf0e10cSrcweir
454cdf0e10cSrcweir if( !IsEos() )
455cdf0e10cSrcweir {
456cdf0e10cSrcweir Peek();
457cdf0e10cSrcweir if( !IsEos() && eCurTok != ELSE )
458cdf0e10cSrcweir {
459cdf0e10cSrcweir // falls das Parsing abgebrochen wurde, bis zum ":" vorgehen:
460cdf0e10cSrcweir Error( SbERR_UNEXPECTED, eCurTok );
461cdf0e10cSrcweir while( !IsEos() ) Next();
462cdf0e10cSrcweir }
463cdf0e10cSrcweir }
464cdf0e10cSrcweir // Der Parser bricht am Ende ab, das naechste Token ist noch nicht
465cdf0e10cSrcweir // geholt!
466cdf0e10cSrcweir return sal_True;
467cdf0e10cSrcweir }
468cdf0e10cSrcweir
469cdf0e10cSrcweir // Innerste With-Variable liefern
GetWithVar()470cdf0e10cSrcweir SbiExprNode* SbiParser::GetWithVar()
471cdf0e10cSrcweir {
472cdf0e10cSrcweir if( pWithVar )
473cdf0e10cSrcweir return pWithVar;
474cdf0e10cSrcweir
475cdf0e10cSrcweir // Sonst im Stack suchen
476cdf0e10cSrcweir SbiParseStack* p = pStack;
477cdf0e10cSrcweir while( p )
478cdf0e10cSrcweir {
479cdf0e10cSrcweir // LoopVar kann zur Zeit nur fuer with sein
480cdf0e10cSrcweir if( p->pWithVar )
481cdf0e10cSrcweir return p->pWithVar;
482cdf0e10cSrcweir p = p->pNext;
483cdf0e10cSrcweir }
484cdf0e10cSrcweir return NULL;
485cdf0e10cSrcweir }
486cdf0e10cSrcweir
487cdf0e10cSrcweir
488cdf0e10cSrcweir // Zuweisung oder Subroutine Call
489cdf0e10cSrcweir
Symbol(const KeywordSymbolInfo * pKeywordSymbolInfo)490cdf0e10cSrcweir void SbiParser::Symbol( const KeywordSymbolInfo* pKeywordSymbolInfo )
491cdf0e10cSrcweir {
492cdf0e10cSrcweir SbiExprMode eMode = bVBASupportOn ? EXPRMODE_STANDALONE : EXPRMODE_STANDARD;
493cdf0e10cSrcweir SbiExpression aVar( this, SbSYMBOL, eMode, pKeywordSymbolInfo );
494cdf0e10cSrcweir
495cdf0e10cSrcweir bool bEQ = ( Peek() == EQ );
496cdf0e10cSrcweir if( !bEQ && bVBASupportOn && aVar.IsBracket() )
497cdf0e10cSrcweir Error( SbERR_EXPECTED, "=" );
498cdf0e10cSrcweir
499cdf0e10cSrcweir RecursiveMode eRecMode = ( bEQ ? PREVENT_CALL : FORCE_CALL );
500cdf0e10cSrcweir bool bSpecialMidHandling = false;
501cdf0e10cSrcweir SbiSymDef* pDef = aVar.GetRealVar();
502cdf0e10cSrcweir if( bEQ && pDef && pDef->GetScope() == SbRTL )
503cdf0e10cSrcweir {
504cdf0e10cSrcweir String aRtlName = pDef->GetName();
505cdf0e10cSrcweir if( aRtlName.EqualsIgnoreCaseAscii("Mid") )
506cdf0e10cSrcweir {
507cdf0e10cSrcweir SbiExprNode* pExprNode = aVar.GetExprNode();
508cdf0e10cSrcweir // SbiNodeType eNodeType;
509cdf0e10cSrcweir if( pExprNode && pExprNode->GetNodeType() == SbxVARVAL )
510cdf0e10cSrcweir {
511cdf0e10cSrcweir SbiExprList* pPar = pExprNode->GetParameters();
512cdf0e10cSrcweir short nParCount = pPar ? pPar->GetSize() : 0;
513cdf0e10cSrcweir if( nParCount == 2 || nParCount == 3 )
514cdf0e10cSrcweir {
515cdf0e10cSrcweir if( nParCount == 2 )
516cdf0e10cSrcweir pPar->addExpression( new SbiExpression( this, -1, SbxLONG ) );
517cdf0e10cSrcweir
518cdf0e10cSrcweir TestToken( EQ );
519cdf0e10cSrcweir pPar->addExpression( new SbiExpression( this ) );
520cdf0e10cSrcweir
521cdf0e10cSrcweir bSpecialMidHandling = true;
522cdf0e10cSrcweir }
523cdf0e10cSrcweir }
524cdf0e10cSrcweir }
525cdf0e10cSrcweir }
526cdf0e10cSrcweir aVar.Gen( eRecMode );
527cdf0e10cSrcweir if( !bSpecialMidHandling )
528cdf0e10cSrcweir {
529cdf0e10cSrcweir if( !bEQ )
530cdf0e10cSrcweir {
531cdf0e10cSrcweir aGen.Gen( _GET );
532cdf0e10cSrcweir }
533cdf0e10cSrcweir else
534cdf0e10cSrcweir {
535cdf0e10cSrcweir // Dann muss es eine Zuweisung sein. Was anderes gibts nicht!
536cdf0e10cSrcweir if( !aVar.IsLvalue() )
537cdf0e10cSrcweir Error( SbERR_LVALUE_EXPECTED );
538cdf0e10cSrcweir TestToken( EQ );
539cdf0e10cSrcweir SbiExpression aExpr( this );
540cdf0e10cSrcweir aExpr.Gen();
541cdf0e10cSrcweir SbiOpcode eOp = _PUT;
542cdf0e10cSrcweir // SbiSymDef* pDef = aVar.GetRealVar();
543cdf0e10cSrcweir if( pDef )
544cdf0e10cSrcweir {
545cdf0e10cSrcweir if( pDef->GetConstDef() )
546cdf0e10cSrcweir Error( SbERR_DUPLICATE_DEF, pDef->GetName() );
547cdf0e10cSrcweir if( pDef->GetType() == SbxOBJECT )
548cdf0e10cSrcweir {
549cdf0e10cSrcweir eOp = _SET;
550cdf0e10cSrcweir if( pDef->GetTypeId() )
551cdf0e10cSrcweir {
552cdf0e10cSrcweir aGen.Gen( _SETCLASS, pDef->GetTypeId() );
553cdf0e10cSrcweir return;
554cdf0e10cSrcweir }
555cdf0e10cSrcweir }
556cdf0e10cSrcweir }
557cdf0e10cSrcweir aGen.Gen( eOp );
558cdf0e10cSrcweir }
559cdf0e10cSrcweir }
560cdf0e10cSrcweir }
561cdf0e10cSrcweir
562cdf0e10cSrcweir // Zuweisungen
563cdf0e10cSrcweir
Assign()564cdf0e10cSrcweir void SbiParser::Assign()
565cdf0e10cSrcweir {
566cdf0e10cSrcweir SbiExpression aLvalue( this, SbLVALUE );
567cdf0e10cSrcweir TestToken( EQ );
568cdf0e10cSrcweir SbiExpression aExpr( this );
569cdf0e10cSrcweir aLvalue.Gen();
570cdf0e10cSrcweir aExpr.Gen();
571cdf0e10cSrcweir sal_uInt16 nLen = 0;
572cdf0e10cSrcweir SbiSymDef* pDef = aLvalue.GetRealVar();
573cdf0e10cSrcweir {
574cdf0e10cSrcweir if( pDef->GetConstDef() )
575cdf0e10cSrcweir Error( SbERR_DUPLICATE_DEF, pDef->GetName() );
576cdf0e10cSrcweir nLen = aLvalue.GetRealVar()->GetLen();
577cdf0e10cSrcweir }
578cdf0e10cSrcweir if( nLen )
579cdf0e10cSrcweir aGen.Gen( _PAD, nLen );
580cdf0e10cSrcweir aGen.Gen( _PUT );
581cdf0e10cSrcweir }
582cdf0e10cSrcweir
583cdf0e10cSrcweir // Zuweisungen einer Objektvariablen
584cdf0e10cSrcweir
Set()585cdf0e10cSrcweir void SbiParser::Set()
586cdf0e10cSrcweir {
587cdf0e10cSrcweir SbiExpression aLvalue( this, SbLVALUE );
588cdf0e10cSrcweir SbxDataType eType = aLvalue.GetType();
589cdf0e10cSrcweir if( eType != SbxOBJECT && eType != SbxEMPTY && eType != SbxVARIANT )
590cdf0e10cSrcweir Error( SbERR_INVALID_OBJECT );
591cdf0e10cSrcweir TestToken( EQ );
592cdf0e10cSrcweir SbiSymDef* pDef = aLvalue.GetRealVar();
593cdf0e10cSrcweir if( pDef && pDef->GetConstDef() )
594cdf0e10cSrcweir Error( SbERR_DUPLICATE_DEF, pDef->GetName() );
595cdf0e10cSrcweir
596cdf0e10cSrcweir SbiToken eTok = Peek();
597cdf0e10cSrcweir if( eTok == NEW )
598cdf0e10cSrcweir {
599cdf0e10cSrcweir Next();
600cdf0e10cSrcweir String aStr;
601cdf0e10cSrcweir SbiSymDef* pTypeDef = new SbiSymDef( aStr );
602cdf0e10cSrcweir TypeDecl( *pTypeDef, sal_True );
603cdf0e10cSrcweir
604cdf0e10cSrcweir aLvalue.Gen();
605cdf0e10cSrcweir // aGen.Gen( _CLASS, pDef->GetTypeId() | 0x8000 );
606cdf0e10cSrcweir aGen.Gen( _CREATE, pDef->GetId(), pTypeDef->GetTypeId() );
607cdf0e10cSrcweir aGen.Gen( _SETCLASS, pDef->GetTypeId() );
608cdf0e10cSrcweir }
609cdf0e10cSrcweir else
610cdf0e10cSrcweir {
611cdf0e10cSrcweir SbiExpression aExpr( this );
612cdf0e10cSrcweir aLvalue.Gen();
613cdf0e10cSrcweir aExpr.Gen();
614cdf0e10cSrcweir // Its a good idea to distinguish between
615cdf0e10cSrcweir // set someting = another &
616cdf0e10cSrcweir // someting = another
617cdf0e10cSrcweir // ( its necessary for vba objects where set is object
618cdf0e10cSrcweir // specific and also doesn't involve processing default params )
619cdf0e10cSrcweir if( pDef->GetTypeId() )
620cdf0e10cSrcweir {
621cdf0e10cSrcweir if ( bVBASupportOn )
622cdf0e10cSrcweir aGen.Gen( _VBASETCLASS, pDef->GetTypeId() );
623cdf0e10cSrcweir else
624cdf0e10cSrcweir aGen.Gen( _SETCLASS, pDef->GetTypeId() );
625cdf0e10cSrcweir }
626cdf0e10cSrcweir else
627cdf0e10cSrcweir {
628cdf0e10cSrcweir if ( bVBASupportOn )
629cdf0e10cSrcweir aGen.Gen( _VBASET );
630cdf0e10cSrcweir else
631cdf0e10cSrcweir aGen.Gen( _SET );
632cdf0e10cSrcweir }
633cdf0e10cSrcweir }
634cdf0e10cSrcweir // aGen.Gen( _SET );
635cdf0e10cSrcweir }
636cdf0e10cSrcweir
637cdf0e10cSrcweir // JSM 07.10.95
LSet()638cdf0e10cSrcweir void SbiParser::LSet()
639cdf0e10cSrcweir {
640cdf0e10cSrcweir SbiExpression aLvalue( this, SbLVALUE );
641cdf0e10cSrcweir if( aLvalue.GetType() != SbxSTRING )
642cdf0e10cSrcweir Error( SbERR_INVALID_OBJECT );
643cdf0e10cSrcweir TestToken( EQ );
644cdf0e10cSrcweir SbiSymDef* pDef = aLvalue.GetRealVar();
645cdf0e10cSrcweir if( pDef && pDef->GetConstDef() )
646cdf0e10cSrcweir Error( SbERR_DUPLICATE_DEF, pDef->GetName() );
647cdf0e10cSrcweir SbiExpression aExpr( this );
648cdf0e10cSrcweir aLvalue.Gen();
649cdf0e10cSrcweir aExpr.Gen();
650cdf0e10cSrcweir aGen.Gen( _LSET );
651cdf0e10cSrcweir }
652cdf0e10cSrcweir
653cdf0e10cSrcweir // JSM 07.10.95
RSet()654cdf0e10cSrcweir void SbiParser::RSet()
655cdf0e10cSrcweir {
656cdf0e10cSrcweir SbiExpression aLvalue( this, SbLVALUE );
657cdf0e10cSrcweir if( aLvalue.GetType() != SbxSTRING )
658cdf0e10cSrcweir Error( SbERR_INVALID_OBJECT );
659cdf0e10cSrcweir TestToken( EQ );
660cdf0e10cSrcweir SbiSymDef* pDef = aLvalue.GetRealVar();
661cdf0e10cSrcweir if( pDef && pDef->GetConstDef() )
662cdf0e10cSrcweir Error( SbERR_DUPLICATE_DEF, pDef->GetName() );
663cdf0e10cSrcweir SbiExpression aExpr( this );
664cdf0e10cSrcweir aLvalue.Gen();
665cdf0e10cSrcweir aExpr.Gen();
666cdf0e10cSrcweir aGen.Gen( _RSET );
667cdf0e10cSrcweir }
668cdf0e10cSrcweir
669cdf0e10cSrcweir // DEFINT, DEFLNG, DEFSNG, DEFDBL, DEFSTR und so weiter
670cdf0e10cSrcweir
DefXXX()671cdf0e10cSrcweir void SbiParser::DefXXX()
672cdf0e10cSrcweir {
673cdf0e10cSrcweir sal_Unicode ch1, ch2;
674cdf0e10cSrcweir SbxDataType t = SbxDataType( eCurTok - DEFINT + SbxINTEGER );
675cdf0e10cSrcweir
676cdf0e10cSrcweir while( !bAbort )
677cdf0e10cSrcweir {
678cdf0e10cSrcweir if( Next() != SYMBOL ) break;
679cdf0e10cSrcweir ch1 = aSym.ToUpperAscii().GetBuffer()[0];
680cdf0e10cSrcweir ch2 = 0;
681cdf0e10cSrcweir if( Peek() == MINUS )
682cdf0e10cSrcweir {
683cdf0e10cSrcweir Next();
684cdf0e10cSrcweir if( Next() != SYMBOL ) Error( SbERR_SYMBOL_EXPECTED );
685cdf0e10cSrcweir else
686cdf0e10cSrcweir {
687cdf0e10cSrcweir ch2 = aSym.ToUpperAscii().GetBuffer()[0];
688cdf0e10cSrcweir //ch2 = aSym.Upper();
689cdf0e10cSrcweir if( ch2 < ch1 ) Error( SbERR_SYNTAX ), ch2 = 0;
690cdf0e10cSrcweir }
691cdf0e10cSrcweir }
692cdf0e10cSrcweir if (!ch2) ch2 = ch1;
693cdf0e10cSrcweir ch1 -= 'A'; ch2 -= 'A';
694cdf0e10cSrcweir for (; ch1 <= ch2; ch1++) eDefTypes[ ch1 ] = t;
695cdf0e10cSrcweir if( !TestComma() ) break;
696cdf0e10cSrcweir }
697cdf0e10cSrcweir }
698cdf0e10cSrcweir
699cdf0e10cSrcweir // STOP/SYSTEM
700cdf0e10cSrcweir
Stop()701cdf0e10cSrcweir void SbiParser::Stop()
702cdf0e10cSrcweir {
703cdf0e10cSrcweir aGen.Gen( _STOP );
704cdf0e10cSrcweir Peek(); // #35694: Nur Peek(), damit EOL in Single-Line-If erkannt wird
705cdf0e10cSrcweir }
706cdf0e10cSrcweir
707cdf0e10cSrcweir // IMPLEMENTS
708cdf0e10cSrcweir
Implements()709cdf0e10cSrcweir void SbiParser::Implements()
710cdf0e10cSrcweir {
711cdf0e10cSrcweir if( !bClassModule )
712cdf0e10cSrcweir {
713cdf0e10cSrcweir Error( SbERR_UNEXPECTED, IMPLEMENTS );
714cdf0e10cSrcweir return;
715cdf0e10cSrcweir }
716cdf0e10cSrcweir
717cdf0e10cSrcweir Peek();
718cdf0e10cSrcweir if( eCurTok != SYMBOL )
719cdf0e10cSrcweir {
720cdf0e10cSrcweir Error( SbERR_SYMBOL_EXPECTED );
721cdf0e10cSrcweir return;
722cdf0e10cSrcweir }
723cdf0e10cSrcweir
724cdf0e10cSrcweir String aImplementedIface = aSym;
725cdf0e10cSrcweir Next();
726cdf0e10cSrcweir if( Peek() == DOT )
727cdf0e10cSrcweir {
728cdf0e10cSrcweir String aDotStr( '.' );
729cdf0e10cSrcweir while( Peek() == DOT )
730cdf0e10cSrcweir {
731cdf0e10cSrcweir aImplementedIface += aDotStr;
732cdf0e10cSrcweir Next();
733cdf0e10cSrcweir SbiToken ePeekTok = Peek();
734cdf0e10cSrcweir if( ePeekTok == SYMBOL || IsKwd( ePeekTok ) )
735cdf0e10cSrcweir {
736cdf0e10cSrcweir Next();
737cdf0e10cSrcweir aImplementedIface += aSym;
738cdf0e10cSrcweir }
739cdf0e10cSrcweir else
740cdf0e10cSrcweir {
741cdf0e10cSrcweir Next();
742cdf0e10cSrcweir Error( SbERR_SYMBOL_EXPECTED );
743cdf0e10cSrcweir break;
744cdf0e10cSrcweir }
745cdf0e10cSrcweir }
746cdf0e10cSrcweir }
747cdf0e10cSrcweir aIfaceVector.push_back( aImplementedIface );
748cdf0e10cSrcweir }
749cdf0e10cSrcweir
EnableCompatibility()750cdf0e10cSrcweir void SbiParser::EnableCompatibility()
751cdf0e10cSrcweir {
752cdf0e10cSrcweir if( !bCompatible )
753cdf0e10cSrcweir AddConstants();
754cdf0e10cSrcweir bCompatible = sal_True;
755cdf0e10cSrcweir }
756cdf0e10cSrcweir
757cdf0e10cSrcweir // OPTION
758cdf0e10cSrcweir
Option()759cdf0e10cSrcweir void SbiParser::Option()
760cdf0e10cSrcweir {
761cdf0e10cSrcweir switch( Next() )
762cdf0e10cSrcweir {
7633d762826SHerbert Dürr case BASIC_EXPLICIT:
764cdf0e10cSrcweir bExplicit = sal_True; break;
765cdf0e10cSrcweir case BASE:
766cdf0e10cSrcweir if( Next() == NUMBER )
767cdf0e10cSrcweir {
768cdf0e10cSrcweir if( nVal == 0 || nVal == 1 )
769cdf0e10cSrcweir {
770cdf0e10cSrcweir nBase = (short) nVal;
771cdf0e10cSrcweir break;
772cdf0e10cSrcweir }
773cdf0e10cSrcweir }
774cdf0e10cSrcweir Error( SbERR_EXPECTED, "0/1" );
775cdf0e10cSrcweir break;
776cdf0e10cSrcweir case PRIVATE:
777cdf0e10cSrcweir {
778cdf0e10cSrcweir String aString = SbiTokenizer::Symbol(Next());
779cdf0e10cSrcweir if( !aString.EqualsIgnoreCaseAscii("Module") )
780cdf0e10cSrcweir Error( SbERR_EXPECTED, "Module" );
781cdf0e10cSrcweir break;
782cdf0e10cSrcweir }
783cdf0e10cSrcweir case COMPARE:
784cdf0e10cSrcweir {
785cdf0e10cSrcweir SbiToken eTok = Next();
786cdf0e10cSrcweir if( eTok == BINARY )
787cdf0e10cSrcweir bText = sal_False;
788cdf0e10cSrcweir else if( eTok == SYMBOL && GetSym().EqualsIgnoreCaseAscii("text") )
789cdf0e10cSrcweir bText = sal_True;
790cdf0e10cSrcweir else
791cdf0e10cSrcweir Error( SbERR_EXPECTED, "Text/Binary" );
792cdf0e10cSrcweir break;
793cdf0e10cSrcweir }
794cdf0e10cSrcweir case COMPATIBLE:
795cdf0e10cSrcweir EnableCompatibility();
796cdf0e10cSrcweir break;
797cdf0e10cSrcweir
798cdf0e10cSrcweir case CLASSMODULE:
799cdf0e10cSrcweir bClassModule = sal_True;
800cdf0e10cSrcweir aGen.GetModule().SetModuleType( com::sun::star::script::ModuleType::CLASS );
801cdf0e10cSrcweir break;
802cdf0e10cSrcweir case VBASUPPORT:
803cdf0e10cSrcweir if( Next() == NUMBER )
804cdf0e10cSrcweir {
805cdf0e10cSrcweir if ( nVal == 1 || nVal == 0 )
806cdf0e10cSrcweir {
807cdf0e10cSrcweir bVBASupportOn = ( nVal == 1 );
808cdf0e10cSrcweir if ( bVBASupportOn )
809cdf0e10cSrcweir EnableCompatibility();
810cdf0e10cSrcweir // if the module setting is different
811cdf0e10cSrcweir // reset it to what the Option tells us
812cdf0e10cSrcweir if ( bVBASupportOn != aGen.GetModule().IsVBACompat() )
813cdf0e10cSrcweir aGen.GetModule().SetVBACompat( bVBASupportOn );
814cdf0e10cSrcweir break;
815cdf0e10cSrcweir }
816cdf0e10cSrcweir }
817cdf0e10cSrcweir Error( SbERR_EXPECTED, "0/1" );
818cdf0e10cSrcweir break;
819cdf0e10cSrcweir default:
820cdf0e10cSrcweir Error( SbERR_BAD_OPTION, eCurTok );
821cdf0e10cSrcweir }
822cdf0e10cSrcweir }
823cdf0e10cSrcweir
addStringConst(SbiSymPool & rPool,const char * pSym,const String & rStr)824cdf0e10cSrcweir void addStringConst( SbiSymPool& rPool, const char* pSym, const String& rStr )
825cdf0e10cSrcweir {
826cdf0e10cSrcweir SbiConstDef* pConst = new SbiConstDef( String::CreateFromAscii( pSym ) );
827cdf0e10cSrcweir pConst->SetType( SbxSTRING );
828cdf0e10cSrcweir pConst->Set( rStr );
829cdf0e10cSrcweir rPool.Add( pConst );
830cdf0e10cSrcweir }
831cdf0e10cSrcweir
addStringConst(SbiSymPool & rPool,const char * pSym,const char * pStr)832cdf0e10cSrcweir inline void addStringConst( SbiSymPool& rPool, const char* pSym, const char* pStr )
833cdf0e10cSrcweir {
834cdf0e10cSrcweir addStringConst( rPool, pSym, String::CreateFromAscii( pStr ) );
835cdf0e10cSrcweir }
836cdf0e10cSrcweir
AddConstants(void)837cdf0e10cSrcweir void SbiParser::AddConstants( void )
838cdf0e10cSrcweir {
839cdf0e10cSrcweir // #113063 Create constant RTL symbols
840cdf0e10cSrcweir addStringConst( aPublics, "vbCr", "\x0D" );
841cdf0e10cSrcweir addStringConst( aPublics, "vbCrLf", "\x0D\x0A" );
842cdf0e10cSrcweir addStringConst( aPublics, "vbFormFeed", "\x0C" );
843cdf0e10cSrcweir addStringConst( aPublics, "vbLf", "\x0A" );
844cdf0e10cSrcweir #if defined(UNX)
845cdf0e10cSrcweir addStringConst( aPublics, "vbNewLine", "\x0A" );
846cdf0e10cSrcweir #else
847cdf0e10cSrcweir addStringConst( aPublics, "vbNewLine", "\x0D\x0A" );
848cdf0e10cSrcweir #endif
849cdf0e10cSrcweir addStringConst( aPublics, "vbNullString", "" );
850cdf0e10cSrcweir addStringConst( aPublics, "vbTab", "\x09" );
851cdf0e10cSrcweir addStringConst( aPublics, "vbVerticalTab", "\x0B" );
852cdf0e10cSrcweir
853cdf0e10cSrcweir // Force length 1 and make char 0 afterwards
854cdf0e10cSrcweir String aNullCharStr( String::CreateFromAscii( " " ) );
855cdf0e10cSrcweir aNullCharStr.SetChar( 0, 0 );
856cdf0e10cSrcweir addStringConst( aPublics, "vbNullChar", aNullCharStr );
857cdf0e10cSrcweir }
858cdf0e10cSrcweir
859cdf0e10cSrcweir // ERROR n
860cdf0e10cSrcweir
ErrorStmnt()861cdf0e10cSrcweir void SbiParser::ErrorStmnt()
862cdf0e10cSrcweir {
863cdf0e10cSrcweir SbiExpression aPar( this );
864cdf0e10cSrcweir aPar.Gen();
865cdf0e10cSrcweir aGen.Gen( _ERROR );
866cdf0e10cSrcweir }
867cdf0e10cSrcweir
868