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_codemaker.hxx"
26
27 #include "rtl/alloc.h"
28 #include "codemaker/typemanager.hxx"
29 #include "registry/reader.hxx"
30 #include "registry/version.h"
31
32 using namespace rtl;
33
TypeManager()34 TypeManager::TypeManager()
35 {
36 m_pImpl = new TypeManagerImpl();
37 acquire();
38 }
39
~TypeManager()40 TypeManager::~TypeManager()
41 {
42 release();
43 }
44
acquire()45 sal_Int32 TypeManager::acquire()
46 {
47 return osl_incrementInterlockedCount(&m_pImpl->m_refCount);
48 }
49
release()50 sal_Int32 TypeManager::release()
51 {
52 sal_Int32 refCount = 0;
53 if (0 == (refCount = osl_decrementInterlockedCount(&m_pImpl->m_refCount)) )
54 {
55 delete m_pImpl;
56 }
57 return refCount;;
58 }
59
isBaseType(const::rtl::OString & name)60 sal_Bool TypeManager::isBaseType(const ::rtl::OString& name)
61 {
62 if ( name.equals(OString("short")) )
63 return sal_True;
64 if ( name.equals(OString("unsigned short")) )
65 return sal_True;
66 if ( name.equals(OString("long")) )
67 return sal_True;
68 if ( name.equals(OString("unsigned long")) )
69 return sal_True;
70 if ( name.equals(OString("hyper")) )
71 return sal_True;
72 if ( name.equals(OString("unsigned hyper")) )
73 return sal_True;
74 if ( name.equals(OString("string")) )
75 return sal_True;
76 if ( name.equals(OString("boolean")) )
77 return sal_True;
78 if ( name.equals(OString("char")) )
79 return sal_True;
80 if ( name.equals(OString("byte")) )
81 return sal_True;
82 if ( name.equals(OString("any")) )
83 return sal_True;
84 if ( name.equals(OString("type")) )
85 return sal_True;
86 if ( name.equals(OString("float")) )
87 return sal_True;
88 if ( name.equals(OString("double")) )
89 return sal_True;
90 if ( name.equals(OString("void")) )
91 return sal_True;
92
93 return sal_False;
94 }
95
RegistryTypeManager()96 RegistryTypeManager::RegistryTypeManager()
97 {
98 m_pImpl = new RegistryTypeManagerImpl();
99 acquire();
100 }
101
~RegistryTypeManager()102 RegistryTypeManager::~RegistryTypeManager()
103 {
104 release();
105 }
106
acquire()107 void RegistryTypeManager::acquire()
108 {
109 TypeManager::acquire();
110 }
111
release()112 void RegistryTypeManager::release()
113 {
114 if (0 == TypeManager::release())
115 {
116 freeRegistries();
117
118 delete m_pImpl;
119 }
120 }
121
init(const StringVector & regFiles,StringVector const & extraFiles)122 sal_Bool RegistryTypeManager::init(
123 const StringVector& regFiles,
124 StringVector const & extraFiles )
125 {
126 if (regFiles.empty())
127 return sal_False;
128
129 StringVector::const_iterator iter = regFiles.begin();
130
131 Registry tmpReg;
132 while (iter != regFiles.end())
133 {
134 if (!tmpReg.open( convertToFileUrl(*iter), REG_READONLY))
135 m_pImpl->m_registries.push_back(new Registry(tmpReg));
136 else
137 {
138 freeRegistries();
139 return sal_False;
140 }
141 ++iter;
142 }
143 iter = extraFiles.begin();
144 while (iter != extraFiles.end())
145 {
146 if (!tmpReg.open( convertToFileUrl(*iter), REG_READONLY))
147 m_pImpl->m_extra_registries.push_back(new Registry(tmpReg));
148 else
149 {
150 freeRegistries();
151 return sal_False;
152 }
153 ++iter;
154 }
155
156 return sal_True;
157 }
158
getTypeName(RegistryKey & rTypeKey) const159 ::rtl::OString RegistryTypeManager::getTypeName(RegistryKey& rTypeKey) const
160 {
161 OString typeName = OUStringToOString(rTypeKey.getName(), RTL_TEXTENCODING_UTF8);
162
163 if (m_pImpl->m_base.getLength() > 1)
164 typeName = typeName.copy(typeName.indexOf('/', 1) + 1);
165 else
166 typeName = typeName.copy(1);
167
168 return typeName;
169 }
170
getTypeReader(const OString & name,sal_Bool * pIsExtraType) const171 typereg::Reader RegistryTypeManager::getTypeReader(
172 const OString& name, sal_Bool * pIsExtraType ) const
173 {
174 typereg::Reader reader;
175 RegistryKey key(searchTypeKey(name, pIsExtraType));
176
177 if (key.isValid())
178 {
179 RegValueType valueType;
180 sal_uInt32 valueSize;
181
182 if (!key.getValueInfo(OUString(), &valueType, &valueSize))
183 {
184 sal_uInt8* pBuffer = (sal_uInt8*)rtl_allocateMemory(valueSize);
185 if (!key.getValue(OUString(), pBuffer))
186 {
187 reader = typereg::Reader(
188 pBuffer, valueSize, true, TYPEREG_VERSION_1);
189 }
190 rtl_freeMemory(pBuffer);
191 }
192 }
193 return reader;
194 }
195
getTypeReader(RegistryKey & rTypeKey) const196 typereg::Reader RegistryTypeManager::getTypeReader(RegistryKey& rTypeKey) const
197 {
198 typereg::Reader reader;
199
200 if (rTypeKey.isValid())
201 {
202 RegValueType valueType;
203 sal_uInt32 valueSize;
204
205 if (!rTypeKey.getValueInfo(OUString(), &valueType, &valueSize))
206 {
207 sal_uInt8* pBuffer = (sal_uInt8*)rtl_allocateMemory(valueSize);
208 if (!rTypeKey.getValue(OUString(), pBuffer))
209 {
210 reader = typereg::Reader(
211 pBuffer, valueSize, true, TYPEREG_VERSION_1);
212 }
213 rtl_freeMemory(pBuffer);
214 }
215 }
216 return reader;
217 }
218
219
getTypeClass(const OString & name) const220 RTTypeClass RegistryTypeManager::getTypeClass(const OString& name) const
221 {
222 if (m_pImpl->m_t2TypeClass.count(name) > 0)
223 {
224 return m_pImpl->m_t2TypeClass[name];
225 } else
226 {
227 RegistryKey key(searchTypeKey(name));
228
229 if (key.isValid())
230 {
231 RegValueType valueType;
232 sal_uInt32 valueSize;
233
234 if (!key.getValueInfo(OUString(), &valueType, &valueSize))
235 {
236 sal_uInt8* pBuffer = (sal_uInt8*)rtl_allocateMemory(valueSize);
237 if (!key.getValue(OUString(), pBuffer))
238 {
239 typereg::Reader reader(
240 pBuffer, valueSize, false, TYPEREG_VERSION_1);
241
242 RTTypeClass ret = reader.getTypeClass();
243
244 rtl_freeMemory(pBuffer);
245
246 m_pImpl->m_t2TypeClass[name] = ret;
247 return ret;
248 }
249 rtl_freeMemory(pBuffer);
250 }
251 }
252 }
253
254 return RT_TYPE_INVALID;
255 }
256
getTypeClass(RegistryKey & rTypeKey) const257 RTTypeClass RegistryTypeManager::getTypeClass(RegistryKey& rTypeKey) const
258 {
259 OString name = getTypeName(rTypeKey);
260
261 if (m_pImpl->m_t2TypeClass.count(name) > 0)
262 {
263 return m_pImpl->m_t2TypeClass[name];
264 } else
265 {
266 if (rTypeKey.isValid())
267 {
268 RegValueType valueType;
269 sal_uInt32 valueSize;
270
271 if (!rTypeKey.getValueInfo(OUString(), &valueType, &valueSize))
272 {
273 sal_uInt8* pBuffer = (sal_uInt8*)rtl_allocateMemory(valueSize);
274 if (!rTypeKey.getValue(OUString(), pBuffer))
275 {
276 typereg::Reader reader(
277 pBuffer, valueSize, false, TYPEREG_VERSION_1);
278
279 RTTypeClass ret = reader.getTypeClass();
280
281 rtl_freeMemory(pBuffer);
282
283 m_pImpl->m_t2TypeClass[name] = ret;
284 return ret;
285 }
286 rtl_freeMemory(pBuffer);
287 }
288 }
289 }
290
291 return RT_TYPE_INVALID;
292 }
293
setBase(const OString & base)294 void RegistryTypeManager::setBase(const OString& base)
295 {
296
297 if (base.lastIndexOf('/') == (base.getLength() - 1))
298 m_pImpl->m_base += base.copy(0, base.lastIndexOf('/') - 1);
299 else
300 m_pImpl->m_base += base;
301 }
302
freeRegistries()303 void RegistryTypeManager::freeRegistries()
304 {
305 RegistryList::const_iterator iter = m_pImpl->m_registries.begin();
306 while (iter != m_pImpl->m_registries.end())
307 {
308 delete *iter;
309 ++iter;
310 }
311 iter = m_pImpl->m_extra_registries.begin();
312 while (iter != m_pImpl->m_extra_registries.end())
313 {
314 delete *iter;
315 ++iter;
316 }
317 }
318
searchTypeKey(const OString & name_,sal_Bool * pIsExtraType) const319 RegistryKey RegistryTypeManager::searchTypeKey(const OString& name_, sal_Bool * pIsExtraType )
320 const
321 {
322 OUString name( OStringToOUString(m_pImpl->m_base + "/" + name_, RTL_TEXTENCODING_UTF8) );
323 RegistryKey key, rootKey;
324
325 RegistryList::const_iterator iter = m_pImpl->m_registries.begin();
326 while (iter != m_pImpl->m_registries.end())
327 {
328 if (!(*iter)->openRootKey(rootKey))
329 {
330 if (!rootKey.openKey(name, key))
331 {
332 if (pIsExtraType)
333 *pIsExtraType = sal_False;
334 return key;
335 }
336 }
337 ++iter;
338 }
339 iter = m_pImpl->m_extra_registries.begin();
340 while (iter != m_pImpl->m_extra_registries.end())
341 {
342 if (!(*iter)->openRootKey(rootKey))
343 {
344 if (!rootKey.openKey(name, key))
345 {
346 if (pIsExtraType)
347 *pIsExtraType = sal_True;
348 break;
349 }
350 }
351 ++iter;
352 }
353
354 return key;
355 }
356
getTypeKeys(const::rtl::OString & name_) const357 RegistryKeyList RegistryTypeManager::getTypeKeys(const ::rtl::OString& name_) const
358 {
359 RegistryKeyList keyList= RegistryKeyList();
360 OString tmpName;
361 if ( name_.equals("/") || name_.equals(m_pImpl->m_base) ) {
362 tmpName = m_pImpl->m_base;
363 } else {
364 if ( m_pImpl->m_base.equals("/") )
365 tmpName = name_;
366 else
367 tmpName = m_pImpl->m_base + "/" + name_;
368 }
369
370 OUString name( OStringToOUString(tmpName, RTL_TEXTENCODING_UTF8) );
371 RegistryKey key, rootKey;
372
373 RegistryList::const_iterator iter = m_pImpl->m_registries.begin();
374 while (iter != m_pImpl->m_registries.end())
375 {
376 if (!(*iter)->openRootKey(rootKey))
377 {
378 if (!rootKey.openKey(name, key))
379 {
380 keyList.push_back(KeyPair(key, sal_False));
381 }
382 }
383 ++iter;
384 }
385 iter = m_pImpl->m_extra_registries.begin();
386 while (iter != m_pImpl->m_extra_registries.end())
387 {
388 if (!(*iter)->openRootKey(rootKey))
389 {
390 if (!rootKey.openKey(name, key))
391 {
392 keyList.push_back(KeyPair(key, sal_True));
393 }
394 }
395 ++iter;
396 }
397
398 return keyList;
399 }
400