[Libreoffice-commits] core.git: 4 commits - include/jvmfwk jvmfwk/inc jvmfwk/plugins jvmfwk/source

Stephan Bergmann sbergman at redhat.com
Mon Dec 15 07:46:25 PST 2014


 include/jvmfwk/framework.h                          |   56 ++-
 jvmfwk/inc/vendorbase.hxx                           |  184 ++++++++++++
 jvmfwk/inc/vendorplugin.hxx                         |   86 +++++
 jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx |  108 +++++++
 jvmfwk/plugins/sunmajor/pluginlib/util.cxx          |  137 +++++----
 jvmfwk/plugins/sunmajor/pluginlib/util.hxx          |   47 +--
 jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx    |  184 ------------
 jvmfwk/source/framework.cxx                         |  291 ++++++++++++--------
 8 files changed, 697 insertions(+), 396 deletions(-)

New commits:
commit 5e9a2e9b0f33ab50aa3a84728db75383aede19d9
Author: Stephan Bergmann <sbergman at redhat.com>
Date:   Mon Dec 15 16:42:03 2014 +0100

    Check each potential JRE location only once
    
    i.e., after recent "fdo#83753: consider JAVA_HOME and PATH when selecting JRE"
    fix, if jfw_findAndSelectJRE found no suitable JRE in
    jfw_plugin_getJavaInfoFromJavaHome or jfw_plugin_getJavaInfosFromPath, do not
    re-check those locations in jfw_plugin_getAllJavaInfos.
    
    Change-Id: If4e085b4fceff5b2494c7b7b84ac51691dbc78cc

diff --git a/jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx b/jvmfwk/inc/vendorbase.hxx
similarity index 100%
rename from jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx
rename to jvmfwk/inc/vendorbase.hxx
diff --git a/jvmfwk/inc/vendorplugin.hxx b/jvmfwk/inc/vendorplugin.hxx
index 35131df..25d9246 100644
--- a/jvmfwk/inc/vendorplugin.hxx
+++ b/jvmfwk/inc/vendorplugin.hxx
@@ -22,11 +22,13 @@
 #define INCLUDED_JVMFWK_INC_VENDORPLUGIN_HXX
 
 #include <jvmfwk/framework.h>
+#include <rtl/ref.hxx>
 #include <rtl/ustring.h>
 #include "jni.h"
 #include <vector>
 #include <utility>
 #include "../source/elements.hxx"
+#include <vendorbase.hxx>
 
 /**
    @file
@@ -112,13 +114,15 @@ typedef enum
     version strings.
  */
 javaPluginError jfw_plugin_getAllJavaInfos(
+    bool checkJavaHomeAndPath,
     OUString const& sVendor,
     OUString const& sMinVersion,
     OUString const& sMaxVersion,
     rtl_uString * * arExcludeList,
     sal_Int32  nSizeExcludeList,
     JavaInfo*** parJavaInfo,
-    sal_Int32 *nSizeJavaInfo);
+    sal_Int32 *nSizeJavaInfo,
+    std::vector<rtl::Reference<jfw_plugin::VendorBase>> & infos);
 
 /** obtains information for a JRE at a given location.
 
@@ -202,7 +206,8 @@ javaPluginError jfw_plugin_getJavaInfoByPath(
  */
 javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
     std::vector<std::pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
