update credits
[LibreOffice.git] / jvmfwk / source / elements.cxx
blobf9f481f5e0a2af1eaf2c7a5537be559167eda6a0
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include "elements.hxx"
21 #include "osl/mutex.hxx"
22 #include "osl/file.hxx"
23 #include "fwkutil.hxx"
24 #include "fwkbase.hxx"
25 #include "framework.hxx"
26 #include "libxmlutil.hxx"
27 #include "osl/thread.hxx"
28 #include <algorithm>
29 #include "libxml/parser.h"
30 #include "libxml/xpath.h"
31 #include "libxml/xpathInternals.h"
32 #include "rtl/bootstrap.hxx"
33 #include "boost/optional.hpp"
34 #include <string.h>
37 using namespace osl;
38 namespace jfw
41 OString getElement(OString const & docPath,
42 xmlChar const * pathExpression, bool bThrowIfEmpty)
44 //Prepare the xml document and context
45 OSL_ASSERT(!docPath.isEmpty());
46 jfw::CXmlDocPtr doc(xmlParseFile(docPath.getStr()));
47 if (doc == NULL)
48 throw FrameworkException(
49 JFW_E_ERROR,
50 OString("[Java framework] Error in function getElement "
51 "(elements.cxx)"));
53 jfw::CXPathContextPtr context(xmlXPathNewContext(doc));
54 if (xmlXPathRegisterNs(context, (xmlChar*) "jf",
55 (xmlChar*) NS_JAVA_FRAMEWORK) == -1)
56 throw FrameworkException(
57 JFW_E_ERROR,
58 OString("[Java framework] Error in function getElement "
59 "(elements.cxx)"));
61 CXPathObjectPtr pathObj;
62 pathObj = xmlXPathEvalExpression(pathExpression, context);
63 OString sValue;
64 if (xmlXPathNodeSetIsEmpty(pathObj->nodesetval))
66 if (bThrowIfEmpty)
67 throw FrameworkException(
68 JFW_E_ERROR,
69 OString("[Java framework] Error in function getElement "
70 "(elements.cxx)"));
72 else
74 sValue = (sal_Char*) pathObj->nodesetval->nodeTab[0]->content;
76 return sValue;
79 OString getElementUpdated()
81 return getElement(jfw::getVendorSettingsPath(),
82 (xmlChar*)"/jf:javaSelection/jf:updated/text()", true);
85 void createSettingsStructure(xmlDoc * document, bool * bNeedsSave)
87 OString sExcMsg("[Java framework] Error in function createSettingsStructure "
88 "(elements.cxx).");
89 xmlNode * root = xmlDocGetRootElement(document);
90 if (root == NULL)
91 throw FrameworkException(JFW_E_ERROR, sExcMsg);
92 bool bFound = false;
93 xmlNode * cur = root->children;
94 while (cur != NULL)
96 if (xmlStrcmp(cur->name, (xmlChar*) "enabled") == 0)
98 bFound = true;
99 break;
101 cur = cur->next;
103 if (bFound)
105 *bNeedsSave = false;
106 return;
108 //We will modify this document
109 *bNeedsSave = true;
110 // Now we create the child elements ------------------
111 //Get xsi:nil namespace
112 xmlNs* nsXsi = xmlSearchNsByHref(
113 document, root,(xmlChar*) NS_SCHEMA_INSTANCE);
115 //<enabled xsi:nil="true"
116 xmlNode * nodeEn = xmlNewTextChild(
117 root,NULL, (xmlChar*) "enabled", (xmlChar*) "");
118 if (nodeEn == NULL)
119 throw FrameworkException(JFW_E_ERROR, sExcMsg);
120 xmlSetNsProp(nodeEn,nsXsi,(xmlChar*) "nil",(xmlChar*) "true");
121 //add a new line
122 xmlNode * nodeCrLf = xmlNewText((xmlChar*) "\n");
123 xmlAddChild(root, nodeCrLf);
125 //<userClassPath xsi:nil="true">
126 xmlNode * nodeUs = xmlNewTextChild(
127 root,NULL, (xmlChar*) "userClassPath", (xmlChar*) "");
128 if (nodeUs == NULL)
129 throw FrameworkException(JFW_E_ERROR, sExcMsg);
130 xmlSetNsProp(nodeUs,nsXsi,(xmlChar*) "nil",(xmlChar*) "true");
131 //add a new line
132 nodeCrLf = xmlNewText((xmlChar*) "\n");
133 xmlAddChild(root, nodeCrLf);
135 //<vmParameters xsi:nil="true">
136 xmlNode * nodeVm = xmlNewTextChild(
137 root,NULL, (xmlChar*) "vmParameters", (xmlChar*) "");
138 if (nodeVm == NULL)
139 throw FrameworkException(JFW_E_ERROR, sExcMsg);
140 xmlSetNsProp(nodeVm,nsXsi,(xmlChar*) "nil",(xmlChar*) "true");
141 //add a new line
142 nodeCrLf = xmlNewText((xmlChar*) "\n");
143 xmlAddChild(root, nodeCrLf);
145 //<jreLocations xsi:nil="true">
146 xmlNode * nodeJre = xmlNewTextChild(
147 root,NULL, (xmlChar*) "jreLocations", (xmlChar*) "");
148 if (nodeJre == NULL)
149 throw FrameworkException(JFW_E_ERROR, sExcMsg);
150 xmlSetNsProp(nodeJre,nsXsi,(xmlChar*) "nil",(xmlChar*) "true");
151 //add a new line
152 nodeCrLf = xmlNewText((xmlChar*) "\n");
153 xmlAddChild(root, nodeCrLf);
155 //<javaInfo xsi:nil="true">
156 xmlNode * nodeJava = xmlNewTextChild(
157 root,NULL, (xmlChar*) "javaInfo", (xmlChar*) "");
158 if (nodeJava == NULL)
159 throw FrameworkException(JFW_E_ERROR, sExcMsg);
160 xmlSetNsProp(nodeJava,nsXsi,(xmlChar*) "nil",(xmlChar*) "true");
161 //add a new line
162 nodeCrLf = xmlNewText((xmlChar*) "\n");
163 xmlAddChild(root, nodeCrLf);
167 //====================================================================
168 VersionInfo::VersionInfo(): arVersions(NULL)
172 VersionInfo::~VersionInfo()
174 delete [] arVersions;
177 void VersionInfo::addExcludeVersion(const OUString& sVersion)
179 vecExcludeVersions.push_back(sVersion);
182 rtl_uString** VersionInfo::getExcludeVersions()
184 osl::MutexGuard guard(FwkMutex::get());
185 if (arVersions != NULL)
186 return arVersions;
188 arVersions = new rtl_uString*[vecExcludeVersions.size()];
189 int j=0;
190 typedef std::vector<OUString>::const_iterator it;
191 for (it i = vecExcludeVersions.begin(); i != vecExcludeVersions.end();
192 ++i, ++j)
194 arVersions[j] = vecExcludeVersions[j].pData;
196 return arVersions;
199 sal_Int32 VersionInfo::getExcludeVersionSize()
201 return vecExcludeVersions.size();
203 //==================================================================
205 NodeJava::NodeJava(Layer layer):
206 m_layer(layer)
208 //This class reads and write to files which should only be done in
209 //application mode
210 if (getMode() == JFW_MODE_DIRECT)
211 throw FrameworkException(
212 JFW_E_DIRECT_MODE,
213 "[Java framework] Trying to access settings files in direct mode.");
217 void NodeJava::load()
219 const OString sExcMsg("[Java framework] Error in function NodeJava::load"
220 "(elements.cxx).");
221 if (SHARED == m_layer)
223 //we do not support yet to write into the shared installation
225 //check if shared settings exist at all.
226 OUString sURL(BootParams::getSharedData());
227 jfw::FileStatus s = sURL.isEmpty()
228 ? FILE_DOES_NOT_EXIST : checkFileURL(sURL);
229 if (s == FILE_INVALID)
230 throw FrameworkException(
231 JFW_E_ERROR,
232 "[Java framework] Invalid file for shared Java settings.");
233 else if (s == FILE_DOES_NOT_EXIST)
234 //Writing shared data is not supported yet.
235 return;
237 else if (USER == m_layer)
239 if (!prepareSettingsDocument())
241 SAL_INFO("jfw.level1", "no path to load user settings document from");
242 return;
245 else
247 OSL_FAIL("[Java framework] Unknown enum used.");
251 //Read the user elements
252 OString sSettingsPath = getSettingsPath();
253 //There must not be a share settings file
254 CXmlDocPtr docUser(xmlParseFile(sSettingsPath.getStr()));
255 if (docUser == NULL)
256 throw FrameworkException(JFW_E_ERROR, sExcMsg);
258 xmlNode * cur = xmlDocGetRootElement(docUser);
259 if (cur == NULL || cur->children == NULL)
260 throw FrameworkException(JFW_E_ERROR, sExcMsg);
262 CXmlCharPtr sNil;
263 cur = cur->children;
264 while (cur != NULL)
266 if (xmlStrcmp(cur->name, (xmlChar*) "enabled") == 0)
268 //only overwrite share settings if xsi:nil="false"
269 sNil = xmlGetNsProp(
270 cur, (xmlChar*) "nil", (xmlChar*) NS_SCHEMA_INSTANCE);
271 if (sNil == NULL)
272 throw FrameworkException(JFW_E_ERROR, sExcMsg);;
273 if (xmlStrcmp(sNil, (xmlChar*) "false") == 0)
275 CXmlCharPtr sEnabled( xmlNodeListGetString(
276 docUser, cur->children, 1));
277 if (xmlStrcmp(sEnabled, (xmlChar*) "true") == 0)
278 m_enabled = boost::optional<sal_Bool>(sal_True);
279 else if (xmlStrcmp(sEnabled, (xmlChar*) "false") == 0)
280 m_enabled = boost::optional<sal_Bool>(sal_False);
283 else if (xmlStrcmp(cur->name, (xmlChar*) "userClassPath") == 0)
285 sNil = xmlGetNsProp(
286 cur, (xmlChar*) "nil", (xmlChar*) NS_SCHEMA_INSTANCE);
287 if (sNil == NULL)
288 throw FrameworkException(JFW_E_ERROR, sExcMsg);
289 if (xmlStrcmp(sNil, (xmlChar*) "false") == 0)
291 CXmlCharPtr sUser(xmlNodeListGetString(
292 docUser, cur->children, 1));
293 m_userClassPath = boost::optional<OUString>(OUString(sUser));
296 else if (xmlStrcmp(cur->name, (xmlChar*) "javaInfo") == 0)
298 sNil = xmlGetNsProp(
299 cur, (xmlChar*) "nil", (xmlChar*) NS_SCHEMA_INSTANCE);
300 if (sNil == NULL)
301 throw FrameworkException(JFW_E_ERROR, sExcMsg);
303 if (xmlStrcmp(sNil, (xmlChar*) "false") == 0)
305 if (! m_javaInfo)
306 m_javaInfo = boost::optional<CNodeJavaInfo>(CNodeJavaInfo());
307 m_javaInfo->loadFromNode(docUser, cur);
310 else if (xmlStrcmp(cur->name, (xmlChar*) "vmParameters") == 0)
312 sNil = xmlGetNsProp(
313 cur, (xmlChar*) "nil", (xmlChar*) NS_SCHEMA_INSTANCE);
314 if (sNil == NULL)
315 throw FrameworkException(JFW_E_ERROR, sExcMsg);
316 if (xmlStrcmp(sNil, (xmlChar*) "false") == 0)
318 if ( ! m_vmParameters)
319 m_vmParameters = boost::optional<std::vector<OUString> >(
320 std::vector<OUString> ());
322 xmlNode * pOpt = cur->children;
323 while (pOpt != NULL)
325 if (xmlStrcmp(pOpt->name, (xmlChar*) "param") == 0)
327 CXmlCharPtr sOpt;
328 sOpt = xmlNodeListGetString(
329 docUser, pOpt->children, 1);
330 m_vmParameters->push_back(sOpt);
332 pOpt = pOpt->next;
336 else if (xmlStrcmp(cur->name, (xmlChar*) "jreLocations") == 0)
338 sNil = xmlGetNsProp(
339 cur, (xmlChar*) "nil", (xmlChar*) NS_SCHEMA_INSTANCE);
340 if (sNil == NULL)
341 throw FrameworkException(JFW_E_ERROR, sExcMsg);
342 if (xmlStrcmp(sNil, (xmlChar*) "false") == 0)
344 if (! m_JRELocations)
345 m_JRELocations = boost::optional<std::vector<OUString> >(
346 std::vector<OUString>());
348 xmlNode * pLoc = cur->children;
349 while (pLoc != NULL)
351 if (xmlStrcmp(pLoc->name, (xmlChar*) "location") == 0)
353 CXmlCharPtr sLoc;
354 sLoc = xmlNodeListGetString(
355 docUser, pLoc->children, 1);
356 m_JRELocations->push_back(sLoc);
358 pLoc = pLoc->next;
362 cur = cur->next;
366 OString NodeJava::getSettingsPath() const
368 OString ret;
369 switch (m_layer)
371 case USER: ret = getUserSettingsPath(); break;
372 case SHARED: ret = getSharedSettingsPath(); break;
373 default:
374 OSL_FAIL("[Java framework] NodeJava::getSettingsPath()");
376 return ret;
379 OUString NodeJava::getSettingsURL() const
381 OUString ret;
382 switch (m_layer)
384 case USER: ret = BootParams::getUserData(); break;
385 case SHARED: ret = BootParams::getSharedData(); break;
386 default:
387 OSL_FAIL("[Java framework] NodeJava::getSettingsURL()");
389 return ret;
392 bool NodeJava::prepareSettingsDocument() const
394 OString sExcMsg(
395 "[Java framework] Error in function prepareSettingsDocument"
396 " (elements.cxx).");
397 if (!createSettingsDocument())
399 return false;
401 OString sSettings = getSettingsPath();
402 CXmlDocPtr doc(xmlParseFile(sSettings.getStr()));
403 if (!doc)
404 throw FrameworkException(JFW_E_ERROR, sExcMsg);
406 bool bNeedsSave = false;
407 createSettingsStructure(doc, & bNeedsSave);
408 if (bNeedsSave)
410 if (xmlSaveFormatFileEnc(
411 sSettings.getStr(), doc,"UTF-8", 1) == -1)
412 throw FrameworkException(JFW_E_ERROR, sExcMsg);
414 return true;
417 void NodeJava::write() const
419 OString sExcMsg("[Java framework] Error in function NodeJava::writeSettings "
420 "(elements.cxx).");
421 CXmlDocPtr docUser;
422 CXPathContextPtr contextUser;
423 CXPathObjectPtr pathObj;
425 if (!prepareSettingsDocument())
427 SAL_INFO("jfw.level1", "no path to write settings document to");
428 return;
431 //Read the user elements
432 OString sSettingsPath = getSettingsPath();
433 docUser = xmlParseFile(sSettingsPath.getStr());
434 if (docUser == NULL)
435 throw FrameworkException(JFW_E_ERROR, sExcMsg);
436 contextUser = xmlXPathNewContext(docUser);
437 if (xmlXPathRegisterNs(contextUser, (xmlChar*) "jf",
438 (xmlChar*) NS_JAVA_FRAMEWORK) == -1)
439 throw FrameworkException(JFW_E_ERROR, sExcMsg);
441 xmlNode * root = xmlDocGetRootElement(docUser);
442 //Get xsi:nil namespace
443 xmlNs* nsXsi = xmlSearchNsByHref(docUser,
444 root,
445 (xmlChar*) NS_SCHEMA_INSTANCE);
447 //set the <enabled> element
448 //The element must exist
449 if (m_enabled)
451 OString sExpression= OString(
452 "/jf:java/jf:enabled");
453 pathObj = xmlXPathEvalExpression((xmlChar*) sExpression.getStr(),
454 contextUser);
455 if ( ! pathObj || xmlXPathNodeSetIsEmpty(pathObj->nodesetval))
456 throw FrameworkException(JFW_E_ERROR, sExcMsg);
458 xmlNode * nodeEnabled = pathObj->nodesetval->nodeTab[0];
459 xmlSetNsProp(nodeEnabled,
460 nsXsi,
461 (xmlChar*) "nil",
462 (xmlChar*) "false");
464 if (m_enabled == boost::optional<sal_Bool>(sal_True))
465 xmlNodeSetContent(nodeEnabled,(xmlChar*) "true");
466 else
467 xmlNodeSetContent(nodeEnabled,(xmlChar*) "false");
470 //set the <userClassPath> element
471 //The element must exist
472 if (m_userClassPath)
474 OString sExpression= OString(
475 "/jf:java/jf:userClassPath");
476 pathObj = xmlXPathEvalExpression((xmlChar*) sExpression.getStr(),
477 contextUser);
478 if ( ! pathObj || xmlXPathNodeSetIsEmpty(pathObj->nodesetval))
479 throw FrameworkException(JFW_E_ERROR, sExcMsg);
481 xmlNode * nodeEnabled = pathObj->nodesetval->nodeTab[0];
482 xmlSetNsProp(nodeEnabled, nsXsi, (xmlChar*) "nil",(xmlChar*) "false");
483 xmlNodeSetContent(nodeEnabled,(xmlChar*) CXmlCharPtr(*m_userClassPath));
486 //set <javaInfo> element
487 if (m_javaInfo)
489 OString sExpression= OString(
490 "/jf:java/jf:javaInfo");
491 pathObj = xmlXPathEvalExpression((xmlChar*) sExpression.getStr(),
492 contextUser);
493 if ( ! pathObj || xmlXPathNodeSetIsEmpty(pathObj->nodesetval))
494 throw FrameworkException(JFW_E_ERROR, sExcMsg);
495 m_javaInfo->writeToNode(
496 docUser, pathObj->nodesetval->nodeTab[0]);
499 //set <vmParameters> element
500 if (m_vmParameters)
502 OString sExpression= OString(
503 "/jf:java/jf:vmParameters");
504 pathObj = xmlXPathEvalExpression((xmlChar*) sExpression.getStr(),
505 contextUser);
506 if ( ! pathObj || xmlXPathNodeSetIsEmpty(pathObj->nodesetval))
507 throw FrameworkException(JFW_E_ERROR, sExcMsg);
508 xmlNode* vmParameters = pathObj->nodesetval->nodeTab[0];
509 //set xsi:nil = false;
510 xmlSetNsProp(vmParameters, nsXsi,(xmlChar*) "nil",
511 (xmlChar*) "false");
513 //remove option elements
514 xmlNode* cur = vmParameters->children;
515 while (cur != NULL)
517 xmlNode* lastNode = cur;
518 cur = cur->next;
519 xmlUnlinkNode(lastNode);
520 xmlFreeNode(lastNode);
522 //add a new line after <vmParameters>
523 if (m_vmParameters->size() > 0)
525 xmlNode * nodeCrLf = xmlNewText((xmlChar*) "\n");
526 xmlAddChild(vmParameters, nodeCrLf);
529 typedef std::vector<OUString>::const_iterator cit;
530 for (cit i = m_vmParameters->begin(); i != m_vmParameters->end(); ++i)
532 xmlNewTextChild(vmParameters, NULL, (xmlChar*) "param",
533 CXmlCharPtr(*i));
534 //add a new line
535 xmlNode * nodeCrLf = xmlNewText((xmlChar*) "\n");
536 xmlAddChild(vmParameters, nodeCrLf);
540 //set <jreLocations> element
541 if (m_JRELocations)
543 OString sExpression= OString(
544 "/jf:java/jf:jreLocations");
545 pathObj = xmlXPathEvalExpression((xmlChar*) sExpression.getStr(),
546 contextUser);
547 if ( ! pathObj || xmlXPathNodeSetIsEmpty(pathObj->nodesetval))
548 throw FrameworkException(JFW_E_ERROR, sExcMsg);
549 xmlNode* jreLocationsNode = pathObj->nodesetval->nodeTab[0];
550 //set xsi:nil = false;
551 xmlSetNsProp(jreLocationsNode, nsXsi,(xmlChar*) "nil",
552 (xmlChar*) "false");
554 //remove option elements
555 xmlNode* cur = jreLocationsNode->children;
556 while (cur != NULL)
558 xmlNode* lastNode = cur;
559 cur = cur->next;
560 xmlUnlinkNode(lastNode);
561 xmlFreeNode(lastNode);
563 //add a new line after <vmParameters>
564 if (m_JRELocations->size() > 0)
566 xmlNode * nodeCrLf = xmlNewText((xmlChar*) "\n");
567 xmlAddChild(jreLocationsNode, nodeCrLf);
570 typedef std::vector<OUString>::const_iterator cit;
571 for (cit i = m_JRELocations->begin(); i != m_JRELocations->end(); ++i)
573 xmlNewTextChild(jreLocationsNode, NULL, (xmlChar*) "location",
574 CXmlCharPtr(*i));
575 //add a new line
576 xmlNode * nodeCrLf = xmlNewText((xmlChar*) "\n");
577 xmlAddChild(jreLocationsNode, nodeCrLf);
581 if (xmlSaveFormatFile(sSettingsPath.getStr(), docUser, 1) == -1)
582 throw FrameworkException(JFW_E_ERROR, sExcMsg);
585 void NodeJava::setEnabled(sal_Bool bEnabled)
587 m_enabled = boost::optional<sal_Bool>(bEnabled);
591 void NodeJava::setUserClassPath(const OUString & sClassPath)
593 m_userClassPath = boost::optional<OUString>(sClassPath);
596 void NodeJava::setJavaInfo(const JavaInfo * pInfo, bool bAutoSelect)
598 if (!m_javaInfo)
599 m_javaInfo = boost::optional<CNodeJavaInfo>(CNodeJavaInfo());
600 m_javaInfo->bAutoSelect = bAutoSelect;
601 m_javaInfo->bNil = false;
603 if (pInfo != NULL)
605 m_javaInfo->m_bEmptyNode = false;
606 m_javaInfo->sVendor = pInfo->sVendor;
607 m_javaInfo->sLocation = pInfo->sLocation;
608 m_javaInfo->sVersion = pInfo->sVersion;
609 m_javaInfo->nFeatures = pInfo->nFeatures;
610 m_javaInfo->nRequirements = pInfo->nRequirements;
611 m_javaInfo->arVendorData = pInfo->arVendorData;
613 else
615 m_javaInfo->m_bEmptyNode = true;
616 OUString sEmpty;
617 m_javaInfo->sVendor = sEmpty;
618 m_javaInfo->sLocation = sEmpty;
619 m_javaInfo->sVersion = sEmpty;
620 m_javaInfo->nFeatures = 0;
621 m_javaInfo->nRequirements = 0;
622 m_javaInfo->arVendorData = rtl::ByteSequence();
626 void NodeJava::setVmParameters(rtl_uString * * arOptions, sal_Int32 size)
628 OSL_ASSERT( !(arOptions == 0 && size != 0));
629 if ( ! m_vmParameters)
630 m_vmParameters = boost::optional<std::vector<OUString> >(
631 std::vector<OUString>());
632 m_vmParameters->clear();
633 if (arOptions != NULL)
635 for (int i = 0; i < size; i++)
637 const OUString sOption(static_cast<rtl_uString*>(arOptions[i]));
638 m_vmParameters->push_back(sOption);
643 void NodeJava::setJRELocations(rtl_uString * * arLocations, sal_Int32 size)
645 OSL_ASSERT( !(arLocations == 0 && size != 0));
646 if (! m_JRELocations)
647 m_JRELocations = boost::optional<std::vector<OUString> > (
648 std::vector<OUString>());
649 m_JRELocations->clear();
650 if (arLocations != NULL)
652 for (int i = 0; i < size; i++)
654 const OUString & sLocation = static_cast<rtl_uString*>(arLocations[i]);
656 //only add the path if not already present
657 std::vector<OUString>::const_iterator it =
658 std::find(m_JRELocations->begin(), m_JRELocations->end(),
659 sLocation);
660 if (it == m_JRELocations->end())
661 m_JRELocations->push_back(sLocation);
666 void NodeJava::addJRELocation(rtl_uString * sLocation)
668 OSL_ASSERT( sLocation);
669 if (!m_JRELocations)
670 m_JRELocations = boost::optional<std::vector<OUString> >(
671 std::vector<OUString> ());
672 //only add the path if not already present
673 std::vector<OUString>::const_iterator it =
674 std::find(m_JRELocations->begin(), m_JRELocations->end(),
675 OUString(sLocation));
676 if (it == m_JRELocations->end())
677 m_JRELocations->push_back(OUString(sLocation));
680 const boost::optional<sal_Bool> & NodeJava::getEnabled() const
682 return m_enabled;
685 const boost::optional<std::vector<OUString> >&
686 NodeJava::getJRELocations() const
688 return m_JRELocations;
691 const boost::optional<OUString> & NodeJava::getUserClassPath() const
693 return m_userClassPath;
696 const boost::optional<std::vector<OUString> > & NodeJava::getVmParameters() const
698 return m_vmParameters;
701 const boost::optional<CNodeJavaInfo> & NodeJava::getJavaInfo() const
703 return m_javaInfo;
706 jfw::FileStatus NodeJava::checkSettingsFileStatus(OUString const & sURL) const
708 jfw::FileStatus ret = FILE_DOES_NOT_EXIST;
710 //check the file time
711 ::osl::DirectoryItem item;
712 File::RC rc = ::osl::DirectoryItem::get(sURL, item);
713 if (File::E_None == rc)
715 ::osl::FileStatus stat(osl_FileStatus_Mask_Validate);
716 File::RC rc_stat = item.getFileStatus(stat);
717 if (File::E_None == rc_stat)
719 ret = FILE_OK;
721 else if (File::E_NOENT == rc_stat)
723 ret = FILE_DOES_NOT_EXIST;
725 else
727 ret = FILE_INVALID;
730 else if(File::E_NOENT == rc)
732 ret = FILE_DOES_NOT_EXIST;
734 else
736 ret = FILE_INVALID;
738 return ret;
741 bool NodeJava::createSettingsDocument() const
743 const OUString sURL = getSettingsURL();
744 if (sURL.isEmpty())
746 return false;
748 //make sure there is a user directory
749 OString sExcMsg("[Java framework] Error in function createSettingsDocument "
750 "(elements.cxx).");
751 // check if javasettings.xml already exist
752 if (FILE_OK == checkSettingsFileStatus(sURL))
753 return true;
755 //make sure that the directories are created in case they do not exist
756 FileBase::RC rcFile = Directory::createPath(getDirFromFile(sURL));
757 if (rcFile != FileBase::E_EXIST && rcFile != FileBase::E_None)
758 throw FrameworkException(JFW_E_ERROR, sExcMsg);
760 //javasettings.xml does not exist yet
761 CXmlDocPtr doc(xmlNewDoc((xmlChar *)"1.0"));
762 if (! doc)
763 throw FrameworkException(JFW_E_ERROR, sExcMsg);
764 //Create a comment
765 xmlNewDocComment(
766 doc, (xmlChar *) "This is a generated file. Do not alter this file!");
768 //Create the root element and name spaces
769 xmlNodePtr root = xmlNewDocNode(
770 doc, NULL, (xmlChar *) "java", (xmlChar *) "\n");
772 if (root == NULL)
773 throw FrameworkException(JFW_E_ERROR, sExcMsg);
775 if (xmlNewNs(root, (xmlChar *) NS_JAVA_FRAMEWORK,NULL) == NULL)
776 throw FrameworkException(JFW_E_ERROR, sExcMsg);
777 if (xmlNewNs(root,(xmlChar*) NS_SCHEMA_INSTANCE,(xmlChar*)"xsi") == NULL)
778 throw FrameworkException(JFW_E_ERROR, sExcMsg);
779 xmlDocSetRootElement(doc, root);
781 //Create a comment
782 xmlNodePtr com = xmlNewComment(
783 (xmlChar *) "This is a generated file. Do not alter this file!");
784 if (com == NULL)
785 throw FrameworkException(JFW_E_ERROR, sExcMsg);
787 if (xmlAddPrevSibling(root, com) == NULL)
788 throw FrameworkException(JFW_E_ERROR, sExcMsg);
790 const OString path = getSettingsPath();
791 if (xmlSaveFormatFileEnc(path.getStr(), doc,"UTF-8", 1) == -1)
792 throw FrameworkException(JFW_E_ERROR, sExcMsg);
793 return true;
796 //=====================================================================
797 CNodeJavaInfo::CNodeJavaInfo() :
798 m_bEmptyNode(false), bNil(true), bAutoSelect(true),
799 nFeatures(0), nRequirements(0)
803 CNodeJavaInfo::~CNodeJavaInfo()
807 void CNodeJavaInfo::loadFromNode(xmlDoc * pDoc, xmlNode * pJavaInfo)
809 OString sExcMsg("[Java framework] Error in function NodeJavaInfo::loadFromNode "
810 "(elements.cxx).");
812 OSL_ASSERT(pJavaInfo && pDoc);
813 if (pJavaInfo->children == NULL)
814 return;
815 //Get the xsi:nil attribute;
816 CXmlCharPtr sNil;
817 sNil = xmlGetNsProp(
818 pJavaInfo, (xmlChar*) "nil", (xmlChar*) NS_SCHEMA_INSTANCE);
819 if ( ! sNil)
820 throw FrameworkException(JFW_E_ERROR, sExcMsg);
822 if (xmlStrcmp(sNil, (xmlChar*) "true") == 0)
823 bNil = true;
824 else if (xmlStrcmp(sNil, (xmlChar*) "false") == 0)
825 bNil = false;
826 else
827 throw FrameworkException(JFW_E_ERROR, sExcMsg);
828 if (bNil == true)
829 return;
831 //Get javaInfo@manuallySelected attribute
832 CXmlCharPtr sAutoSelect;
833 sAutoSelect = xmlGetProp(
834 pJavaInfo, (xmlChar*) "autoSelect");
835 if ( ! sAutoSelect)
836 throw FrameworkException(JFW_E_ERROR, sExcMsg);
838 if (xmlStrcmp(sAutoSelect, (xmlChar*) "true") == 0)
839 bAutoSelect = true;
840 else if (xmlStrcmp(sAutoSelect, (xmlChar*) "false") == 0)
841 bAutoSelect = false;
842 else
843 throw FrameworkException(JFW_E_ERROR, sExcMsg);
845 xmlNode * cur = pJavaInfo->children;
847 while (cur != NULL)
849 if (xmlStrcmp(cur->name, (xmlChar*) "vendor") == 0)
851 CXmlCharPtr xmlVendor;
852 xmlVendor = xmlNodeListGetString(
853 pDoc, cur->children, 1);
854 if (! xmlVendor)
855 return;
856 sVendor = xmlVendor;
858 else if (xmlStrcmp(cur->name, (xmlChar*) "location") == 0)
860 CXmlCharPtr xmlLocation;
861 xmlLocation = xmlNodeListGetString(
862 pDoc, cur->children, 1);
863 sLocation = xmlLocation;
865 else if (xmlStrcmp(cur->name, (xmlChar*) "version") == 0)
867 CXmlCharPtr xmlVersion;
868 xmlVersion = xmlNodeListGetString(
869 pDoc, cur->children, 1);
870 sVersion = xmlVersion;
872 else if (xmlStrcmp(cur->name, (xmlChar*) "features")== 0)
874 CXmlCharPtr xmlFeatures;
875 xmlFeatures = xmlNodeListGetString(
876 pDoc, cur->children, 1);
877 OUString sFeatures = xmlFeatures;
878 nFeatures = sFeatures.toInt64(16);
880 else if (xmlStrcmp(cur->name, (xmlChar*) "requirements") == 0)
882 CXmlCharPtr xmlRequire;
883 xmlRequire = xmlNodeListGetString(
884 pDoc, cur->children, 1);
885 OUString sRequire = xmlRequire;
886 nRequirements = sRequire.toInt64(16);
887 #ifdef MACOSX
888 //javaldx is not used anymore in the mac build. In case the Java
889 //corresponding to the saved settings does not exist anymore the
890 //javavm services will look for an existing Java after creation of
891 //the JVM failed. See stoc/source/javavm/javavm.cxx. Only if
892 //nRequirements does not have the flag JFW_REQUIRE_NEEDRESTART the
893 //jvm of the new selected JRE will be started. Old settings (before
894 //OOo 3.3) still contain the flag which can be safely ignored.
895 nRequirements &= ~JFW_REQUIRE_NEEDRESTART;
896 #endif
898 else if (xmlStrcmp(cur->name, (xmlChar*) "vendorData") == 0)
900 CXmlCharPtr xmlData;
901 xmlData = xmlNodeListGetString(
902 pDoc, cur->children, 1);
903 xmlChar* _data = (xmlChar*) xmlData;
904 if (_data)
906 rtl::ByteSequence seq((sal_Int8*) _data, strlen((char*)_data));
907 arVendorData = decodeBase16(seq);
910 cur = cur->next;
913 if (sVendor.isEmpty())
914 m_bEmptyNode = true;
915 //Get the javainfo attributes
916 CXmlCharPtr sVendorUpdate;
917 sVendorUpdate = xmlGetProp(pJavaInfo,
918 (xmlChar*) "vendorUpdate");
919 if ( ! sVendorUpdate)
920 throw FrameworkException(JFW_E_ERROR, sExcMsg);
921 sAttrVendorUpdate = sVendorUpdate;
925 void CNodeJavaInfo::writeToNode(xmlDoc* pDoc,
926 xmlNode* pJavaInfoNode) const
929 OSL_ASSERT(pJavaInfoNode && pDoc);
930 //write the attribute vendorSettings
932 //javaInfo@vendorUpdate
933 //creates the attribute if necessary
934 OString sUpdated = getElementUpdated();
936 xmlSetProp(pJavaInfoNode, (xmlChar*)"vendorUpdate",
937 (xmlChar*) sUpdated.getStr());
939 //javaInfo@autoSelect
940 xmlSetProp(pJavaInfoNode, (xmlChar*)"autoSelect",
941 (xmlChar*) (bAutoSelect == true ? "true" : "false"));
943 //Set xsi:nil in javaInfo element to false
944 //the xmlNs pointer must not be destroyed
945 xmlNs* nsXsi = xmlSearchNsByHref((xmlDoc*) pDoc,
946 pJavaInfoNode,
947 (xmlChar*) NS_SCHEMA_INSTANCE);
949 xmlSetNsProp(pJavaInfoNode,
950 nsXsi,
951 (xmlChar*) "nil",
952 (xmlChar*) "false");
954 //Delete the children of JavaInfo
955 xmlNode* cur = pJavaInfoNode->children;
956 while (cur != NULL)
958 xmlNode* lastNode = cur;
959 cur = cur->next;
960 xmlUnlinkNode(lastNode);
961 xmlFreeNode(lastNode);
964 //If the JavaInfo was set with an empty value,
965 //then we are done.
966 if (m_bEmptyNode)
967 return;
969 //add a new line after <javaInfo>
970 xmlNode * nodeCrLf = xmlNewText((xmlChar*) "\n");
971 xmlAddChild(pJavaInfoNode, nodeCrLf);
973 //Create the vendor element
974 xmlNewTextChild(pJavaInfoNode, NULL, (xmlChar*) "vendor",
975 CXmlCharPtr(sVendor));
976 //add a new line for better readability
977 nodeCrLf = xmlNewText((xmlChar*) "\n");
978 xmlAddChild(pJavaInfoNode, nodeCrLf);
980 //Create the location element
981 xmlNewTextChild(pJavaInfoNode, NULL, (xmlChar*) "location",
982 CXmlCharPtr(sLocation));
983 //add a new line for better readability
984 nodeCrLf = xmlNewText((xmlChar*) "\n");
985 xmlAddChild(pJavaInfoNode, nodeCrLf);
987 //Create the version element
988 xmlNewTextChild(pJavaInfoNode, NULL, (xmlChar*) "version",
989 CXmlCharPtr(sVersion));
990 //add a new line for better readability
991 nodeCrLf = xmlNewText((xmlChar*) "\n");
992 xmlAddChild(pJavaInfoNode, nodeCrLf);
994 //Create the features element
995 OUString sFeatures = OUString::valueOf(
996 (sal_Int64)nFeatures, 16);
997 xmlNewTextChild(pJavaInfoNode, NULL, (xmlChar*) "features",
998 CXmlCharPtr(sFeatures));
999 //add a new line for better readability
1000 nodeCrLf = xmlNewText((xmlChar*) "\n");
1001 xmlAddChild(pJavaInfoNode, nodeCrLf);
1004 //Create the requirements element
1005 OUString sRequirements = OUString::valueOf(
1006 (sal_Int64) nRequirements, 16);
1007 xmlNewTextChild(pJavaInfoNode, NULL, (xmlChar*) "requirements",
1008 CXmlCharPtr(sRequirements));
1009 //add a new line for better readability
1010 nodeCrLf = xmlNewText((xmlChar*) "\n");
1011 xmlAddChild(pJavaInfoNode, nodeCrLf);
1014 //Create the features element
1015 rtl::ByteSequence data = encodeBase16(arVendorData);
1016 xmlNode* dataNode = xmlNewChild(pJavaInfoNode, NULL,
1017 (xmlChar*) "vendorData",
1018 (xmlChar*) "");
1019 xmlNodeSetContentLen(dataNode,
1020 (xmlChar*) data.getArray(), data.getLength());
1021 //add a new line for better readability
1022 nodeCrLf = xmlNewText((xmlChar*) "\n");
1023 xmlAddChild(pJavaInfoNode, nodeCrLf);
1026 JavaInfo * CNodeJavaInfo::makeJavaInfo() const
1028 if (bNil == true || m_bEmptyNode == true)
1029 return NULL;
1030 JavaInfo * pInfo = (JavaInfo*) rtl_allocateMemory(sizeof(JavaInfo));
1031 if (pInfo == NULL)
1032 return NULL;
1033 memset(pInfo, 0, sizeof(JavaInfo));
1034 pInfo->sVendor = sVendor.pData;
1035 rtl_uString_acquire(pInfo->sVendor);
1036 pInfo->sLocation = sLocation.pData;
1037 rtl_uString_acquire(pInfo->sLocation);
1038 pInfo->sVersion = sVersion.pData;
1039 rtl_uString_acquire(pInfo->sVersion);
1040 pInfo->nFeatures = nFeatures;
1041 pInfo->nRequirements = nRequirements;
1042 pInfo->arVendorData = arVendorData.getHandle();
1043 rtl_byte_sequence_acquire(pInfo->arVendorData);
1044 return pInfo;
1047 //================================================================================
1048 MergedSettings::MergedSettings():
1049 m_bEnabled(false),
1050 m_sClassPath(),
1051 m_vmParams(),
1052 m_JRELocations(),
1053 m_javaInfo()
1055 NodeJava settings(NodeJava::USER);
1056 settings.load();
1057 NodeJava sharedSettings(NodeJava::SHARED);
1058 sharedSettings.load();
1059 merge(sharedSettings, settings);
1062 MergedSettings::~MergedSettings()
1066 void MergedSettings::merge(const NodeJava & share, const NodeJava & user)
1068 if (user.getEnabled())
1069 m_bEnabled = * user.getEnabled();
1070 else if (share.getEnabled())
1071 m_bEnabled = * share.getEnabled();
1072 else
1073 m_bEnabled = sal_True;
1075 if (user.getUserClassPath())
1076 m_sClassPath = * user.getUserClassPath();
1077 else if (share.getUserClassPath())
1078 m_sClassPath = * share.getUserClassPath();
1080 if (user.getJavaInfo())
1081 m_javaInfo = * user.getJavaInfo();
1082 else if (share.getJavaInfo())
1083 m_javaInfo = * share.getJavaInfo();
1085 if (user.getVmParameters())
1086 m_vmParams = * user.getVmParameters();
1087 else if (share.getVmParameters())
1088 m_vmParams = * share.getVmParameters();
1090 if (user.getJRELocations())
1091 m_JRELocations = * user.getJRELocations();
1092 else if (share.getJRELocations())
1093 m_JRELocations = * share.getJRELocations();
1096 bool MergedSettings::getEnabled() const
1098 return m_bEnabled;
1100 const OUString& MergedSettings::getUserClassPath() const
1102 return m_sClassPath;
1105 ::std::vector< OString> MergedSettings::getVmParametersUtf8() const
1107 ::std::vector< OString> ret;
1108 typedef ::std::vector< OUString>::const_iterator cit;
1109 for (cit i = m_vmParams.begin(); i != m_vmParams.end(); ++i)
1111 ret.push_back( OUStringToOString(*i, RTL_TEXTENCODING_UTF8));
1113 return ret;
1116 const OString & MergedSettings::getJavaInfoAttrVendorUpdate() const
1118 return m_javaInfo.sAttrVendorUpdate;
1122 JavaInfo * MergedSettings::createJavaInfo() const
1124 return m_javaInfo.makeJavaInfo();
1126 #ifdef WNT
1127 bool MergedSettings::getJavaInfoAttrAutoSelect() const
1129 return m_javaInfo.bAutoSelect;
1131 #endif
1132 void MergedSettings::getVmParametersArray(
1133 rtl_uString *** parParams, sal_Int32 * size) const
1135 osl::MutexGuard guard(FwkMutex::get());
1136 OSL_ASSERT(parParams != NULL && size != NULL);
1138 *parParams = (rtl_uString **)
1139 rtl_allocateMemory(sizeof(rtl_uString*) * m_vmParams.size());
1140 if (*parParams == NULL)
1141 return;
1143 int j=0;
1144 typedef std::vector<OUString>::const_iterator it;
1145 for (it i = m_vmParams.begin(); i != m_vmParams.end();
1146 ++i, ++j)
1148 (*parParams)[j] = i->pData;
1149 rtl_uString_acquire(i->pData);
1151 *size = m_vmParams.size();
1154 void MergedSettings::getJRELocations(
1155 rtl_uString *** parLocations, sal_Int32 * size) const
1157 osl::MutexGuard guard(FwkMutex::get());
1158 OSL_ASSERT(parLocations != NULL && size != NULL);
1160 *parLocations = (rtl_uString **)
1161 rtl_allocateMemory(sizeof(rtl_uString*) * m_JRELocations.size());
1162 if (*parLocations == NULL)
1163 return;
1165 int j=0;
1166 typedef std::vector<OUString>::const_iterator it;
1167 for (it i = m_JRELocations.begin(); i != m_JRELocations.end();
1168 ++i, ++j)
1170 (*parLocations)[j] = i->pData;
1171 rtl_uString_acquire(i->pData);
1173 *size = m_JRELocations.size();
1175 const std::vector<OUString> & MergedSettings::getJRELocations() const
1177 return m_JRELocations;
1181 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */