1*89b56da7SAndrew Rist /**************************************************************
2cdf0e10cSrcweir *
3*89b56da7SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one
4*89b56da7SAndrew Rist * or more contributor license agreements. See the NOTICE file
5*89b56da7SAndrew Rist * distributed with this work for additional information
6*89b56da7SAndrew Rist * regarding copyright ownership. The ASF licenses this file
7*89b56da7SAndrew Rist * to you under the Apache License, Version 2.0 (the
8*89b56da7SAndrew Rist * "License"); you may not use this file except in compliance
9*89b56da7SAndrew Rist * with the License. You may obtain a copy of the License at
10*89b56da7SAndrew Rist *
11*89b56da7SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0
12*89b56da7SAndrew Rist *
13*89b56da7SAndrew Rist * Unless required by applicable law or agreed to in writing,
14*89b56da7SAndrew Rist * software distributed under the License is distributed on an
15*89b56da7SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*89b56da7SAndrew Rist * KIND, either express or implied. See the License for the
17*89b56da7SAndrew Rist * specific language governing permissions and limitations
18*89b56da7SAndrew Rist * under the License.
19*89b56da7SAndrew Rist *
20*89b56da7SAndrew Rist *************************************************************/
21*89b56da7SAndrew Rist
22*89b56da7SAndrew Rist
23cdf0e10cSrcweir
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_tools.hxx"
26cdf0e10cSrcweir
27cdf0e10cSrcweir #define _CONFIG_CXX
28cdf0e10cSrcweir
29cdf0e10cSrcweir #include <cstddef>
30cdf0e10cSrcweir #include <cstdlib>
31cdf0e10cSrcweir #include <limits>
32cdf0e10cSrcweir #include <new>
33cdf0e10cSrcweir #include <string.h>
34cdf0e10cSrcweir
35cdf0e10cSrcweir #ifdef WNT
36cdf0e10cSrcweir #include "stdlib.h"
37cdf0e10cSrcweir #endif
38cdf0e10cSrcweir #include <osl/file.hxx>
39cdf0e10cSrcweir #include <tools/stream.hxx>
40cdf0e10cSrcweir #include <tools/debug.hxx>
41cdf0e10cSrcweir #include <tools/config.hxx>
42cdf0e10cSrcweir #include <osl/security.h>
43cdf0e10cSrcweir
44cdf0e10cSrcweir #define MAXBUFLEN 1024 // Fuer Buffer bei VOS-Funktionen
45cdf0e10cSrcweir
46cdf0e10cSrcweir // -----------------
47cdf0e10cSrcweir // - ImplConfigData -
48cdf0e10cSrcweir // -----------------
49cdf0e10cSrcweir
50cdf0e10cSrcweir struct ImplKeyData
51cdf0e10cSrcweir {
52cdf0e10cSrcweir ImplKeyData* mpNext;
53cdf0e10cSrcweir ByteString maKey;
54cdf0e10cSrcweir ByteString maValue;
55cdf0e10cSrcweir sal_Bool mbIsComment;
56cdf0e10cSrcweir };
57cdf0e10cSrcweir
58cdf0e10cSrcweir struct ImplGroupData
59cdf0e10cSrcweir {
60cdf0e10cSrcweir ImplGroupData* mpNext;
61cdf0e10cSrcweir ImplKeyData* mpFirstKey;
62cdf0e10cSrcweir ByteString maGroupName;
63cdf0e10cSrcweir sal_uInt16 mnEmptyLines;
64cdf0e10cSrcweir };
65cdf0e10cSrcweir
66cdf0e10cSrcweir struct ImplConfigData
67cdf0e10cSrcweir {
68cdf0e10cSrcweir ImplGroupData* mpFirstGroup;
69cdf0e10cSrcweir XubString maFileName;
70cdf0e10cSrcweir sal_uIntPtr mnDataUpdateId;
71cdf0e10cSrcweir sal_uIntPtr mnTimeStamp;
72cdf0e10cSrcweir LineEnd meLineEnd;
73cdf0e10cSrcweir sal_uInt16 mnRefCount;
74cdf0e10cSrcweir sal_Bool mbModified;
75cdf0e10cSrcweir sal_Bool mbRead;
76cdf0e10cSrcweir sal_Bool mbIsUTF8BOM;
77cdf0e10cSrcweir };
78cdf0e10cSrcweir
79cdf0e10cSrcweir // =======================================================================
80cdf0e10cSrcweir
getEmptyByteString()81cdf0e10cSrcweir static ByteString& getEmptyByteString()
82cdf0e10cSrcweir {
83cdf0e10cSrcweir static ByteString aEmpty;
84cdf0e10cSrcweir return aEmpty;
85cdf0e10cSrcweir }
86cdf0e10cSrcweir
87cdf0e10cSrcweir // =======================================================================
88cdf0e10cSrcweir
toUncPath(const String & rPath)89cdf0e10cSrcweir static String toUncPath( const String& rPath )
90cdf0e10cSrcweir {
91cdf0e10cSrcweir ::rtl::OUString aFileURL;
92cdf0e10cSrcweir
93cdf0e10cSrcweir // check if rFileName is already a URL; if not make it so
94cdf0e10cSrcweir if( rPath.CompareToAscii( "file://", 7 ) == COMPARE_EQUAL )
95cdf0e10cSrcweir aFileURL = rPath;
96cdf0e10cSrcweir else if( ::osl::FileBase::getFileURLFromSystemPath( rPath, aFileURL ) != ::osl::FileBase::E_None )
97cdf0e10cSrcweir aFileURL = rPath;
98cdf0e10cSrcweir
99cdf0e10cSrcweir return aFileURL;
100cdf0e10cSrcweir }
101cdf0e10cSrcweir
ImplSysGetConfigTimeStamp(const XubString & rFileName)102cdf0e10cSrcweir static sal_uIntPtr ImplSysGetConfigTimeStamp( const XubString& rFileName )
103cdf0e10cSrcweir {
104cdf0e10cSrcweir sal_uIntPtr nTimeStamp = 0;
105cdf0e10cSrcweir ::osl::DirectoryItem aItem;
106cdf0e10cSrcweir ::osl::FileStatus aStatus( osl_FileStatus_Mask_ModifyTime );
107cdf0e10cSrcweir
108cdf0e10cSrcweir int nError = 0;
109cdf0e10cSrcweir if( ( nError = ::osl::DirectoryItem::get( rFileName, aItem ) ) == ::osl::FileBase::E_None &&
110cdf0e10cSrcweir aItem.getFileStatus( aStatus ) == ::osl::FileBase::E_None )
111cdf0e10cSrcweir {
112cdf0e10cSrcweir nTimeStamp = aStatus.getModifyTime().Seconds;
113cdf0e10cSrcweir }
114cdf0e10cSrcweir
115cdf0e10cSrcweir return nTimeStamp;
116cdf0e10cSrcweir }
117cdf0e10cSrcweir
118cdf0e10cSrcweir // -----------------------------------------------------------------------
119cdf0e10cSrcweir
ImplSysReadConfig(const XubString & rFileName,sal_uInt64 & rRead,sal_Bool & rbRead,sal_Bool & rbIsUTF8BOM,sal_uIntPtr & rTimeStamp)120cdf0e10cSrcweir static sal_uInt8* ImplSysReadConfig( const XubString& rFileName,
121cdf0e10cSrcweir sal_uInt64& rRead, sal_Bool& rbRead, sal_Bool& rbIsUTF8BOM, sal_uIntPtr& rTimeStamp )
122cdf0e10cSrcweir {
123cdf0e10cSrcweir sal_uInt8* pBuf = NULL;
124cdf0e10cSrcweir ::osl::File aFile( rFileName );
125cdf0e10cSrcweir
126cdf0e10cSrcweir if( aFile.open( osl_File_OpenFlag_Read ) == ::osl::FileBase::E_None )
127cdf0e10cSrcweir {
128cdf0e10cSrcweir sal_uInt64 nPos = 0, nRead = 0;
129cdf0e10cSrcweir if( aFile.getSize( nPos ) == ::osl::FileBase::E_None )
130cdf0e10cSrcweir {
131cdf0e10cSrcweir if (nPos > std::numeric_limits< std::size_t >::max()) {
132cdf0e10cSrcweir aFile.close();
133cdf0e10cSrcweir return 0;
134cdf0e10cSrcweir }
135cdf0e10cSrcweir pBuf = new sal_uInt8[static_cast< std::size_t >(nPos)];
136cdf0e10cSrcweir if( aFile.read( pBuf, nPos, nRead ) == ::osl::FileBase::E_None && nRead == nPos )
137cdf0e10cSrcweir {
138cdf0e10cSrcweir //skip the byte-order-mark 0xEF 0xBB 0xBF, if it was UTF8 files
139cdf0e10cSrcweir unsigned char BOM[3] = {0xEF, 0xBB, 0xBF};
140cdf0e10cSrcweir if (nRead > 2 && memcmp(pBuf, BOM, 3) == 0)
141cdf0e10cSrcweir {
142cdf0e10cSrcweir nRead -= 3;
143cdf0e10cSrcweir rtl_moveMemory(pBuf, pBuf + 3, sal::static_int_cast<sal_Size>(nRead * sizeof(sal_uInt8)) );
144cdf0e10cSrcweir rbIsUTF8BOM = sal_True;
145cdf0e10cSrcweir }
146cdf0e10cSrcweir
147cdf0e10cSrcweir rTimeStamp = ImplSysGetConfigTimeStamp( rFileName );
148cdf0e10cSrcweir rbRead = sal_True;
149cdf0e10cSrcweir rRead = nRead;
150cdf0e10cSrcweir }
151cdf0e10cSrcweir else
152cdf0e10cSrcweir {
153cdf0e10cSrcweir delete[] pBuf;
154cdf0e10cSrcweir pBuf = NULL;
155cdf0e10cSrcweir }
156cdf0e10cSrcweir }
157cdf0e10cSrcweir aFile.close();
158cdf0e10cSrcweir }
159cdf0e10cSrcweir
160cdf0e10cSrcweir return pBuf;
161cdf0e10cSrcweir }
162cdf0e10cSrcweir
163cdf0e10cSrcweir // -----------------------------------------------------------------------
164cdf0e10cSrcweir
ImplSysWriteConfig(const XubString & rFileName,const sal_uInt8 * pBuf,sal_uIntPtr nBufLen,sal_Bool rbIsUTF8BOM,sal_uIntPtr & rTimeStamp)165cdf0e10cSrcweir static sal_Bool ImplSysWriteConfig( const XubString& rFileName,
166cdf0e10cSrcweir const sal_uInt8* pBuf, sal_uIntPtr nBufLen, sal_Bool rbIsUTF8BOM, sal_uIntPtr& rTimeStamp )
167cdf0e10cSrcweir {
168cdf0e10cSrcweir sal_Bool bSuccess = sal_False;
169cdf0e10cSrcweir sal_Bool bUTF8BOMSuccess = sal_False;
170cdf0e10cSrcweir
171cdf0e10cSrcweir ::osl::File aFile( rFileName );
172cdf0e10cSrcweir ::osl::FileBase::RC eError = aFile.open( osl_File_OpenFlag_Write | osl_File_OpenFlag_Create );
173cdf0e10cSrcweir if( eError != ::osl::FileBase::E_None )
174cdf0e10cSrcweir eError = aFile.open( osl_File_OpenFlag_Write );
175cdf0e10cSrcweir if( eError == ::osl::FileBase::E_None )
176cdf0e10cSrcweir {
177cdf0e10cSrcweir // truncate
178cdf0e10cSrcweir aFile.setSize( 0 );
179cdf0e10cSrcweir sal_uInt64 nWritten;
180cdf0e10cSrcweir
181cdf0e10cSrcweir //write the the byte-order-mark 0xEF 0xBB 0xBF first , if it was UTF8 files
182cdf0e10cSrcweir if ( rbIsUTF8BOM )
183cdf0e10cSrcweir {
184cdf0e10cSrcweir unsigned char BOM[3] = {0xEF, 0xBB, 0xBF};
185cdf0e10cSrcweir sal_uInt64 nUTF8BOMWritten;
186cdf0e10cSrcweir if( aFile.write( BOM, 3, nUTF8BOMWritten ) == ::osl::FileBase::E_None && 3 == nUTF8BOMWritten )
187cdf0e10cSrcweir {
188cdf0e10cSrcweir bUTF8BOMSuccess = sal_True;
189cdf0e10cSrcweir }
190cdf0e10cSrcweir }
191cdf0e10cSrcweir
192cdf0e10cSrcweir if( aFile.write( pBuf, nBufLen, nWritten ) == ::osl::FileBase::E_None && nWritten == nBufLen )
193cdf0e10cSrcweir {
194cdf0e10cSrcweir bSuccess = sal_True;
195cdf0e10cSrcweir }
196cdf0e10cSrcweir if ( rbIsUTF8BOM ? bSuccess && bUTF8BOMSuccess : bSuccess )
197cdf0e10cSrcweir {
198cdf0e10cSrcweir rTimeStamp = ImplSysGetConfigTimeStamp( rFileName );
199cdf0e10cSrcweir }
200cdf0e10cSrcweir }
201cdf0e10cSrcweir
202cdf0e10cSrcweir return rbIsUTF8BOM ? bSuccess && bUTF8BOMSuccess : bSuccess;
203cdf0e10cSrcweir }
204cdf0e10cSrcweir
205cdf0e10cSrcweir // -----------------------------------------------------------------------
206cdf0e10cSrcweir
ImplMakeConfigName(const XubString * pFileName,const XubString * pPathName)207cdf0e10cSrcweir static String ImplMakeConfigName( const XubString* pFileName,
208cdf0e10cSrcweir const XubString* pPathName )
209cdf0e10cSrcweir {
210cdf0e10cSrcweir ::rtl::OUString aFileName;
211cdf0e10cSrcweir ::rtl::OUString aPathName;
212cdf0e10cSrcweir if ( pFileName )
213cdf0e10cSrcweir {
214cdf0e10cSrcweir #ifdef UNX
215cdf0e10cSrcweir aFileName = ::rtl::OUString::createFromAscii( "." );
216cdf0e10cSrcweir aFileName += *pFileName;
217cdf0e10cSrcweir aFileName += ::rtl::OUString::createFromAscii( "rc" );
218cdf0e10cSrcweir #else
219cdf0e10cSrcweir aFileName = *pFileName;
220cdf0e10cSrcweir aFileName += ::rtl::OUString::createFromAscii( ".ini" );
221cdf0e10cSrcweir #endif
222cdf0e10cSrcweir }
223cdf0e10cSrcweir else
224cdf0e10cSrcweir {
225cdf0e10cSrcweir #ifdef UNX
226cdf0e10cSrcweir aFileName = ::rtl::OUString::createFromAscii( ".sversionrc" );
227cdf0e10cSrcweir #else
228cdf0e10cSrcweir aFileName = ::rtl::OUString::createFromAscii( "sversion.ini" );
229cdf0e10cSrcweir #endif
230cdf0e10cSrcweir }
231cdf0e10cSrcweir
232cdf0e10cSrcweir // #88208# in case pPathName is set but empty and pFileName is set
233cdf0e10cSrcweir // and not empty just return the filename; on the default case
234cdf0e10cSrcweir // prepend default path as usual
235cdf0e10cSrcweir if ( pPathName && pPathName->Len() )
236cdf0e10cSrcweir aPathName = toUncPath( *pPathName );
237cdf0e10cSrcweir else if( pPathName && pFileName && pFileName->Len() )
238cdf0e10cSrcweir return aFileName;
239cdf0e10cSrcweir else
240cdf0e10cSrcweir {
241cdf0e10cSrcweir oslSecurity aSec = osl_getCurrentSecurity();
242cdf0e10cSrcweir osl_getConfigDir( aSec, &aPathName.pData );
243cdf0e10cSrcweir osl_freeSecurityHandle( aSec );
244cdf0e10cSrcweir }
245cdf0e10cSrcweir
246cdf0e10cSrcweir ::rtl::OUString aName( aPathName );
247cdf0e10cSrcweir aName += ::rtl::OUString::createFromAscii( "/" );
248cdf0e10cSrcweir aName += aFileName;
249cdf0e10cSrcweir
250cdf0e10cSrcweir return aName;
251cdf0e10cSrcweir }
252cdf0e10cSrcweir
253cdf0e10cSrcweir // -----------------------------------------------------------------------
254cdf0e10cSrcweir
255cdf0e10cSrcweir namespace {
256cdf0e10cSrcweir
makeByteString(sal_uInt8 const * p,sal_uInt64 n)257cdf0e10cSrcweir ByteString makeByteString(sal_uInt8 const * p, sal_uInt64 n) {
258cdf0e10cSrcweir if (n > STRING_MAXLEN) {
259cdf0e10cSrcweir #ifdef WNT
260cdf0e10cSrcweir abort();
261cdf0e10cSrcweir #else
262cdf0e10cSrcweir ::std::abort(); //TODO: handle this gracefully
263cdf0e10cSrcweir #endif
264cdf0e10cSrcweir }
265cdf0e10cSrcweir return ByteString(
266cdf0e10cSrcweir reinterpret_cast< char const * >(p),
267cdf0e10cSrcweir sal::static_int_cast< xub_StrLen >(n));
268cdf0e10cSrcweir }
269cdf0e10cSrcweir
270cdf0e10cSrcweir }
271cdf0e10cSrcweir
ImplMakeConfigList(ImplConfigData * pData,const sal_uInt8 * pBuf,sal_uInt64 nLen)272cdf0e10cSrcweir static void ImplMakeConfigList( ImplConfigData* pData,
273cdf0e10cSrcweir const sal_uInt8* pBuf, sal_uInt64 nLen )
274cdf0e10cSrcweir {
275cdf0e10cSrcweir // kein Buffer, keine Daten
276cdf0e10cSrcweir if ( !nLen )
277cdf0e10cSrcweir return;
278cdf0e10cSrcweir
279cdf0e10cSrcweir // Buffer parsen und Liste zusammenbauen
280cdf0e10cSrcweir sal_uInt64 nStart;
281cdf0e10cSrcweir sal_uInt64 nLineLen;
282cdf0e10cSrcweir xub_StrLen nNameLen;
283cdf0e10cSrcweir xub_StrLen nKeyLen;
284cdf0e10cSrcweir sal_uInt64 i;
285cdf0e10cSrcweir const sal_uInt8* pLine;
286cdf0e10cSrcweir ImplKeyData* pPrevKey = NULL;
287cdf0e10cSrcweir ImplKeyData* pKey;
288cdf0e10cSrcweir ImplGroupData* pPrevGroup = NULL;
289cdf0e10cSrcweir ImplGroupData* pGroup = NULL;
290cdf0e10cSrcweir i = 0;
291cdf0e10cSrcweir while ( i < nLen )
292cdf0e10cSrcweir {
293cdf0e10cSrcweir // Ctrl+Z
294cdf0e10cSrcweir if ( pBuf[i] == 0x1A )
295cdf0e10cSrcweir break;
296cdf0e10cSrcweir
297cdf0e10cSrcweir // Spaces und Tabs entfernen
298cdf0e10cSrcweir while ( (pBuf[i] == ' ') || (pBuf[i] == '\t') )
299cdf0e10cSrcweir i++;
300cdf0e10cSrcweir
301cdf0e10cSrcweir // Zeilenanfang merken
302cdf0e10cSrcweir nStart = i;
303cdf0e10cSrcweir pLine = pBuf+i;
304cdf0e10cSrcweir
305cdf0e10cSrcweir // Zeilenende suchen
306cdf0e10cSrcweir while ( (i < nLen) && pBuf[i] && (pBuf[i] != '\r') && (pBuf[i] != '\n') &&
307cdf0e10cSrcweir (pBuf[i] != 0x1A) )
308cdf0e10cSrcweir i++;
309cdf0e10cSrcweir
310cdf0e10cSrcweir nLineLen = i-nStart;
311cdf0e10cSrcweir
312cdf0e10cSrcweir // Wenn Zeilenende (CR/LF), dann noch einen weiterschalten
313cdf0e10cSrcweir if ( (i+1 < nLen) &&
314cdf0e10cSrcweir (pBuf[i] != pBuf[i+1]) &&
315cdf0e10cSrcweir ((pBuf[i+1] == '\r') || (pBuf[i+1] == '\n')) )
316cdf0e10cSrcweir i++;
317cdf0e10cSrcweir i++;
318cdf0e10cSrcweir
319cdf0e10cSrcweir // Zeile auswerten
320cdf0e10cSrcweir if ( *pLine == '[' )
321cdf0e10cSrcweir {
322cdf0e10cSrcweir pGroup = new ImplGroupData;
323cdf0e10cSrcweir pGroup->mpNext = NULL;
324cdf0e10cSrcweir pGroup->mpFirstKey = NULL;
325cdf0e10cSrcweir pGroup->mnEmptyLines = 0;
326cdf0e10cSrcweir if ( pPrevGroup )
327cdf0e10cSrcweir pPrevGroup->mpNext = pGroup;
328cdf0e10cSrcweir else
329cdf0e10cSrcweir pData->mpFirstGroup = pGroup;
330cdf0e10cSrcweir pPrevGroup = pGroup;
331cdf0e10cSrcweir pPrevKey = NULL;
332cdf0e10cSrcweir pKey = NULL;
333cdf0e10cSrcweir
334cdf0e10cSrcweir // Gruppennamen rausfiltern
335cdf0e10cSrcweir pLine++;
336cdf0e10cSrcweir nLineLen--;
337cdf0e10cSrcweir // Spaces und Tabs entfernen
338cdf0e10cSrcweir while ( (*pLine == ' ') || (*pLine == '\t') )
339cdf0e10cSrcweir {
340cdf0e10cSrcweir nLineLen--;
341cdf0e10cSrcweir pLine++;
342cdf0e10cSrcweir }
343cdf0e10cSrcweir nNameLen = 0;
344cdf0e10cSrcweir while ( (nNameLen < nLineLen) && (pLine[nNameLen] != ']') )
345cdf0e10cSrcweir nNameLen++;
346cdf0e10cSrcweir if ( nNameLen )
347cdf0e10cSrcweir {
348cdf0e10cSrcweir while ( (pLine[nNameLen-1] == ' ') || (pLine[nNameLen-1] == '\t') )
349cdf0e10cSrcweir nNameLen--;
350cdf0e10cSrcweir }
351cdf0e10cSrcweir pGroup->maGroupName = ByteString( (const sal_Char*)pLine, nNameLen );
352cdf0e10cSrcweir }
353cdf0e10cSrcweir else
354cdf0e10cSrcweir {
355cdf0e10cSrcweir if ( nLineLen )
356cdf0e10cSrcweir {
357cdf0e10cSrcweir // Wenn noch keine Gruppe existiert, dann alle Keys in die
358cdf0e10cSrcweir // Default-Gruppe
359cdf0e10cSrcweir if ( !pGroup )
360cdf0e10cSrcweir {
361cdf0e10cSrcweir pGroup = new ImplGroupData;
362cdf0e10cSrcweir pGroup->mpNext = NULL;
363cdf0e10cSrcweir pGroup->mpFirstKey = NULL;
364cdf0e10cSrcweir pGroup->mnEmptyLines = 0;
365cdf0e10cSrcweir if ( pPrevGroup )
366cdf0e10cSrcweir pPrevGroup->mpNext = pGroup;
367cdf0e10cSrcweir else
368cdf0e10cSrcweir pData->mpFirstGroup = pGroup;
369cdf0e10cSrcweir pPrevGroup = pGroup;
370cdf0e10cSrcweir pPrevKey = NULL;
371cdf0e10cSrcweir }
372cdf0e10cSrcweir
373cdf0e10cSrcweir // Falls Leerzeile vorhanden, dann anhaengen
374cdf0e10cSrcweir if ( pPrevKey )
375cdf0e10cSrcweir {
376cdf0e10cSrcweir while ( pGroup->mnEmptyLines )
377cdf0e10cSrcweir {
378cdf0e10cSrcweir pKey = new ImplKeyData;
379cdf0e10cSrcweir pKey->mbIsComment = sal_True;
380cdf0e10cSrcweir pPrevKey->mpNext = pKey;
381cdf0e10cSrcweir pPrevKey = pKey;
382cdf0e10cSrcweir pGroup->mnEmptyLines--;
383cdf0e10cSrcweir }
384cdf0e10cSrcweir }
385cdf0e10cSrcweir
386cdf0e10cSrcweir // Neuen Key erzeugen
387cdf0e10cSrcweir pKey = new ImplKeyData;
388cdf0e10cSrcweir pKey->mpNext = NULL;
389cdf0e10cSrcweir if ( pPrevKey )
390cdf0e10cSrcweir pPrevKey->mpNext = pKey;
391cdf0e10cSrcweir else
392cdf0e10cSrcweir pGroup->mpFirstKey = pKey;
393cdf0e10cSrcweir pPrevKey = pKey;
394cdf0e10cSrcweir if ( pLine[0] == ';' )
395cdf0e10cSrcweir {
396cdf0e10cSrcweir pKey->maValue = makeByteString(pLine, nLineLen);
397cdf0e10cSrcweir pKey->mbIsComment = sal_True;
398cdf0e10cSrcweir }
399cdf0e10cSrcweir else
400cdf0e10cSrcweir {
401cdf0e10cSrcweir pKey->mbIsComment = sal_False;
402cdf0e10cSrcweir nNameLen = 0;
403cdf0e10cSrcweir while ( (nNameLen < nLineLen) && (pLine[nNameLen] != '=') )
404cdf0e10cSrcweir nNameLen++;
405cdf0e10cSrcweir nKeyLen = nNameLen;
406cdf0e10cSrcweir // Spaces und Tabs entfernen
407cdf0e10cSrcweir if ( nNameLen )
408cdf0e10cSrcweir {
409cdf0e10cSrcweir while ( (pLine[nNameLen-1] == ' ') || (pLine[nNameLen-1] == '\t') )
410cdf0e10cSrcweir nNameLen--;
411cdf0e10cSrcweir }
412cdf0e10cSrcweir pKey->maKey = ByteString( (const sal_Char*)pLine, nNameLen );
413cdf0e10cSrcweir nKeyLen++;
414cdf0e10cSrcweir if ( nKeyLen < nLineLen )
415cdf0e10cSrcweir {
416cdf0e10cSrcweir pLine += nKeyLen;
417cdf0e10cSrcweir nLineLen -= nKeyLen;
418cdf0e10cSrcweir // Spaces und Tabs entfernen
419cdf0e10cSrcweir while ( (*pLine == ' ') || (*pLine == '\t') )
420cdf0e10cSrcweir {
421cdf0e10cSrcweir nLineLen--;
422cdf0e10cSrcweir pLine++;
423cdf0e10cSrcweir }
424cdf0e10cSrcweir if ( nLineLen )
425cdf0e10cSrcweir {
426cdf0e10cSrcweir while ( (pLine[nLineLen-1] == ' ') || (pLine[nLineLen-1] == '\t') )
427cdf0e10cSrcweir nLineLen--;
428cdf0e10cSrcweir pKey->maValue = makeByteString(pLine, nLineLen);
429cdf0e10cSrcweir }
430cdf0e10cSrcweir }
431cdf0e10cSrcweir }
432cdf0e10cSrcweir }
433cdf0e10cSrcweir else
434cdf0e10cSrcweir {
435cdf0e10cSrcweir // Leerzeilen werden nur gezaehlt und beim Erzeugen des
436cdf0e10cSrcweir // naechsten Keys angehaengt, da wir Leerzeilen am Ende
437cdf0e10cSrcweir // einer Gruppe auch nach hinzufuegen von neuen Keys nur
438cdf0e10cSrcweir // am Ende der Gruppe wieder speichern wollen
439cdf0e10cSrcweir if ( pGroup )
440cdf0e10cSrcweir pGroup->mnEmptyLines++;
441cdf0e10cSrcweir }
442cdf0e10cSrcweir }
443cdf0e10cSrcweir }
444cdf0e10cSrcweir }
445cdf0e10cSrcweir
446cdf0e10cSrcweir // -----------------------------------------------------------------------
447cdf0e10cSrcweir
ImplGetConfigBuffer(const ImplConfigData * pData,sal_uIntPtr & rLen)448cdf0e10cSrcweir static sal_uInt8* ImplGetConfigBuffer( const ImplConfigData* pData, sal_uIntPtr& rLen )
449cdf0e10cSrcweir {
450cdf0e10cSrcweir sal_uInt8* pWriteBuf;
451cdf0e10cSrcweir sal_uInt8* pBuf;
452cdf0e10cSrcweir sal_uInt8 aLineEndBuf[2] = {0, 0};
453cdf0e10cSrcweir ImplKeyData* pKey;
454cdf0e10cSrcweir ImplGroupData* pGroup;
455cdf0e10cSrcweir unsigned int nBufLen;
456cdf0e10cSrcweir sal_uInt16 nValueLen;
457cdf0e10cSrcweir sal_uInt16 nKeyLen;
458cdf0e10cSrcweir sal_uInt16 nLineEndLen;
459cdf0e10cSrcweir
460cdf0e10cSrcweir if ( pData->meLineEnd == LINEEND_CR )
461cdf0e10cSrcweir {
462cdf0e10cSrcweir aLineEndBuf[0] = _CR;
463cdf0e10cSrcweir nLineEndLen = 1;
464cdf0e10cSrcweir }
465cdf0e10cSrcweir else if ( pData->meLineEnd == LINEEND_LF )
466cdf0e10cSrcweir {
467cdf0e10cSrcweir aLineEndBuf[0] = _LF;
468cdf0e10cSrcweir nLineEndLen = 1;
469cdf0e10cSrcweir }
470cdf0e10cSrcweir else
471cdf0e10cSrcweir {
472cdf0e10cSrcweir aLineEndBuf[0] = _CR;
473cdf0e10cSrcweir aLineEndBuf[1] = _LF;
474cdf0e10cSrcweir nLineEndLen = 2;
475cdf0e10cSrcweir }
476cdf0e10cSrcweir
477cdf0e10cSrcweir // Buffergroesse ermitteln
478cdf0e10cSrcweir nBufLen = 0;
479cdf0e10cSrcweir pGroup = pData->mpFirstGroup;
480cdf0e10cSrcweir while ( pGroup )
481cdf0e10cSrcweir {
482cdf0e10cSrcweir // Leere Gruppen werden nicht geschrieben
483cdf0e10cSrcweir if ( pGroup->mpFirstKey )
484cdf0e10cSrcweir {
485cdf0e10cSrcweir nBufLen += pGroup->maGroupName.Len() + nLineEndLen + 2;
486cdf0e10cSrcweir pKey = pGroup->mpFirstKey;
487cdf0e10cSrcweir while ( pKey )
488cdf0e10cSrcweir {
489cdf0e10cSrcweir nValueLen = pKey->maValue.Len();
490cdf0e10cSrcweir if ( pKey->mbIsComment )
491cdf0e10cSrcweir nBufLen += nValueLen + nLineEndLen;
492cdf0e10cSrcweir else
493cdf0e10cSrcweir nBufLen += pKey->maKey.Len() + nValueLen + nLineEndLen + 1;
494cdf0e10cSrcweir
495cdf0e10cSrcweir pKey = pKey->mpNext;
496cdf0e10cSrcweir }
497cdf0e10cSrcweir
498cdf0e10cSrcweir // Leerzeile nach jeder Gruppe auch wieder speichern
499cdf0e10cSrcweir if ( !pGroup->mnEmptyLines )
500cdf0e10cSrcweir pGroup->mnEmptyLines = 1;
501cdf0e10cSrcweir nBufLen += nLineEndLen * pGroup->mnEmptyLines;
502cdf0e10cSrcweir }
503cdf0e10cSrcweir
504cdf0e10cSrcweir pGroup = pGroup->mpNext;
505cdf0e10cSrcweir }
506cdf0e10cSrcweir
507cdf0e10cSrcweir // Laenge dem Aufrufer mitteilen
508cdf0e10cSrcweir rLen = nBufLen;
509cdf0e10cSrcweir if ( !nBufLen )
510cdf0e10cSrcweir {
511cdf0e10cSrcweir pWriteBuf = new sal_uInt8[nLineEndLen];
512cdf0e10cSrcweir if ( pWriteBuf )
513cdf0e10cSrcweir {
514cdf0e10cSrcweir pWriteBuf[0] = aLineEndBuf[0];
515cdf0e10cSrcweir if ( nLineEndLen == 2 )
516cdf0e10cSrcweir pWriteBuf[1] = aLineEndBuf[1];
517cdf0e10cSrcweir return pWriteBuf;
518cdf0e10cSrcweir }
519cdf0e10cSrcweir else
520cdf0e10cSrcweir return 0;
521cdf0e10cSrcweir }
522cdf0e10cSrcweir
523cdf0e10cSrcweir // Schreibbuffer anlegen (wird vom Aufrufer zerstoert)
524cdf0e10cSrcweir pWriteBuf = new sal_uInt8[nBufLen];
525cdf0e10cSrcweir if ( !pWriteBuf )
526cdf0e10cSrcweir return 0;
527cdf0e10cSrcweir
528cdf0e10cSrcweir // Buffer fuellen
529cdf0e10cSrcweir pBuf = pWriteBuf;
530cdf0e10cSrcweir pGroup = pData->mpFirstGroup;
531cdf0e10cSrcweir while ( pGroup )
532cdf0e10cSrcweir {
533cdf0e10cSrcweir // Leere Gruppen werden nicht geschrieben
534cdf0e10cSrcweir if ( pGroup->mpFirstKey )
535cdf0e10cSrcweir {
536cdf0e10cSrcweir *pBuf = '['; pBuf++;
537cdf0e10cSrcweir memcpy( pBuf, pGroup->maGroupName.GetBuffer(), pGroup->maGroupName.Len() );
538cdf0e10cSrcweir pBuf += pGroup->maGroupName.Len();
539cdf0e10cSrcweir *pBuf = ']'; pBuf++;
540cdf0e10cSrcweir *pBuf = aLineEndBuf[0]; pBuf++;
541cdf0e10cSrcweir if ( nLineEndLen == 2 )
542cdf0e10cSrcweir {
543cdf0e10cSrcweir *pBuf = aLineEndBuf[1]; pBuf++;
544cdf0e10cSrcweir }
545cdf0e10cSrcweir pKey = pGroup->mpFirstKey;
546cdf0e10cSrcweir while ( pKey )
547cdf0e10cSrcweir {
548cdf0e10cSrcweir nValueLen = pKey->maValue.Len();
549cdf0e10cSrcweir if ( pKey->mbIsComment )
550cdf0e10cSrcweir {
551cdf0e10cSrcweir if ( nValueLen )
552cdf0e10cSrcweir {
553cdf0e10cSrcweir memcpy( pBuf, pKey->maValue.GetBuffer(), nValueLen );
554cdf0e10cSrcweir pBuf += nValueLen;
555cdf0e10cSrcweir }
556cdf0e10cSrcweir *pBuf = aLineEndBuf[0]; pBuf++;
557cdf0e10cSrcweir if ( nLineEndLen == 2 )
558cdf0e10cSrcweir {
559cdf0e10cSrcweir *pBuf = aLineEndBuf[1]; pBuf++;
560cdf0e10cSrcweir }
561cdf0e10cSrcweir }
562cdf0e10cSrcweir else
563cdf0e10cSrcweir {
564cdf0e10cSrcweir nKeyLen = pKey->maKey.Len();
565cdf0e10cSrcweir memcpy( pBuf, pKey->maKey.GetBuffer(), nKeyLen );
566cdf0e10cSrcweir pBuf += nKeyLen;
567cdf0e10cSrcweir *pBuf = '='; pBuf++;
568cdf0e10cSrcweir memcpy( pBuf, pKey->maValue.GetBuffer(), nValueLen );
569cdf0e10cSrcweir pBuf += nValueLen;
570cdf0e10cSrcweir *pBuf = aLineEndBuf[0]; pBuf++;
571cdf0e10cSrcweir if ( nLineEndLen == 2 )
572cdf0e10cSrcweir {
573cdf0e10cSrcweir *pBuf = aLineEndBuf[1]; pBuf++;
574cdf0e10cSrcweir }
575cdf0e10cSrcweir }
576cdf0e10cSrcweir
577cdf0e10cSrcweir pKey = pKey->mpNext;
578cdf0e10cSrcweir }
579cdf0e10cSrcweir
580cdf0e10cSrcweir // Leerzeile nach jeder Gruppe auch wieder speichern
581cdf0e10cSrcweir sal_uInt16 nEmptyLines = pGroup->mnEmptyLines;
582cdf0e10cSrcweir while ( nEmptyLines )
583cdf0e10cSrcweir {
584cdf0e10cSrcweir *pBuf = aLineEndBuf[0]; pBuf++;
585cdf0e10cSrcweir if ( nLineEndLen == 2 )
586cdf0e10cSrcweir {
587cdf0e10cSrcweir *pBuf = aLineEndBuf[1]; pBuf++;
588cdf0e10cSrcweir }
589cdf0e10cSrcweir nEmptyLines--;
590cdf0e10cSrcweir }
591cdf0e10cSrcweir }
592cdf0e10cSrcweir
593cdf0e10cSrcweir pGroup = pGroup->mpNext;
594cdf0e10cSrcweir }
595cdf0e10cSrcweir
596cdf0e10cSrcweir return pWriteBuf;
597cdf0e10cSrcweir }
598cdf0e10cSrcweir
599cdf0e10cSrcweir // -----------------------------------------------------------------------
600cdf0e10cSrcweir
ImplReadConfig(ImplConfigData * pData)601cdf0e10cSrcweir static void ImplReadConfig( ImplConfigData* pData )
602cdf0e10cSrcweir {
603cdf0e10cSrcweir sal_uIntPtr nTimeStamp = 0;
604cdf0e10cSrcweir sal_uInt64 nRead = 0;
605cdf0e10cSrcweir sal_Bool bRead = sal_False;
606cdf0e10cSrcweir sal_Bool bIsUTF8BOM =sal_False;
607cdf0e10cSrcweir sal_uInt8* pBuf = ImplSysReadConfig( pData->maFileName, nRead, bRead, bIsUTF8BOM, nTimeStamp );
608cdf0e10cSrcweir
609cdf0e10cSrcweir // Aus dem Buffer die Config-Verwaltungsliste aufbauen
610cdf0e10cSrcweir if ( pBuf )
611cdf0e10cSrcweir {
612cdf0e10cSrcweir ImplMakeConfigList( pData, pBuf, nRead );
613cdf0e10cSrcweir delete[] pBuf;
614cdf0e10cSrcweir }
615cdf0e10cSrcweir pData->mnTimeStamp = nTimeStamp;
616cdf0e10cSrcweir pData->mbModified = sal_False;
617cdf0e10cSrcweir if ( bRead )
618cdf0e10cSrcweir pData->mbRead = sal_True;
619cdf0e10cSrcweir if ( bIsUTF8BOM )
620cdf0e10cSrcweir pData->mbIsUTF8BOM = sal_True;
621cdf0e10cSrcweir }
622cdf0e10cSrcweir
623cdf0e10cSrcweir // -----------------------------------------------------------------------
624cdf0e10cSrcweir
ImplWriteConfig(ImplConfigData * pData)625cdf0e10cSrcweir static void ImplWriteConfig( ImplConfigData* pData )
626cdf0e10cSrcweir {
627cdf0e10cSrcweir #ifdef DBG_UTIL
628cdf0e10cSrcweir if ( DbgIsAssert() )
629cdf0e10cSrcweir {
630cdf0e10cSrcweir if ( pData->mnTimeStamp != ImplSysGetConfigTimeStamp( pData->maFileName ) )
631cdf0e10cSrcweir {
632cdf0e10cSrcweir DBG_ERROR1( "Config overwrites modified configfile:\n %s", ByteString( pData->maFileName, RTL_TEXTENCODING_UTF8 ).GetBuffer() );
633cdf0e10cSrcweir }
634cdf0e10cSrcweir }
635cdf0e10cSrcweir #endif
636cdf0e10cSrcweir
637cdf0e10cSrcweir // Aus der Config-Liste einen Buffer zusammenbauen
638cdf0e10cSrcweir sal_uIntPtr nBufLen;
639cdf0e10cSrcweir sal_uInt8* pBuf = ImplGetConfigBuffer( pData, nBufLen );
640cdf0e10cSrcweir if ( pBuf )
641cdf0e10cSrcweir {
642cdf0e10cSrcweir if ( ImplSysWriteConfig( pData->maFileName, pBuf, nBufLen, pData->mbIsUTF8BOM, pData->mnTimeStamp ) )
643cdf0e10cSrcweir pData->mbModified = sal_False;
644cdf0e10cSrcweir delete[] pBuf;
645cdf0e10cSrcweir }
646cdf0e10cSrcweir else
647cdf0e10cSrcweir pData->mbModified = sal_False;
648cdf0e10cSrcweir }
649cdf0e10cSrcweir
650cdf0e10cSrcweir // -----------------------------------------------------------------------
651cdf0e10cSrcweir
ImplDeleteConfigData(ImplConfigData * pData)652cdf0e10cSrcweir static void ImplDeleteConfigData( ImplConfigData* pData )
653cdf0e10cSrcweir {
654cdf0e10cSrcweir ImplKeyData* pTempKey;
655cdf0e10cSrcweir ImplKeyData* pKey;
656cdf0e10cSrcweir ImplGroupData* pTempGroup;
657cdf0e10cSrcweir ImplGroupData* pGroup = pData->mpFirstGroup;
658cdf0e10cSrcweir while ( pGroup )
659cdf0e10cSrcweir {
660cdf0e10cSrcweir pTempGroup = pGroup->mpNext;
661cdf0e10cSrcweir
662cdf0e10cSrcweir // Alle Keys loeschen
663cdf0e10cSrcweir pKey = pGroup->mpFirstKey;
664cdf0e10cSrcweir while ( pKey )
665cdf0e10cSrcweir {
666cdf0e10cSrcweir pTempKey = pKey->mpNext;
667cdf0e10cSrcweir delete pKey;
668cdf0e10cSrcweir pKey = pTempKey;
669cdf0e10cSrcweir }
670cdf0e10cSrcweir
671cdf0e10cSrcweir // Gruppe loeschen und weiterschalten
672cdf0e10cSrcweir delete pGroup;
673cdf0e10cSrcweir pGroup = pTempGroup;
674cdf0e10cSrcweir }
675cdf0e10cSrcweir
676cdf0e10cSrcweir pData->mpFirstGroup = NULL;
677cdf0e10cSrcweir }
678cdf0e10cSrcweir
679cdf0e10cSrcweir // =======================================================================
680cdf0e10cSrcweir
ImplGetConfigData(const XubString & rFileName)681cdf0e10cSrcweir static ImplConfigData* ImplGetConfigData( const XubString& rFileName )
682cdf0e10cSrcweir {
683cdf0e10cSrcweir ImplConfigData* pData;
684cdf0e10cSrcweir
685cdf0e10cSrcweir pData = new ImplConfigData;
686cdf0e10cSrcweir pData->maFileName = rFileName;
687cdf0e10cSrcweir pData->mpFirstGroup = NULL;
688cdf0e10cSrcweir pData->mnDataUpdateId = 0;
689cdf0e10cSrcweir pData->meLineEnd = LINEEND_CRLF;
690cdf0e10cSrcweir pData->mnRefCount = 0;
691cdf0e10cSrcweir pData->mbRead = sal_False;
692cdf0e10cSrcweir pData->mbIsUTF8BOM = sal_False;
693cdf0e10cSrcweir ImplReadConfig( pData );
694cdf0e10cSrcweir
695cdf0e10cSrcweir return pData;
696cdf0e10cSrcweir }
697cdf0e10cSrcweir
698cdf0e10cSrcweir // -----------------------------------------------------------------------
699cdf0e10cSrcweir
ImplFreeConfigData(ImplConfigData * pDelData)700cdf0e10cSrcweir static void ImplFreeConfigData( ImplConfigData* pDelData )
701cdf0e10cSrcweir {
702cdf0e10cSrcweir ImplDeleteConfigData( pDelData );
703cdf0e10cSrcweir delete pDelData;
704cdf0e10cSrcweir }
705cdf0e10cSrcweir
706cdf0e10cSrcweir // =======================================================================
707cdf0e10cSrcweir
ImplUpdateConfig() const708cdf0e10cSrcweir sal_Bool Config::ImplUpdateConfig() const
709cdf0e10cSrcweir {
710cdf0e10cSrcweir // Wenn sich TimeStamp unterscheidet, dann Datei neu einlesen
711cdf0e10cSrcweir if ( mpData->mnTimeStamp != ImplSysGetConfigTimeStamp( maFileName ) )
712cdf0e10cSrcweir {
713cdf0e10cSrcweir ImplDeleteConfigData( mpData );
714cdf0e10cSrcweir ImplReadConfig( mpData );
715cdf0e10cSrcweir mpData->mnDataUpdateId++;
716cdf0e10cSrcweir return sal_True;
717cdf0e10cSrcweir }
718cdf0e10cSrcweir else
719cdf0e10cSrcweir return sal_False;
720cdf0e10cSrcweir }
721cdf0e10cSrcweir
722cdf0e10cSrcweir // -----------------------------------------------------------------------
723cdf0e10cSrcweir
ImplGetGroup() const724cdf0e10cSrcweir ImplGroupData* Config::ImplGetGroup() const
725cdf0e10cSrcweir {
726cdf0e10cSrcweir if ( !mpActGroup || (mnDataUpdateId != mpData->mnDataUpdateId) )
727cdf0e10cSrcweir {
728cdf0e10cSrcweir ImplGroupData* pPrevGroup = NULL;
729cdf0e10cSrcweir ImplGroupData* pGroup = mpData->mpFirstGroup;
730cdf0e10cSrcweir while ( pGroup )
731cdf0e10cSrcweir {
732cdf0e10cSrcweir if ( pGroup->maGroupName.EqualsIgnoreCaseAscii( maGroupName ) )
733cdf0e10cSrcweir break;
734cdf0e10cSrcweir
735cdf0e10cSrcweir pPrevGroup = pGroup;
736cdf0e10cSrcweir pGroup = pGroup->mpNext;
737cdf0e10cSrcweir }
738cdf0e10cSrcweir
739cdf0e10cSrcweir // Falls Gruppe noch nicht existiert, dann dazufuegen
740cdf0e10cSrcweir if ( !pGroup )
741cdf0e10cSrcweir {
742cdf0e10cSrcweir pGroup = new ImplGroupData;
743cdf0e10cSrcweir pGroup->mpNext = NULL;
744cdf0e10cSrcweir pGroup->mpFirstKey = NULL;
745cdf0e10cSrcweir pGroup->mnEmptyLines = 1;
746cdf0e10cSrcweir if ( pPrevGroup )
747cdf0e10cSrcweir pPrevGroup->mpNext = pGroup;
748cdf0e10cSrcweir else
749cdf0e10cSrcweir mpData->mpFirstGroup = pGroup;
750cdf0e10cSrcweir }
751cdf0e10cSrcweir
752cdf0e10cSrcweir // Gruppenname immer uebernehmen, da er auch in dieser Form
753cdf0e10cSrcweir // geschrieben werden soll. Ausserdem die Cache-Members der
754cdf0e10cSrcweir // Config-Klasse updaten
755cdf0e10cSrcweir pGroup->maGroupName = maGroupName;
756cdf0e10cSrcweir ((Config*)this)->mnDataUpdateId = mpData->mnDataUpdateId;
757cdf0e10cSrcweir ((Config*)this)->mpActGroup = pGroup;
758cdf0e10cSrcweir }
759cdf0e10cSrcweir
760cdf0e10cSrcweir return mpActGroup;
761cdf0e10cSrcweir }
762cdf0e10cSrcweir
763cdf0e10cSrcweir // =======================================================================
764cdf0e10cSrcweir
Config()765cdf0e10cSrcweir Config::Config()
766cdf0e10cSrcweir {
767cdf0e10cSrcweir // Daten initialisieren und einlesen
768cdf0e10cSrcweir maFileName = ImplMakeConfigName( NULL, NULL );
769cdf0e10cSrcweir mpData = ImplGetConfigData( maFileName );
770cdf0e10cSrcweir mpActGroup = NULL;
771cdf0e10cSrcweir mnDataUpdateId = 0;
772cdf0e10cSrcweir mnLockCount = 1;
773cdf0e10cSrcweir mbPersistence = sal_True;
774cdf0e10cSrcweir
775cdf0e10cSrcweir #ifdef DBG_UTIL
776cdf0e10cSrcweir DBG_TRACE( "Config::Config()" );
777cdf0e10cSrcweir #endif
778cdf0e10cSrcweir }
779cdf0e10cSrcweir
780cdf0e10cSrcweir // -----------------------------------------------------------------------
781cdf0e10cSrcweir
Config(const XubString & rFileName)782cdf0e10cSrcweir Config::Config( const XubString& rFileName )
783cdf0e10cSrcweir {
784cdf0e10cSrcweir // Daten initialisieren und einlesen
785cdf0e10cSrcweir maFileName = toUncPath( rFileName );
786cdf0e10cSrcweir mpData = ImplGetConfigData( maFileName );
787cdf0e10cSrcweir mpActGroup = NULL;
788cdf0e10cSrcweir mnDataUpdateId = 0;
789cdf0e10cSrcweir mnLockCount = 1;
790cdf0e10cSrcweir mbPersistence = sal_True;
791cdf0e10cSrcweir
792cdf0e10cSrcweir #ifdef DBG_UTIL
793cdf0e10cSrcweir ByteString aTraceStr( "Config::Config( " );
794cdf0e10cSrcweir aTraceStr += ByteString( maFileName, RTL_TEXTENCODING_UTF8 );
795cdf0e10cSrcweir aTraceStr += " )";
796cdf0e10cSrcweir DBG_TRACE( aTraceStr.GetBuffer() );
797cdf0e10cSrcweir #endif
798cdf0e10cSrcweir }
799cdf0e10cSrcweir
800cdf0e10cSrcweir // -----------------------------------------------------------------------
801cdf0e10cSrcweir
~Config()802cdf0e10cSrcweir Config::~Config()
803cdf0e10cSrcweir {
804cdf0e10cSrcweir #ifdef DBG_UTIL
805cdf0e10cSrcweir DBG_TRACE( "Config::~Config()" );
806cdf0e10cSrcweir #endif
807cdf0e10cSrcweir
808cdf0e10cSrcweir Flush();
809cdf0e10cSrcweir ImplFreeConfigData( mpData );
810cdf0e10cSrcweir }
811cdf0e10cSrcweir
812cdf0e10cSrcweir // -----------------------------------------------------------------------
813cdf0e10cSrcweir
GetDefDirectory()814cdf0e10cSrcweir String Config::GetDefDirectory()
815cdf0e10cSrcweir {
816cdf0e10cSrcweir ::rtl::OUString aDefConfig;
817cdf0e10cSrcweir oslSecurity aSec = osl_getCurrentSecurity();
818cdf0e10cSrcweir osl_getConfigDir( aSec, &aDefConfig.pData );
819cdf0e10cSrcweir osl_freeSecurityHandle( aSec );
820cdf0e10cSrcweir
821cdf0e10cSrcweir return aDefConfig;
822cdf0e10cSrcweir }
823cdf0e10cSrcweir
824cdf0e10cSrcweir // -----------------------------------------------------------------------
825cdf0e10cSrcweir
GetConfigName(const XubString & rPath,const XubString & rBaseName)826cdf0e10cSrcweir XubString Config::GetConfigName( const XubString& rPath,
827cdf0e10cSrcweir const XubString& rBaseName )
828cdf0e10cSrcweir {
829cdf0e10cSrcweir return ImplMakeConfigName( &rBaseName, &rPath );
830cdf0e10cSrcweir }
831cdf0e10cSrcweir
832cdf0e10cSrcweir // -----------------------------------------------------------------------
833cdf0e10cSrcweir
SetGroup(const ByteString & rGroup)834cdf0e10cSrcweir void Config::SetGroup( const ByteString& rGroup )
835cdf0e10cSrcweir {
836cdf0e10cSrcweir // Wenn neue Gruppe gesetzt wird, muss beim naechsten mal die
837cdf0e10cSrcweir // Gruppe neu ermittelt werden
838cdf0e10cSrcweir if ( maGroupName != rGroup )
839cdf0e10cSrcweir {
840cdf0e10cSrcweir maGroupName = rGroup;
841cdf0e10cSrcweir mnDataUpdateId = mpData->mnDataUpdateId-1;
842cdf0e10cSrcweir }
843cdf0e10cSrcweir }
844cdf0e10cSrcweir
845cdf0e10cSrcweir // -----------------------------------------------------------------------
846cdf0e10cSrcweir
DeleteGroup(const ByteString & rGroup)847cdf0e10cSrcweir void Config::DeleteGroup( const ByteString& rGroup )
848cdf0e10cSrcweir {
849cdf0e10cSrcweir // Config-Daten evt. updaten
850cdf0e10cSrcweir if ( !mnLockCount || !mpData->mbRead )
851cdf0e10cSrcweir {
852cdf0e10cSrcweir ImplUpdateConfig();
853cdf0e10cSrcweir mpData->mbRead = sal_True;
854cdf0e10cSrcweir }
855cdf0e10cSrcweir
856cdf0e10cSrcweir ImplGroupData* pPrevGroup = NULL;
857cdf0e10cSrcweir ImplGroupData* pGroup = mpData->mpFirstGroup;
858cdf0e10cSrcweir while ( pGroup )
859cdf0e10cSrcweir {
860cdf0e10cSrcweir if ( pGroup->maGroupName.EqualsIgnoreCaseAscii( rGroup ) )
861cdf0e10cSrcweir break;
862cdf0e10cSrcweir
863cdf0e10cSrcweir pPrevGroup = pGroup;
864cdf0e10cSrcweir pGroup = pGroup->mpNext;
865cdf0e10cSrcweir }
866cdf0e10cSrcweir
867cdf0e10cSrcweir if ( pGroup )
868cdf0e10cSrcweir {
869cdf0e10cSrcweir // Alle Keys loeschen
870cdf0e10cSrcweir ImplKeyData* pTempKey;
871cdf0e10cSrcweir ImplKeyData* pKey = pGroup->mpFirstKey;
872cdf0e10cSrcweir while ( pKey )
873cdf0e10cSrcweir {
874cdf0e10cSrcweir pTempKey = pKey->mpNext;
875cdf0e10cSrcweir delete pKey;
876cdf0e10cSrcweir pKey = pTempKey;
877cdf0e10cSrcweir }
878cdf0e10cSrcweir
879cdf0e10cSrcweir // Gruppe weiterschalten und loeschen
880cdf0e10cSrcweir if ( pPrevGroup )
881cdf0e10cSrcweir pPrevGroup->mpNext = pGroup->mpNext;
882cdf0e10cSrcweir else
883cdf0e10cSrcweir mpData->mpFirstGroup = pGroup->mpNext;
884cdf0e10cSrcweir delete pGroup;
885cdf0e10cSrcweir
886cdf0e10cSrcweir // Config-Datei neu schreiben
887cdf0e10cSrcweir if ( !mnLockCount && mbPersistence )
888cdf0e10cSrcweir ImplWriteConfig( mpData );
889cdf0e10cSrcweir else
890cdf0e10cSrcweir {
891cdf0e10cSrcweir mpData->mbModified = sal_True;
892cdf0e10cSrcweir }
893cdf0e10cSrcweir
894cdf0e10cSrcweir // Gruppen auf ungluetig setzen
895cdf0e10cSrcweir mnDataUpdateId = mpData->mnDataUpdateId;
896cdf0e10cSrcweir mpData->mnDataUpdateId++;
897cdf0e10cSrcweir }
898cdf0e10cSrcweir }
899cdf0e10cSrcweir
900cdf0e10cSrcweir // -----------------------------------------------------------------------
901cdf0e10cSrcweir
GetGroupName(sal_uInt16 nGroup) const902cdf0e10cSrcweir ByteString Config::GetGroupName( sal_uInt16 nGroup ) const
903cdf0e10cSrcweir {
904cdf0e10cSrcweir // Config-Daten evt. updaten
905cdf0e10cSrcweir if ( !mnLockCount )
906cdf0e10cSrcweir ImplUpdateConfig();
907cdf0e10cSrcweir
908cdf0e10cSrcweir ImplGroupData* pGroup = mpData->mpFirstGroup;
909cdf0e10cSrcweir sal_uInt16 nGroupCount = 0;
910cdf0e10cSrcweir ByteString aGroupName;
911cdf0e10cSrcweir while ( pGroup )
912cdf0e10cSrcweir {
913cdf0e10cSrcweir if ( nGroup == nGroupCount )
914cdf0e10cSrcweir {
915cdf0e10cSrcweir aGroupName = pGroup->maGroupName;
916cdf0e10cSrcweir break;
917cdf0e10cSrcweir }
918cdf0e10cSrcweir
919cdf0e10cSrcweir nGroupCount++;
920cdf0e10cSrcweir pGroup = pGroup->mpNext;
921cdf0e10cSrcweir }
922cdf0e10cSrcweir
923cdf0e10cSrcweir return aGroupName;
924cdf0e10cSrcweir }
925cdf0e10cSrcweir
926cdf0e10cSrcweir // -----------------------------------------------------------------------
927cdf0e10cSrcweir
GetGroupCount() const928cdf0e10cSrcweir sal_uInt16 Config::GetGroupCount() const
929cdf0e10cSrcweir {
930cdf0e10cSrcweir // Config-Daten evt. updaten
931cdf0e10cSrcweir if ( !mnLockCount )
932cdf0e10cSrcweir ImplUpdateConfig();
933cdf0e10cSrcweir
934cdf0e10cSrcweir ImplGroupData* pGroup = mpData->mpFirstGroup;
935cdf0e10cSrcweir sal_uInt16 nGroupCount = 0;
936cdf0e10cSrcweir while ( pGroup )
937cdf0e10cSrcweir {
938cdf0e10cSrcweir nGroupCount++;
939cdf0e10cSrcweir pGroup = pGroup->mpNext;
940cdf0e10cSrcweir }
941cdf0e10cSrcweir
942cdf0e10cSrcweir return nGroupCount;
943cdf0e10cSrcweir }
944cdf0e10cSrcweir
945cdf0e10cSrcweir // -----------------------------------------------------------------------
946cdf0e10cSrcweir
HasGroup(const ByteString & rGroup) const947cdf0e10cSrcweir sal_Bool Config::HasGroup( const ByteString& rGroup ) const
948cdf0e10cSrcweir {
949cdf0e10cSrcweir // Config-Daten evt. updaten
950cdf0e10cSrcweir if ( !mnLockCount )
951cdf0e10cSrcweir ImplUpdateConfig();
952cdf0e10cSrcweir
953cdf0e10cSrcweir ImplGroupData* pGroup = mpData->mpFirstGroup;
954cdf0e10cSrcweir sal_Bool bRet = sal_False;
955cdf0e10cSrcweir
956cdf0e10cSrcweir while( pGroup )
957cdf0e10cSrcweir {
958cdf0e10cSrcweir if( pGroup->maGroupName.EqualsIgnoreCaseAscii( rGroup ) )
959cdf0e10cSrcweir {
960cdf0e10cSrcweir bRet = sal_True;
961cdf0e10cSrcweir break;
962cdf0e10cSrcweir }
963cdf0e10cSrcweir
964cdf0e10cSrcweir pGroup = pGroup->mpNext;
965cdf0e10cSrcweir }
966cdf0e10cSrcweir
967cdf0e10cSrcweir return bRet;
968cdf0e10cSrcweir }
969cdf0e10cSrcweir
970cdf0e10cSrcweir // -----------------------------------------------------------------------
971cdf0e10cSrcweir
ReadKey(const ByteString & rKey) const972cdf0e10cSrcweir ByteString Config::ReadKey( const ByteString& rKey ) const
973cdf0e10cSrcweir {
974cdf0e10cSrcweir return ReadKey( rKey, getEmptyByteString() );
975cdf0e10cSrcweir }
976cdf0e10cSrcweir
977cdf0e10cSrcweir // -----------------------------------------------------------------------
978cdf0e10cSrcweir
ReadKey(const ByteString & rKey,rtl_TextEncoding eEncoding) const979cdf0e10cSrcweir UniString Config::ReadKey( const ByteString& rKey, rtl_TextEncoding eEncoding ) const
980cdf0e10cSrcweir {
981cdf0e10cSrcweir if ( mpData->mbIsUTF8BOM )
982cdf0e10cSrcweir eEncoding = RTL_TEXTENCODING_UTF8;
983cdf0e10cSrcweir return UniString( ReadKey( rKey ), eEncoding );
984cdf0e10cSrcweir }
985cdf0e10cSrcweir
986cdf0e10cSrcweir // -----------------------------------------------------------------------
987cdf0e10cSrcweir
ReadKey(const ByteString & rKey,const ByteString & rDefault) const988cdf0e10cSrcweir ByteString Config::ReadKey( const ByteString& rKey, const ByteString& rDefault ) const
989cdf0e10cSrcweir {
990cdf0e10cSrcweir #ifdef DBG_UTIL
991cdf0e10cSrcweir ByteString aTraceStr( "Config::ReadKey( " );
992cdf0e10cSrcweir aTraceStr += rKey;
993cdf0e10cSrcweir aTraceStr += " ) from ";
994cdf0e10cSrcweir aTraceStr += GetGroup();
995cdf0e10cSrcweir aTraceStr += " in ";
996cdf0e10cSrcweir aTraceStr += ByteString( maFileName, RTL_TEXTENCODING_UTF8 );
997cdf0e10cSrcweir DBG_TRACE( aTraceStr.GetBuffer() );
998cdf0e10cSrcweir #endif
999cdf0e10cSrcweir
1000cdf0e10cSrcweir // Config-Daten evt. updaten
1001cdf0e10cSrcweir if ( !mnLockCount )
1002cdf0e10cSrcweir ImplUpdateConfig();
1003cdf0e10cSrcweir
1004cdf0e10cSrcweir // Key suchen und Value zurueckgeben
1005cdf0e10cSrcweir ImplGroupData* pGroup = ImplGetGroup();
1006cdf0e10cSrcweir if ( pGroup )
1007cdf0e10cSrcweir {
1008cdf0e10cSrcweir ImplKeyData* pKey = pGroup->mpFirstKey;
1009cdf0e10cSrcweir while ( pKey )
1010cdf0e10cSrcweir {
1011cdf0e10cSrcweir if ( !pKey->mbIsComment && pKey->maKey.EqualsIgnoreCaseAscii( rKey ) )
1012cdf0e10cSrcweir return pKey->maValue;
1013cdf0e10cSrcweir
1014cdf0e10cSrcweir pKey = pKey->mpNext;
1015cdf0e10cSrcweir }
1016cdf0e10cSrcweir }
1017cdf0e10cSrcweir
1018cdf0e10cSrcweir return rDefault;
1019cdf0e10cSrcweir }
1020cdf0e10cSrcweir
1021cdf0e10cSrcweir // -----------------------------------------------------------------------
1022cdf0e10cSrcweir
WriteKey(const ByteString & rKey,const ByteString & rStr)1023cdf0e10cSrcweir void Config::WriteKey( const ByteString& rKey, const ByteString& rStr )
1024cdf0e10cSrcweir {
1025cdf0e10cSrcweir #ifdef DBG_UTIL
1026cdf0e10cSrcweir ByteString aTraceStr( "Config::WriteKey( " );
1027cdf0e10cSrcweir aTraceStr += rKey;
1028cdf0e10cSrcweir aTraceStr += ", ";
1029cdf0e10cSrcweir aTraceStr += rStr;
1030cdf0e10cSrcweir aTraceStr += " ) to ";
1031cdf0e10cSrcweir aTraceStr += GetGroup();
1032cdf0e10cSrcweir aTraceStr += " in ";
1033cdf0e10cSrcweir aTraceStr += ByteString( maFileName, RTL_TEXTENCODING_UTF8 );
1034cdf0e10cSrcweir DBG_TRACE( aTraceStr.GetBuffer() );
1035cdf0e10cSrcweir DBG_ASSERTWARNING( rStr != ReadKey( rKey ), "Config::WriteKey() with the same Value" );
1036cdf0e10cSrcweir #endif
1037cdf0e10cSrcweir
1038cdf0e10cSrcweir // Config-Daten evt. updaten
1039cdf0e10cSrcweir if ( !mnLockCount || !mpData->mbRead )
1040cdf0e10cSrcweir {
1041cdf0e10cSrcweir ImplUpdateConfig();
1042cdf0e10cSrcweir mpData->mbRead = sal_True;
1043cdf0e10cSrcweir }
1044cdf0e10cSrcweir
1045cdf0e10cSrcweir // Key suchen und Value setzen
1046cdf0e10cSrcweir ImplGroupData* pGroup = ImplGetGroup();
1047cdf0e10cSrcweir if ( pGroup )
1048cdf0e10cSrcweir {
1049cdf0e10cSrcweir ImplKeyData* pPrevKey = NULL;
1050cdf0e10cSrcweir ImplKeyData* pKey = pGroup->mpFirstKey;
1051cdf0e10cSrcweir while ( pKey )
1052cdf0e10cSrcweir {
1053cdf0e10cSrcweir if ( !pKey->mbIsComment && pKey->maKey.EqualsIgnoreCaseAscii( rKey ) )
1054cdf0e10cSrcweir break;
1055cdf0e10cSrcweir
1056cdf0e10cSrcweir pPrevKey = pKey;
1057cdf0e10cSrcweir pKey = pKey->mpNext;
1058cdf0e10cSrcweir }
1059cdf0e10cSrcweir
1060cdf0e10cSrcweir sal_Bool bNewValue;
1061cdf0e10cSrcweir if ( !pKey )
1062cdf0e10cSrcweir {
1063cdf0e10cSrcweir pKey = new ImplKeyData;
1064cdf0e10cSrcweir pKey->mpNext = NULL;
1065cdf0e10cSrcweir pKey->maKey = rKey;
1066cdf0e10cSrcweir pKey->mbIsComment = sal_False;
1067cdf0e10cSrcweir if ( pPrevKey )
1068cdf0e10cSrcweir pPrevKey->mpNext = pKey;
1069cdf0e10cSrcweir else
1070cdf0e10cSrcweir pGroup->mpFirstKey = pKey;
1071cdf0e10cSrcweir bNewValue = sal_True;
1072cdf0e10cSrcweir }
1073cdf0e10cSrcweir else
1074cdf0e10cSrcweir bNewValue = pKey->maValue != rStr;
1075cdf0e10cSrcweir
1076cdf0e10cSrcweir if ( bNewValue )
1077cdf0e10cSrcweir {
1078cdf0e10cSrcweir pKey->maValue = rStr;
1079cdf0e10cSrcweir
1080cdf0e10cSrcweir if ( !mnLockCount && mbPersistence )
1081cdf0e10cSrcweir ImplWriteConfig( mpData );
1082cdf0e10cSrcweir else
1083cdf0e10cSrcweir {
1084cdf0e10cSrcweir mpData->mbModified = sal_True;
1085cdf0e10cSrcweir }
1086cdf0e10cSrcweir }
1087cdf0e10cSrcweir }
1088cdf0e10cSrcweir }
1089cdf0e10cSrcweir
1090cdf0e10cSrcweir // -----------------------------------------------------------------------
1091cdf0e10cSrcweir
WriteKey(const ByteString & rKey,const UniString & rValue,rtl_TextEncoding eEncoding)1092cdf0e10cSrcweir void Config::WriteKey( const ByteString& rKey, const UniString& rValue, rtl_TextEncoding eEncoding )
1093cdf0e10cSrcweir {
1094cdf0e10cSrcweir if ( mpData->mbIsUTF8BOM )
1095cdf0e10cSrcweir eEncoding = RTL_TEXTENCODING_UTF8;
1096cdf0e10cSrcweir WriteKey( rKey, ByteString( rValue, eEncoding ) );
1097cdf0e10cSrcweir }
1098cdf0e10cSrcweir
1099cdf0e10cSrcweir // -----------------------------------------------------------------------
1100cdf0e10cSrcweir
DeleteKey(const ByteString & rKey)1101cdf0e10cSrcweir void Config::DeleteKey( const ByteString& rKey )
1102cdf0e10cSrcweir {
1103cdf0e10cSrcweir // Config-Daten evt. updaten
1104cdf0e10cSrcweir if ( !mnLockCount || !mpData->mbRead )
1105cdf0e10cSrcweir {
1106cdf0e10cSrcweir ImplUpdateConfig();
1107cdf0e10cSrcweir mpData->mbRead = sal_True;
1108cdf0e10cSrcweir }
1109cdf0e10cSrcweir
1110cdf0e10cSrcweir // Key suchen und Value setzen
1111cdf0e10cSrcweir ImplGroupData* pGroup = ImplGetGroup();
1112cdf0e10cSrcweir if ( pGroup )
1113cdf0e10cSrcweir {
1114cdf0e10cSrcweir ImplKeyData* pPrevKey = NULL;
1115cdf0e10cSrcweir ImplKeyData* pKey = pGroup->mpFirstKey;
1116cdf0e10cSrcweir while ( pKey )
1117cdf0e10cSrcweir {
1118cdf0e10cSrcweir if ( !pKey->mbIsComment && pKey->maKey.EqualsIgnoreCaseAscii( rKey ) )
1119cdf0e10cSrcweir break;
1120cdf0e10cSrcweir
1121cdf0e10cSrcweir pPrevKey = pKey;
1122cdf0e10cSrcweir pKey = pKey->mpNext;
1123cdf0e10cSrcweir }
1124cdf0e10cSrcweir
1125cdf0e10cSrcweir if ( pKey )
1126cdf0e10cSrcweir {
1127cdf0e10cSrcweir // Gruppe weiterschalten und loeschen
1128cdf0e10cSrcweir if ( pPrevKey )
1129cdf0e10cSrcweir pPrevKey->mpNext = pKey->mpNext;
1130cdf0e10cSrcweir else
1131cdf0e10cSrcweir pGroup->mpFirstKey = pKey->mpNext;
1132cdf0e10cSrcweir delete pKey;
1133cdf0e10cSrcweir
1134cdf0e10cSrcweir // Config-Datei neu schreiben
1135cdf0e10cSrcweir if ( !mnLockCount && mbPersistence )
1136cdf0e10cSrcweir ImplWriteConfig( mpData );
1137cdf0e10cSrcweir else
1138cdf0e10cSrcweir {
1139cdf0e10cSrcweir mpData->mbModified = sal_True;
1140cdf0e10cSrcweir }
1141cdf0e10cSrcweir }
1142cdf0e10cSrcweir }
1143cdf0e10cSrcweir }
1144cdf0e10cSrcweir
1145cdf0e10cSrcweir // -----------------------------------------------------------------------
1146cdf0e10cSrcweir
GetKeyCount() const1147cdf0e10cSrcweir sal_uInt16 Config::GetKeyCount() const
1148cdf0e10cSrcweir {
1149cdf0e10cSrcweir #ifdef DBG_UTIL
1150cdf0e10cSrcweir ByteString aTraceStr( "Config::GetKeyCount()" );
1151cdf0e10cSrcweir aTraceStr += " from ";
1152cdf0e10cSrcweir aTraceStr += GetGroup();
1153cdf0e10cSrcweir aTraceStr += " in ";
1154cdf0e10cSrcweir aTraceStr += ByteString( maFileName, RTL_TEXTENCODING_UTF8 );
1155cdf0e10cSrcweir DBG_TRACE( aTraceStr.GetBuffer() );
1156cdf0e10cSrcweir #endif
1157cdf0e10cSrcweir
1158cdf0e10cSrcweir // Config-Daten evt. updaten
1159cdf0e10cSrcweir if ( !mnLockCount )
1160cdf0e10cSrcweir ImplUpdateConfig();
1161cdf0e10cSrcweir
1162cdf0e10cSrcweir // Key suchen und Value zurueckgeben
1163cdf0e10cSrcweir sal_uInt16 nCount = 0;
1164cdf0e10cSrcweir ImplGroupData* pGroup = ImplGetGroup();
1165cdf0e10cSrcweir if ( pGroup )
1166cdf0e10cSrcweir {
1167cdf0e10cSrcweir ImplKeyData* pKey = pGroup->mpFirstKey;
1168cdf0e10cSrcweir while ( pKey )
1169cdf0e10cSrcweir {
1170cdf0e10cSrcweir if ( !pKey->mbIsComment )
1171cdf0e10cSrcweir nCount++;
1172cdf0e10cSrcweir
1173cdf0e10cSrcweir pKey = pKey->mpNext;
1174cdf0e10cSrcweir }
1175cdf0e10cSrcweir }
1176cdf0e10cSrcweir
1177cdf0e10cSrcweir return nCount;
1178cdf0e10cSrcweir }
1179cdf0e10cSrcweir
1180cdf0e10cSrcweir // -----------------------------------------------------------------------
1181cdf0e10cSrcweir
GetKeyName(sal_uInt16 nKey) const1182cdf0e10cSrcweir ByteString Config::GetKeyName( sal_uInt16 nKey ) const
1183cdf0e10cSrcweir {
1184cdf0e10cSrcweir #ifdef DBG_UTIL
1185cdf0e10cSrcweir ByteString aTraceStr( "Config::GetKeyName( " );
1186cdf0e10cSrcweir aTraceStr += ByteString::CreateFromInt32(nKey);
1187cdf0e10cSrcweir aTraceStr += " ) from ";
1188cdf0e10cSrcweir aTraceStr += GetGroup();
1189cdf0e10cSrcweir aTraceStr += " in ";
1190cdf0e10cSrcweir aTraceStr += ByteString( maFileName, RTL_TEXTENCODING_UTF8 );
1191cdf0e10cSrcweir DBG_TRACE( aTraceStr.GetBuffer() );
1192cdf0e10cSrcweir #endif
1193cdf0e10cSrcweir
1194cdf0e10cSrcweir // Key suchen und Name zurueckgeben
1195cdf0e10cSrcweir ImplGroupData* pGroup = ImplGetGroup();
1196cdf0e10cSrcweir if ( pGroup )
1197cdf0e10cSrcweir {
1198cdf0e10cSrcweir ImplKeyData* pKey = pGroup->mpFirstKey;
1199cdf0e10cSrcweir while ( pKey )
1200cdf0e10cSrcweir {
1201cdf0e10cSrcweir if ( !pKey->mbIsComment )
1202cdf0e10cSrcweir {
1203cdf0e10cSrcweir if ( !nKey )
1204cdf0e10cSrcweir return pKey->maKey;
1205cdf0e10cSrcweir nKey--;
1206cdf0e10cSrcweir }
1207cdf0e10cSrcweir
1208cdf0e10cSrcweir pKey = pKey->mpNext;
1209cdf0e10cSrcweir }
1210cdf0e10cSrcweir }
1211cdf0e10cSrcweir
1212cdf0e10cSrcweir return getEmptyByteString();
1213cdf0e10cSrcweir }
1214cdf0e10cSrcweir
1215cdf0e10cSrcweir // -----------------------------------------------------------------------
1216cdf0e10cSrcweir
ReadKey(sal_uInt16 nKey) const1217cdf0e10cSrcweir ByteString Config::ReadKey( sal_uInt16 nKey ) const
1218cdf0e10cSrcweir {
1219cdf0e10cSrcweir #ifdef DBG_UTIL
1220cdf0e10cSrcweir ByteString aTraceStr( "Config::ReadKey( " );
1221cdf0e10cSrcweir aTraceStr += ByteString::CreateFromInt32( nKey );
1222cdf0e10cSrcweir aTraceStr += " ) from ";
1223cdf0e10cSrcweir aTraceStr += GetGroup();
1224cdf0e10cSrcweir aTraceStr += " in ";
1225cdf0e10cSrcweir aTraceStr += ByteString( maFileName, RTL_TEXTENCODING_UTF8 );
1226cdf0e10cSrcweir DBG_TRACE( aTraceStr.GetBuffer() );
1227cdf0e10cSrcweir #endif
1228cdf0e10cSrcweir
1229cdf0e10cSrcweir // Key suchen und Value zurueckgeben
1230cdf0e10cSrcweir ImplGroupData* pGroup = ImplGetGroup();
1231cdf0e10cSrcweir if ( pGroup )
1232cdf0e10cSrcweir {
1233cdf0e10cSrcweir ImplKeyData* pKey = pGroup->mpFirstKey;
1234cdf0e10cSrcweir while ( pKey )
1235cdf0e10cSrcweir {
1236cdf0e10cSrcweir if ( !pKey->mbIsComment )
1237cdf0e10cSrcweir {
1238cdf0e10cSrcweir if ( !nKey )
1239cdf0e10cSrcweir return pKey->maValue;
1240cdf0e10cSrcweir nKey--;
1241cdf0e10cSrcweir }
1242cdf0e10cSrcweir
1243cdf0e10cSrcweir pKey = pKey->mpNext;
1244cdf0e10cSrcweir }
1245cdf0e10cSrcweir }
1246cdf0e10cSrcweir
1247cdf0e10cSrcweir return getEmptyByteString();
1248cdf0e10cSrcweir }
1249cdf0e10cSrcweir
1250cdf0e10cSrcweir // -----------------------------------------------------------------------
1251cdf0e10cSrcweir
EnterLock()1252cdf0e10cSrcweir void Config::EnterLock()
1253cdf0e10cSrcweir {
1254cdf0e10cSrcweir // Config-Daten evt. updaten
1255cdf0e10cSrcweir if ( !mnLockCount )
1256cdf0e10cSrcweir ImplUpdateConfig();
1257cdf0e10cSrcweir
1258cdf0e10cSrcweir mnLockCount++;
1259cdf0e10cSrcweir }
1260cdf0e10cSrcweir
1261cdf0e10cSrcweir // -----------------------------------------------------------------------
1262cdf0e10cSrcweir
LeaveLock()1263cdf0e10cSrcweir void Config::LeaveLock()
1264cdf0e10cSrcweir {
1265cdf0e10cSrcweir DBG_ASSERT( mnLockCount, "Config::LeaveLook() without Config::EnterLook()" );
1266cdf0e10cSrcweir mnLockCount--;
1267cdf0e10cSrcweir
1268cdf0e10cSrcweir if ( (mnLockCount == 0) && mpData->mbModified && mbPersistence )
1269cdf0e10cSrcweir ImplWriteConfig( mpData );
1270cdf0e10cSrcweir }
1271cdf0e10cSrcweir
1272cdf0e10cSrcweir // -----------------------------------------------------------------------
1273cdf0e10cSrcweir
Update()1274cdf0e10cSrcweir sal_Bool Config::Update()
1275cdf0e10cSrcweir {
1276cdf0e10cSrcweir return ImplUpdateConfig();
1277cdf0e10cSrcweir }
1278cdf0e10cSrcweir
1279cdf0e10cSrcweir // -----------------------------------------------------------------------
1280cdf0e10cSrcweir
Flush()1281cdf0e10cSrcweir void Config::Flush()
1282cdf0e10cSrcweir {
1283cdf0e10cSrcweir if ( mpData->mbModified && mbPersistence )
1284cdf0e10cSrcweir ImplWriteConfig( mpData );
1285cdf0e10cSrcweir }
1286cdf0e10cSrcweir
1287cdf0e10cSrcweir // -----------------------------------------------------------------------
1288cdf0e10cSrcweir
SetLineEnd(LineEnd eLineEnd)1289cdf0e10cSrcweir void Config::SetLineEnd( LineEnd eLineEnd )
1290cdf0e10cSrcweir {
1291cdf0e10cSrcweir mpData->meLineEnd = eLineEnd;
1292cdf0e10cSrcweir }
1293cdf0e10cSrcweir
1294cdf0e10cSrcweir // -----------------------------------------------------------------------
1295cdf0e10cSrcweir
GetLineEnd() const1296cdf0e10cSrcweir LineEnd Config::GetLineEnd() const
1297cdf0e10cSrcweir {
1298cdf0e10cSrcweir return mpData->meLineEnd;
1299cdf0e10cSrcweir }
1300cdf0e10cSrcweir
1301