-    JavaInfo ** ppInfo);
+    JavaInfo ** ppInfo,
+    std::vector<rtl::Reference<jfw_plugin::VendorBase>> & infos);
 
 
 /** obtains information about installations of Java Runtime Environments (JREs)
@@ -244,7 +249,8 @@ javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
 
 javaPluginError jfw_plugin_getJavaInfosFromPath(
     std::vector<std::pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
-    std::vector<JavaInfo*> & vecJavaInfosFromPath);
+    std::vector<JavaInfo*> & vecJavaInfosFromPath,
+    std::vector<rtl::Reference<jfw_plugin::VendorBase>> & infos);
 
 /** starts a Java Virtual Machine.
 
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx b/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx
index 1771bcc..d3ac151 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx
@@ -299,13 +299,15 @@ javaPluginError checkJavaVersionRequirements(
 }
 
 javaPluginError jfw_plugin_getAllJavaInfos(
+    bool checkJavaHomeAndPath,
     OUString const& sVendor,
     OUString const& sMinVersion,
     OUString const& sMaxVersion,
     rtl_uString  * *arExcludeList,
     sal_Int32  nLenList,
     JavaInfo*** parJavaInfo,
-    sal_Int32 *nLenInfoList)
+    sal_Int32 *nLenInfoList,
+    std::vector<rtl::Reference<jfw_plugin::VendorBase>> & infos)
 {
     OSL_ASSERT(parJavaInfo);
     OSL_ASSERT(nLenInfoList);
@@ -326,7 +328,7 @@ javaPluginError jfw_plugin_getAllJavaInfos(
 
     //Find all JREs
     vector<rtl::Reference<VendorBase> > vecInfos =
-        getAllJREInfos();
+        addAllJREInfos(checkJavaHomeAndPath, infos);
     vector<rtl::Reference<VendorBase> > vecVerifiedInfos;
 
     typedef vector<rtl::Reference<VendorBase> >::iterator it;
@@ -406,15 +408,17 @@ javaPluginError jfw_plugin_getJavaInfoByPath(
 
 javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
     std::vector<pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
-    JavaInfo ** ppInfo)
+    JavaInfo ** ppInfo, std::vector<rtl::Reference<VendorBase>> & infos)
 {
     if (!ppInfo)
         return JFW_PLUGIN_E_INVALID_ARG;
 
-    rtl::Reference<VendorBase> infoJavaHome = getJavaInfoFromJavaHome();
+    std::vector<rtl::Reference<VendorBase>> infoJavaHome;
+    addJavaInfoFromJavaHome(infos, infoJavaHome);
 
-    if (!infoJavaHome.is())
+    if (infoJavaHome.empty())
         return JFW_PLUGIN_E_NO_JRE;
+    assert(infoJavaHome.size() == 1);
 
     //Check if the detected JRE matches the version requirements
     typedef std::vector<pair<OUString, jfw::VersionInfo>>::const_iterator ci_pl;
@@ -423,10 +427,10 @@ javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
         const OUString& vendor = vendorInfo->first;
         jfw::VersionInfo versionInfo = vendorInfo->second;
 
-        if (vendor.equals(infoJavaHome->getVendor()))
+        if (vendor.equals(infoJavaHome[0]->getVendor()))
         {
             javaPluginError errorcode = checkJavaVersionRequirements(
-                infoJavaHome,
+                infoJavaHome[0],
                 versionInfo.sMinVersion,
                 versionInfo.sMaxVersion,
                 versionInfo.getExcludeVersions(),
@@ -434,7 +438,7 @@ javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
 
             if (errorcode == JFW_PLUGIN_E_NONE)
             {
-                *ppInfo = createJavaInfo(infoJavaHome);
+                *ppInfo = createJavaInfo(infoJavaHome[0]);
                 return JFW_PLUGIN_E_NONE;
             }
         }
@@ -445,11 +449,12 @@ javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
 
 javaPluginError jfw_plugin_getJavaInfosFromPath(
     std::vector<std::pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
-    std::vector<JavaInfo*> & javaInfosFromPath)
+    std::vector<JavaInfo*> & javaInfosFromPath,
+    std::vector<rtl::Reference<jfw_plugin::VendorBase>> & infos)
 {
     // find JREs from PATH
     vector<rtl::Reference<VendorBase>> vecInfosFromPath;
-    createJavaInfoFromPath(vecInfosFromPath);
+    addJavaInfosFromPath(infos, vecInfosFromPath);
 
     vector<rtl::Reference<VendorBase> > vecVerifiedInfos;
 
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
index 621b358..7b29faf 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
@@ -139,23 +139,35 @@ bool decodeOutput(const OString& s, OUString* out);
 namespace
 {
 
-bool getAndAddJREInfoByPath(const OUString& path,
-                      std::vector<rtl::Reference<VendorBase> > & vecInfos)
+bool addJREInfo(
+    rtl::Reference<VendorBase> const & info,
+    std::vector<rtl::Reference<VendorBase>> & infos)
 {
-    bool ret = false;
+    auto i(
+        std::find_if(
+            infos.begin(), infos.end(), InfoFindSame(info->getHome())));
+    if (i == infos.end()) {
+        infos.push_back(info);
+        return true;
+    } else {
+        return false;
+    }
+}
 
+bool getAndAddJREInfoByPath(
+    const OUString& path,
+    std::vector<rtl::Reference<VendorBase> > & allInfos,
+    std::vector<rtl::Reference<VendorBase> > & addedInfos)
+{
     rtl::Reference<VendorBase> aInfo = getJREInfoByPath(path);
-    if (aInfo.is())
-    {
-        ret = true;
-        vector<rtl::Reference<VendorBase> >::const_iterator it_impl= std::find_if(
-            vecInfos.begin(),vecInfos.end(), InfoFindSame(aInfo->getHome()));
-        if(it_impl == vecInfos.end())
-        {
-            vecInfos.push_back(aInfo);
+    if (aInfo.is()) {
+        if (addJREInfo(aInfo, allInfos)) {
+            addedInfos.push_back(aInfo);
         }
+        return true;
+    } else {
+        return false;
     }
-    return ret;
 }
 
     OUString getLibraryLocation()
@@ -572,7 +584,9 @@ bool decodeOutput(const OString& s, OUString* out)
 
 
 #if defined WNT
-void createJavaInfoFromWinReg(std::vector<rtl::Reference<VendorBase> > & vecInfos)
+void addJavaInfoFromWinReg(
+    std::vector<rtl::Reference<VendorBase> > & allInfos,
+    std::vector<rtl::Reference<VendorBase> > & addedInfos)
 {
         // Get Java s from registry
     std::vector<OUString> vecJavaHome;
@@ -583,7 +597,7 @@ void createJavaInfoFromWinReg(std::vector<rtl::Reference<VendorBase> > & vecInfo
         for(ItHome it_home= vecJavaHome.begin(); it_home != vecJavaHome.end();
             it_home++)
         {
-            getAndAddJREInfoByPath(*it_home, vecInfos);
+            getAndAddJREInfoByPath(*it_home, allInfos, addedInfos);
         }
     }
 
@@ -594,7 +608,7 @@ void createJavaInfoFromWinReg(std::vector<rtl::Reference<VendorBase> > & vecInfo
         for(ItHome it_home= vecJavaHome.begin(); it_home != vecJavaHome.end();
             it_home++)
         {
-            getAndAddJREInfoByPath(*it_home, vecInfos);
+            getAndAddJREInfoByPath(*it_home, allInfos, addedInfos);
         }
    }
 }
@@ -736,8 +750,9 @@ void bubbleSortVersion(vector<rtl::Reference<VendorBase> >& vec)
 }
 
 
-void getJREInfoFromBinPath(
-    const OUString& path, vector<rtl::Reference<VendorBase> > & vecInfos)
+void addJREInfoFromBinPath(
+    const OUString& path, vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos)
 {
     // file:///c:/jre/bin
     //map:       jre/bin/java.exe
@@ -782,37 +797,41 @@ void getJREInfoFromBinPath(
                     sHome = sBinPath.copy(index - 1);
                 }
             }
-            if (!sHome.isEmpty())
+            if (!sHome.isEmpty()
+                && getAndAddJREInfoByPath(path, allInfos, addedInfos))
             {
-                if (getAndAddJREInfoByPath(sHome, vecInfos))
-                    return;
+                return;
             }
         }
     }
 }
 
-vector<Reference<VendorBase> > getAllJREInfos()
+vector<Reference<VendorBase> > addAllJREInfos(
+    bool checkJavaHomeAndPath,
+    std::vector<rtl::Reference<VendorBase>> & allInfos)
 {
-    vector<Reference<VendorBase> > vecInfos;
+    vector<Reference<VendorBase> > addedInfos;
 
 #if defined WNT
     // Get Javas from the registry
-    createJavaInfoFromWinReg(vecInfos);
+    addJavaInfoFromWinReg(allInfos, addedInfos);
 #endif // WNT
 
 #ifndef JVM_ONE_PATH_CHECK
-    createJavaInfoFromJavaHome(vecInfos);
-    //this function should be called after createJavaInfoDirScan.
-    //Otherwise in SDKs Java may be started twice
-     createJavaInfoFromPath(vecInfos);
+    if (checkJavaHomeAndPath) {
+        addJavaInfoFromJavaHome(allInfos, addedInfos);
+        //this function should be called after addJavaInfosDirScan.
+        //Otherwise in SDKs Java may be started twice
+        addJavaInfosFromPath(allInfos, addedInfos);
+    }
 #endif
 
 #ifdef UNX
-    createJavaInfoDirScan(vecInfos);
+    addJavaInfosDirScan(allInfos, addedInfos);
 #endif
 
-    bubbleSortVersion(vecInfos);
-    return vecInfos;
+    bubbleSortVersion(addedInfos);
+    return addedInfos;
 }
 
 
@@ -1080,7 +1099,9 @@ inline OUString getDirFromFile(const OUString& usFilePath)
     return usFilePath.copy(0, index);
 }
 
-void createJavaInfoFromPath(vector<rtl::Reference<VendorBase> >& vecInfos)
+void addJavaInfosFromPath(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos)
 {
 // Get Java from PATH environment variable
     static const char sCurDir[] = ".";
@@ -1119,7 +1140,7 @@ void createJavaInfoFromPath(vector<rtl::Reference<VendorBase> >& vecInfos)
                     }
                     if(!usBin.isEmpty())
                     {
-                        getJREInfoFromBinPath(usBin, vecInfos);
+                        addJREInfoFromBinPath(usBin, allInfos, addedInfos);
                     }
                 }
             }
@@ -1129,7 +1150,9 @@ void createJavaInfoFromPath(vector<rtl::Reference<VendorBase> >& vecInfos)
 }
 
 
-rtl::Reference<VendorBase> getJavaInfoFromJavaHome()
+void addJavaInfoFromJavaHome(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos)
 {
     // Get Java from JAVA_HOME environment
 
@@ -1144,24 +1167,7 @@ rtl::Reference<VendorBase> getJavaInfoFromJavaHome()
         OUString sHomeUrl;
         if(File::getFileURLFromSystemPath(sHome, sHomeUrl) == File::E_None)
         {
-            return getJREInfoByPath(sHomeUrl);
-        }
-    }
-
-    return NULL;
-}
-
-void createJavaInfoFromJavaHome(vector<rtl::Reference<VendorBase> >& vecInfos)
-{
-    rtl::Reference<VendorBase> aInfo = getJavaInfoFromJavaHome();
-
-    if (aInfo.is())
-    {
-        vector<rtl::Reference<VendorBase> >::const_iterator it_impl= std::find_if(
-            vecInfos.begin(),vecInfos.end(), InfoFindSame(aInfo->getHome()));
-        if(it_impl == vecInfos.end())
-        {
-            vecInfos.push_back(aInfo);
+            getAndAddJREInfoByPath(sHomeUrl, allInfos, addedInfos);
         }
     }
 }
@@ -1185,25 +1191,31 @@ bool makeDriveLetterSame(OUString * fileURL)
 #ifdef UNX
 #ifdef SOLARIS
 
-void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
+void addJavaInfosDirScan(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos)
 {
     JFW_TRACE2("Checking /usr/jdk/latest");
-    getAndAddJREInfoByPath("file:////usr/jdk/latest", vecInfos);
+    getAndAddJREInfoByPath("file:////usr/jdk/latest", allInfos, addedInfos);
 }
 
 #elif defined MACOSX && defined X86_64
 
-void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
+void addJavaInfosDirScan(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos)
 {
     // Oracle Java 7
-    getAndAddJREInfoByPath("file:///Library/Internet Plug-Ins/JavaAppletPlugin.plugin/Contents/Home", vecInfos);
+    getAndAddJREInfoByPath("file:///Library/Internet Plug-Ins/JavaAppletPlugin.plugin/Contents/Home", allInfos, addedInfos);
 }
 
 #else
-void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
+void addJavaInfosDirScan(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos)
 {
     OUString excMessage = "[Java framework] sunjavaplugin: "
-                          "Error in function createJavaInfoDirScan in util.cxx.";
+                          "Error in function addJavaInfosDirScan in util.cxx.";
     int cJavaNames= sizeof(g_arJavaNames) / sizeof(char*);
     boost::scoped_array<OUString> sarJavaNames(new OUString[cJavaNames]);
     OUString *arNames = sarJavaNames.get();
@@ -1273,7 +1285,8 @@ void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
                         }
                         JFW_TRACE2("Checking if directory: " << aStatus.getFileURL() << " is a Java");
 
-                        getAndAddJREInfoByPath(aStatus.getFileURL(),vecInfos);
+                        getAndAddJREInfoByPath(
+                            aStatus.getFileURL(), allInfos, addedInfos);
                     }
 
                     JFW_ENSURE(errNext == File::E_None || errNext == File::E_NOENT,
@@ -1305,7 +1318,8 @@ void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
                                     && (islash
                                         > RTL_CONSTASCII_LENGTH("file://")))
                                     usDir3 = usDir3.copy(0, islash);
-                                getAndAddJREInfoByPath(usDir3,vecInfos);
+                                getAndAddJREInfoByPath(
+                                    usDir3, allInfos, addedInfos);
                             }
                         }
                     }
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
index 18232e8..ffe07c2 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
@@ -35,21 +35,25 @@ std::vector<OUString> getVectorFromCharArray(char const * const * ar, int size);
      argument to getJREInfoByPath. For example usBinDir is
      file:///c:/j2sdk/jre/bin then file:///c:/j2sdk/jre would be derived.
  */
