xref: /trunk/main/sc/source/filter/excel/excform.cxx (revision b77af630)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_scfilt.hxx"
26 #include "excform.hxx"
27 #include <osl/endian.h>
28 
29 #include "cell.hxx"
30 #include "document.hxx"
31 #include "rangenam.hxx"
32 #include "global.hxx"
33 #include "formula/errorcodes.hxx"
34 
35 #include "imp_op.hxx"
36 #include "root.hxx"
37 #include "xltracer.hxx"
38 #include "xihelper.hxx"
39 #include "xilink.hxx"
40 #include "xiname.hxx"
41 
42 using ::std::vector;
43 
44 const sal_uInt16 ExcelToSc::nRowMask = 0x3FFF;
45 const sal_uInt16 ExcelToSc::nLastInd = 399;
46 
47 
48 
49 
Formula25()50 void ImportExcel::Formula25()
51 {
52     XclAddress aXclPos;
53     sal_uInt16  nXF = 0, nFormLen;
54 	double	fCurVal;
55 	sal_uInt8	nFlag0;
56 	sal_Bool	bShrFmla;
57 
58     aIn >> aXclPos;
59 
60     if( GetBiff() == EXC_BIFF2 )
61 	{//						BIFF2
62 		sal_uInt8 nDummy;
63 
64         aIn.Ignore( 3 );
65 
66 		aIn >> fCurVal;
67         aIn.Ignore( 1 );
68 		aIn >> nDummy;
69 		nFormLen = nDummy;
70 		bShrFmla = sal_False;
71 	}
72 	else
73 	{//						BIFF5
74 		aIn >> nXF >> fCurVal >> nFlag0;
75         aIn.Ignore( 5 );
76 
77 		aIn >> nFormLen;
78 
79 		bShrFmla = nFlag0 & 0x08;	// shared or not shared
80 	}
81 
82     Formula( aXclPos, nXF, nFormLen, fCurVal, bShrFmla );
83 }
84 
85 
Formula3()86 void ImportExcel::Formula3()
87 {
88 	Formula4();
89 }
90 
91 
Formula4()92 void ImportExcel::Formula4()
93 {
94     XclAddress aXclPos;
95     sal_uInt16  nXF, nFormLen;
96 	double	fCurVal;
97 	sal_uInt8	nFlag0;
98 
99     aIn >> aXclPos >> nXF >> fCurVal >> nFlag0;
100     aIn.Ignore( 1 );
101 	aIn >> nFormLen;
102 
103     Formula( aXclPos, nXF, nFormLen, fCurVal, sal_False );
104 }
105 
106 
Formula(const XclAddress & rXclPos,sal_uInt16 nXF,sal_uInt16 nFormLen,double & rCurVal,sal_Bool bShrFmla)107 void ImportExcel::Formula( const XclAddress& rXclPos,
108     sal_uInt16 nXF, sal_uInt16 nFormLen, double& rCurVal, sal_Bool bShrFmla )
109 {
110 	ConvErr eErr = ConvOK;
111 
112     ScAddress aScPos( ScAddress::UNINITIALIZED );
113     if( GetAddressConverter().ConvertAddress( aScPos, rXclPos, GetCurrScTab(), true ) )
114 	{
115 		// jetzt steht Lesemarke auf Formel, Laenge in nFormLen
116         const ScTokenArray* pErgebnis = 0;
117 		sal_Bool				bConvert;
118 
119         pFormConv->Reset( aScPos );
120 
121 		if( bShrFmla )
122             bConvert = !pFormConv->GetShrFmla( pErgebnis, maStrm, nFormLen );
123 		else
124             bConvert = sal_True;
125 
126         if( bConvert )
127             eErr = pFormConv->Convert( pErgebnis, maStrm, nFormLen, true, FT_CellFormula);
128 
129         ScFormulaCell*		pZelle = NULL;
130 
131 		if( pErgebnis )
132 		{
133             pZelle = new ScFormulaCell( pD, aScPos, pErgebnis );
134             pD->PutCell( aScPos.Col(), aScPos.Row(), aScPos.Tab(), pZelle, (sal_Bool)sal_True );
135 		}
136 		else
137 		{
138 			CellType		eCellType;
139 			ScBaseCell*		pBaseCell;
140             pD->GetCellType( aScPos.Col(), aScPos.Row(), aScPos.Tab(), eCellType );
141 			if( eCellType == CELLTYPE_FORMULA )
142 			{
143                 pD->GetCell( aScPos.Col(), aScPos.Row(), aScPos.Tab(), pBaseCell );
144 				pZelle = ( ScFormulaCell* ) pBaseCell;
145 				if( pZelle )
146 					pZelle->AddRecalcMode( RECALCMODE_ONLOAD_ONCE );
147 			}
148 		}
149 
150 		if( pZelle )
151 		{
152 			if( eErr != ConvOK )
153 				ExcelToSc::SetError( *pZelle, eErr );
154 #if 0
155             else
156                 ExcelToSc::SetCurVal( *pZelle, rCurVal );
157 #else
158             (void)rCurVal;
159 #endif
160 		}
161 
162         GetXFRangeBuffer().SetXF( aScPos, nXF );
163 	}
164 }
165 
166 
167 
168 
ExcelToSc(const XclImpRoot & rRoot)169 ExcelToSc::ExcelToSc( const XclImpRoot& rRoot ) :
170     ExcelConverterBase( 512 ),
171     XclImpRoot( rRoot ),
172     maFuncProv( rRoot ),
173     meBiff( rRoot.GetBiff() )
174 {
175 }
176 
~ExcelToSc()177 ExcelToSc::~ExcelToSc()
178 {
179 }
180 
GetDummy(const ScTokenArray * & pErgebnis)181 void ExcelToSc::GetDummy( const ScTokenArray*& pErgebnis )
182 {
183     aPool.Store( CREATE_STRING( "Dummy()" ) );
184 	aPool >> aStack;
185 	pErgebnis = aPool[ aStack.Get() ];
186 }
187 
188 
189 // if bAllowArrays is false stream seeks to first byte after <nFormulaLen>
190 // otherwise it will seek to the first byte after the additional content (eg
191 // inline arrays) following <nFormulaLen>
Convert(const ScTokenArray * & pErgebnis,XclImpStream & aIn,sal_Size nFormulaLen,bool bAllowArrays,const FORMULA_TYPE eFT)192 ConvErr ExcelToSc::Convert( const ScTokenArray*& pErgebnis, XclImpStream& aIn, sal_Size nFormulaLen, bool bAllowArrays, const FORMULA_TYPE eFT )
193 {
194     RootData&       rR = GetOldRoot();
195 	sal_uInt8			nOp, nLen, nByte;
196     sal_uInt16          nUINT16;
197 	sal_Int16			nINT16;
198 	double			fDouble;
199 	String			aString;
200 	sal_Bool			bError = sal_False;
201 	sal_Bool			bArrayFormula = sal_False;
202 	TokenId			nMerk0;
203 	const sal_Bool		bRangeName = eFT == FT_RangeName;
204 	const sal_Bool		bSharedFormula = eFT == FT_SharedFormula;
205 	const sal_Bool		bConditional = eFT == FT_Conditional;
206 	const sal_Bool		bRNorSF = bRangeName || bSharedFormula || bConditional;
207 
208 	ScSingleRefData		aSRD;
209 	ScComplexRefData		aCRD;
210     ExtensionTypeVec    aExtensions;
211 
212 	bExternName = sal_False;
213 
214 	if( eStatus != ConvOK )
215 	{
216         aIn.Ignore( nFormulaLen );
217 		return eStatus;
218 	}
219 
220 	if( nFormulaLen == 0 )
221 	{
222         aPool.Store( CREATE_STRING( "-/-" ) );
223 		aPool >> aStack;
224 		pErgebnis = aPool[ aStack.Get() ];
225 		return ConvOK;
226 	}
227 
228     sal_Size nEndPos = aIn.GetRecPos() + nFormulaLen;
229 
230     while( (aIn.GetRecPos() < nEndPos) && !bError )
231 	{
232 		aIn >> nOp;
233 
234         // #98524# always reset flags
235         aSRD.InitFlags();
236         aCRD.InitFlags();
237 
238 		switch( nOp )	//								Buch Seite:
239 		{			//										SDK4 SDK5
240 			case 0x01: // Array Formula							[325    ]
241 					   // Array Formula or Shared Formula		[    277]
242 			case 0x02: // Data Table							[325 277]
243 				nUINT16 = 3;
244 
245                 if( meBiff != EXC_BIFF2 )
246 					nUINT16++;
247 
248                 aIn.Ignore( nUINT16 );
249 
250 				bArrayFormula = sal_True;
251 				break;
252 			case 0x03: // Addition								[312 264]
253 				aStack >> nMerk0;
254 				aPool <<  aStack << ocAdd << nMerk0;
255 				aPool >> aStack;
256 				break;
257 			case 0x04: // Subtraction							[313 264]
258 				// SECOMD-TOP minus TOP
259 				aStack >> nMerk0;
260 				aPool << aStack << ocSub << nMerk0;
261 				aPool >> aStack;
262 				break;
263 			case 0x05: // Multiplication						[313 264]
264 				aStack >> nMerk0;
265 				aPool << aStack << ocMul << nMerk0;
266 				aPool >> aStack;
267 				break;
268 			case 0x06: // Division								[313 264]
269 				// divide TOP by SECOND-TOP
270 				aStack >> nMerk0;
271 				aPool << aStack << ocDiv << nMerk0;
272 				aPool >> aStack;
273 				break;
274 			case 0x07: // Exponetiation							[313 265]
275 				// raise SECOND-TOP to power of TOP
276 				aStack >> nMerk0;
277 				aPool << aStack << ocPow << nMerk0;
278 				aPool >> aStack;
279 				break;
280 			case 0x08: // Concatenation							[313 265]
281 				// append TOP to SECOND-TOP
282 				aStack >> nMerk0;
283 				aPool << aStack << ocAmpersand << nMerk0;
284 				aPool >> aStack;
285 				break;
286 			case 0x09: // Less Than								[313 265]
287 				// SECOND-TOP < TOP
288 				aStack >> nMerk0;
289 				aPool << aStack << ocLess << nMerk0;
290 				aPool >> aStack;
291 				break;
292 			case 0x0A: // Less Than or Equal					[313 265]
293 				// SECOND-TOP <= TOP
294 				aStack >> nMerk0;
295 				aPool << aStack << ocLessEqual << nMerk0;
296 				aPool >> aStack;
297 				break;
298 			case 0x0B: // Equal									[313 265]
299 				// SECOND-TOP == TOP
300 				aStack >> nMerk0;
301 				aPool << aStack << ocEqual << nMerk0;
302 				aPool >> aStack;
303 				break;
304 			case 0x0C: // Greater Than or Equal					[313 265]
305 				// SECOND-TOP == TOP
306 				aStack >> nMerk0;
307 				aPool << aStack << ocGreaterEqual << nMerk0;
308 				aPool >> aStack;
309 				break;
310 			case 0x0D: // Greater Than							[313 265]
311 				// SECOND-TOP == TOP
312 				aStack >> nMerk0;
313 				aPool << aStack << ocGreater << nMerk0;
314 				aPool >> aStack;
315 				break;
316 			case 0x0E: // Not Equal								[313 265]
317 				// SECOND-TOP == TOP
318 				aStack >> nMerk0;
319 				aPool << aStack << ocNotEqual << nMerk0;
320 				aPool >> aStack;
321 				break;
322 			case 0x0F: // Intersection							[314 265]
323 				aStack >> nMerk0;
324 				aPool << aStack << ocIntersect << nMerk0;
325 				aPool >> aStack;
326 				break;
327 			case 0x10: // Union									[314 265]
328 				// ocSep behelfsweise statt 'ocUnion'
329 				aStack >> nMerk0;
330 //#100928#      aPool << ocOpen << aStack << ocSep << nMerk0 << ocClose;
331                 aPool << aStack << ocSep << nMerk0;
332 					// doesn't fit exactly, but is more Excel-like
333 				aPool >> aStack;
334 				break;
335 			case 0x11: // Range									[314 265]
336 				aStack >> nMerk0;
337 				aPool << aStack << ocRange << nMerk0;
338 				aPool >> aStack;
339 				break;
340 			case 0x12: // Unary Plus							[312 264]
341                 aPool << ocAdd << aStack;
342                 aPool >> aStack;
343 				break;
344 			case 0x13: // Unary Minus							[312 264]
345 				aPool << ocNegSub << aStack;
346 				aPool >> aStack;
347 				break;
348 			case 0x14: // Percent Sign							[312 264]
349                 aPool << aStack << ocPercentSign;
350 				aPool >> aStack;
351 				break;
352 			case 0x15: // Parenthesis							[326 278]
353 				aPool << ocOpen << aStack << ocClose;
354 				aPool >> aStack;
355 				break;
356 			case 0x16: // Missing Argument						[314 266]
357 				aPool << ocMissing;
358 				aPool >> aStack;
359                 GetTracer().TraceFormulaMissingArg();
360 				break;
361 			case 0x17: // String Constant						[314 266]
362 				aIn >> nLen;
363                 aString = aIn.ReadRawByteString( nLen );
364 
365 				aStack << aPool.Store( aString );
366 				break;
367 			case 0x19: // Special Attribute						[327 279]
368 			{
369 				sal_uInt16	nData, nFakt;
370 				sal_uInt8	nOpt;
371 
372 				aIn >> nOpt;
373 
374                 if( meBiff == EXC_BIFF2 )
375 				{
376 					nData = aIn.ReaduInt8();
377 					nFakt = 1;
378 				}
379 				else
380 				{
381 					aIn >> nData;
382 					nFakt = 2;
383 				}
384 
385 				if( nOpt & 0x04 )
386 				{// nFakt -> Bytes oder Words ueberlesen	AttrChoose
387 					nData++;
388                     aIn.Ignore( nData * nFakt );
389 				}
390 				else if( nOpt & 0x10 )						// AttrSum
391 					DoMulArgs( ocSum, 1 );
392 			}
393 				break;
394 			case 0x1A: // External Reference					[330    ]
395                 switch( meBiff )
396 				{
397                     case EXC_BIFF2: aIn.Ignore( 7 );    break;
398                     case EXC_BIFF3:
399                     case EXC_BIFF4: aIn.Ignore( 10 );   break;
400                     case EXC_BIFF5:
401 						DBG_WARNING( "-ExcelToSc::Convert(): 0x1A gibt's nicht in Biff5!" );
402 					default:
403 						DBG_WARNING( "-ExcelToSc::Convert(): Ein wenig vergesslich, was?" );
404 				}
405 				break;
406 			case 0x1B: // End External Reference				[330    ]
407                 switch( meBiff )
408 				{
409                     case EXC_BIFF2: aIn.Ignore( 3 );    break;
410                     case EXC_BIFF3:
411                     case EXC_BIFF4: aIn.Ignore( 4 );    break;
412                     case EXC_BIFF5:
413 						DBG_WARNING( "-ExcelToSc::Convert(): 0x1B gibt's nicht in Biff5!" );
414 					default:
415 						DBG_WARNING( "-ExcelToSc::Convert(): Ein wenig vergesslich, was?" );
416 				}
417 				break;
418 			case 0x1C: // Error Value							[314 266]
419 			{
420 				aIn >> nByte;
421 #if 0   // erAck
422                 aPool.StoreError( XclTools::GetScErrorCode( nByte ) );
423 #else
424 				DefTokenId			eOc;
425 				switch( nByte )
426 				{
427                     case EXC_ERR_NULL:
428                     case EXC_ERR_DIV0:
429                     case EXC_ERR_VALUE:
430                     case EXC_ERR_REF:
431                     case EXC_ERR_NAME:
432                     case EXC_ERR_NUM:   eOc = ocStop;       break;
433                     case EXC_ERR_NA:    eOc = ocNotAvail;   break;
434                     default:            eOc = ocNoName;
435 				}
436 				aPool << eOc;
437 				if( eOc != ocStop )
438 					aPool << ocOpen << ocClose;
439 #endif
440 				aPool >> aStack;
441 			}
442 				break;
443 			case 0x1D: // Boolean								[315 266]
444 				aIn >> nByte;
445 				if( nByte == 0 )
446 					aPool << ocFalse << ocOpen << ocClose;
447 				else
448 					aPool << ocTrue << ocOpen << ocClose;
449 				aPool >> aStack;
450 				break;
451 			case 0x1E: // Integer								[315 266]
452 				aIn >> nUINT16;
453 				aStack << aPool.Store( ( double ) nUINT16 );
454 				break;
455 			case 0x1F: // Number								[315 266]
456 				aIn >> fDouble;
457 				aStack << aPool.Store( fDouble );
458 				break;
459 			case 0x40:
460 			case 0x60:
461             case 0x20: // Array Constant						[317 268]
462                 aIn >> nByte >> nUINT16;
463                 aIn.Ignore( (meBiff == EXC_BIFF2) ? 3 : 4 );
464                 if( bAllowArrays )
465                 {
466                     aStack << aPool.StoreMatrix();
467                     aExtensions.push_back( EXTENSION_ARRAY );
468                 }
469                 else
470                 {
471                     aPool << ocBad;
472                     aPool >> aStack;
473                 }
474                 break;
475 			case 0x41:
476 			case 0x61:
477 			case 0x21: // Function, Fixed Number of Arguments	[333 282]
478             {
479                 sal_uInt16 nXclFunc;
480                 if( meBiff <= EXC_BIFF3 )
481                     nXclFunc = aIn.ReaduInt8();
482                 else
483                     aIn >> nXclFunc;
484                 if( const XclFunctionInfo* pFuncInfo = maFuncProv.GetFuncInfoFromXclFunc( nXclFunc ) )
485                     DoMulArgs( pFuncInfo->meOpCode, pFuncInfo->mnMaxParamCount, pFuncInfo->mnMinParamCount );
486                 else
487                     DoMulArgs( ocNoName, 0 );
488             }
489             break;
490 			case 0x42:
491 			case 0x62:
492 			case 0x22: // Function, Variable Number of Arg.		[333 283]
493             {
494                 sal_uInt16 nXclFunc;
495                 sal_uInt8 nParamCount;
496                 aIn >> nParamCount;
497                 nParamCount &= 0x7F;
498                 if( meBiff <= EXC_BIFF3 )
499                     nXclFunc = aIn.ReaduInt8();
500                 else
501                     aIn >> nXclFunc;
502                 if( const XclFunctionInfo* pFuncInfo = maFuncProv.GetFuncInfoFromXclFunc( nXclFunc ) )
503                     DoMulArgs( pFuncInfo->meOpCode, nParamCount, pFuncInfo->mnMinParamCount );
504                 else
505                     DoMulArgs( ocNoName, 0 );
506             }
507             break;
508 			case 0x43:
509 			case 0x63:
510 			case 0x23: // Name									[318 269]
511             {
512 				aIn >> nUINT16;
513                 switch( meBiff )
514 				{
515                     case EXC_BIFF2: aIn.Ignore( 5 );    break;
516                     case EXC_BIFF3:
517                     case EXC_BIFF4: aIn.Ignore( 8 );    break;
518                     case EXC_BIFF5: aIn.Ignore( 12 );   break;
519 					default:
520 						DBG_ERROR(
521 						"-ExcelToSc::Convert(): Ein wenig vergesslich, was?" );
522 				}
523                 const XclImpName* pName = GetNameManager().GetName( nUINT16 );
524 				if(pName && !pName->GetScRangeData())
525 				    aStack << aPool.Store( ocMacro, pName->GetXclName() );
526 				else
527 				    aStack << aPool.Store( nUINT16 );
528 			}
529 				break;
530 			case 0x44:
531 			case 0x64:
532 			case 0x24: // Cell Reference						[319 270]
533 			case 0x4A:
534 			case 0x6A:
535 			case 0x2A: // Deleted Cell Reference				[323 273]
536 				aIn >> nUINT16 >> nByte;
537 				aSRD.nCol = static_cast<SCsCOL>(nByte);
538 				aSRD.nRow = nUINT16 & 0x3FFF;
539 				aSRD.nRelTab = 0;
540 				aSRD.SetTabRel( sal_True );
541 				aSRD.SetFlag3D( bRangeName );
542 
543 				ExcRelToScRel( nUINT16, nByte, aSRD, bRangeName );
544 
545 				switch ( nOp )
546 				{
547 					case 0x4A:
548 					case 0x6A:
549 					case 0x2A: // Deleted Cell Reference	 	[323 273]
550 						// no information which part is deleted, set both
551 						aSRD.SetColDeleted( sal_True );
552 						aSRD.SetRowDeleted( sal_True );
553 				}
554 
555 				aStack << aPool.Store( aSRD );
556 				break;
557 			case 0x45:
558 			case 0x65:
559 			case 0x25: // Area Reference						[320 270]
560 			case 0x4B:
561 			case 0x6B:
562 			case 0x2B: // Deleted Area Refernce					[323 273]
563 			{
564 				sal_uInt16			nRowFirst, nRowLast;
565 				sal_uInt8			nColFirst, nColLast;
566 				ScSingleRefData&	rSRef1 = aCRD.Ref1;
567 				ScSingleRefData&	rSRef2 = aCRD.Ref2;
568 
569 				aIn >> nRowFirst >> nRowLast >> nColFirst >> nColLast;
570 
571 				rSRef1.nRelTab = rSRef2.nRelTab = 0;
572 				rSRef1.SetTabRel( sal_True );
573 				rSRef2.SetTabRel( sal_True );
574 				rSRef1.SetFlag3D( bRangeName );
575 				rSRef2.SetFlag3D( bRangeName );
576 
577 				ExcRelToScRel( nRowFirst, nColFirst, aCRD.Ref1, bRangeName );
578 				ExcRelToScRel( nRowLast, nColLast, aCRD.Ref2, bRangeName );
579 
580 				if( IsComplColRange( nColFirst, nColLast ) )
581 					SetComplCol( aCRD );
582 				else if( IsComplRowRange( nRowFirst, nRowLast ) )
583 					SetComplRow( aCRD );
584 
585 				switch ( nOp )
586 				{
587 					case 0x4B:
588 					case 0x6B:
589 					case 0x2B: // Deleted Area Refernce			[323 273]
590 						// no information which part is deleted, set all
591 						rSRef1.SetColDeleted( sal_True );
592 						rSRef1.SetRowDeleted( sal_True );
593 						rSRef2.SetColDeleted( sal_True );
594 						rSRef2.SetRowDeleted( sal_True );
595 				}
596 
597 				aStack << aPool.Store( aCRD );
598 			}
599 				break;
600 			case 0x46:
601 			case 0x66:
602 			case 0x26: // Constant Reference Subexpression		[321 271]
603                 aExtensions.push_back( EXTENSION_MEMAREA );
604                 // fall through
605 
606 			case 0x47:
607 			case 0x67:
608 			case 0x27: // Erroneous Constant Reference Subexpr.	[322 272]
609 			case 0x48:
610 			case 0x68:
611 			case 0x28: // Incomplete Constant Reference Subexpr.[331 281]
612                 aIn.Ignore( (meBiff == EXC_BIFF2) ? 4 : 6 );
613 				break;
614 			case 0x4C:
615 			case 0x6C:
616 			case 0x2C: // Cell Reference Within a Name			[323    ]
617 					   // Cell Reference Within a Shared Formula[    273]
618 			{
619 				aIn >> nUINT16 >> nByte;	// >> Attribute, Row >> Col
620 
621 				aSRD.nRelTab = 0;
622 				aSRD.SetTabRel( sal_True );
623 				aSRD.SetFlag3D( bRangeName );
624 
625 				ExcRelToScRel( nUINT16, nByte, aSRD, bRNorSF );
626 
627 				aStack << aPool.Store( aSRD );
628 			}
629 				break;
630 			case 0x4D:
631 			case 0x6D:
632 			case 0x2D: // Area Reference Within a Name			[324    ]
633 			{	   // Area Reference Within a Shared Formula[    274]
634 				sal_uInt16					nRowFirst, nRowLast;
635 				sal_uInt8					nColFirst, nColLast;
636 
637 				aCRD.Ref1.nRelTab = aCRD.Ref2.nRelTab = 0;
638 				aCRD.Ref1.SetTabRel( sal_True );
639 				aCRD.Ref2.SetTabRel( sal_True );
640 				aCRD.Ref1.SetFlag3D( bRangeName );
641 				aCRD.Ref2.SetFlag3D( bRangeName );
642 
643 				aIn >> nRowFirst >> nRowLast >> nColFirst >> nColLast;
644 
645 				ExcRelToScRel( nRowFirst, nColFirst, aCRD.Ref1, bRNorSF );
646 				ExcRelToScRel( nRowLast, nColLast, aCRD.Ref2, bRNorSF );
647 
648 				if( IsComplColRange( nColFirst, nColLast ) )
649 					SetComplCol( aCRD );
650 				else if( IsComplRowRange( nRowFirst, nRowLast ) )
651 					SetComplRow( aCRD );
652 
653 				aStack << aPool.Store( aCRD );
654 			}
655 				break;
656             case 0x49:
657             case 0x69:
658             case 0x29: // Variable Reference Subexpression      [331 281]
659 			case 0x4E:
660 			case 0x6E:
661 			case 0x2E: // Reference Subexpression Within a Name	[332 282]
662 			case 0x4F:
663 			case 0x6F:
664 			case 0x2F: // Incomplete Reference Subexpression...	[332 282]
665                 aIn.Ignore( (meBiff == EXC_BIFF2) ? 1 : 2 );
666 				break;
667 			case 0x58:
668 			case 0x78:
669 			case 0x38: // Command-Equivalent Function			[333    ]
670 				aString.AssignAscii( "COMM_EQU_FUNC" );
671 				aIn >> nByte;
672 				aString += String::CreateFromInt32( nByte );
673 				aIn >> nByte;
674 				aStack << aPool.Store( aString );
675 				DoMulArgs( ocPush, nByte + 1 );
676 				break;
677 			case 0x59:
678 			case 0x79:
679 			case 0x39: // Name or External Name					[    275]
680 				aIn >> nINT16;
681                 aIn.Ignore( 8 );
682 				aIn >> nUINT16;
683 				if( nINT16 >= 0 )
684 				{
685                     const ExtName* pExtName = rR.pExtNameBuff->GetNameByIndex( nINT16, nUINT16 );
686 					if( pExtName && pExtName->IsDDE() &&
687                         rR.pExtSheetBuff->IsLink( ( sal_uInt16 ) nINT16 ) )
688 					{
689 						String			aAppl, aExtDoc;
690 						TokenId			nPar1, nPar2;
691 
692                         rR.pExtSheetBuff->GetLink( ( sal_uInt16 ) nINT16 , aAppl, aExtDoc );
693 						nPar1 = aPool.Store( aAppl );
694 						nPar2 = aPool.Store( aExtDoc );
695 						nMerk0 = aPool.Store( pExtName->aName );
696 						aPool	<< ocDde << ocOpen << nPar1 << ocSep << nPar2 << ocSep
697 								<< nMerk0 << ocClose;
698 
699                         GetDoc().CreateDdeLink( aAppl, aExtDoc, pExtName->aName, SC_DDE_DEFAULT );
700 					}
701 					else
702 						aPool << ocBad;
703 
704 					aPool >> aStack;
705 				}
706 				else
707                     aStack << aPool.Store( nUINT16 );
708                 aIn.Ignore( 12 );
709 				break;
710 			case 0x5A:
711 			case 0x7A:
712 			case 0x3A: // 3-D Cell Reference					[    275]
713 			case 0x5C:
714 			case 0x7C:
715 			case 0x3C: // Deleted 3-D Cell Reference			[    277]
716 			{
717 				sal_uInt16			nTabFirst, nTabLast, nRow;
718 				sal_Int16			nExtSheet;
719 				sal_uInt8			nCol;
720 
721 				aIn >> nExtSheet;
722                 aIn.Ignore( 8 );
723 				aIn >> nTabFirst >> nTabLast >> nRow >> nCol;
724 
725 				if( nExtSheet >= 0 )
726 				{	// von extern
727                     if( rR.pExtSheetBuff->GetScTabIndex( nExtSheet, nTabLast ) )
728 					{
729 						nTabFirst = nTabLast;
730 						nExtSheet = 0;		// gefunden
731 					}
732 					else
733 					{
734 						aPool << ocBad;
735 						aPool >> aStack;
736 						nExtSheet = 1;		// verhindert Erzeugung einer SingleRef
737 					}
738 				}
739 
740 				if( nExtSheet <= 0 )
741 				{	// in aktuellem Workbook
742 					aSRD.nTab = static_cast<SCTAB>(nTabFirst);
743                     aSRD.SetFlag3D( sal_True );
744 					aSRD.SetTabRel( sal_False );
745 
746 					ExcRelToScRel( nRow, nCol, aSRD, bRangeName );
747 
748 					switch ( nOp )
749 					{
750 						case 0x5C:
751 						case 0x7C:
752 						case 0x3C: // Deleted 3-D Cell Reference	[    277]
753 							// no information which part is deleted, set both
754 							aSRD.SetColDeleted( sal_True );
755 							aSRD.SetRowDeleted( sal_True );
756 					}
757 					if ( !ValidTab(static_cast<SCTAB>(nTabFirst)) )
758 						aSRD.SetTabDeleted( sal_True );
759 
760 					if( nTabLast != nTabFirst )
761 					{
762                         aCRD.Ref1 = aCRD.Ref2 = aSRD;
763 						aCRD.Ref2.nTab = static_cast<SCTAB>(nTabLast);
764 						aCRD.Ref2.SetTabDeleted( !ValidTab(static_cast<SCTAB>(nTabLast)) );
765 						aStack << aPool.Store( aCRD );
766 					}
767 					else
768 						aStack << aPool.Store( aSRD );
769 				}
770 			}
771 
772 				break;
773 			case 0x5B:
774 			case 0x7B:
775 			case 0x3B: // 3-D Area Reference					[    276]
776 			case 0x5D:
777 			case 0x7D:
778 			case 0x3D: // Deleted 3-D Area Reference			[    277]
779 			{
780 				sal_uInt16		nTabFirst, nTabLast, nRowFirst, nRowLast;
781 				sal_Int16		nExtSheet;
782 				sal_uInt8		nColFirst, nColLast;
783 
784 				aIn >> nExtSheet;
785                 aIn.Ignore( 8 );
786 				aIn >> nTabFirst >> nTabLast >> nRowFirst >> nRowLast
787 					>> nColFirst >> nColLast;
788 
789 				if( nExtSheet >= 0 )
790 					// von extern
791 				{
792                     if( rR.pExtSheetBuff->GetScTabIndex( nExtSheet, nTabLast ) )
793 					{
794 						nTabFirst = nTabLast;
795 						nExtSheet = 0;		// gefunden
796 					}
797 					else
798 					{
799 						aPool << ocBad;
800 						aPool >> aStack;
801 						nExtSheet = 1;		// verhindert Erzeugung einer CompleteRef
802 					}
803 				}
804 
805 				if( nExtSheet <= 0 )
806 				{// in aktuellem Workbook
807 					// erster Teil des Bereichs
808 					ScSingleRefData&	rR1 = aCRD.Ref1;
809 					ScSingleRefData&	rR2 = aCRD.Ref2;
810 
811 					rR1.nTab = static_cast<SCTAB>(nTabFirst);
812 					rR2.nTab = static_cast<SCTAB>(nTabLast);
813                     rR1.SetFlag3D( sal_True );
814 					rR1.SetTabRel( sal_False );
815                     rR2.SetFlag3D( nTabFirst != nTabLast );
816 					rR2.SetTabRel( sal_False );
817 
818 					ExcRelToScRel( nRowFirst, nColFirst, aCRD.Ref1, bRangeName );
819 					ExcRelToScRel( nRowLast, nColLast, aCRD.Ref2, bRangeName );
820 
821 					if( IsComplColRange( nColFirst, nColLast ) )
822 						SetComplCol( aCRD );
823 					else if( IsComplRowRange( nRowFirst, nRowLast ) )
824 						SetComplRow( aCRD );
825 
826 					switch ( nOp )
827 					{
828 						case 0x5D:
829 						case 0x7D:
830 						case 0x3D: // Deleted 3-D Area Reference	[    277]
831 						   	// no information which part is deleted, set all
832 							rR1.SetColDeleted( sal_True );
833 							rR1.SetRowDeleted( sal_True );
834 							rR2.SetColDeleted( sal_True );
835 							rR2.SetRowDeleted( sal_True );
836 					}
837 					if ( !ValidTab(static_cast<SCTAB>(nTabFirst)) )
838 						rR1.SetTabDeleted( sal_True );
839 					if ( !ValidTab(static_cast<SCTAB>(nTabLast)) )
840 						rR2.SetTabDeleted( sal_True );
841 
842 					aStack << aPool.Store( aCRD );
843 				}//ENDE in aktuellem Workbook
844 			}
845 				break;
846 			default: bError = sal_True;
847 		}
848 		bError |= !aIn.IsValid();
849 	}
850 
851 	ConvErr eRet;
852 
853 	if( bError )
854 	{
855 		aPool << ocBad;
856 		aPool >> aStack;
857 		pErgebnis = aPool[ aStack.Get() ];
858 		eRet = ConvErrNi;
859 	}
860     else if( aIn.GetRecPos() != nEndPos )
861 	{
862 		aPool << ocBad;
863 		aPool >> aStack;
864 		pErgebnis = aPool[ aStack.Get() ];
865 		eRet = ConvErrCount;
866 	}
867 	else if( bExternName )
868 	{
869 		pErgebnis = aPool[ aStack.Get() ];
870 		eRet = ConvErrExternal;
871 	}
872 	else if( bArrayFormula )
873 	{
874 		pErgebnis = NULL;
875 		eRet = ConvOK;
876 	}
877 	else
878 	{
879 		pErgebnis = aPool[ aStack.Get() ];
880 		eRet = ConvOK;
881 	}
882 
883     aIn.Seek( nEndPos );
884 
885     if( eRet == ConvOK )
886         ReadExtensions( aExtensions, aIn );
887 
888 	return eRet;
889 }
890 
891 
892 // stream seeks to first byte after <nFormulaLen>
Convert(_ScRangeListTabs & rRangeList,XclImpStream & aIn,sal_Size nFormulaLen,const FORMULA_TYPE eFT)893 ConvErr ExcelToSc::Convert( _ScRangeListTabs& rRangeList, XclImpStream& aIn, sal_Size nFormulaLen, const FORMULA_TYPE eFT )
894 {
895     RootData&       rR = GetOldRoot();
896 	sal_uInt8			nOp, nLen;
897     sal_Size        nIgnore;
898 	sal_uInt16			nUINT16;
899 	sal_uInt8			nByte;
900 	sal_Bool			bError = sal_False;
901 	sal_Bool			bArrayFormula = sal_False;
902 	const sal_Bool		bRangeName = eFT == FT_RangeName;
903 	const sal_Bool		bSharedFormula = eFT == FT_SharedFormula;
904 	const sal_Bool		bRNorSF = bRangeName || bSharedFormula;
905 
906 	ScSingleRefData	aSRD;
907 	ScComplexRefData	aCRD;
908 	aCRD.Ref1.nTab = aCRD.Ref2.nTab = aEingPos.Tab();
909 
910 	bExternName = sal_False;
911 
912 	if( eStatus != ConvOK )
913 	{
914         aIn.Ignore( nFormulaLen );
915 		return eStatus;
916 	}
917 
918 	if( nFormulaLen == 0 )
919 		return ConvOK;
920 
921     sal_Size nEndPos = aIn.GetRecPos() + nFormulaLen;
922 
923     while( (aIn.GetRecPos() < nEndPos) && !bError )
924 	{
925 		aIn >> nOp;
926 		nIgnore = 0;
927 
928         // #98524# always reset flags
929         aSRD.InitFlags();
930         aCRD.InitFlags();
931 
932 		switch( nOp )	//								Buch Seite:
933 		{			//										SDK4 SDK5
934 			case 0x01: // Array Formula							[325    ]
935 					   // Array Formula or Shared Formula		[    277]
936                 nIgnore = (meBiff == EXC_BIFF2) ? 3 : 4;
937 				bArrayFormula = sal_True;
938 				break;
939 			case 0x02: // Data Table							[325 277]
940                 nIgnore = (meBiff == EXC_BIFF2) ? 3 : 4;
941 				break;
942 			case 0x03: // Addition								[312 264]
943 			case 0x04: // Subtraction							[313 264]
944 			case 0x05: // Multiplication						[313 264]
945 			case 0x06: // Division								[313 264]
946 			case 0x07: // Exponetiation							[313 265]
947 			case 0x08: // Concatenation							[313 265]
948 			case 0x09: // Less Than								[313 265]
949 			case 0x0A: // Less Than or Equal					[313 265]
950 			case 0x0B: // Equal									[313 265]
951 			case 0x0C: // Greater Than or Equal					[313 265]
952 			case 0x0D: // Greater Than							[313 265]
953 			case 0x0E: // Not Equal								[313 265]
954 			case 0x0F: // Intersection							[314 265]
955 			case 0x10: // Union									[314 265]
956 			case 0x11: // Range									[314 265]
957 			case 0x12: // Unary Plus							[312 264]
958 			case 0x13: // Unary Minus							[312 264]
959 			case 0x14: // Percent Sign							[312 264]
960 			case 0x15: // Parenthesis							[326 278]
961 			case 0x16: // Missing Argument						[314 266]
962 				break;
963 			case 0x17: // String Constant						[314 266]
964 				aIn >> nLen;
965 				nIgnore = nLen;
966 				break;
967 			case 0x19: // Special Attribute						[327 279]
968 			{
969 				sal_uInt16 nData, nFakt;
970 				sal_uInt8 nOpt;
971 
972 				aIn >> nOpt;
973 
974                 if( meBiff == EXC_BIFF2 )
975 				{
976 					nData = aIn.ReaduInt8();
977 					nFakt = 1;
978 				}
979 				else
980 				{
981 					aIn >> nData;
982 					nFakt = 2;
983 				}
984 
985 				if( nOpt & 0x04 )
986 				{// nFakt -> Bytes oder Words ueberlesen	AttrChoose
987 					nData++;
988                     aIn.Ignore( nData * nFakt );
989 				}
990 			}
991 				break;
992 			case 0x1A: // External Reference					[330    ]
993                 switch( meBiff )
994 				{
995                     case EXC_BIFF2: nIgnore = 7;    break;
996                     case EXC_BIFF3:
997                     case EXC_BIFF4: nIgnore = 10;   break;
998                     case EXC_BIFF5: DBG_WARNING( "-ExcelToSc::Convert(): 0x1A gibt's nicht in Biff5!" );
999                     default:        DBG_WARNING( "-ExcelToSc::Convert(): Ein wenig vergesslich, was?" );
1000 				}
1001 				break;
1002 			case 0x1B: // End External Reference				[330    ]
1003                 switch( meBiff )
1004 				{
1005                     case EXC_BIFF2: nIgnore = 3;        break;
1006                     case EXC_BIFF3:
1007                     case EXC_BIFF4: nIgnore = 4;        break;
1008                     case EXC_BIFF5: DBG_WARNING( "-ExcelToSc::Convert(): 0x1B gibt's nicht in Biff5!" );
1009                     default:        DBG_WARNING( "-ExcelToSc::Convert(): Ein wenig vergesslich, was?" );
1010 				}
1011 				break;
1012 			case 0x1C: // Error Value							[314 266]
1013 			case 0x1D: // Boolean								[315 266]
1014 				nIgnore = 1;
1015 				break;
1016 			case 0x1E: // Integer								[315 266]
1017 				nIgnore = 2;
1018 				break;
1019 			case 0x1F: // Number								[315 266]
1020                 nIgnore = 8;
1021 				break;
1022 			case 0x40:
1023 			case 0x60:
1024 			case 0x20: // Array Constant						[317 268]
1025                 nIgnore = (meBiff == EXC_BIFF2) ? 6 : 7;
1026 				break;
1027 			case 0x41:
1028 			case 0x61:
1029 			case 0x21: // Function, Fixed Number of Arguments	[333 282]
1030                 nIgnore = (meBiff <= EXC_BIFF3) ? 1 : 2;
1031 				break;
1032 			case 0x42:
1033 			case 0x62:
1034 			case 0x22: // Function, Variable Number of Arg.		[333 283]
1035                 nIgnore = (meBiff <= EXC_BIFF3) ? 2 : 3;
1036 				break;
1037 			case 0x43:
1038 			case 0x63:
1039 			case 0x23: // Name									[318 269]
1040                 switch( meBiff )
1041 				{
1042                     case EXC_BIFF2: nIgnore = 7;    break;
1043                     case EXC_BIFF3:
1044                     case EXC_BIFF4: nIgnore = 10;   break;
1045                     case EXC_BIFF5: nIgnore = 14;   break;
1046                     default:        DBG_ERROR( "-ExcelToSc::Convert(): Ein wenig vergesslich, was?" );
1047 				}
1048 				break;
1049 			case 0x44:
1050 			case 0x64:
1051 			case 0x24: // Cell Reference						[319 270]
1052 				aIn >> nUINT16 >> nByte;
1053 				aSRD.nCol = static_cast<SCsCOL>(nByte);
1054 				aSRD.nRow = nUINT16 & 0x3FFF;
1055 				aSRD.nRelTab = 0;
1056 				aSRD.SetTabRel( sal_True );
1057 				aSRD.SetFlag3D( bRangeName );
1058 
1059 				ExcRelToScRel( nUINT16, nByte, aSRD, bRangeName );
1060 
1061 				rRangeList.Append( aSRD );
1062 				break;
1063 			case 0x45:
1064 			case 0x65:
1065 			case 0x25: // Area Reference						[320 270]
1066 			{
1067 				sal_uInt16			nRowFirst, nRowLast;
1068 				sal_uInt8			nColFirst, nColLast;
1069 				ScSingleRefData	&rSRef1 = aCRD.Ref1;
1070 				ScSingleRefData	&rSRef2 = aCRD.Ref2;
1071 
1072 				aIn >> nRowFirst >> nRowLast >> nColFirst >> nColLast;
1073 
1074 				rSRef1.nRelTab = rSRef2.nRelTab = 0;
1075 				rSRef1.SetTabRel( sal_True );
1076 				rSRef2.SetTabRel( sal_True );
1077 				rSRef1.SetFlag3D( bRangeName );
1078 				rSRef2.SetFlag3D( bRangeName );
1079 
1080 				ExcRelToScRel( nRowFirst, nColFirst, aCRD.Ref1, bRangeName );
1081 				ExcRelToScRel( nRowLast, nColLast, aCRD.Ref2, bRangeName );
1082 
1083 				if( IsComplColRange( nColFirst, nColLast ) )
1084 					SetComplCol( aCRD );
1085 				else if( IsComplRowRange( nRowFirst, nRowLast ) )
1086 					SetComplRow( aCRD );
1087 
1088 				rRangeList.Append( aCRD );
1089 			}
1090 				break;
1091 			case 0x46:
1092 			case 0x66:
1093 			case 0x26: // Constant Reference Subexpression		[321 271]
1094 			case 0x47:
1095 			case 0x67:
1096 			case 0x27: // Erroneous Constant Reference Subexpr.	[322 272]
1097 			case 0x48:
1098 			case 0x68:
1099 			case 0x28: // Incomplete Constant Reference Subexpr.[331 281]
1100                 nIgnore = (meBiff == EXC_BIFF2) ? 4 : 6;
1101 				break;
1102 			case 0x4A:
1103 			case 0x6A:
1104 			case 0x2A: // Deleted Cell Reference				[323 273]
1105 				nIgnore = 3;
1106 				break;
1107 			case 0x4B:
1108 			case 0x6B:
1109 			case 0x2B: // Deleted Area Refernce					[323 273]
1110 				nIgnore = 6;
1111 				break;
1112 			case 0x4C:
1113 			case 0x6C:
1114 			case 0x2C: // Cell Reference Within a Name			[323    ]
1115 					   // Cell Reference Within a Shared Formula[    273]
1116 			{
1117 				aIn >> nUINT16 >> nByte;	// >> Attribute, Row >> Col
1118 
1119 				aSRD.nRelTab = 0;
1120 				aSRD.SetTabRel( sal_True );
1121 				aSRD.SetFlag3D( bRangeName );
1122 
1123 				ExcRelToScRel( nUINT16, nByte, aSRD, bRNorSF );
1124 
1125 				rRangeList.Append( aSRD );
1126 			}
1127 				break;
1128 			case 0x4D:
1129 			case 0x6D:
1130 			case 0x2D: // Area Reference Within a Name			[324    ]
1131 			{	   // Area Reference Within a Shared Formula[    274]
1132 				sal_uInt16					nRowFirst, nRowLast;
1133 				sal_uInt8					nColFirst, nColLast;
1134 
1135 				aCRD.Ref1.nRelTab = aCRD.Ref2.nRelTab = 0;
1136 				aCRD.Ref1.SetTabRel( sal_True );
1137 				aCRD.Ref2.SetTabRel( sal_True );
1138 				aCRD.Ref1.SetFlag3D( bRangeName );
1139 				aCRD.Ref2.SetFlag3D( bRangeName );
1140 
1141 				aIn >> nRowFirst >> nRowLast >> nColFirst >> nColLast;
1142 
1143 				ExcRelToScRel( nRowFirst, nColFirst, aCRD.Ref1, bRNorSF );
1144 				ExcRelToScRel( nRowLast, nColLast, aCRD.Ref2, bRNorSF );
1145 
1146 				if( IsComplColRange( nColFirst, nColLast ) )
1147 					SetComplCol( aCRD );
1148 				else if( IsComplRowRange( nRowFirst, nRowLast ) )
1149 					SetComplRow( aCRD );
1150 
1151 				rRangeList.Append( aCRD );
1152 			}
1153 				break;
1154             case 0x49:
1155             case 0x69:
1156             case 0x29: // Variable Reference Subexpression      [331 281]
1157 			case 0x4E:
1158 			case 0x6E:
1159 			case 0x2E: // Reference Subexpression Within a Name	[332 282]
1160 			case 0x4F:
1161 			case 0x6F:
1162 			case 0x2F: // Incomplete Reference Subexpression...	[332 282]
1163                 nIgnore = (meBiff == EXC_BIFF2) ? 1 : 2;
1164 				break;
1165 			case 0x58:
1166 			case 0x78:
1167 			case 0x38: // Command-Equivalent Function			[333    ]
1168 				nIgnore = 2;
1169 				break;
1170 			case 0x59:
1171 			case 0x79:
1172 			case 0x39: // Name or External Name					[    275]
1173 				nIgnore = 24;
1174 				break;
1175 			case 0x5A:
1176 			case 0x7A:
1177 			case 0x3A: // 3-D Cell Reference					[    275]
1178 			{
1179 				sal_uInt16			nTabFirst, nTabLast, nRow;
1180 				sal_Int16			nExtSheet;
1181 				sal_uInt8			nCol;
1182 
1183 				aIn >> nExtSheet;
1184                 aIn.Ignore( 8 );
1185 				aIn >> nTabFirst >> nTabLast >> nRow >> nCol;
1186 
1187 				if( nExtSheet >= 0 )
1188 					// von extern
1189 				{
1190                     if( rR.pExtSheetBuff->GetScTabIndex( nExtSheet, nTabLast ) )
1191 					{
1192 						nTabFirst = nTabLast;
1193 						nExtSheet = 0;		// gefunden
1194 					}
1195 					else
1196 					{
1197 						aPool << ocBad;
1198 						aPool >> aStack;
1199 						nExtSheet = 1;		// verhindert Erzeugung einer SingleRef
1200 					}
1201 				}
1202 
1203 				if( nExtSheet <= 0 )
1204 				{// in aktuellem Workbook
1205 					sal_Bool b3D = ( static_cast<SCTAB>(nTabFirst) != aEingPos.Tab() ) || bRangeName;
1206 					aSRD.nTab = static_cast<SCTAB>(nTabFirst);
1207 					aSRD.SetFlag3D( b3D );
1208 					aSRD.SetTabRel( sal_False );
1209 
1210 					ExcRelToScRel( nRow, nCol, aSRD, bRangeName );
1211 
1212 					if( nTabLast != nTabFirst )
1213 					{
1214 						aCRD.Ref1 = aSRD;
1215 						aCRD.Ref2.nCol = aSRD.nCol;
1216 						aCRD.Ref2.nRow = aSRD.nRow;
1217 						aCRD.Ref2.nTab = static_cast<SCTAB>(nTabLast);
1218 						b3D = ( static_cast<SCTAB>(nTabLast) != aEingPos.Tab() );
1219 						aCRD.Ref2.SetFlag3D( b3D );
1220 						aCRD.Ref2.SetTabRel( sal_False );
1221 						rRangeList.Append( aCRD );
1222 					}
1223 					else
1224 						rRangeList.Append( aSRD );
1225 				}
1226 			}
1227 
1228 				break;
1229 			case 0x5B:
1230 			case 0x7B:
1231 			case 0x3B: // 3-D Area Reference					[    276]
1232 			{
1233 				sal_uInt16		nTabFirst, nTabLast, nRowFirst, nRowLast;
1234 				sal_Int16		nExtSheet;
1235 				sal_uInt8		nColFirst, nColLast;
1236 
1237 				aIn >> nExtSheet;
1238                 aIn.Ignore( 8 );
1239 				aIn >> nTabFirst >> nTabLast >> nRowFirst >> nRowLast
1240 					>> nColFirst >> nColLast;
1241 
1242 				if( nExtSheet >= 0 )
1243 					// von extern
1244 				{
1245                     if( rR.pExtSheetBuff->GetScTabIndex( nExtSheet, nTabLast ) )
1246 					{
1247 						nTabFirst = nTabLast;
1248 						nExtSheet = 0;		// gefunden
1249 					}
1250 					else
1251 					{
1252 						aPool << ocBad;
1253 						aPool >> aStack;
1254 						nExtSheet = 1;		// verhindert Erzeugung einer CompleteRef
1255 					}
1256 				}
1257 
1258 				if( nExtSheet <= 0 )
1259 				{// in aktuellem Workbook
1260 					// erster Teil des Bereichs
1261 					ScSingleRefData	&rR1 = aCRD.Ref1;
1262 					ScSingleRefData	&rR2 = aCRD.Ref2;
1263 
1264 					rR1.nTab = static_cast<SCTAB>(nTabFirst);
1265 					rR2.nTab = static_cast<SCTAB>(nTabLast);
1266 					rR1.SetFlag3D( ( static_cast<SCTAB>(nTabFirst) != aEingPos.Tab() ) || bRangeName );
1267 					rR1.SetTabRel( sal_False );
1268 					rR2.SetFlag3D( ( static_cast<SCTAB>(nTabLast) != aEingPos.Tab() ) || bRangeName );
1269 					rR2.SetTabRel( sal_False );
1270 
1271 					ExcRelToScRel( nRowFirst, nColFirst, aCRD.Ref1, bRangeName );
1272 					ExcRelToScRel( nRowLast, nColLast, aCRD.Ref2, bRangeName );
1273 
1274 					if( IsComplColRange( nColFirst, nColLast ) )
1275 						SetComplCol( aCRD );
1276 					else if( IsComplRowRange( nRowFirst, nRowLast ) )
1277 						SetComplRow( aCRD );
1278 
1279 					rRangeList.Append( aCRD );
1280 				}//ENDE in aktuellem Workbook
1281 			}
1282 				break;
1283 			case 0x5C:
1284 			case 0x7C:
1285 			case 0x3C: // Deleted 3-D Cell Reference			[    277]
1286 				nIgnore = 17;
1287 				break;
1288 			case 0x5D:
1289 			case 0x7D:
1290 			case 0x3D: // Deleted 3-D Area Reference			[    277]
1291 				nIgnore = 20;
1292 				break;
1293 			default: bError = sal_True;
1294 		}
1295 		bError |= !aIn.IsValid();
1296 
1297         aIn.Ignore( nIgnore );
1298 	}
1299 
1300 	ConvErr eRet;
1301 
1302 	if( bError )
1303 		eRet = ConvErrNi;
1304     else if( aIn.GetRecPos() != nEndPos )
1305 		eRet = ConvErrCount;
1306 	else if( bExternName )
1307 		eRet = ConvErrExternal;
1308 	else if( bArrayFormula )
1309 		eRet = ConvOK;
1310 	else
1311 		eRet = ConvOK;
1312 
1313     aIn.Seek( nEndPos );
1314 	return eRet;
1315 }
1316 
ConvertExternName(const ScTokenArray * &,XclImpStream &,sal_Size,const String &,const vector<String> &)1317 ConvErr ExcelToSc::ConvertExternName( const ScTokenArray*& /*rpArray*/, XclImpStream& /*rStrm*/, sal_Size /*nFormulaLen*/,
1318                                       const String& /*rUrl*/, const vector<String>& /*rTabNames*/ )
1319 {
1320     // not implemented ...
1321     return ConvErrNi;
1322 }
1323 
GetAbsRefs(ScRangeList & rRangeList,XclImpStream & rStrm,sal_Size nLen)1324 sal_Bool ExcelToSc::GetAbsRefs( ScRangeList& rRangeList, XclImpStream& rStrm, sal_Size nLen )
1325 {
1326     DBG_ASSERT_BIFF( GetBiff() == EXC_BIFF5 );
1327     if( GetBiff() != EXC_BIFF5 )
1328         return sal_False;
1329 
1330     sal_uInt8 nOp;
1331     sal_uInt16 nRow1, nRow2;
1332     sal_uInt8 nCol1, nCol2;
1333     SCTAB nTab1, nTab2;
1334     sal_uInt16 nTabFirst, nTabLast;
1335     sal_Int16 nRefIdx;
1336 
1337     sal_Size nSeek;
1338     sal_Size nEndPos = rStrm.GetRecPos() + nLen;
1339 
1340     while( rStrm.IsValid() && (rStrm.GetRecPos() < nEndPos) )
1341     {
1342         rStrm >> nOp;
1343         nSeek = 0;
1344 
1345         switch( nOp )
1346         {
1347             case 0x44:
1348             case 0x64:
1349             case 0x24: // Cell Reference                        [319 270]
1350             case 0x4C:
1351             case 0x6C:
1352             case 0x2C: // Cell Reference Within a Name          [323    ]
1353                        // Cell Reference Within a Shared Formula[    273]
1354                 rStrm >> nRow1 >> nCol1;
1355 
1356                 nRow2 = nRow1;
1357                 nCol2 = nCol1;
1358                 nTab1 = nTab2 = GetCurrScTab();
1359                 goto _common;
1360             case 0x45:
1361             case 0x65:
1362             case 0x25: // Area Reference                        [320 270]
1363             case 0x4D:
1364             case 0x6D:
1365             case 0x2D: // Area Reference Within a Name          [324    ]
1366                        // Area Reference Within a Shared Formula[    274]
1367                 rStrm >> nRow1 >> nRow2 >> nCol1 >> nCol2;
1368 
1369                 nTab1 = nTab2 = GetCurrScTab();
1370                 goto _common;
1371             case 0x5A:
1372             case 0x7A:
1373             case 0x3A: // 3-D Cell Reference                    [    275]
1374                 rStrm >> nRefIdx;
1375                 rStrm.Ignore( 8 );
1376                 rStrm >> nTabFirst >> nTabLast >> nRow1 >> nCol1;
1377 
1378                 nRow2 = nRow1;
1379                 nCol2 = nCol1;
1380 
1381                 goto _3d_common;
1382             case 0x5B:
1383             case 0x7B:
1384             case 0x3B: // 3-D Area Reference                    [    276]
1385                 rStrm >> nRefIdx;
1386                 rStrm.Ignore( 8 );
1387                 rStrm >> nTabFirst >> nTabLast >> nRow1 >> nRow2 >> nCol1 >> nCol2;
1388 
1389     _3d_common:
1390                 nTab1 = static_cast< SCTAB >( nTabFirst );
1391                 nTab2 = static_cast< SCTAB >( nTabLast );
1392 
1393                 // #122885# skip references to deleted sheets
1394                 if( (nRefIdx >= 0) || !ValidTab( nTab1 ) || (nTab1 != nTab2) )
1395                     break;
1396 
1397                 goto _common;
1398     _common:
1399                 // do not check abs/rel flags, linked controls have set them!
1400 //               if( !(( nCol1 & 0xC000 ) || ( nCol2 & 0xC000 )) )
1401                 {
1402                     ScRange aScRange;
1403                     nRow1 &= 0x3FFF;
1404                     nRow2 &= 0x3FFF;
1405                     if( GetAddressConverter().ConvertRange( aScRange, XclRange( nCol1, nRow1, nCol2, nRow2 ), nTab1, nTab2, true ) )
1406                         rRangeList.Append( aScRange );
1407                 }
1408                 break;
1409 
1410             case 0x03: // Addition                              [312 264]
1411             case 0x04: // Subtraction                           [313 264]
1412             case 0x05: // Multiplication                        [313 264]
1413             case 0x06: // Division                              [313 264]
1414             case 0x07: // Exponetiation                         [313 265]
1415             case 0x08: // Concatenation                         [313 265]
1416             case 0x09: // Less Than                             [313 265]
1417             case 0x0A: // Less Than or Equal                    [313 265]
1418             case 0x0B: // Equal                                 [313 265]
1419             case 0x0C: // Greater Than or Equal                 [313 265]
1420             case 0x0D: // Greater Than                          [313 265]
1421             case 0x0E: // Not Equal                             [313 265]
1422             case 0x0F: // Intersection                          [314 265]
1423             case 0x10: // Union                                 [314 265]
1424             case 0x11: // Range                                 [314 265]
1425             case 0x12: // Unary Plus                            [312 264]
1426             case 0x13: // Unary Minus                           [312 264]
1427             case 0x14: // Percent Sign                          [312 264]
1428             case 0x15: // Parenthesis                           [326 278]
1429             case 0x16: // Missing Argument                      [314 266]
1430                 break;
1431             case 0x1C: // Error Value                           [314 266]
1432             case 0x1D: // Boolean                               [315 266]
1433                 nSeek = 1;
1434                 break;
1435             case 0x1E: // Integer                               [315 266]
1436             case 0x41:
1437             case 0x61:
1438             case 0x21: // Function, Fixed Number of Arguments   [333 282]
1439             case 0x49:
1440             case 0x69:
1441             case 0x29: // Variable Reference Subexpression      [331 281]
1442             case 0x4E:
1443             case 0x6E:
1444             case 0x2E: // Reference Subexpression Within a Name [332 282]
1445             case 0x4F:
1446             case 0x6F:
1447             case 0x2F: // Incomplete Reference Subexpression... [332 282]
1448             case 0x58:
1449             case 0x78:
1450             case 0x38: // Command-Equivalent Function           [333    ]
1451                 nSeek = 2;
1452                 break;
1453             case 0x42:
1454             case 0x62:
1455             case 0x22: // Function, Variable Number of Arg.     [333 283]
1456             case 0x4A:
1457             case 0x6A:
1458             case 0x2A: // Deleted Cell Reference                [323 273]
1459                 nSeek = 3;
1460                 break;
1461             case 0x01: // Array Formula                         [325    ]
1462                        // Array Formula or Shared Formula       [    277]
1463             case 0x02: // Data Table                            [325 277]
1464                 nSeek = 4;
1465                 break;
1466             case 0x46:
1467             case 0x66:
1468             case 0x26: // Constant Reference Subexpression      [321 271]
1469             case 0x47:
1470             case 0x67:
1471             case 0x27: // Erroneous Constant Reference Subexpr. [322 272]
1472             case 0x48:
1473             case 0x68:
1474             case 0x28: // Incomplete Constant Reference Subexpr.[331 281]
1475             case 0x4B:
1476             case 0x6B:
1477             case 0x2B: // Deleted Area Refernce                 [323 273]
1478                 nSeek = 6;
1479                 break;
1480             case 0x40:
1481             case 0x60:
1482             case 0x20: // Array Constant                        [317 268]
1483                 nSeek = 7;
1484                 break;
1485             case 0x1F: // Number                                [315 266]
1486                 nSeek = 8;
1487                 break;
1488             case 0x43:
1489             case 0x63:
1490             case 0x23: // Name                                  [318 269]
1491                 nSeek = 14;
1492                 break;
1493             case 0x5C:
1494             case 0x7C:
1495             case 0x3C: // Deleted 3-D Cell Reference            [    277]
1496                 nSeek = 17;
1497                 break;
1498             case 0x5D:
1499             case 0x7D:
1500             case 0x3D: // Deleted 3-D Area Reference            [    277]
1501                 nSeek = 20;
1502                 break;
1503             case 0x59:
1504             case 0x79:
1505             case 0x39: // Name or External Name                 [    275]
1506                 nSeek = 24;
1507                 break;
1508             case 0x17: // String Constant                       [314 266]
1509                 nSeek = rStrm.ReaduInt8();
1510                 break;
1511             case 0x19: // Special Attribute                     [327 279]
1512             {
1513                 sal_uInt8 nOpt;
1514                 sal_uInt16 nData;
1515                 rStrm >> nOpt >> nData;
1516                 if( nOpt & 0x04 )
1517                     nSeek = nData * 2 + 2;
1518             }
1519                 break;
1520         }
1521 
1522         rStrm.Ignore( nSeek );
1523     }
1524     rStrm.Seek( nEndPos );
1525 
1526     return rRangeList.Count() != 0;
1527 }
1528 
1529 static DefTokenId missArgForZeroList[] = {
1530 	ocCount,
1531 	ocCount2,
1532 	ocAverage,
1533 	ocMin,
1534 	ocMinA,
1535 	ocMax,
1536 	ocMaxA,
1537 	ocStDev,
1538 	ocStDevA,
1539 	ocVar,
1540 	ocVarP,
1541 	ocAveDev,
1542 	ocKurt,
1543 	ocSchiefe,
1544 	ocVarPA,
1545 	ocVarA,
1546 	ocDevSq
1547 };
1548 
1549 #define missArgForZeroCount sizeof(missArgForZeroList)/sizeof(DefTokenId)
1550 
1551 
lcl_isInMissArgForZeroList(DefTokenId id)1552 sal_Bool lcl_isInMissArgForZeroList(DefTokenId id)
1553 {
1554 	for (sal_uInt32 nIndex = 0; nIndex < missArgForZeroCount; nIndex++)
1555 		if(missArgForZeroList[nIndex] == id)
1556 			return sal_True;
1557 	return sal_False;
1558 
1559 }
DoMulArgs(DefTokenId eId,sal_uInt8 nAnz,sal_uInt8 nMinParamCount)1560 void ExcelToSc::DoMulArgs( DefTokenId eId, sal_uInt8 nAnz, sal_uInt8 nMinParamCount )
1561 {
1562 	TokenId					eParam[ 256 ];
1563 	sal_Int32					nLauf;
1564 
1565 	if( eId == ocCeil || eId == ocFloor )
1566 	{
1567 		aStack << aPool.Store( 1.0 );	// default, da in Excel nicht vorhanden
1568 		nAnz++;
1569 	}
1570 
1571     for( nLauf = 0; aStack.HasMoreTokens() && (nLauf < nAnz); nLauf++ )
1572 		aStack >> eParam[ nLauf ];
1573     // #i70925# reduce parameter count, if no more tokens available on token stack
1574     if( nLauf < nAnz )
1575         nAnz = static_cast< sal_uInt8 >( nLauf );
1576 
1577 	if( nAnz > 0 && eId == ocExternal )
1578 	{
1579 		TokenId				n = eParam[ nAnz - 1 ];
1580 //##### GRUETZE FUER BASIC-FUNCS RICHTEN!
1581         if( const String* pExt = aPool.GetExternal( n ) )
1582 		{
1583             if( const XclFunctionInfo* pFuncInfo = maFuncProv.GetFuncInfoFromXclMacroName( *pExt ) )
1584                 aPool << pFuncInfo->meOpCode;
1585             else
1586                 aPool << n;
1587             nAnz--;
1588 		}
1589 		else
1590 			aPool << eId;
1591 	}
1592 	else
1593 		aPool << eId;
1594 
1595 	aPool << ocOpen;
1596 
1597 	if( nAnz > 0 )
1598 	{
1599 		// attention: 0 = last parameter, nAnz-1 = first parameter
1600 		sal_Int16 nNull = -1;		// skip this parameter
1601 		sal_Int16 nSkipEnd = -1;	// skip all parameters <= nSkipEnd
1602 
1603 		sal_Int16 nLast = nAnz - 1;
1604 
1605 		// Funktionen, bei denen Parameter wegfallen muessen
1606 		if( eId == ocPercentrank && nAnz == 3 )
1607 			nSkipEnd = 0;		// letzten Parameter bei Bedarf weglassen
1608 
1609 		// Joost-Spezialfaelle
1610 		else if( eId == ocIf || lcl_isInMissArgForZeroList(eId))
1611 		{
1612 			sal_uInt16			nNullParam = 0;
1613 			for( nLauf = 0 ; nLauf < nAnz ; nLauf++ )
1614 			{
1615 				if( aPool.IsSingleOp( eParam[ nLauf ], ocMissing ) )
1616 				{
1617 					if( !nNullParam )
1618 						nNullParam = (sal_uInt16) aPool.Store( ( double ) 0.0 );
1619 					eParam[ nLauf ] = nNullParam;
1620 				}
1621 			}
1622 		}
1623 
1624 		// FIXME: ideally we'd want to import all missing args, but this
1625 		// conflicts with lots of fn's understanding of nParams - we need
1626 		// a function table, and pre-call argument normalisation 1st.
1627 		sal_Int16 nLastRemovable = nLast - nMinParamCount;
1628 
1629 		// #84453# skip missing parameters at end of parameter list
1630 		while( nSkipEnd < nLastRemovable &&
1631 			   aPool.IsSingleOp( eParam[ nSkipEnd + 1 ], ocMissing ) )
1632 			nSkipEnd++;
1633 
1634 //		fprintf (stderr, "Fn %d nSkipEnd %d nLast %d nMinParamCnt %d %d\n",
1635 //				 eId, nSkipEnd, nLast, nMinParamCount, nLastRemovable);
1636 
1637 		// [Parameter{;Parameter}]
1638 		if( nLast > nSkipEnd )
1639 		{
1640 			aPool << eParam[ nLast ];
1641 			for( nLauf = nLast - 1 ; nLauf > nSkipEnd ; nLauf-- )
1642 			{
1643 				if( nLauf != nNull )
1644 					aPool << ocSep << eParam[ nLauf ];
1645 			}
1646 		}
1647 	}
1648 	aPool << ocClose;
1649 
1650 	aPool >> aStack;
1651 }
1652 
1653 
ExcRelToScRel(sal_uInt16 nRow,sal_uInt8 nCol,ScSingleRefData & rSRD,const sal_Bool bName)1654 void ExcelToSc::ExcRelToScRel( sal_uInt16 nRow, sal_uInt8 nCol, ScSingleRefData &rSRD, const sal_Bool bName )
1655 {
1656 	if( bName )
1657 	{
1658 		// C O L
1659 		if( nRow & 0x4000 )
1660 		{//															rel Col
1661 			rSRD.SetColRel( sal_True );
1662 			rSRD.nRelCol = static_cast<SCsCOL>(static_cast<sal_Int8>(nCol));
1663 		}
1664 		else
1665 		{//															abs Col
1666 			rSRD.SetColRel( sal_False );
1667 			rSRD.nCol = static_cast<SCCOL>(nCol);
1668 		}
1669 
1670 		// R O W
1671 		if( nRow & 0x8000 )
1672 		{//															rel Row
1673 			rSRD.SetRowRel( sal_True );
1674 			if( nRow & 0x2000 )	// Bit 13 gesetzt?
1675 				//												-> Row negativ
1676 				rSRD.nRelRow = static_cast<SCsROW>(static_cast<sal_Int16>(nRow | 0xC000));
1677 			else
1678 				//												-> Row positiv
1679 				rSRD.nRelRow = static_cast<SCsROW>(nRow & nRowMask);
1680 		}
1681 		else
1682 		{//															abs Row
1683 			rSRD.SetRowRel( sal_False );
1684 			rSRD.nRow = static_cast<SCROW>(nRow & nRowMask);
1685 		}
1686 
1687 		// T A B
1688 		// #67965# abs needed if rel in shared formula for ScCompiler UpdateNameReference
1689 		if ( rSRD.IsTabRel() && !rSRD.IsFlag3D() )
1690             rSRD.nTab = GetCurrScTab();
1691 	}
1692 	else
1693 	{
1694 		// C O L
1695 		rSRD.SetColRel( ( nRow & 0x4000 ) > 0 );
1696 		rSRD.nCol = static_cast<SCsCOL>(nCol);
1697 
1698 		// R O W
1699 		rSRD.SetRowRel( ( nRow & 0x8000 ) > 0 );
1700 		rSRD.nRow = static_cast<SCsROW>(nRow & nRowMask);
1701 
1702 		if ( rSRD.IsColRel() )
1703 			rSRD.nRelCol = rSRD.nCol - aEingPos.Col();
1704 		if ( rSRD.IsRowRel() )
1705 			rSRD.nRelRow = rSRD.nRow - aEingPos.Row();
1706 
1707         // T A B
1708         // #i10184# abs needed if rel in shared formula for ScCompiler UpdateNameReference
1709         if ( rSRD.IsTabRel() && !rSRD.IsFlag3D() )
1710             rSRD.nTab = GetCurrScTab() + rSRD.nRelTab;
1711 	}
1712 }
1713 
1714 
GetBoolErr(XclBoolError eType)1715 const ScTokenArray* ExcelToSc::GetBoolErr( XclBoolError eType )
1716 {
1717 	sal_uInt16					nError;
1718 	aPool.Reset();
1719 	aStack.Reset();
1720 
1721 	DefTokenId				eOc;
1722 
1723 	switch( eType )
1724 	{
1725         case xlErrNull:     eOc = ocStop;       nError = errNoCode;             break;
1726         case xlErrDiv0:     eOc = ocStop;       nError = errDivisionByZero;     break;
1727         case xlErrValue:    eOc = ocStop;       nError = errNoValue;            break;
1728         case xlErrRef:      eOc = ocStop;       nError = errNoRef;              break;
1729         case xlErrName:     eOc = ocStop;       nError = errNoName;             break;
1730         case xlErrNum:      eOc = ocStop;       nError = errIllegalFPOperation; break;
1731         case xlErrNA:       eOc = ocNotAvail;   nError = NOTAVAILABLE;          break;
1732         case xlErrTrue:     eOc = ocTrue;       nError = 0;                     break;
1733         case xlErrFalse:    eOc = ocFalse;      nError = 0;                     break;
1734         case xlErrUnknown:  eOc = ocStop;       nError = errUnknownState;       break;
1735 		default:
1736             DBG_ERROR( "ExcelToSc::GetBoolErr - wrong enum!" );
1737 			eOc = ocNoName;
1738 			nError = errUnknownState;
1739 	}
1740 
1741 	aPool << eOc;
1742 	if( eOc != ocStop )
1743 		aPool << ocOpen << ocClose;
1744 
1745 	aPool >> aStack;
1746 
1747 	const ScTokenArray*		pErgebnis = aPool[ aStack.Get() ];
1748 	if( nError )
1749 		( ( ScTokenArray* ) pErgebnis )->SetCodeError( nError );
1750 
1751 	( ( ScTokenArray* ) pErgebnis )->SetRecalcModeNormal();
1752 
1753 	return pErgebnis;
1754 }
1755 
1756 
1757 // if a shared formula was found, stream seeks to first byte after <nFormulaLen>,
1758 // else stream pointer stays unchanged
GetShrFmla(const ScTokenArray * & rpErgebnis,XclImpStream & aIn,sal_Size nFormulaLen)1759 sal_Bool ExcelToSc::GetShrFmla( const ScTokenArray*& rpErgebnis, XclImpStream& aIn, sal_Size nFormulaLen )
1760 {
1761 	sal_uInt8			nOp;
1762 	sal_Bool			bRet = sal_True;
1763 
1764 	if( nFormulaLen == 0 )
1765 		bRet = sal_False;
1766 	else
1767 	{
1768 		aIn.PushPosition();
1769 
1770 		aIn >> nOp;
1771 
1772 		if( nOp == 0x01 )	// Shared Formula		[    277]
1773 		{
1774 			sal_uInt16 nCol, nRow;
1775 
1776 			aIn >> nRow >> nCol;
1777 
1778             aStack << aPool.Store( GetOldRoot().pShrfmlaBuff->Find(
1779                 ScAddress( static_cast<SCCOL>(nCol), static_cast<SCROW>(nRow), GetCurrScTab() ) ) );
1780 
1781 			bRet = sal_True;
1782 		}
1783 		else
1784 			bRet = sal_False;
1785 
1786 		aIn.PopPosition();
1787 	}
1788 
1789 	if( bRet )
1790 	{
1791         aIn.Ignore( nFormulaLen );
1792 		rpErgebnis = aPool[ aStack.Get() ];
1793 	}
1794 	else
1795 		rpErgebnis = NULL;
1796 
1797 	return bRet;
1798 }
1799 
1800 
1801 #if 0
1802 sal_Bool ExcelToSc::SetCurVal( ScFormulaCell &rCell, double &rfCurVal )
1803 {
1804 	sal_uInt16	nInd;
1805 	sal_uInt8	nType;
1806 	sal_uInt8	nVal;
1807 	sal_Bool	bString = sal_False;
1808 
1809 #ifdef OSL_BIGENDIAN
1810 	// Code fuer alle anstaendigen Prozessoren
1811 	nType = *( ( ( sal_uInt8 * ) &rfCurVal ) + 7 );
1812 	nVal = *( ( ( sal_uInt8 * ) &rfCurVal ) + 5 );
1813 	nInd = *( ( sal_uInt16 * ) &rfCurVal );
1814 #else
1815 	// fuer Schund-Prozessoren
1816 	nType = *( ( sal_uInt8 * ) &rfCurVal );
1817 	nVal = *( ( ( sal_uInt8 * ) &rfCurVal ) + 2 );
1818 	nInd = *( ( ( sal_uInt16 * ) &rfCurVal ) + 3 );
1819 #endif
1820 
1821 	if( ( sal_uInt16 ) ~nInd )
1822 		// Wert ist Float
1823 		rCell.SetHybridDouble( rfCurVal );
1824 	else
1825 	{
1826 		switch( nType )
1827 		{
1828 			case 0:		// String
1829 				bString = sal_True;
1830 				break;
1831 			case 1:		// Bool
1832 				if( nVal )
1833 					rfCurVal = 1.0;
1834 				else
1835 					rfCurVal = 0.0;
1836 				rCell.SetHybridDouble( rfCurVal );
1837 				break;
1838 			case 2:		// Error
1839                 rCell.SetErrCode( XclTools::GetScErrorCode( nVal ) );
1840 				break;
1841 		}
1842 	}
1843 
1844 	return bString;
1845 }
1846 #endif
1847 
1848 
SetError(ScFormulaCell & rCell,const ConvErr eErr)1849 void ExcelToSc::SetError( ScFormulaCell &rCell, const ConvErr eErr )
1850 {
1851 	sal_uInt16	nInd;
1852 
1853 	switch( eErr )
1854 	{
1855 		case ConvErrNi:			nInd = errUnknownToken; break;
1856 		case ConvErrNoMem:		nInd = errCodeOverflow; break;
1857 		case ConvErrExternal:	nInd = errNoName; break;
1858 		case ConvErrCount:		nInd = errCodeOverflow; break;
1859 		default:				nInd = errNoCode;	// hier fiel mir nichts
1860 													//  Besseres ein...
1861 	}
1862 
1863 	rCell.SetErrCode( nInd );
1864 }
1865 
1866 
SetComplCol(ScComplexRefData & rCRD)1867 void ExcelToSc::SetComplCol( ScComplexRefData &rCRD )
1868 {
1869 	ScSingleRefData	&rSRD = rCRD.Ref2;
1870 	if( rSRD.IsColRel() )
1871 		rSRD.nRelCol = MAXCOL - aEingPos.Col();
1872 	else
1873 		rSRD.nCol = MAXCOL;
1874 }
1875 
1876 
SetComplRow(ScComplexRefData & rCRD)1877 void ExcelToSc::SetComplRow( ScComplexRefData &rCRD )
1878 {
1879 	ScSingleRefData	&rSRD = rCRD.Ref2;
1880 	if( rSRD.IsRowRel() )
1881 		rSRD.nRelRow = MAXROW - aEingPos.Row();
1882 	else
1883 		rSRD.nRow = MAXROW;
1884 }
1885 
ReadExtensionArray(unsigned int n,XclImpStream & aIn)1886 void ExcelToSc::ReadExtensionArray( unsigned int n, XclImpStream& aIn )
1887 {
1888     // printf( "inline array;\n" );
1889 
1890     sal_uInt8        nByte;
1891     sal_uInt16      nUINT16;
1892     double      fDouble;
1893     String      aString;
1894     ScMatrix*   pMatrix;
1895 
1896     aIn >> nByte >> nUINT16;
1897 
1898     SCSIZE nC, nCols;
1899     SCSIZE nR, nRows;
1900     if( GetBiff() == EXC_BIFF8 )
1901     {
1902         nCols = nByte + 1;
1903         nRows = nUINT16 + 1;
1904     }
1905     else
1906     {
1907         nCols = nByte ? nByte : 256;
1908         nRows = nUINT16;
1909     }
1910 
1911     pMatrix = aPool.GetMatrix( n );
1912 
1913     if( NULL != pMatrix )
1914     {
1915         pMatrix->Resize(nCols, nRows);
1916         pMatrix->GetDimensions( nC, nR);
1917         if( nC != nCols || nR != nRows )
1918         {
1919             DBG_ERRORFILE( "ExcelToSc::ReadExtensionArray - matrix size mismatch" );
1920             pMatrix = NULL;
1921         }
1922     }
1923     else
1924     {
1925         DBG_ERRORFILE( "ExcelToSc::ReadExtensionArray - missing matrix" );
1926     }
1927 
1928     for( nR = 0 ; nR < nRows; nR++ )
1929     {
1930         for( nC = 0 ; nC < nCols; nC++ )
1931         {
1932             aIn >> nByte;
1933             switch( nByte )
1934             {
1935                 case EXC_CACHEDVAL_EMPTY:
1936                     aIn.Ignore( 8 );
1937                     if( NULL != pMatrix )
1938                     {
1939                         pMatrix->PutEmpty( nC, nR );
1940                     }
1941                     break;
1942 
1943                 case EXC_CACHEDVAL_DOUBLE:
1944                     aIn >> fDouble;
1945                     if( NULL != pMatrix )
1946                     {
1947                         pMatrix->PutDouble( fDouble, nC, nR );
1948                     }
1949                     break;
1950 
1951                 case EXC_CACHEDVAL_STRING:
1952                     if( GetBiff() == EXC_BIFF8 )
1953                     {
1954                         aIn >> nUINT16;
1955                         aString = aIn.ReadUniString( nUINT16 );
1956                     }
1957                     else
1958                     {
1959                         aIn >> nByte;
1960                         aString = aIn.ReadRawByteString( nByte );
1961                     }
1962                     if( NULL != pMatrix )
1963                     {
1964                         pMatrix->PutString( aString, nC, nR );
1965                     }
1966                     break;
1967 
1968                 case EXC_CACHEDVAL_BOOL:
1969                     aIn >> nByte;
1970                     aIn.Ignore( 7 );
1971                     if( NULL != pMatrix )
1972                     {
1973                         pMatrix->PutBoolean( nByte != 0, nC, nR );
1974                     }
1975                     break;
1976 
1977                 case EXC_CACHEDVAL_ERROR:
1978                     aIn >> nByte;
1979                     aIn.Ignore( 7 );
1980                     if( NULL != pMatrix )
1981                     {
1982                         pMatrix->PutError( XclTools::GetScErrorCode( nByte ), nC, nR );
1983                     }
1984                     break;
1985             }
1986         }
1987     }
1988 }
1989 
ReadExtensionNlr(XclImpStream & aIn)1990 void ExcelToSc::ReadExtensionNlr( XclImpStream& aIn )
1991 {
1992     // printf( "natural lang fmla;\n" );
1993 
1994     sal_uInt32 nFlags;
1995     aIn >> nFlags;
1996 
1997     sal_uInt32 nCount = nFlags & EXC_TOK_NLR_ADDMASK;
1998     aIn.Ignore( nCount * 4 ); // Drop the cell positions
1999 }
2000 
ReadExtensionMemArea(XclImpStream & aIn)2001 void ExcelToSc::ReadExtensionMemArea( XclImpStream& aIn )
2002 {
2003     // printf( "mem area;\n" );
2004 
2005     sal_uInt16 nCount;
2006     aIn >> nCount;
2007 
2008     aIn.Ignore( nCount * ((GetBiff() == EXC_BIFF8) ? 8 : 6) ); // drop the ranges
2009 }
2010 
ReadExtensions(const ExtensionTypeVec & rExtensions,XclImpStream & aIn)2011 void ExcelToSc::ReadExtensions( const ExtensionTypeVec& rExtensions,
2012                                 XclImpStream& aIn )
2013 {
2014     unsigned int nArray = 0;
2015 
2016     for( unsigned int i = 0 ; i < rExtensions.size() ; i++ )
2017     {
2018         ExtensionType eType = rExtensions[i];
2019 
2020         switch( eType )
2021         {
2022             case EXTENSION_ARRAY:
2023                 ReadExtensionArray( nArray++, aIn );
2024                 break;
2025 
2026             case EXTENSION_NLR:
2027                 ReadExtensionNlr( aIn );
2028                 break;
2029 
2030             case EXTENSION_MEMAREA:
2031                 ReadExtensionMemArea( aIn );
2032                 break;
2033         }
2034     }
2035 }
2036 
2037