Branch data Line data Source code
1 : : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : : /*
3 : : * This file is part of the LibreOffice project.
4 : : *
5 : : * This Source Code Form is subject to the terms of the Mozilla Public
6 : : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : : *
9 : : * This file incorporates work covered by the following license notice:
10 : : *
11 : : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : : * contributor license agreements. See the NOTICE file distributed
13 : : * with this work for additional information regarding copyright
14 : : * ownership. The ASF licenses this file to you under the Apache
15 : : * License, Version 2.0 (the "License"); you may not use this file
16 : : * except in compliance with the License. You may obtain a copy of
17 : : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : : */
19 : :
20 : :
21 : : #include <vector>
22 : :
23 : : #include <com/sun/star/registry/XRegistryKey.hpp>
24 : : #include <com/sun/star/registry/MergeConflictException.hpp>
25 : :
26 : : #include "mergekeys.hxx"
27 : :
28 : : #define OUSTR(x) ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM(x) )
29 : :
30 : : using namespace ::rtl;
31 : : using namespace ::osl;
32 : : using namespace ::com::sun::star::uno;
33 : : using namespace ::com::sun::star;
34 : :
35 : : namespace stoc_impreg
36 : : {
37 : :
38 : 0 : struct Link
39 : : {
40 : : OUString m_name;
41 : : OUString m_target;
42 : :
43 : 0 : inline Link( OUString const & name, OUString const & target )
44 : : : m_name( name )
45 : 0 : , m_target( target )
46 : 0 : {}
47 : : };
48 : : typedef ::std::vector< Link > t_links;
49 : :
50 : : //==================================================================================================
51 : 884 : static void mergeKeys(
52 : : Reference< registry::XRegistryKey > const & xDest,
53 : : Reference< registry::XRegistryKey > const & xSource,
54 : : t_links & links )
55 : : // throw( registry::InvalidRegistryException, registry::MergeConflictException, RuntimeException )
56 : : {
57 [ + - ][ + - ]: 884 : if (!xSource.is() || !xSource->isValid()) {
[ + - ][ - + ]
[ - + ]
58 : : throw registry::InvalidRegistryException(
59 : : OUSTR("source key is null or invalid!"),
60 [ # # ][ # # ]: 0 : Reference<XInterface>() );
61 : : }
62 [ + - ][ + - ]: 884 : if (!xDest.is() || !xDest->isValid()) {
[ + - ][ - + ]
[ - + ]
63 : : throw registry::InvalidRegistryException(
64 : : OUSTR("destination key is null or invalid!"),
65 [ # # ][ # # ]: 0 : Reference<XInterface>() );
66 : : }
67 : :
68 : : // write value
69 [ + - ][ + - ]: 884 : switch (xSource->getValueType())
[ + - + -
- - - -
- ]
70 : : {
71 : : case registry::RegistryValueType_NOT_DEFINED:
72 : 632 : break;
73 : : case registry::RegistryValueType_LONG:
74 [ # # ][ # # ]: 0 : xDest->setLongValue( xSource->getLongValue() );
[ # # ][ # # ]
75 : 0 : break;
76 : : case registry::RegistryValueType_ASCII:
77 [ + - ][ + - ]: 252 : xDest->setAsciiValue( xSource->getAsciiValue() );
[ + - ][ + - ]
78 : 252 : break;
79 : : case registry::RegistryValueType_STRING:
80 [ # # ][ # # ]: 0 : xDest->setStringValue( xSource->getStringValue() );
[ # # ][ # # ]
81 : 0 : break;
82 : : case registry::RegistryValueType_BINARY:
83 [ # # ][ # # ]: 0 : xDest->setBinaryValue( xSource->getBinaryValue() );
[ # # ][ # # ]
[ # # ]
84 : 0 : break;
85 : : case registry::RegistryValueType_LONGLIST:
86 [ # # ][ # # ]: 0 : xDest->setLongListValue( xSource->getLongListValue() );
[ # # ][ # # ]
[ # # ]
87 : 0 : break;
88 : : case registry::RegistryValueType_ASCIILIST:
89 [ # # ][ # # ]: 0 : xDest->setAsciiListValue( xSource->getAsciiListValue() );
[ # # ][ # # ]
[ # # ]
90 : 0 : break;
91 : : case registry::RegistryValueType_STRINGLIST:
92 [ # # ][ # # ]: 0 : xDest->setStringListValue( xSource->getStringListValue() );
[ # # ][ # # ]
[ # # ]
93 : 0 : break;
94 : : default:
95 : : OSL_ASSERT(false);
96 : 0 : break;
97 : : }
98 : :
99 : : // sub keys
100 [ + - ][ + - ]: 884 : Sequence< OUString > sourceKeys( xSource->getKeyNames() );
101 : 884 : OUString const * pSourceKeys = sourceKeys.getConstArray();
102 [ + + ]: 1704 : for ( sal_Int32 nPos = sourceKeys.getLength(); nPos--; )
103 : : {
104 : : // key name
105 : 820 : OUString name( pSourceKeys[ nPos ] );
106 : 820 : sal_Int32 nSlash = name.lastIndexOf( '/' );
107 [ + - ]: 820 : if (nSlash >= 0)
108 : : {
109 : 820 : name = name.copy( nSlash +1 );
110 : : }
111 : :
112 [ + - ][ + - ]: 820 : if (xSource->getKeyType( name ) == registry::RegistryKeyType_KEY)
[ + - ]
113 : : {
114 : : // try to open exisiting dest key or create new one
115 [ + - ][ + - ]: 820 : Reference< registry::XRegistryKey > xDestKey( xDest->createKey( name ) );
116 [ + - ][ + - ]: 820 : Reference< registry::XRegistryKey > xSourceKey( xSource->openKey( name ) );
117 [ + - ]: 820 : mergeKeys( xDestKey, xSourceKey, links );
118 [ + - ][ + - ]: 820 : xSourceKey->closeKey();
119 [ + - ][ + - ]: 820 : xDestKey->closeKey();
120 : : }
121 : : else // link
122 : : {
123 : : // remove existing key
124 [ # # ][ # # ]: 0 : Reference< registry::XRegistryKey > xDestKey( xDest->openKey( name ) );
125 [ # # ][ # # ]: 0 : if (xDestKey.is() && xDestKey->isValid()) // something to remove
[ # # ][ # # ]
[ # # ]
126 : : {
127 [ # # ][ # # ]: 0 : xDestKey->closeKey();
128 [ # # ][ # # ]: 0 : if (xDest->getKeyType( name ) == registry::RegistryKeyType_LINK)
[ # # ]
129 : : {
130 [ # # ][ # # ]: 0 : xDest->deleteLink( name );
131 : : }
132 : : else
133 : : {
134 [ # # ][ # # ]: 0 : xDest->deleteKey( name );
135 : : }
136 : : }
137 : :
138 : : links.push_back( Link(
139 : 0 : pSourceKeys[ nPos ], // abs path
140 [ # # ]: 0 : xSource->getResolvedName( name ) // abs resolved name
141 [ # # ][ # # ]: 0 : ) );
142 : : }
143 [ + - ]: 1704 : }
144 : 884 : }
145 : :
146 : : //==================================================================================================
147 : 64 : void mergeKeys(
148 : : Reference< registry::XRegistryKey > const & xDest,
149 : : Reference< registry::XRegistryKey > const & xSource )
150 : : // throw( registry::InvalidRegistryException, registry::MergeConflictException, RuntimeException )
151 : : {
152 [ + - ][ + - ]: 64 : if (!xDest.is() || !xDest->isValid()) {
[ + - ][ - + ]
[ - + ]
153 : : throw registry::InvalidRegistryException(
154 : : OUSTR("destination key is null or invalid!"),
155 [ # # ][ # # ]: 0 : Reference<XInterface>() );
156 : : }
157 [ + - ][ + - ]: 64 : if (xDest->isReadOnly())
[ - + ]
158 : : {
159 : : throw registry::InvalidRegistryException(
160 : : OUString( RTL_CONSTASCII_USTRINGPARAM(
161 : : "destination registry is read-only! cannot merge!") ),
162 [ # # ][ # # ]: 0 : Reference< XInterface >() );
163 : : }
164 : :
165 [ + - ]: 64 : t_links links;
166 [ + - ]: 64 : links.reserve( 16 );
167 [ + - ]: 64 : mergeKeys( xDest, xSource, links );
168 : :
169 [ - + ]: 64 : for ( size_t nPos = links.size(); nPos--; )
170 : : {
171 : 0 : Link const & r = links[ nPos ];
172 [ # # ][ # # ]: 0 : OSL_VERIFY( xDest->createLink( r.m_name, r.m_target ) );
173 : 64 : }
174 : 64 : }
175 : :
176 : : }
177 : :
178 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|