1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*************************************************************************
4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
6 * Copyright 2000, 2010 Oracle and/or its affiliates.
8 * OpenOffice.org - a multi-platform office productivity suite
10 * This file is part of OpenOffice.org.
12 * OpenOffice.org is free software: you can redistribute it and/or modify
13 * it under the terms of the GNU Lesser General Public License version 3
14 * only, as published by the Free Software Foundation.
16 * OpenOffice.org is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU Lesser General Public License version 3 for more details
20 * (a copy is included in the LICENSE file that accompanied this code).
22 * You should have received a copy of the GNU Lesser General Public License
23 * version 3 along with OpenOffice.org. If not, see
24 * <http://www.openoffice.org/license.html>
25 * for a copy of the LGPLv3 License.
27 ************************************************************************/
34 #include <globals.hxx>
35 #include <database.hxx>
36 #include <tools/fsys.hxx>
37 #include <tools/debug.hxx>
39 SV_IMPL_META_FACTORY1( SvMetaModule
, SvMetaExtern
);
41 SvMetaModule::SvMetaModule()
42 : bImported( sal_False
)
43 , bIsModified( sal_False
)
47 SvMetaModule::SvMetaModule( const String
& rIdlFileName
, sal_Bool bImp
)
48 : aIdlFileName( rIdlFileName
)
49 , bImported( bImp
), bIsModified( sal_False
)
53 #define MODULE_VER 0x0001
54 void SvMetaModule::Load( SvPersistStream
& rStm
)
56 bImported
= sal_True
; // import always
57 SvMetaExtern::Load( rStm
);
61 rStm
>> nVer
; // version
62 DBG_ASSERT( (nVer
& ~IDL_WRITE_MASK
) == MODULE_VER
, "false version" );
68 aIdlFileName
= rStm
.ReadUniOrByteString( rStm
.GetStreamCharSet() );
69 aHelpFileName
.setString(read_lenPrefixed_uInt8s_ToOString
<sal_uInt16
>(rStm
));
70 aSlotIdFile
.setString(read_lenPrefixed_uInt8s_ToOString
<sal_uInt16
>(rStm
));
71 aModulePrefix
.setString(read_lenPrefixed_uInt8s_ToOString
<sal_uInt16
>(rStm
));
76 DBG_ASSERT( (nVer
& IDL_WRITE_MASK
) == IDL_WRITE_COMPILER
,
77 "no idl compiler format" );
83 void SvMetaModule::Save( SvPersistStream
& rStm
)
85 SvMetaExtern::Save( rStm
);
87 rStm
<< (sal_uInt16
)(MODULE_VER
| IDL_WRITE_COMPILER
); // Version
93 rStm
.WriteUniOrByteString( aIdlFileName
, rStm
.GetStreamCharSet() );
94 write_lenPrefixed_uInt8s_FromOString
<sal_uInt16
>(rStm
, aHelpFileName
.getString());
95 write_lenPrefixed_uInt8s_FromOString
<sal_uInt16
>(rStm
, aSlotIdFile
.getString());
96 write_lenPrefixed_uInt8s_FromOString
<sal_uInt16
>(rStm
, aModulePrefix
.getString());
98 // write compiler data
99 sal_uInt16 nCmpLen
= 0;
100 sal_uLong nLenPos
= rStm
.Tell();
105 // write length of compiler data
106 sal_uLong nPos
= rStm
.Tell();
107 rStm
.Seek( nLenPos
);
108 rStm
<< (sal_uInt16
)( nPos
- nLenPos
- sizeof( sal_uInt16
) );
112 sal_Bool
SvMetaModule::SetName( const rtl::OString
& rName
, SvIdlDataBase
* pBase
)
116 if( pBase
->GetModule( rName
) )
119 return SvMetaExtern::SetName( rName
);
122 sal_Bool
SvMetaModule::FillNextName( SvGlobalName
* pName
)
126 if( aNextName
< aEndName
)
129 bIsModified
= sal_True
;
135 void SvMetaModule::ReadAttributesSvIdl( SvIdlDataBase
& rBase
,
136 SvTokenStream
& rInStm
)
138 SvMetaExtern::ReadAttributesSvIdl( rBase
, rInStm
);
140 aHelpFileName
.ReadSvIdl( SvHash_HelpFile(), rInStm
);
141 if( aSlotIdFile
.ReadSvIdl( SvHash_SlotIdFile(), rInStm
) )
143 sal_uInt32 nTokPos
= rInStm
.Tell();
144 if( !rBase
.ReadIdFile( String::CreateFromAscii( aSlotIdFile
.getString().getStr() ) ) )
146 rtl::OStringBuffer
aStr(RTL_CONSTASCII_STRINGPARAM("cannot read file: "));
147 aStr
.append(aSlotIdFile
.getString());
148 rBase
.SetError( aStr
.makeStringAndClear(), rInStm
.GetToken() );
149 rBase
.WriteError( rInStm
);
151 rInStm
.Seek( nTokPos
);
154 aTypeLibFile
.ReadSvIdl( SvHash_TypeLibFile(), rInStm
);
155 aModulePrefix
.ReadSvIdl( SvHash_ModulePrefix(), rInStm
);
158 void SvMetaModule::WriteAttributesSvIdl( SvIdlDataBase
& rBase
,
162 SvMetaExtern::WriteAttributesSvIdl( rBase
, rOutStm
, nTab
);
163 if( !aTypeLibFile
.getString().isEmpty() || !aSlotIdFile
.getString().isEmpty() || !aTypeLibFile
.getString().isEmpty() )
165 if( !aHelpFileName
.getString().isEmpty() )
167 WriteTab( rOutStm
, nTab
);
168 aHelpFileName
.WriteSvIdl( SvHash_HelpFile(), rOutStm
, nTab
+1 );
169 rOutStm
<< ';' << endl
;
171 if( !aSlotIdFile
.getString().isEmpty() )
173 WriteTab( rOutStm
, nTab
);
174 aSlotIdFile
.WriteSvIdl( SvHash_SlotIdFile(), rOutStm
, nTab
+1 );
175 rOutStm
<< ';' << endl
;
177 if( !aTypeLibFile
.getString().isEmpty() )
179 WriteTab( rOutStm
, nTab
);
180 aTypeLibFile
.WriteSvIdl( SvHash_TypeLibFile(), rOutStm
, nTab
+1 );
181 rOutStm
<< ';' << endl
;
186 void SvMetaModule::ReadContextSvIdl( SvIdlDataBase
& rBase
,
187 SvTokenStream
& rInStm
)
189 sal_uInt32 nTokPos
= rInStm
.Tell();
190 if( rInStm
.GetToken()->Is( SvHash_interface() )
191 || rInStm
.GetToken()->Is( SvHash_shell() ) )
193 SvMetaClassRef aClass
= new SvMetaClass();
194 if( aClass
->ReadSvIdl( rBase
, rInStm
) )
196 aClassList
.Append( aClass
);
198 rBase
.GetClassList().Append( aClass
);
201 else if( rInStm
.GetToken()->Is( SvHash_enum() ) )
203 SvMetaTypeEnumRef aEnum
= new SvMetaTypeEnum();
205 if( aEnum
->ReadSvIdl( rBase
, rInStm
) )
207 // declared in module
208 aTypeList
.Append( aEnum
);
210 rBase
.GetTypeList().Append( aEnum
);
213 else if( rInStm
.GetToken()->Is( SvHash_item() )
214 || rInStm
.GetToken()->Is( SvHash_struct() )
215 || rInStm
.GetToken()->Is( SvHash_typedef() ) )
217 SvMetaTypeRef xItem
= new SvMetaType();
219 if( xItem
->ReadSvIdl( rBase
, rInStm
) )
221 // declared in module
222 aTypeList
.Append( xItem
);
224 rBase
.GetTypeList().Append( xItem
);
227 else if( rInStm
.GetToken()->Is( SvHash_include() ) )
229 sal_Bool bOk
= sal_False
;
230 rInStm
.GetToken_Next();
231 SvToken
* pTok
= rInStm
.GetToken_Next();
232 if( pTok
->IsString() )
234 DirEntry
aFullName( String::CreateFromAscii( pTok
->GetString().getStr() ) );
235 rBase
.StartNewFile( aFullName
.GetFull() );
236 if( aFullName
.Find( rBase
.GetPath() ) )
238 rBase
.AddDepFile(aFullName
.GetFull());
239 SvTokenStream
aTokStm( aFullName
.GetFull() );
240 if( SVSTREAM_OK
== aTokStm
.GetStream().GetError() )
242 // rescue error from old file
243 SvIdlError aOldErr
= rBase
.GetError();
245 rBase
.SetError( SvIdlError() );
247 sal_uInt32 nBeginPos
= 0xFFFFFFFF; // can not happen with Tell
248 while( nBeginPos
!= aTokStm
.Tell() )
250 nBeginPos
= aTokStm
.Tell();
251 ReadContextSvIdl( rBase
, aTokStm
);
252 aTokStm
.ReadDelemiter();
254 bOk
= aTokStm
.GetToken()->IsEof();
257 rBase
.WriteError( aTokStm
);
259 // recover error from old file
260 rBase
.SetError( aOldErr
);
264 rtl::OStringBuffer
aStr(RTL_CONSTASCII_STRINGPARAM(
265 "cannot open file: "));
266 aStr
.append(rtl::OUStringToOString(aFullName
.GetFull(),
267 RTL_TEXTENCODING_UTF8
));
268 rBase
.SetError(aStr
.makeStringAndClear(), pTok
);
273 rtl::OStringBuffer
aStr(RTL_CONSTASCII_STRINGPARAM(
274 "cannot find file:"));
275 aStr
.append(rtl::OUStringToOString(aFullName
.GetFull(),
276 RTL_TEXTENCODING_UTF8
));
277 rBase
.SetError(aStr
.makeStringAndClear(), pTok
);
281 rInStm
.Seek( nTokPos
);
285 SvMetaSlotRef xSlot
= new SvMetaSlot();
287 if( xSlot
->ReadSvIdl( rBase
, rInStm
) )
289 if( xSlot
->Test( rBase
, rInStm
) )
291 // declared in module
292 aAttrList
.Append( xSlot
);
294 rBase
.AppendAttr( xSlot
);
300 void SvMetaModule::WriteContextSvIdl( SvIdlDataBase
& rBase
,
304 SvMetaExtern::WriteContextSvIdl( rBase
, rOutStm
, nTab
);
306 for( n
= 0; n
< aTypeList
.Count(); n
++ )
308 WriteTab( rOutStm
, nTab
);
309 aTypeList
.GetObject( n
)->WriteSvIdl( rBase
, rOutStm
, nTab
);
312 for( n
= 0; n
< aAttrList
.Count(); n
++ )
314 WriteTab( rOutStm
, nTab
);
315 aAttrList
.GetObject( n
)->WriteSvIdl( rBase
, rOutStm
, nTab
);
318 for( n
= 0; n
< aClassList
.Count(); n
++ )
320 WriteTab( rOutStm
, nTab
);
321 aClassList
.GetObject( n
)->WriteSvIdl( rBase
, rOutStm
, nTab
);
325 sal_Bool
SvMetaModule::ReadSvIdl( SvIdlDataBase
& rBase
, SvTokenStream
& rInStm
)
327 bIsModified
= sal_True
; // up to now always when compiler running
329 sal_uInt32 nTokPos
= rInStm
.Tell();
330 SvToken
* pTok
= rInStm
.GetToken_Next();
331 sal_Bool bOk
= sal_False
;
332 bOk
= pTok
->Is( SvHash_module() );
335 pTok
= rInStm
.GetToken_Next();
336 if( pTok
->IsString() )
337 bOk
= aBeginName
.MakeId( String::CreateFromAscii( pTok
->GetString().getStr() ) );
339 rInStm
.ReadDelemiter();
342 pTok
= rInStm
.GetToken_Next();
343 if( pTok
->IsString() )
344 bOk
= aEndName
.MakeId( String::CreateFromAscii( pTok
->GetString().getStr() ) );
346 rInStm
.ReadDelemiter();
349 aNextName
= aBeginName
;
351 rBase
.Push( this ); // onto the context stack
353 if( ReadNameSvIdl( rBase
, rInStm
) )
355 // set pointer to itself
357 bOk
= SvMetaName::ReadSvIdl( rBase
, rInStm
);
359 rBase
.GetStack().Pop(); // remove from stack
362 rInStm
.Seek( nTokPos
);
366 void SvMetaModule::WriteSvIdl( SvIdlDataBase
& rBase
, SvStream
& rOutStm
,
369 rOutStm
<< SvHash_module()->GetName().getStr() << endl
371 rOutStm
.WriteUniOrByteString( aBeginName
.GetHexName(), rOutStm
.GetStreamCharSet() );
372 rOutStm
<< '\"' << endl
<< '\"';
373 rOutStm
.WriteUniOrByteString( aEndName
.GetHexName(), rOutStm
.GetStreamCharSet() );
374 rOutStm
<< '\"' << endl
;
375 SvMetaExtern::WriteSvIdl( rBase
, rOutStm
, nTab
);
378 void SvMetaModule::WriteSfx( SvIdlDataBase
& rBase
, SvStream
& rOutStm
)
380 for( sal_uLong n
= 0; n
< aClassList
.Count(); n
++ )
382 SvMetaClass
* pClass
= aClassList
.GetObject( n
);
383 pClass
->WriteSfx( rBase
, rOutStm
);
387 void SvMetaModule::WriteHelpIds( SvIdlDataBase
& rBase
, SvStream
& rOutStm
,
388 HelpIdTable
& rTable
)
390 for( sal_uLong n
= 0; n
< aClassList
.Count(); n
++ )
392 SvMetaClass
* pClass
= aClassList
.GetObject( n
);
393 pClass
->WriteHelpIds( rBase
, rOutStm
, rTable
);
397 void SvMetaModule::WriteAttributes( SvIdlDataBase
& rBase
,
400 WriteType nT
, WriteAttribute nA
)
402 SvMetaExtern::WriteAttributes( rBase
, rOutStm
, nTab
, nT
, nA
);
403 if( !aHelpFileName
.getString().isEmpty() )
405 WriteTab( rOutStm
, nTab
);
406 rOutStm
<< "// class SvMetaModule" << endl
;
407 WriteTab( rOutStm
, nTab
);
408 rOutStm
<< "helpfile(\"" << aHelpFileName
.getString().getStr() << "\");" << endl
;
412 void SvMetaModule::Write( SvIdlDataBase
& rBase
, SvStream
& rOutStm
,
414 WriteType nT
, WriteAttribute nA
)
420 if( !aSlotIdFile
.getString().isEmpty() )
422 WriteTab( rOutStm
, nTab
);
423 rOutStm
<< "#include \"" << aSlotIdFile
.getString().getStr() << '"' << endl
<< endl
;
425 SvMetaExtern::Write( rBase
, rOutStm
, nTab
, nT
, nA
);
427 WriteTab( rOutStm
, nTab
);
428 rOutStm
<< "library " << GetName().getString().getStr() << endl
;
429 WriteTab( rOutStm
, nTab
);
430 rOutStm
<< '{' << endl
;
431 WriteTab( rOutStm
, nTab
);
432 rOutStm
<< "importlib(\"STDOLE.TLB\");" << endl
;
434 for( sal_uLong n
= 0; n
< aClassList
.Count(); n
++ )
436 SvMetaClass
* pClass
= aClassList
.GetObject( n
);
437 if( !pClass
->IsShell() && pClass
->GetAutomation() )
439 WriteTab( rOutStm
, nTab
);
440 WriteStars( rOutStm
);
441 pClass
->Write( rBase
, rOutStm
, nTab
+1, nT
, nA
);
442 if( n
+1 < aClassList
.Count() )
447 rOutStm
<< '}' << endl
;
452 rOutStm
<< "SvIDL interface documentation" << endl
<< endl
;
453 rOutStm
<< "<MODULE>" << endl
<< GetName().getString().getStr() << endl
;
454 WriteDescription( rOutStm
);
455 rOutStm
<< "</MODULE>" << endl
<< endl
;
457 rOutStm
<< "<CLASSES>" << endl
;
458 for( sal_uLong n
= 0; n
< aClassList
.Count(); n
++ )
460 SvMetaClass
* pClass
= aClassList
.GetObject( n
);
461 if( !pClass
->IsShell() )
463 rOutStm
<< pClass
->GetName().getString().getStr();
464 SvMetaClass
* pSC
= pClass
->GetSuperClass();
466 rOutStm
<< " : " << pSC
->GetName().getString().getStr();
469 const SvClassElementMemberList
& rClassList
= pClass
->GetClassList();
470 if ( rClassList
.Count() )
474 for( sal_uLong m
=0; m
<rClassList
.Count(); ++m
)
476 SvClassElement
*pEle
= rClassList
.GetObject(m
);
477 SvMetaClass
*pCl
= pEle
->GetClass();
478 rOutStm
<< pCl
->GetName().getString().getStr();
479 if ( m
+1 == rClassList
.Count() )
489 rOutStm
<< "</CLASSES>" << endl
<< endl
;
496 for( sal_uLong n
= 0; n
< aClassList
.Count(); n
++ )
498 SvMetaClass
* pClass
= aClassList
.GetObject( n
);
499 if( !pClass
->IsShell() )
500 pClass
->Write( rBase
, rOutStm
, nTab
, nT
, nA
);
510 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */