1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: userinstall.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_desktop.hxx"
35 #include "userinstall.hxx"
36 #include "langselect.hxx"
39 #include <rtl/ustring.hxx>
40 #include <rtl/ustrbuf.hxx>
41 #include <osl/file.hxx>
42 #include <osl/mutex.hxx>
43 #include <osl/process.h>
44 #include <osl/diagnose.h>
45 #include <vos/security.hxx>
46 #include <vos/ref.hxx>
47 #include <vos/process.hxx>
49 #ifndef _TOOLS_RESMGR_HXX_
50 #include <tools/resmgr.hxx>
52 #include <unotools/bootstrap.hxx>
53 #include <svtools/languageoptions.hxx>
54 #ifndef _SVTOOLS_SYSLOCALEOPTIONSOPTIONS_HXX
55 #include <svtools/syslocaleoptions.hxx>
57 #include <comphelper/processfactory.hxx>
58 #include <com/sun/star/container/XNameAccess.hpp>
59 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
60 #include <com/sun/star/beans/XPropertySet.hpp>
61 #include <i18npool/mslangid.hxx>
62 #include <com/sun/star/uno/Any.hxx>
63 #include <com/sun/star/util/XChangesBatch.hpp>
64 #include <com/sun/star/beans/XHierarchicalPropertySet.hpp>
65 #include <com/sun/star/beans/NamedValue.hpp>
66 #include <com/sun/star/container/XHierarchicalNameAccess.hpp>
67 #include <com/sun/star/lang/XComponent.hpp>
68 #include <com/sun/star/lang/XLocalizable.hpp>
69 #include <com/sun/star/lang/Locale.hpp>
76 using namespace com::sun::star::container
;
77 using namespace com::sun::star::uno
;
78 using namespace com::sun::star::lang
;
79 using namespace com::sun::star::beans
;
80 using namespace com::sun::star::util
;
85 static UserInstall::UserInstallError
create_user_install(OUString
&);
87 static bool is_user_install()
92 RTL_CONSTASCII_USTRINGPARAM(
93 "com.sun.star.configuration.ConfigurationProvider" ) );
95 RTL_CONSTASCII_USTRINGPARAM(
96 "com.sun.star.configuration.ConfigurationAccess" ) );
98 // get configuration provider
99 Reference
< XMultiServiceFactory
> theMSF
100 = comphelper::getProcessServiceFactory();
101 Reference
< XMultiServiceFactory
> theConfigProvider
102 = Reference
< XMultiServiceFactory
>(
103 theMSF
->createInstance(sConfigSrvc
), UNO_QUERY_THROW
);
105 // localize the provider to user selection
106 // Reference< XLocalizable > localizable(theConfigProvider, UNO_QUERY_THROW);
107 // LanguageType aUserLanguageType = LanguageSelection::getLanguageType();
108 // Locale aLocale( MsLangId::convertLanguageToIsoString(aUserLanguageType));
109 // localizable->setLocale(aLocale);
111 Reference
< XLocalizable
> localizable(theConfigProvider
, UNO_QUERY_THROW
);
112 OUString aUserLanguage
= LanguageSelection::getLanguageString();
113 Locale aLocale
= LanguageSelection::IsoStringToLocale(aUserLanguage
);
114 localizable
->setLocale(aLocale
);
116 Sequence
< Any
> theArgs(1);
118 v
.Name
= OUString::createFromAscii("NodePath");
119 v
.Value
= makeAny(OUString::createFromAscii("org.openoffice.Setup"));
121 Reference
< XHierarchicalNameAccess
> hnacc(
122 theConfigProvider
->createInstanceWithArguments(
123 sAccessSrvc
, theArgs
), UNO_QUERY_THROW
);
127 sal_Bool bValue
= sal_False
;
128 hnacc
->getByHierarchicalName(
129 OUString( RTL_CONSTASCII_USTRINGPARAM(
130 "Office/ooSetupInstCompleted" ) ) ) >>= bValue
;
132 return bValue
? true : false;
134 catch ( NoSuchElementException
const & )
136 // just return false in this case.
139 catch (Exception
const & e
)
141 OString
msg(OUStringToOString(e
.Message
, RTL_TEXTENCODING_ASCII_US
));
142 OSL_ENSURE(sal_False
, msg
.getStr());
148 UserInstall::UserInstallError
UserInstall::finalize()
150 OUString aUserInstallPath
;
151 utl::Bootstrap::PathStatus aLocateResult
=
152 utl::Bootstrap::locateUserInstallation(aUserInstallPath
);
154 switch (aLocateResult
) {
156 case utl::Bootstrap::DATA_INVALID
:
157 case utl::Bootstrap::DATA_MISSING
:
158 case utl::Bootstrap::DATA_UNKNOWN
:
159 // cannot find a valid path or path is missing
162 case utl::Bootstrap::PATH_EXISTS
:
164 // path exists, check if an installation lives there
165 if ( is_user_install() )
169 // Note: fall-thru intended.
171 case utl::Bootstrap::PATH_VALID
:
172 // found a path but need to create user install
173 return create_user_install(aUserInstallPath
);
179 static osl::FileBase::RC
copy_recursive( const rtl::OUString
& srcUnqPath
, const rtl::OUString
& dstUnqPath
)
183 DirectoryItem aDirItem
;
184 DirectoryItem::get(srcUnqPath
, aDirItem
);
185 FileStatus
aFileStatus(FileStatusMask_All
);
186 aDirItem
.getFileStatus(aFileStatus
);
188 if( aFileStatus
.getFileType() == FileStatus::Directory
)
190 // create directory if not already there
191 err
= Directory::create( dstUnqPath
);
192 if (err
== osl::FileBase::E_EXIST
)
193 err
= osl::FileBase::E_None
;
195 FileBase::RC next
= err
;
196 if (err
== osl::FileBase::E_None
)
198 // iterate through directory contents
199 Directory
aDir( srcUnqPath
);
201 while (err
== osl::FileBase::E_None
&&
202 (next
= aDir
.getNextItem( aDirItem
)) == osl::FileBase::E_None
)
204 aDirItem
.getFileStatus(aFileStatus
);
205 // generate new src/dst pair and make recursive call
206 rtl::OUString newSrcUnqPath
= aFileStatus
.getFileURL();
207 rtl::OUString newDstUnqPath
= dstUnqPath
;
208 rtl::OUString itemname
= aFileStatus
.getFileName();
209 // append trailing '/' if needed
210 if (newDstUnqPath
.lastIndexOf(sal_Unicode('/')) != newDstUnqPath
.getLength()-1)
211 newDstUnqPath
+= rtl::OUString::createFromAscii("/");
212 newDstUnqPath
+= itemname
;
214 err
= copy_recursive(newSrcUnqPath
, newDstUnqPath
);
218 if ( err
!= osl::FileBase::E_None
)
220 if( next
!= FileBase::E_NOENT
)
221 err
= FileBase::E_INVAL
;
226 // copy single file - foldback
227 err
= File::copy( srcUnqPath
,dstUnqPath
);
232 static const char *pszSrcList
[] = {
236 static const char *pszDstList
[] = {
242 static UserInstall::UserInstallError
create_user_install(OUString
& aUserPath
)
245 if (utl::Bootstrap::locateBaseInstallation(aBasePath
) != utl::Bootstrap::PATH_EXISTS
)
246 return UserInstall::E_InvalidBaseinstall
;
248 // create the user directory
249 FileBase::RC rc
= Directory::create(aUserPath
);
250 if ((rc
!= FileBase::E_None
) && (rc
!= FileBase::E_EXIST
)) return UserInstall::E_Creation
;
253 // set safer permissions for the user directory by default
254 File::setAttributes(aUserPath
, Attribute_OwnWrite
| Attribute_OwnRead
| Attribute_OwnExe
);
257 // copy data from shared data directory of base installation
258 for (sal_Int32 i
=0; pszSrcList
[i
]!=NULL
&& pszDstList
[i
]!=NULL
; i
++)
261 aBasePath
+ OUString::createFromAscii(pszSrcList
[i
]),
262 aUserPath
+ OUString::createFromAscii(pszDstList
[i
]));
263 if ((rc
!= FileBase::E_None
) && (rc
!= FileBase::E_EXIST
))
265 if ( rc
== FileBase::E_NOSPC
)
266 return UserInstall::E_NoDiskSpace
;
267 else if ( rc
== FileBase::E_ACCES
)
268 return UserInstall::E_NoWriteAccess
;
270 return UserInstall::E_Creation
;
275 OUString sConfigSrvc
= OUString::createFromAscii("com.sun.star.configuration.ConfigurationProvider");
276 OUString sAccessSrvc
= OUString::createFromAscii("com.sun.star.configuration.ConfigurationUpdateAccess");
278 // get configuration provider
279 Reference
< XMultiServiceFactory
> theMSF
= comphelper::getProcessServiceFactory();
280 Reference
< XMultiServiceFactory
> theConfigProvider
= Reference
< XMultiServiceFactory
>(
281 theMSF
->createInstance(sConfigSrvc
), UNO_QUERY_THROW
);
282 Sequence
< Any
> theArgs(1);
283 NamedValue
v(OUString::createFromAscii("NodePath"), makeAny(OUString::createFromAscii("org.openoffice.Setup")));
284 //v.Name = OUString::createFromAscii("NodePath");
285 //v.Value = makeAny(OUString::createFromAscii("org.openoffice.Setup"));
287 Reference
< XHierarchicalPropertySet
> hpset(
288 theConfigProvider
->createInstanceWithArguments(sAccessSrvc
, theArgs
), UNO_QUERY_THROW
);
289 hpset
->setHierarchicalPropertyValue(OUString::createFromAscii("Office/ooSetupInstCompleted"), makeAny(sal_True
));
290 Reference
< XChangesBatch
>(hpset
, UNO_QUERY_THROW
)->commitChanges();
292 catch ( PropertyVetoException
& )
294 // we are not allowed to change this
298 OString
aMsg("create_user_install(): ");
299 aMsg
+= OUStringToOString(e
.Message
, RTL_TEXTENCODING_ASCII_US
);
300 OSL_ENSURE(sal_False
, aMsg
.getStr());
301 return UserInstall::E_Creation
;
304 return UserInstall::E_None
;