-void getJREInfoFromBinPath(
-    const OUString& path, std::vector<rtl::Reference<VendorBase> > & vecInfos);
+void addJREInfoFromBinPath(
+    const OUString& path,
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos);
 inline OUString getDirFromFile(const OUString& usFilePath);
-void createJavaInfoFromPath(std::vector<rtl::Reference<VendorBase> >& vecInfos);
+void addJavaInfosFromPath(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos);
 
 /* Returns a VendorBase object if JAVA_HOME environment variable points
    to a JRE.
  */
-rtl::Reference<VendorBase> getJavaInfoFromJavaHome();
+void addJavaInfoFromJavaHome(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos);
 
-void createJavaInfoFromJavaHome(std::vector<rtl::Reference<VendorBase> > &vecInfos);
-void createJavaInfoDirScan(std::vector<rtl::Reference<VendorBase> >& vecInfos);
-#ifdef WNT
-void createJavaInfoFromWinReg(std::vector<rtl::Reference<VendorBase> >& vecInfos);
-#endif
+void addJavaInfosDirScan(
+    std::vector<rtl::Reference<VendorBase>> & allInfos,
+    std::vector<rtl::Reference<VendorBase>> & addedInfos);
 
 bool makeDriveLetterSame(OUString * fileURL);
 
@@ -95,7 +99,8 @@ struct SameOrSubDirJREMap
  */
 rtl::Reference<VendorBase> getJREInfoByPath(const OUString& path);
 
-std::vector<rtl::Reference<VendorBase> > getAllJREInfos();
+std::vector<rtl::Reference<VendorBase> > addAllJREInfos(
+    bool checkJavaHomeAndPath, std::vector<rtl::Reference<VendorBase>> & infos);
 
 bool getJavaProps(
     const OUString & exePath,
@@ -105,8 +110,6 @@ bool getJavaProps(
     std::vector<std::pair<OUString, OUString> >& props,
     bool * bProcessRun);
 
-void  createJavaInfoFromWinReg(std::vector<rtl::Reference<VendorBase> > & vecInfos);
-
 void bubbleSortVersion(std::vector<rtl::Reference<VendorBase> >& vec);
 
 rtl::Bootstrap* getBootstrap();
diff --git a/jvmfwk/source/framework.cxx b/jvmfwk/source/framework.cxx
index 75daa77..314e92f 100644
--- a/jvmfwk/source/framework.cxx
+++ b/jvmfwk/source/framework.cxx
@@ -86,14 +86,17 @@ javaFrameworkError SAL_CALL jfw_findAllJREs(JavaInfo ***pparInfo, sal_Int32 *pSi
             //maxVersion and excludeVersions
             sal_Int32 cInfos = 0;
             JavaInfo** arInfos = NULL;
+            std::vector<rtl::Reference<jfw_plugin::VendorBase>> infos;
             javaPluginError plerr = jfw_plugin_getAllJavaInfos(
+                true,
                 vendor,
                 versionInfo.sMinVersion,
                 versionInfo.sMaxVersion,
                 versionInfo.getExcludeVersions(),
                 versionInfo.getExcludeVersionSize(),
                 & arInfos,
-                & cInfos);
+                & cInfos,
+                infos);
 
             if (plerr != JFW_PLUGIN_E_NONE)
                 return JFW_E_ERROR;
@@ -408,10 +411,12 @@ javaFrameworkError SAL_CALL jfw_findAndSelectJRE(JavaInfo **pInfo)
                 std::pair<OUString, jfw::VersionInfo>(vendor, versionInfo));
         }
 
+        std::vector<rtl::Reference<jfw_plugin::VendorBase>> infos;
+
         // first inspect Java installation that the JAVA_HOME
         // environment variable points to (if it is set)
         JavaInfo* pHomeInfo = NULL;
-        if (jfw_plugin_getJavaInfoFromJavaHome(versionInfos, &pHomeInfo)
+        if (jfw_plugin_getJavaInfoFromJavaHome(versionInfos, &pHomeInfo, infos)
             == JFW_PLUGIN_E_NONE)
         {
             aCurrentInfo = pHomeInfo;
@@ -431,7 +436,8 @@ javaFrameworkError SAL_CALL jfw_findAndSelectJRE(JavaInfo **pInfo)
         if (!bInfoFound)
         {
             std::vector<JavaInfo*> vecJavaInfosFromPath;
-            if (jfw_plugin_getJavaInfosFromPath(versionInfos, vecJavaInfosFromPath)
+            if (jfw_plugin_getJavaInfosFromPath(
+                    versionInfos, vecJavaInfosFromPath, infos)
                 == JFW_PLUGIN_E_NONE)
             {
                 std::vector<JavaInfo*>::const_iterator it = vecJavaInfosFromPath.begin();
@@ -482,13 +488,15 @@ javaFrameworkError SAL_CALL jfw_findAndSelectJRE(JavaInfo **pInfo)
                 sal_Int32 cInfos = 0;
                 JavaInfo** arInfos = NULL;
                 javaPluginError plerr = jfw_plugin_getAllJavaInfos(
+                    false,
                     vendor,
                     versionInfo.sMinVersion,
                     versionInfo.sMaxVersion,
                     versionInfo.getExcludeVersions(),
                     versionInfo.getExcludeVersionSize(),
                     & arInfos,
-                    & cInfos);
+                    & cInfos,
+                    infos);
 
                 if (plerr != JFW_PLUGIN_E_NONE)
                     continue;
commit 0136acb836f3451786c4bd9c34dafe66e30d4dda
Author: Stephan Bergmann <sbergman at redhat.com>
Date:   Mon Dec 15 15:10:55 2014 +0100

    Rename getJREInfoByPath overload to getAndAddJREInfoByPath
    
    Change-Id: Ib6eac731a4b8193a8d9b9132da78e7961aec22ab

diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
index 567e011..621b358 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
@@ -138,6 +138,26 @@ bool decodeOutput(const OString& s, OUString* out);
 
 namespace
 {
+
+bool getAndAddJREInfoByPath(const OUString& path,
+                      std::vector<rtl::Reference<VendorBase> > & vecInfos)
+{
+    bool ret = false;
+
+    rtl::Reference<VendorBase> aInfo = getJREInfoByPath(path);
+    if (aInfo.is())
+    {
+        ret = true;
+        vector<rtl::Reference<VendorBase> >::const_iterator it_impl= std::find_if(
+            vecInfos.begin(),vecInfos.end(), InfoFindSame(aInfo->getHome()));
+        if(it_impl == vecInfos.end())
+        {
+            vecInfos.push_back(aInfo);
+        }
+    }
+    return ret;
+}
+
     OUString getLibraryLocation()
     {
         OUString libraryFileUrl;
@@ -563,7 +583,7 @@ void createJavaInfoFromWinReg(std::vector<rtl::Reference<VendorBase> > & vecInfo
         for(ItHome it_home= vecJavaHome.begin(); it_home != vecJavaHome.end();
             it_home++)
         {
-            getJREInfoByPath(*it_home, vecInfos);
+            getAndAddJREInfoByPath(*it_home, vecInfos);
         }
     }
 
@@ -574,7 +594,7 @@ void createJavaInfoFromWinReg(std::vector<rtl::Reference<VendorBase> > & vecInfo
         for(ItHome it_home= vecJavaHome.begin(); it_home != vecJavaHome.end();
             it_home++)
         {
-            getJREInfoByPath(*it_home, vecInfos);
+            getAndAddJREInfoByPath(*it_home, vecInfos);
         }
    }
 }
@@ -764,7 +784,7 @@ void getJREInfoFromBinPath(
             }
             if (!sHome.isEmpty())
             {
-                if (getJREInfoByPath(sHome, vecInfos))
+                if (getAndAddJREInfoByPath(sHome, vecInfos))
                     return;
             }
         }
@@ -806,24 +826,6 @@ vector<OUString> getVectorFromCharArray(char const * const * ar, int size)
     }
     return vec;
 }
-bool getJREInfoByPath(const OUString& path,
-                      std::vector<rtl::Reference<VendorBase> > & vecInfos)
-{
-    bool ret = false;
-
-    rtl::Reference<VendorBase> aInfo = getJREInfoByPath(path);
-    if (aInfo.is())
-    {
-        ret = true;
-        vector<rtl::Reference<VendorBase> >::const_iterator it_impl= std::find_if(
-            vecInfos.begin(),vecInfos.end(), InfoFindSame(aInfo->getHome()));
-        if(it_impl == vecInfos.end())
-        {
-            vecInfos.push_back(aInfo);
-        }
-    }
-    return ret;
-}
 
 /** Checks if the path is a directory. Links are resolved.
     In case of an error the returned string has the length 0.
@@ -1186,7 +1188,7 @@ bool makeDriveLetterSame(OUString * fileURL)
 void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
 {
     JFW_TRACE2("Checking /usr/jdk/latest");
-    getJREInfoByPath("file:////usr/jdk/latest", vecInfos);
+    getAndAddJREInfoByPath("file:////usr/jdk/latest", vecInfos);
 }
 
 #elif defined MACOSX && defined X86_64
@@ -1194,7 +1196,7 @@ void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
 void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
 {
     // Oracle Java 7
-    getJREInfoByPath("file:///Library/Internet Plug-Ins/JavaAppletPlugin.plugin/Contents/Home", vecInfos);
+    getAndAddJREInfoByPath("file:///Library/Internet Plug-Ins/JavaAppletPlugin.plugin/Contents/Home", vecInfos);
 }
 
 #else
@@ -1271,7 +1273,7 @@ void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
                         }
                         JFW_TRACE2("Checking if directory: " << aStatus.getFileURL() << " is a Java");
 
-                        getJREInfoByPath(aStatus.getFileURL(),vecInfos);
+                        getAndAddJREInfoByPath(aStatus.getFileURL(),vecInfos);
                     }
 
                     JFW_ENSURE(errNext == File::E_None || errNext == File::E_NOENT,
@@ -1303,7 +1305,7 @@ void createJavaInfoDirScan(vector<rtl::Reference<VendorBase> >& vecInfos)
                                     && (islash
                                         > RTL_CONSTASCII_LENGTH("file://")))
                                     usDir3 = usDir3.copy(0, islash);
-                                getJREInfoByPath(usDir3,vecInfos);
+                                getAndAddJREInfoByPath(usDir3,vecInfos);
                             }
                         }
                     }
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
index e8bfb11..18232e8 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
@@ -95,22 +95,6 @@ struct SameOrSubDirJREMap
  */
 rtl::Reference<VendorBase> getJREInfoByPath(const OUString& path);
 
-/* Creates a VendorBase object if a JRE could be found at the specified path.
-
-   The difference to the other getJREInfoByPath is that this function checks
-   first if the path corresponds to one of the VendorBase::getHome path already
-   contained in vecInfo. Only if there is no such entry, then the other
-   getJREInfoByPath is called. Again the created VendorBase is compared to
-   those contained in vecInfos. If it is not in there then it's added.
-
-   @return
-   true a VendorBase was created and added to the end of vecInfos.
-   false - no VendorBase has been created. Either the path did not represent a
-   supported JRE installation or there was already a VendorBase in vecInfos.
- */
-bool getJREInfoByPath(const OUString& path,
-                      std::vector<rtl::Reference<VendorBase> > & vecInfos);
-
 std::vector<rtl::Reference<VendorBase> > getAllJREInfos();
 
 bool getJavaProps(
commit 5d2398a982ea756c99d5f9300b93d61b884eddc4
Author: Stephan Bergmann <sbergman at redhat.com>
Date:   Mon Dec 15 15:00:15 2014 +0100

    getJREInfoFromBinPath return value is unused
    
    Change-Id: I360d7cb7c03e78739883db4b989ba5f31bc8e24b

diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
index 8924a59..567e011 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
@@ -716,12 +716,11 @@ void bubbleSortVersion(vector<rtl::Reference<VendorBase> >& vec)
 }
 
 
-bool getJREInfoFromBinPath(
+void getJREInfoFromBinPath(
     const OUString& path, vector<rtl::Reference<VendorBase> > & vecInfos)
 {
     // file:///c:/jre/bin
     //map:       jre/bin/java.exe
-    bool ret = false;
 
     for ( sal_Int32 pos = 0;
           gVendorMap[pos].sVendorName != NULL; ++pos )
@@ -765,15 +764,11 @@ bool getJREInfoFromBinPath(
             }
             if (!sHome.isEmpty())
             {
-                ret = getJREInfoByPath(sHome, vecInfos);
-                if (ret)
-                    break;
+                if (getJREInfoByPath(sHome, vecInfos))
+                    return;
             }
         }
-        if (ret)
-            break;
     }
-    return ret;
 }
 
 vector<Reference<VendorBase> > getAllJREInfos()
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
index 38d3175..e8bfb11 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
@@ -35,7 +35,7 @@ std::vector<OUString> getVectorFromCharArray(char const * const * ar, int size);
      argument to getJREInfoByPath. For example usBinDir is
      file:///c:/j2sdk/jre/bin then file:///c:/j2sdk/jre would be derived.
  */
-bool getJREInfoFromBinPath(
+void getJREInfoFromBinPath(
     const OUString& path, std::vector<rtl::Reference<VendorBase> > & vecInfos);
 inline OUString getDirFromFile(const OUString& usFilePath);
 void createJavaInfoFromPath(std::vector<rtl::Reference<VendorBase> >& vecInfos);
commit 40138cee6b6f19a7725f3ce9316f285b86366a06
Author: Michael Weghorn <m.weghorn at posteo.de>
Date:   Wed Sep 10 14:56:25 2014 +0200

    fdo#83753: consider JAVA_HOME and PATH when selecting JRE
    
    adapted algorithm that selects the Java runtime to be used so that
    Java installations associated with the JAVA_HOME and PATH
    environment variables are preferred over others
    
    Java installations are now analysed in the following order:
    * installation that the JAVA_HOME environment
        variable refers to (if it is set)
    * Java installations in PATH
    * other Java installation (algorithm that was used before)
    
    Signed-off-by: Stephan Bergmann <sbergman at redhat.com>
    
    Conflicts:
    	jvmfwk/source/framework.cxx
    
    Change-Id: I3a3ade25322def0c0432b369848f13a6b82034a1

diff --git a/include/jvmfwk/framework.h b/include/jvmfwk/framework.h
index 7abf3e1..8421134 100644
--- a/include/jvmfwk/framework.h
+++ b/include/jvmfwk/framework.h
@@ -72,7 +72,7 @@ extern "C" {
     necessary to specify the bootstrap parameter <code>UNO_JAVA_JFW_SHARED_DATA</code>.
     </p>
 
-    <p>Setting the class path used by a Java VM should not be necesarry. The locations
+    <p>Setting the class path used by a Java VM should not be necessary. The locations
     of Jar files should be known by a class loader. If a jar file depends on another
     jar file then it can be referenced in the manifest file of the first jar. However,
     a user may add jars to the class path by using this API. If it becomes necessary
@@ -320,16 +320,11 @@ JVMFWK_DLLPUBLIC javaFrameworkError SAL_CALL jfw_isVMRunning(sal_Bool *bRunning)
 /** detects a suitable JRE and configures the framework to use it.
 
     <p>Which JREs can be used is determined by the file javavendors.xml,
-    which contains version requirements, as well as information about available
-    plug-in libraries. Only these libraries are responsible for locating JRE
-    installations.</p>
+    which contains version requirements.</p>
     <p>
-    JREs can be provided by different vendors. In order to find the JREs of
-    a certain vendor a plug-in library must be provided. There must be only one
-    library for one vendor. The names of locations of those libraries have to
-    be put into the javavendors.xml file.<br/>
-    The function uses the plug-in libraries to obtain information about JRE
-    installation and checks if they there is one among them that supports
+    JREs can be provided by different vendors.
+    The function obtains information about JRE installations and checks if
+    there is one among them that supports
     a set of features (currently only accessibilty is possible). If none was
     found then it also uses a list of paths, which have been registered
     by <code>jfw_addJRELocation</code>
@@ -342,27 +337,36 @@ JVMFWK_DLLPUBLIC javaFrameworkError SAL_CALL jfw_isVMRunning(sal_Bool *bRunning)
     <p>
     While determining a proper JRE this function takes into account if a
     user requires support for assistive technology tools. If user
-    need that support they have to set up their system accordingly. When support
-    for assistive technology is required, then the lists of
+    need that support they have to set up their system accordingly.</p>
+    <p>
+    If the JAVA_HOME environment variable is set, this function prefers
+    the JRE which the variable refers to over other JREs.
+    If JAVA_HOME is not set or does not refer to a suitable JRE,
+    the PATH environment variable is inspected and the respective JREs
+    are checked for their suitability next.</p>
+    <p>
+    When support for assistive technology is required, then the
     <code>JavaInfo</code> objects,
-    which are provided by the <code>getJavaInfo</code> functions of the plug-ins, are
-    examined for a suitable JRE. That is, the <code>JavaInfo</code> objects
-    from the list
-    obtained from the first plug-in, are examined. If no <code>JavaInfo</code>
-    object has the flag
+    which are provided by the <code>getJavaInfo</code> functions, are
+    examined for a suitable JRE.
+    That is, the <code>JavaInfo</code> object that refers to the JRE referred to
+    by JAVA_HOME is examined. If it does not have the flag
     <code>JFW_FEATURE_ACCESSBRIDGE</code> in the member <code>nFeatures</code>
-    then the
-    next plug-in is used to obtain a list of <code>JavaInfo</code> objects.
+    then the <JavaInfo></code> objects that are related to the PATH variable
+    are examined.
+    If no suitable <code>JavaInfo</code> object is found, all <code>JavaInfo</code>
+    objects - representing Java installations on the system -, are examined.
+    As long as no <code>JavaInfo</code> object has the flag
+    <code>JFW_FEATURE_ACCESSBRIDGE</code> in the member <code>nFeatures</code>, more
+    <code>JavaInfo</code> objects are examined.
     This goes on until a <code>JavaInfo</code> object was found which
-    represents a suitable JRE. Or neither plug-in provided such a
-    <code>JavaInfo</code> object. In that case the first
-    <code>JavaInfo</code> object from the first plug-in is used to determine
-    the JRE which is to be used.</p>
+    represents a suitable JRE. Or no such <code>JavaInfo</code> object was found.
+    In that case the first <code>JavaInfo</code> object that was detected
+    by the algorithm described above is used to determine the JRE which is to be used.</p>
     <p>
     If there is no need for the support of assistive technology tools then
-    the first <code>JavaInfo</code> object from the list obtained by the
-    first plug-in is used. If this plug-in does not find any JREs then the
-    next plug-in is used, and so on.</p>
+    the first <code>JavaInfo</code> object that is detected by the algorithm
+    as described above is used.</p>
 
     @param ppInfo
     [out] a <code>JavaInfo</code> pointer, representing the selected JRE.
diff --git a/jvmfwk/inc/vendorplugin.hxx b/jvmfwk/inc/vendorplugin.hxx
index 3fd4d35..35131df 100644
--- a/jvmfwk/inc/vendorplugin.hxx
+++ b/jvmfwk/inc/vendorplugin.hxx
@@ -24,6 +24,9 @@
 #include <jvmfwk/framework.h>
 #include <rtl/ustring.h>
 #include "jni.h"
+#include <vector>
+#include <utility>
+#include "../source/elements.hxx"
 
 /**
    @file
@@ -168,6 +171,81 @@ javaPluginError jfw_plugin_getJavaInfoByPath(
     sal_Int32  nSizeExcludeList,
     JavaInfo ** ppInfo);
 
+
+
+/** obtains information for a JRE referenced by the JAVA_HOME environment variable.
+
+   <p>If the JAVA_HOME environment variable is set and points to a JRE whoose vendor
+   matches the requirements given by vecVendorInfos (i.e. it has a vendor that is
+   given in vecVendorInfos and the version requirements for the vendor are met),
+   then this function shall return a JavaInfo object for this JRE.</p>
+
+   @param vecVendorInfos
+       [in] vector specifying the vendor and version requirements that the JRE must fulfill.
+       The vector contains pairs of vendors and the respective version requirements
+       for those vendors. The JRE must support the requirements of one given pair in the
+       vector (i.e. it must be of one of the vendors and meet the version requirements
+       - minVersion, maxVersion, excludeVersions - for that specific vendor).
+   @param ppInfo
+       [out] if the JAVA_HOME environment variable is set and points to a suitable
+       JRE, then then <code>ppInfo</code> contains
+        on return a pointer to its <code>JavaInfo</code> object.
+
+   @return
+   JFW_PLUGIN_E_NONE the function ran successfully.</br>
+   JFW_PLUGIN_E_INVALID_ARG an argument was not valid, for example
+    <code>ppInfo</code> is an invalid pointer.
+   JFW_PLUGIN_E_NO_JRE no suitable JRE could be detected at the given location. However, that
+   does not mean necessarily that there is no JRE. There could be a JRE but it has
+   a vendor which is not supported by this API implementation or it does not
+   meet the version requirements.
+ */
+javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
+    std::vector<std::pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
+    JavaInfo ** ppInfo);
+
+
+/** obtains information about installations of Java Runtime Environments (JREs)
+    whose executable is in the PATH.
+
+    <p>The function gathers information about available JREs which are on the PATH
+    (PATH environment variable) and meet the vendor and version requirements given by
+    <code>vecVendorInfos</code> (i.e. they have a vendor that is given in
+    <code>vecVendorInfos</code> and the version requirements for the vendor are met).
+    </p>
+    <p>
+    The JavaInfo structures returned in <code>vecJavaInfosFromPath</code> should be ordered
+    according to their occurrence in the PATH. The one that is the first one on the PATH
+    is also the first element in the vector.</p>
+    <p>
+    The function allocates memory for all the JavaInfo objects returned
+    in <code>vecJavaInfosFromPath</code>. The caller must free each JavaInfo object by calling
+    <code>jfw_freeJavaInfo</code> (#include "jvmfwk/framework.h").
+    </p>
+    @param vecVendorInfos
+       [in] vector specifying the vendor and version requirements that the JRE must fulfill.
+       The vector contains pairs of vendors and the respective version requirements
+       for those vendors. The JRE must support the requirements of one given pair in the
+       vector (i.e. it must be of one of the vendors and meet the version requirements
+       - minVersion, maxVersion, excludeVersions - for that specific vendor).
+    @param vecJavaInfosFromPath
+        [out] if the function runs successfully then <code>vecJavaInfosFromPath</code>
+        contains on return a vector of pointers to <code>JavaInfo</code> objects.
+        On return of this function, <code>vecJavaInfosFromPath</code> references
+        a newly created vector rather than the same vector as before with
+        the <code>JavaInfo</code> objects inserted into the existing vector.
+
+    @return
+    JFW_PLUGIN_E_NONE the function ran successfully and at least one JRE
+    that meets the requirements was found.</br>
+    JFW_PLUGIN_E_NO_JRE no JavaInfo that meets the version criteria was found
+    when inspecting the PATH
+ */
+
+javaPluginError jfw_plugin_getJavaInfosFromPath(
+    std::vector<std::pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
+    std::vector<JavaInfo*> & vecJavaInfosFromPath);
+
 /** starts a Java Virtual Machine.
 
     <p>The caller should provide all essential JavaVMOptions, such as the
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx b/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx
index d0dac26..1771bcc 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/sunjavaplugin.cxx
@@ -404,6 +404,105 @@ javaPluginError jfw_plugin_getJavaInfoByPath(
     return errorcode;
 }
 
+javaPluginError jfw_plugin_getJavaInfoFromJavaHome(
+    std::vector<pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
+    JavaInfo ** ppInfo)
+{
+    if (!ppInfo)
+        return JFW_PLUGIN_E_INVALID_ARG;
+
+    rtl::Reference<VendorBase> infoJavaHome = getJavaInfoFromJavaHome();
+
+    if (!infoJavaHome.is())
+        return JFW_PLUGIN_E_NO_JRE;
+
+    //Check if the detected JRE matches the version requirements
+    typedef std::vector<pair<OUString, jfw::VersionInfo>>::const_iterator ci_pl;
+    for (ci_pl vendorInfo = vecVendorInfos.begin(); vendorInfo != vecVendorInfos.end(); ++vendorInfo)
+    {
+        const OUString& vendor = vendorInfo->first;
+        jfw::VersionInfo versionInfo = vendorInfo->second;
+
+        if (vendor.equals(infoJavaHome->getVendor()))
+        {
+            javaPluginError errorcode = checkJavaVersionRequirements(
+                infoJavaHome,
+                versionInfo.sMinVersion,
+                versionInfo.sMaxVersion,
+                versionInfo.getExcludeVersions(),
+                versionInfo.getExcludeVersionSize());
+
+            if (errorcode == JFW_PLUGIN_E_NONE)
+            {
+                *ppInfo = createJavaInfo(infoJavaHome);
+                return JFW_PLUGIN_E_NONE;
+            }
+        }
+    }
+
+    return JFW_PLUGIN_E_NO_JRE;
+}
+
+javaPluginError jfw_plugin_getJavaInfosFromPath(
+    std::vector<std::pair<OUString, jfw::VersionInfo>> const& vecVendorInfos,
+    std::vector<JavaInfo*> & javaInfosFromPath)
+{
+    // find JREs from PATH
+    vector<rtl::Reference<VendorBase>> vecInfosFromPath;
+    createJavaInfoFromPath(vecInfosFromPath);
+
+    vector<rtl::Reference<VendorBase> > vecVerifiedInfos;
+
+    // copy JREs that meet version requirements to vecVerifiedInfos
+    typedef vector<rtl::Reference<VendorBase> >::iterator it;
+    for (it i= vecInfosFromPath.begin(); i != vecInfosFromPath.end(); ++i)
+    {
+        const rtl::Reference<VendorBase>& cur = *i;
+
+        typedef std::vector<pair<OUString, jfw::VersionInfo>>::const_iterator ci_pl;
+        for (ci_pl vendorInfo = vecVendorInfos.begin(); vendorInfo != vecVendorInfos.end(); ++vendorInfo)
+        {
+            const OUString& vendor = vendorInfo->first;
+            jfw::VersionInfo versionInfo = vendorInfo->second;
+
+            if (vendor.equals(cur->getVendor()))
+            {
+                javaPluginError errorcode = checkJavaVersionRequirements(
+                    cur,
+                    versionInfo.sMinVersion,
+                    versionInfo.sMaxVersion,
+                    versionInfo.getExcludeVersions(),
+                    versionInfo.getExcludeVersionSize());
+
+                if (errorcode == JFW_PLUGIN_E_NONE)
+                {
+                    vecVerifiedInfos.push_back(*i);
+                }
+            }
+        }
+    }
+
+    if (vecVerifiedInfos.empty())
+        return JFW_PLUGIN_E_NO_JRE;
+
+    // Now vecVerifiedInfos contains all those JREs which meet the version requirements
+    // Transfer them into the vector that is passed out.
+    vector<JavaInfo*> infosFromPath;
+
+    typedef vector<rtl::Reference<VendorBase> >::const_iterator cit;
+    for (cit ii = vecVerifiedInfos.begin(); ii != vecVerifiedInfos.end(); ++ii)
+    {
+        infosFromPath.push_back(createJavaInfo(*ii));
+    }
+
+    javaInfosFromPath = infosFromPath;
+
+    return JFW_PLUGIN_E_NONE;
+}
+
+
+
+
 #if defined(WNT)
 
 // Load msvcr71.dll using an explicit full path from where it is
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
index a305139..8924a59 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.cxx
@@ -1131,7 +1131,8 @@ void createJavaInfoFromPath(vector<rtl::Reference<VendorBase> >& vecInfos)
     }
 }
 
-void createJavaInfoFromJavaHome(vector<rtl::Reference<VendorBase> >& vecInfos)
+
+rtl::Reference<VendorBase> getJavaInfoFromJavaHome()
 {
     // Get Java from JAVA_HOME environment
 
@@ -1142,11 +1143,28 @@ void createJavaInfoFromJavaHome(vector<rtl::Reference<VendorBase> >& vecInfos)
     char *szJavaHome= getenv("JAVA_HOME");
     if(szJavaHome)
     {
-        OUString sHome(szJavaHome,strlen(szJavaHome),osl_getThreadTextEncoding());
+        OUString sHome(szJavaHome, strlen(szJavaHome), osl_getThreadTextEncoding());
         OUString sHomeUrl;
         if(File::getFileURLFromSystemPath(sHome, sHomeUrl) == File::E_None)
         {
-            getJREInfoByPath(sHomeUrl, vecInfos);
+            return getJREInfoByPath(sHomeUrl);
+        }
+    }
+
+    return NULL;
+}
+
+void createJavaInfoFromJavaHome(vector<rtl::Reference<VendorBase> >& vecInfos)
+{
+    rtl::Reference<VendorBase> aInfo = getJavaInfoFromJavaHome();
+
+    if (aInfo.is())
+    {
+        vector<rtl::Reference<VendorBase> >::const_iterator it_impl= std::find_if(
+            vecInfos.begin(),vecInfos.end(), InfoFindSame(aInfo->getHome()));
+        if(it_impl == vecInfos.end())
+        {
+            vecInfos.push_back(aInfo);
         }
     }
 }
diff --git a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
index 0f0bf04..38d3175 100644
--- a/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
+++ b/jvmfwk/plugins/sunmajor/pluginlib/util.hxx
@@ -39,6 +39,12 @@ bool getJREInfoFromBinPath(
     const OUString& path, std::vector<rtl::Reference<VendorBase> > & vecInfos);
 inline OUString getDirFromFile(const OUString& usFilePath);
 void createJavaInfoFromPath(std::vector<rtl::Reference<VendorBase> >& vecInfos);
+
+/* Returns a VendorBase object if JAVA_HOME environment variable points
+   to a JRE.
+ */
+rtl::Reference<VendorBase> getJavaInfoFromJavaHome();
+
 void createJavaInfoFromJavaHome(std::vector<rtl::Reference<VendorBase> > &vecInfos);
 void createJavaInfoDirScan(std::vector<rtl::Reference<VendorBase> >& vecInfos);
 #ifdef WNT
diff --git a/jvmfwk/source/framework.cxx b/jvmfwk/source/framework.cxx
index d43423d..75daa77 100644
--- a/jvmfwk/source/framework.cxx
+++ b/jvmfwk/source/framework.cxx
@@ -366,9 +366,9 @@ javaFrameworkError SAL_CALL jfw_startVM(
 
 /** We do not use here jfw_findAllJREs and then check if a JavaInfo
     meets the requirements, because that means using all plug-ins, which
-    may take quite a while. The implementation uses one plug-in and if
-    it already finds a suitable JRE then it is done and does not need to
-    load another plug-in
+    may take quite a while. The implementation first inspects JAVA_HOME and
+    PATH environment variables. If no suitable JavaInfo is found there, it
+    inspects all JavaInfos found by the jfw_plugin_get* functions.
  */
 javaFrameworkError SAL_CALL jfw_findAndSelectJRE(JavaInfo **pInfo)
 {
@@ -380,134 +380,213 @@ javaFrameworkError SAL_CALL jfw_findAndSelectJRE(JavaInfo **pInfo)
             return JFW_E_DIRECT_MODE;
         sal_uInt64 nFeatureFlags = 0;
         jfw::CJavaInfo aCurrentInfo;
-//Determine if accessibility support is needed
+        //Determine if accessibility support is needed
         bool bSupportAccessibility = jfw::isAccessibilitySupportDesired();
         nFeatureFlags = bSupportAccessibility ?
             JFW_FEATURE_ACCESSBRIDGE : 0L;
 
-        //Get a list of services which provide Java information
+
+        // 'bInfoFound' indicates whether a Java installation has been found
+        // that supports all desired features
+        bool bInfoFound = false;
+
+        // get list of vendors for Java installations
         jfw::VendorSettings aVendorSettings;
         std::vector<OUString> vecVendors =
-             aVendorSettings.getSupportedVendors();
-        //Use every vendor to get Java installations. At the first usable
-        //Java the loop will break
-        typedef std::vector<OUString>::const_iterator ci_pl;
-        for (ci_pl i = vecVendors.begin(); i != vecVendors.end(); ++i)
+            aVendorSettings.getSupportedVendors();
+
+        // save vendors and respective version requirements pair-wise in a vector
+        std::vector<std::pair<OUString, jfw::VersionInfo>> versionInfos;
+        typedef std::vector<OUString>::const_iterator ciVendor;
+        for (ciVendor i = vecVendors.begin(); i != vecVendors.end(); ++i)
         {
             const OUString & vendor = *i;
             jfw::VersionInfo versionInfo =
                 aVendorSettings.getVersionInformation(vendor);
 
-            //get all installations of one vendor according to minVersion,
-            //maxVersion and excludeVersions
-            sal_Int32 cInfos = 0;
-            JavaInfo** arInfos = NULL;
-            javaPluginError plerr = jfw_plugin_getAllJavaInfos(
-                vendor,
-                versionInfo.sMinVersion,
-                versionInfo.sMaxVersion,
-                versionInfo.getExcludeVersions(),
-                versionInfo.getExcludeVersionSize(),
-                & arInfos,
-                & cInfos);
+            versionInfos.push_back(
+                std::pair<OUString, jfw::VersionInfo>(vendor, versionInfo));
+        }
 
-            if (plerr != JFW_PLUGIN_E_NONE)
-                continue;
-            //iterate over all installations to find the best which has
-            //all features
-            if (cInfos == 0)
+        // first inspect Java installation that the JAVA_HOME
+        // environment variable points to (if it is set)
+        JavaInfo* pHomeInfo = NULL;
+        if (jfw_plugin_getJavaInfoFromJavaHome(versionInfos, &pHomeInfo)
+            == JFW_PLUGIN_E_NONE)
+        {
+            aCurrentInfo = pHomeInfo;
+
+            // compare features
+            // if the user does not require any features (nFeatureFlags = 0)
+            // or the Java installation provides all features, then this installation is used
+            if ((pHomeInfo->nFeatures & nFeatureFlags) == nFeatureFlags)
             {
-                rtl_freeMemory(arInfos);
-                continue;
+                bInfoFound = true;
             }
-            bool bInfoFound = false;
-            for (int ii = 0; ii < cInfos; ii++)
-            {
-                JavaInfo* pJInfo = arInfos[ii];
+            jfw_freeJavaInfo(pHomeInfo);
+        }
 
-                //We remember the very first installation in aCurrentInfo
-                if (aCurrentInfo.getLocation().isEmpty())
-                        aCurrentInfo = pJInfo;
-                // compare features
-                // If the user does not require any features (nFeatureFlags = 0)
-                // then the first installation is used
-                if ((pJInfo->nFeatures & nFeatureFlags) == nFeatureFlags)
+        // if no Java installation providing all features was detected by using JAVA_HOME,
+        // query PATH for Java installations
+        if (!bInfoFound)
+        {
+            std::vector<JavaInfo*> vecJavaInfosFromPath;
+            if (jfw_plugin_getJavaInfosFromPath(versionInfos, vecJavaInfosFromPath)
+                == JFW_PLUGIN_E_NONE)
+            {
+                std::vector<JavaInfo*>::const_iterator it = vecJavaInfosFromPath.begin();
+                while(it != vecJavaInfosFromPath.end() && !bInfoFound)
                 {
-                    //the just found Java implements all required features
-                    //currently there is only accessibility!!!
-                    aCurrentInfo = pJInfo;
-                    bInfoFound = true;
-                    break;
+                    JavaInfo* pJInfo = *it;
+                    if (pJInfo != NULL)
+                    {
+                        // if the current Java installation implements all required features: use it
+                        if ((pJInfo->nFeatures & nFeatureFlags) == nFeatureFlags)
+                        {
+                            aCurrentInfo = pJInfo;
+                            bInfoFound = true;
+                        }
+                        else if ((JavaInfo*) aCurrentInfo == NULL)
+                        {
+                            // current Java installation does not provide all features
+                            // but no Java installation has been detected before
+                            // -> remember the current one until one is found
+                            // that provides all features
+                            aCurrentInfo = pJInfo;
+                        }
+
+                        jfw_freeJavaInfo(pJInfo);
+                    }
+                    ++it;
                 }
             }
-            //The array returned by jfw_plugin_getAllJavaInfos must be freed as well as
-            //its contents
-            for (int j = 0; j < cInfos; j++)
-                jfw_freeJavaInfo(arInfos[j]);
-            rtl_freeMemory(arInfos);
-
-            if (bInfoFound == true)
-                break;
-            //All Java installations found by the current plug-in lib
-            //do not provide the required features. Try the next plug-in
         }
-        if ((JavaInfo*) aCurrentInfo == NULL)
-        {//The plug-ins did not find a suitable Java. Now try the paths which have been
-        //added manually.
-            //get the list of paths to jre locations which have been added manually
-            const jfw::MergedSettings settings;
-            //node.loadFromSettings();
-            const std::vector<OUString> & vecJRELocations =
-                settings.getJRELocations();
-            //use every plug-in to determine the JavaInfo objects
-            bool bInfoFound = false;
+
+
+        // if no suitable Java installation has been found yet:
+        // first iterate over all vendors to find a suitable Java installation,
+        // then try paths that have been added manually
+        if (!bInfoFound)
+        {
+            //Use every vendor to get Java installations. At the first usable
+            //Java the loop will break
+            typedef std::vector<OUString>::const_iterator ci_pl;
             for (ci_pl i = vecVendors.begin(); i != vecVendors.end(); ++i)
             {
                 const OUString & vendor = *i;
                 jfw::VersionInfo versionInfo =
                     aVendorSettings.getVersionInformation(vendor);
 
-                typedef std::vector<OUString>::const_iterator citLoc;
-                for (citLoc it = vecJRELocations.begin();
-                    it != vecJRELocations.end(); ++it)
+                //get all installations of one vendor according to minVersion,
+                //maxVersion and excludeVersions
+                sal_Int32 cInfos = 0;
+                JavaInfo** arInfos = NULL;
+                javaPluginError plerr = jfw_plugin_getAllJavaInfos(
+                    vendor,
+                    versionInfo.sMinVersion,
+                    versionInfo.sMaxVersion,
+                    versionInfo.getExcludeVersions(),
+                    versionInfo.getExcludeVersionSize(),
+                    & arInfos,
+                    & cInfos);
+
+                if (plerr != JFW_PLUGIN_E_NONE)
+                    continue;
+                //iterate over all installations to find the best which has
+                //all features
+                if (cInfos == 0)
                 {
-                    jfw::CJavaInfo aInfo;
-                    javaPluginError err = jfw_plugin_getJavaInfoByPath(
-                        *it,
-                        vendor,
-                        versionInfo.sMinVersion,
-                        versionInfo.sMaxVersion,
-                        versionInfo.getExcludeVersions(),
-                        versionInfo.getExcludeVersionSize(),
-                        & aInfo.pInfo);
-                    if (err == JFW_PLUGIN_E_NO_JRE)
-                        continue;
-                    if (err == JFW_PLUGIN_E_FAILED_VERSION)
-                        continue;
-                    else if (err !=JFW_PLUGIN_E_NONE)
-                        return JFW_E_ERROR;
-
-                    if (aInfo)
+                    rtl_freeMemory(arInfos);
+                    continue;
+                }
+                for (int ii = 0; ii < cInfos; ii++)
+                {
+                    JavaInfo* pJInfo = arInfos[ii];
+
+                    //We remember the first installation in aCurrentInfo
+                    // if no JavaInfo has been found before
+                    if (aCurrentInfo.getLocation().isEmpty())
+                            aCurrentInfo = pJInfo;
+                    // compare features
+                    // If the user does not require any features (nFeatureFlags = 0)
+                    // then the first installation is used
+                    if ((pJInfo->nFeatures & nFeatureFlags) == nFeatureFlags)
                     {
-                        //We remember the very first installation in aCurrentInfo
-                        if (aCurrentInfo.getLocation().isEmpty())
-                            aCurrentInfo = aInfo;
-                        // compare features
-                        // If the user does not require any features (nFeatureFlags = 0)
-                        // then the first installation is used
-                        if ((aInfo.getFeatures() & nFeatureFlags) == nFeatureFlags)
-                        {
-                            //the just found Java implements all required features
-                            //currently there is only accessibility!!!
-                            aCurrentInfo = aInfo;
-                            bInfoFound = true;
-                            break;
-                        }
+                        //the just found Java implements all required features
+                        //currently there is only accessibility!!!
+                        aCurrentInfo = pJInfo;
+                        bInfoFound = true;
+                        break;
                     }
-                }//end iterate over paths
+                }
+                //The array returned by jfw_plugin_getAllJavaInfos must be freed as well as
+                //its contents
+                for (int j = 0; j < cInfos; j++)
+                    jfw_freeJavaInfo(arInfos[j]);
+                rtl_freeMemory(arInfos);
+
                 if (bInfoFound == true)
                     break;
-            }// end iterate plug-ins
+                //All Java installations found by the current plug-in lib
+                //do not provide the required features. Try the next plug-in
+            }
+            if ((JavaInfo*) aCurrentInfo == NULL)
+            {//The plug-ins did not find a suitable Java. Now try the paths which have been
+            //added manually.
+                //get the list of paths to jre locations which have been added manually
+                const jfw::MergedSettings settings;
+                //node.loadFromSettings();
+                const std::vector<OUString> & vecJRELocations =
+                    settings.getJRELocations();
+                //use every plug-in to determine the JavaInfo objects
+                for (ci_pl i = vecVendors.begin(); i != vecVendors.end(); ++i)
+                {
+                    const OUString & vendor = *i;
+                    jfw::VersionInfo versionInfo =
+                        aVendorSettings.getVersionInformation(vendor);
+
+                    typedef std::vector<OUString>::const_iterator citLoc;
+                    for (citLoc it = vecJRELocations.begin();
+                        it != vecJRELocations.end(); ++it)
+                    {
+                        jfw::CJavaInfo aInfo;
+                        javaPluginError err = jfw_plugin_getJavaInfoByPath(
+                            *it,
+                            vendor,
+                            versionInfo.sMinVersion,
+                            versionInfo.sMaxVersion,
+                            versionInfo.getExcludeVersions(),
+                            versionInfo.getExcludeVersionSize(),
+                            & aInfo.pInfo);
+                        if (err == JFW_PLUGIN_E_NO_JRE)
+                            continue;
+                        if (err == JFW_PLUGIN_E_FAILED_VERSION)
+                            continue;
+                        else if (err !=JFW_PLUGIN_E_NONE)
+                            return JFW_E_ERROR;
+
+                        if (aInfo)
+                        {
+                            //We remember the very first installation in aCurrentInfo
+                            if (aCurrentInfo.getLocation().isEmpty())
+                                aCurrentInfo = aInfo;
+                            // compare features
+                            // If the user does not require any features (nFeatureFlags = 0)
+                            // then the first installation is used
+                            if ((aInfo.getFeatures() & nFeatureFlags) == nFeatureFlags)
+                            {
+                                //the just found Java implements all required features
+                                //currently there is only accessibility!!!
+                                aCurrentInfo = aInfo;
+                                bInfoFound = true;
+                                break;
+                            }
+                        }
+                    }//end iterate over paths
+                    if (bInfoFound == true)
+                        break;
+                }// end iterate plug-ins
+            }
         }
         if ((JavaInfo*) aCurrentInfo)
         {


More information about the Libreoffice-commits mailing list