OSDN Git Service

カスタムLaunch4jheadの更新
authorseraphy <seraphy@users.osdn.me>
Sun, 13 Jan 2019 04:29:53 +0000 (13:29 +0900)
committerseraphy <seraphy@users.osdn.me>
Sun, 13 Jan 2019 04:29:53 +0000 (13:29 +0900)
src/Launch4JStub/head/guihead.o
src/Launch4JStub/head/head.o
src/Launch4JStub/head_src/head.c
src/Launch4JStub/head_src/head.h

index 3cec998..1dc121c 100644 (file)
Binary files a/src/Launch4JStub/head/guihead.o and b/src/Launch4JStub/head/guihead.o differ
index 073b871..12cad11 100644 (file)
Binary files a/src/Launch4JStub/head/head.o and b/src/Launch4JStub/head/head.o differ
index fcca481..edcf9c9 100644 (file)
@@ -254,6 +254,52 @@ int loadInt(const int resID)
        return atoi(intStr);
 }
 
+typedef enum __PE6432
+{
+       PE_UNKNOWN, // x86, x64\82Ì\82¢\82¸\82ê\82Å\82à\82È\82¢ (\97L\8cø\82ÈPE\82ÌIA64, ARM\82È\82Ç\82à\8aY\93\96\82·\82é) 
+       PE_X86,
+       PE_X64
+} PE6432;
+
+/**
+ * \8ew\92è\82µ\82½PE\83t\83@\83C\83\8b(EXE, DLL)\82Ì32/64\83r\83b\83g\82ð\94»\92è\82·\82é\81
+ * @param pFileName \83t\83@\83C\83\8b\82Ì\83p\83X
+ * @return \94»\92è\8c\8b\89Ê 
+ */
+PE6432 CheckPE6432(LPCTSTR pFileName)
+{
+       PE6432 result = PE_UNKNOWN;     
+       HANDLE fh = CreateFile(pFileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
+       if (fh != INVALID_HANDLE_VALUE) {
+               // DOS\83w\83b\83_\93Ç\82Ý\8eæ\82è 
+               IMAGE_DOS_HEADER imageDosHeader = { 0 };
+               DWORD rd = 0;
+               if (ReadFile(fh, &imageDosHeader, sizeof(IMAGE_DOS_HEADER), &rd, NULL) &&
+                       rd == sizeof(IMAGE_DOS_HEADER) &&
+                       imageDosHeader.e_magic == IMAGE_DOS_SIGNATURE) { // "MZ"
+                       // NT\83w\83b\83_\95\94\82Ü\82Å\88Ú\93® 
+                       SetFilePointer(fh, imageDosHeader.e_lfanew, NULL, FILE_BEGIN);
+                       if (GetLastError() == NO_ERROR) {
+                               // NT\83w\83b\83_\93Ç\82Ý\8eæ\82è 
+                               IMAGE_NT_HEADERS imageNTHeader = { 0 };
+                               if (ReadFile(fh, &imageNTHeader, sizeof(IMAGE_NT_HEADERS), &rd, NULL) &&
+                                       rd == sizeof(IMAGE_NT_HEADERS) &&
+                                       imageNTHeader.Signature == IMAGE_NT_SIGNATURE) {
+                                       // \83}\83V\83\93\83^\83C\83v\82Ì\94»\92è 
+                                       if (imageNTHeader.FileHeader.Machine == IMAGE_FILE_MACHINE_I386) {
+                                               result = PE_X86;
+                                       } else if (imageNTHeader.FileHeader.Machine == IMAGE_FILE_MACHINE_AMD64) {
+                                               result = PE_X64;
+                                       }
+                                       // IA64, ARM\82È\82Ç\82ÍUNKNOWN\82É\82·\82é 
+                               }
+                       }
+               }
+               CloseHandle(fh);
+       }
+       return result;
+}
+
 BOOL regQueryValue(const char* regPath, unsigned char* buffer,
                unsigned long bufferLength)
 {
@@ -666,41 +712,6 @@ BOOL findJavaHome(char* path, const int jdkPreference)
        return FALSE;
 }
 
-BOOL checkJavaExe(char *path)
-{
-       char path2[MAX_PATH];
-       strcpy(path2, path);
-       strcat(path2, "\\bin\\java.exe");
-       
-       DWORD attr = GetFileAttributes(path2);
-       return attr != -1;
-}
-
-BOOL chooseJavaHome(char *path)
-{
-       // \83t\83H\83\8b\83_\91I\91ð\83_\83C\83A\83\8d\83O\82É\95\\8e¦\82·\82é\83\81\83b\83Z\81[\83W\82Í\83G\83\89\81[\83\81\83b\83Z\81[\83W\82ð\8eØ\97p\82·\82é 
-       createJreSearchError();
-
-       BROWSEINFO bInfo = { 0 };
-       bInfo.hwndOwner = NULL;
-       bInfo.pidlRoot  = NULL;
-       bInfo.pszDisplayName = path;
-       bInfo.lpszTitle = error.msg;
-       bInfo.ulFlags   = BIF_RETURNONLYFSDIRS | BIF_NEWDIALOGSTYLE;
-
-       LPITEMIDLIST result = NULL;
-       while (!checkJavaExe(path))
-       {
-               result = SHBrowseForFolder(&bInfo);
-               if (result == NULL)
-               {
-                       return FALSE;
-               }
-
-               SHGetPathFromIDList(result, path);
-       }
-       return TRUE;
-}
 
 /*
  * Extract the executable name, returns path length.
@@ -723,12 +734,17 @@ void getCfgPath(const char *exePath, char *cfgPath)
        strcpy(cfgPath + strlen(cfgPath) - 4, ".cfg");
 }
 
-void appendPath(char* basepath, const char* path)
+void appendPath(LPTSTR basepath, LPCTSTR path)
 {
-       if (basepath[strlen(basepath) - 1] != '\\')
+       LPCTSTR pLast = basepath;
+       while (*pLast++); // \96\96\94ö\82Ü\82Å\88Ú\93®
+       pLast = CharPrev(basepath, pLast); // \88ê\95\8e\9a\96ß\82é (MBCS\95\8e\9a\89Â) 
+
+       if (*pLast != '\\')
        {
                strcat(basepath, "\\");
        }
+       
        strcat(basepath, path);
 }
 
@@ -754,74 +770,158 @@ void appendAppClasspath(char* dst, const char* src)
  * \8ew\92è\82µ\82½\83f\83B\83\8c\83N\83g\83\8a\82ð\90e\82É\82³\82©\82Ì\82Ú\82Á\82Ä\8ew\92è\82µ\82½\83t\83@\83C\83\8b\81E\83t\83H\83\8b\83_\96¼\82É\88ê\92v\82·\82é
  * \83p\83X\82ð\8c\9f\8dõ\82µ\82Ädst\82É\92Ç\8bL\82·\82é\81B\91\8dÝ\82µ\82È\82¢\8fê\8d\87\82Í\89½\82à\82µ\82È\82¢\81B
  * @param dst \94­\8c©\82³\82ê\82½\83p\83X\82ð\92Ç\8bL\82·\82é\83o\83b\83t\83@
- * @param dir \8dÅ\8f\89\82É\8ew\92è\82·\82é\82Ì\82ÍEXE\82Ö\82Ì\83t\83\8b\83p\83X(*.exe)\82ð\8ew\92è\82·\82é\81B
- * @param name \8c\9f\8dõ\82·\82é\96¼\91
+ * @param dir \96\96\94ö\82ª\\82Ì\83f\83B\83\8c\83N\83g\83\8a\81A\82Ü\82½\82Í\8dÅ\8f\89\82É\8ew\92è\82·\82é\82Ì\82ÍEXE\82Ö\82Ì\83t\83\8b\83p\83X(*.exe)\82ð\8ew\92è\82·\82é\81B
+ * @param name \8c\9f\8dõ\82·\82é\96¼\91O(A\B\C\82Ì\82æ\82¤\82É\83t\83H\83\8b\83_\8bæ\90Ø\82è\82ª\82 \82Á\82Ä\82à\97Ç\82¢) 
+ * @return \94­\8c©\82³\82ê\82½\8fê\8d\87\82ÍTRUE\81A\94­\8c©\82³\82ê\82È\82©\82Á\82½\8fê\8d\87\82ÍFALSE 
  */
-void findAncestor(char* dst, const char *dir, const char* name)
+BOOL findAncestor(char* dst, const char *dir, const char* name)
 {
        //      \90e\83t\83H\83\8b\83_\82ð\8c\9f\8dõ 
        char parent[MAX_PATH];
        strcpy(parent, dir);
        char *p = parent;
-       while (*p++);
+       while (*p++); // \96\96\94ö\82É\88Ú\93® 
+
+       // UNC\8c`\8e®\82Ì\8fê\8d\87(\83l\83b\83g\83\8f\81[\83N\83p\83X\82Ì\8fê\8d\87
+       // \8dÅ\8f\89\82Ì\83t\83H\83\8b\83_\82Ü\82Å\82Í\8cÅ\92è\82É\82·\82é\81B
+       // (ex.) \\ABC\DEF\XYZ \82Ì\8fê\8d\87\81A\\ABC\DEF\ \82æ\82è\91k\82ç\82È\82¢ 
+       char *top = parent;
+       if (*top == '\\' && *(top + 1) == '\\')
+       {
+               top += 2;
+               while(*top && *top != '\\') top = CharNext(top);
+       }
        
-       while (p > parent)
+       while (p > top)
        {
-               if (*p == '\\' || *p == '/')
+               if (*p == '\\' && *(p + 1))
                {
-                       if (*(p + 1))
-                       {
-                               // \8c»\8dÝ\82Ì\96\96\94ö\82Ì\83t\83H\83\8b\83_\8bæ\90Ø\82è\88È\8aO\82Å\82 \82ê\82Î\81A\82±\82±\82ð\96\96\94ö\82É\82·\82é 
-                               *(p + 1)  = 0;
-                               break;  
-                       }
+                       // \8c»\8dÝ\82Ì\96\96\94ö\82Ì\83t\83H\83\8b\83_\8bæ\90Ø\82è\88È\8aO\82Å\82 \82ê\82Î\81A\82±\82±\82ð\96\96\94ö\82É\82·\82é 
+                       // C:\a\b\c.exe \82ð\8aJ\8en\82µ\82½\8fê\8d\87\82Í\81AC:\a\b\ \82ª\83}\83b\83`\82·\82é\81
+                       // C:\a\b\ \82Å\8aJ\8en\82µ\82½\8fê\8d\87\82Í\81AC:\a\ \82ª\83}\83b\83`\82·\82é\81B
+                       // C:\a\ \82Å\8aJ\8en\82µ\82½\8fê\8d\87\82Í\81AC:\ \82ª\83}\83b\83`\82·\82é\81
+                       // C:\ \82Å\8aJ\8en\82µ\82½\8fê\8d\87\82Í\83}\83b\83`\82·\82é\82à\82Ì\82ª\82È\82¢\82Ì\82Å\8fI\97¹\82·\82é 
+                       // UNC\8c`\8e®\82Å \\ABC\DEF\XYZ.exe \82Å\8aJ\8en\82µ\82½\8fê\8d\87\82Í\\ABC\DEF\ \82ª\83}\83b\83`\82·\82é 
+                       // UNC\8c`\8e®\82Å \\ABC\DEF\ \82Å\8aJ\8en\82µ\82½\8fê\8d\87\82Í\81A\\ABC\DEF\\82æ\82è\91k\82ê\82È\82¢\82Ì\82Å\8fI\97¹\82·\82é 
+                       *(p + 1)  = 0;
+                       break;  
                }
                p = CharPrev(parent, p);
        }
+
        if (strcmp(dir, parent) == 0)
        {
                // \95Ï\89»\82È\82µ\82È\82Ì\82Å\81A\82·\82Å\82É\8c\9f\8dõ\8dÏ\82Ý\82Ì\82Í\82¸ 
-           debug("Find End");
-               return;
+           debug("Not Found\n");
+               return FALSE;
        }
-    
-       // \90e\83t\83H\83\8b\83_\82ð\97ñ\8b\93 
-       WIN32_FIND_DATA data = {0};
-       
-       char searchdir[MAX_PATH];
-    strcpy(searchdir, parent);
-    strcat(searchdir, "*.*");
-    debug("FindFirstFile:\t%s\n", searchdir);
-
-       HANDLE fh = FindFirstFile(searchdir, &data);
-       if (fh == INVALID_HANDLE_VALUE) {
-           debug("FindFirstFile:\tErr=%d\n", GetLastError());
-               return;
+
+       // \83t\83H\83\8b\83_ + name \82Å\83t\83\8b\83p\83X\82ð\8dì\90¬\82·\82é 
+       char temp[MAX_PATH] = { 0 };
+       strcpy(temp, parent);
+       strcat(temp, name);
+
+       // \83t\83@\83C\83\8b\82Ü\82½\82Í\83t\83H\83\8b\83_\82Ì\8eÀ\8dÝ\83`\83F\83b\83
+       debug("check exist: %s\n", temp);
+       DWORD attr = GetFileAttributes(temp);
+       if (attr != -1) {
+               // \83p\83X\82ª\8eÀ\8dÝ\82·\82ê\82ÎOK. 
+               strcat(dst, temp);
+           debug("Found: %s\n", temp);
+               return TRUE;
        }
-       
-       for (;;)
+    
+       // \8dX\82É\81A\82±\82Ì\90e\82ð\8c\9f\8dõ\82·\82é 
+       findAncestor(dst, parent, name);
+}
+
+/**
+ * \8ew\92è\82µ\82½\83f\83B\83\8c\83N\83g\83\8a\82ð\90e\82É\82³\82©\82Ì\82Ú\82Á\82Ä\81A\83Z\83~\83R\83\8d\83\93\82Å\8bæ\90Ø\82ç\82ê\82½\95¡\90\94\82Ì
+ * \83t\83@\83C\83\8b\81E\83t\83H\83\8b\83_\96¼\82É\88ê\92v\82·\82é\83p\83X\82ð\8c\9f\8dõ\82µ\82Ädst\82É\92Ç\8bL\82·\82é\81B
+ * \91\8dÝ\82µ\82È\82¢\8fê\8d\87\82Í\89½\82à\82µ\82È\82¢\81B
+ * \83Z\83~\83R\83\8d\83\93\82Å\8bæ\90Ø\82Á\82½\96¼\91O\82Í\90æ\93ª\82Ì\82à\82Ì\82©\82ç\8f\87\94Ô\82É\95]\89¿\82³\82ê\81A
+ * \8dÅ\8f\89\82É\82Ý\82Â\82©\82Á\82½\8e\9e\93_\82Å\8a®\97¹\82·\82é\81B
+ * @param dst \94­\8c©\82³\82ê\82½\83p\83X\82ð\92Ç\8bL\82·\82é\83o\83b\83t\83@
+ * @param dir \8dÅ\8f\89\82É\8ew\92è\82·\82é\82Ì\82ÍEXE\82Ö\82Ì\83t\83\8b\83p\83X(*.exe)\82ð\8ew\92è\82·\82é\81B
+ * @param name \8c\9f\8dõ\82·\82é\96¼\91O(A\B\C\82Ì\82æ\82¤\82É\83t\83H\83\8b\83_\8bæ\90Ø\82è\82ª\82 \82Á\82Ä\82à\97Ç\82¢) 
+ * @return \94­\8c©\82³\82ê\82½\8fê\8d\87\82ÍTRUE\81A\94­\8c©\82³\82ê\82È\82©\82Á\82½\8fê\8d\87\82ÍFALSE 
+ */
+BOOL multiFindAncestor(char* dst, const char *dir, const char* names)
+{
+       char name[MAX_PATH];
+       const char *p = names;
+       while (*p)
        {
-        //debug("cFileName:\t%s\n", data.cFileName);
+               // \83Z\83~\83R\83\8d\83\93\82Ü\82½\82Í\96\96\94ö\82Ü\82Å\82Ì\96¼\91O\82ð\8eæ\82è\8fo\82· 
+               char *d = name;
+               while (*p && *p != ';') *d++ = *p++;
+               *d = 0;
+               if (*p) p++; // \83Z\83~\83R\83\8d\83\93\82Å\82 \82ê\82Î1\95\8e\9a\90i\82ß\82é 
 
-               if (strcasecmp(data.cFileName, name) == 0) // \91å\8f¬\95\8e\9a\82Í\8bæ\95Ê\82µ\82È\82¢ 
+               if (*name)
                {
-                       strcat(dst, parent);
-                       strcat(dst, data.cFileName);
-                       return;
+                       // \8eæ\82è\8fo\82µ\82½\96¼\91O\82ÅfindAncestor\82ð\8e\8e\8ds\82·\82é 
+                       debug("FIND_ANCESTOR: %s\n", name);
+                       if (findAncestor(dst, dir, name))
+                       {
+                               return TRUE;
+                       }
                }
-               
-               if (!FindNextFile(fh, &data))
+       }
+       // \82·\82×\82Ä\8c©\82Â\82©\82ç\82È\82©\82Á\82½\8fê\8d\87 
+       return FALSE;
+}
+
+/**
+ * java\82Ì\8eÀ\8ds\83t\83@\83C\83\8b\82ª64/32\83r\83b\83g\82Ì\82¢\82¸\82ê\82Å\82 \82é\82©\82ð\8e¦\82· \95\8e\9a\97ñ\82ð\95Ô\82·\81B
+ * \81u\95Ï\90\94\96¼:X86\96¼,X64\96¼\81v\82Ì\82æ\82¤\82É\81A\95Ï\90\94\96¼\8cã\82É\83R\83\8d\83\93\82ð\82Â\82¯\82Ä\95\\8e¦\96¼\82ð\8ew\92è\82Å\82«\82é\81B
+ * x86, x64 \82Ì\8f\87\82É\83J\83\93\83}\82Å\8bæ\90Ø\82è\81A\8fÈ\97ª\82³\82ê\82½\8fê\8d\87\82Í\81ux86\81v\81ux64\81v\82Æ\82È\82é\81
+ * @param dst \95Ï\90\94\93W\8aJ\90æ
+ * @param args \95Ï\90\94\96¼\82Ì\8cã\82É\95t\97^\82³\82ê\82é\88ø\90\94\81B\8bó\82Å\82à\97Ç\82¢\81
+ */
+void jreArch(char* dst, const char* args)
+{
+       char tempBuf[MAX_PATH] = { 0 };
+       LPCTSTR displayArchs[] =
+       {
+               "x86",
+               "x64"
+       };
+
+       if (*args == ':')
+       {
+               strcpy(tempBuf, args + 1);
+               displayArchs[0] = tempBuf; // x86\97p\95\8e\9a\97ñ 
+               int idx = 1;
+               char *p = tempBuf;
+               while (*p)
                {
-                       // ERROR_NO_MORE_FILES \82Å\83G\83\89\81[\97L\96³\82Ì\94»\92è\82Í\81
-                       // \8c\8b\8bÇ\81A\83\8b\81[\83v\82ð\91Å\82¿\90Ø\82é\82¾\82¯\82È\82Ì\82Å\8fÈ\97ª\81
-                       break;
+                       if (*p == ',')
+                       {
+                               *p = 0;
+                               displayArchs[1] = p + 1; // \83J\83\93\83}\8bæ\90Ø\82è\82Åx64\97p\95\8e\9a\97ñ 
+                               break;
+                       }
+                       p = CharNext(p);
                }
        }
-       FindClose(fh);
-    debug("FindClose:\t%s\n", parent);
-
-       // \8dX\82É\81A\82±\82Ì\90e\82ð\8c\9f\8dõ\82·\82é 
-       findAncestor(dst, parent, name);
+       
+       char launcherPath[MAX_PATH] = { 0 };
+       strcpy(launcherPath, search.foundJavaHome);
+       appendLauncher(launcherPath);
+       
+       PE6432 peType = CheckPE6432(launcherPath);
+       
+       debug("PE Type: %s = %d\n", launcherPath, peType);
+       
+       if (peType == PE_X64)
+       {
+        strcat(dst, displayArchs[1]);
+       }
+       else if (peType == PE_X86)
+       {
+        strcat(dst, displayArchs[0]);
+       }
 }
 
 /* 
@@ -852,8 +952,13 @@ BOOL expandVars(char *dst, const char *src, const char *exePath, const int pathL
             
             if (strstr(varName, "FIND_ANCESTOR:") == varName)
                        {
-                               char *findName = varName + 14;
-                               findAncestor(dst, exePath, findName);
+                               char *findNames = varName + 14;
+                               multiFindAncestor(dst, exePath, findNames);
+            }
+            else if (strstr(varName, "JRE_ARCH") == varName)
+                       {
+                               char *findName = varName + 8;
+                               jreArch(dst, findName);
             }
                        else if (strcmp(varName, "EXEDIR") == 0)
                        {
@@ -940,14 +1045,41 @@ void appendHeapSize(char *dst, const int megabytesID, const int percentID,
        }
 }
 
-void setJvmOptions(char *jvmOptions, const char *exePath)
+void setJvmOptions(char *jvmOptions, const char *exePath, const int pathLen)
 {
+       // \83\8a\83\\81[\83X\82É\96\84\82ß\8d\9e\82ñ\82¾\8cÅ\92è\82ÌJVM\83I\83v\83V\83\87\83\93 
        if (loadString(JVM_OPTIONS, jvmOptions))
        {
                strcat(jvmOptions, " ");
        }
 
+       // *.cfg\83t\83@\83C\83\8b\82©\82ç\83I\83v\83V\83\87\83\93\88ø\90\94\82Ì\93Ç\82Ý\8eæ\82è 
+       char cfgPath[MAX_PATH];
+       getCfgPath(exePath, cfgPath);
+       
+       char optbuf[MAX_VAR_SIZE] = { 0 }; // 32kbytes
+       char optValue[MAX_ARGS] = { 0 };
+       GetPrivateProfileString("JVM_OPTIONS", NULL, "", optbuf, sizeof(optbuf), cfgPath);
+
+       char *pOpt = optbuf;
+       char tmp[MAX_ARGS] = {0};
+       while (*pOpt)
+       {
+               GetPrivateProfileString("JVM_OPTIONS", pOpt, "", optValue, sizeof(optValue), cfgPath);
+               
+               *tmp = 0;
+               expandVars(tmp, optValue, exePath, pathLen);
+               debug("Set jvm_option:\t%s = %s\n", pOpt, tmp);
+
+               // \95Ï\90\94\93W\8aJ\8dÏ\82Ý\83I\83v\83V\83\87\83\93\82ð\92Ç\8b
+               strcat(jvmOptions, tmp);
+               strcat(jvmOptions, " ");
+
+               while (*pOpt++);
+       }
+
        /*
+        * ini\90Ý\92è\83t\83@\83C\83\8b \82©\82ç\82ÌJVM\83I\83v\83V\83\87\83\93 
         * Load additional JVM options from .l4j.ini file
         * Options are separated by spaces or CRLF
         * # starts an inline comment
@@ -956,13 +1088,17 @@ void setJvmOptions(char *jvmOptions, const char *exePath)
 
        strncpy(iniFilePath, exePath, strlen(exePath) - 3);
        strcat(iniFilePath, "l4j.ini");
+       debug("try loading 1:\t%s\n", iniFilePath);
 
        long hFile;
        if ((hFile = _open(iniFilePath, _O_RDONLY)) == -1)
        {
                // *.l4j.ini\82ª\82È\82¯\82ê\82Π*.ini \82Å\8e\8e\82· 
+               memset(iniFilePath, 0, sizeof(iniFilePath));
                strncpy(iniFilePath, exePath, strlen(exePath) - 3);
-               strcat(iniFilePath, ".ini");
+               strcat(iniFilePath, "ini");
+
+               debug("try loading 2:\t%s\n", iniFilePath);
                hFile = _open(iniFilePath, _O_RDONLY);
        }
 
@@ -1044,6 +1180,49 @@ void setWorkingDirectory(const char *exePath, const int pathLen)
        }
 }
 
+BOOL isValidCfgJrePath(LPCTSTR jrePath, PE6432 *pPEType)
+{
+       // java.exe\82Ö\82Ì\83p\83
+       char launcherPath[MAX_PATH] = { 0 };
+       strcpy(launcherPath, jrePath);
+       appendLauncher(launcherPath);
+
+       // 64/32bit\94»\92è
+       PE6432 peType = CheckPE6432(launcherPath);
+       if (pPEType)
+       {
+               *pPEType = peType;
+       }
+
+       if (peType != PE_UNKNOWN)
+       {
+               int runtimeBits = loadInt(RUNTIME_BITS);
+
+               switch (peType)
+               {
+                       case PE_X86:
+                               if (runtimeBits == USE_64_BIT_RUNTIME) {
+                                       // 64\83r\83b\83g\82ð\97v\8b\81\82µ\82Ä\82¢\82é\82Ì\82Éjava.exe\82ª32\83r\83b\83g\82È\82Ì\82Å\95s\89 
+                                       return FALSE;
+                               }
+                   search.foundJava = FOUND_BUNDLED;
+                               break;
+                               
+                       case PE_X64:
+                               if (!wow64 || runtimeBits == USE_32_BIT_RUNTIME) {
+                                       // 32\83r\83b\83g\82ð\97v\8b\81\82µ\82Ä\82¢\82é\82Ì\82Éjava.exe\82ª64\83r\83b\83g\82È\82Ì\82Å\95s\89 
+                                       // \82à\82µ\82­\82Í\8c»\8dÝ64\83r\83b\83gOS\82Å\82È\82¢\82Ì\82Éjava.exe\82ª64\83r\83b\83g\82Ì\8fê\8d\87 
+                                       // (\96{head\82Í32\83r\83b\83g\82Å\83r\83\8b\83h\82³\82ê\82é\82½\82ß\81A64\83r\83b\83gOS\82Å\82Íwow64\82Å\8eÀ\8ds\82³\82ê\82é) 
+                                       return FALSE;
+                               }
+                   search.foundJava = FOUND_BUNDLED | KEY_WOW64_64KEY;
+                               break;
+               }
+               return TRUE;
+       }
+       return FALSE;
+}
+
 BOOL cfgJreSearch(const char *exePath, int pathLen)
 {
        char tmpPath[MAX_PATH] = { 0 };
@@ -1057,16 +1236,23 @@ BOOL cfgJreSearch(const char *exePath, int pathLen)
                char jrePath[MAX_ARGS] = {0};
                expandVars(jrePath, tmpPath, exePath, pathLen);
                debug("Config JRE:\t%s\n", jrePath);
-
-               if (checkJavaExe(jrePath))
+               
+               PE6432 peType = PE_UNKNOWN;
+               if (isValidCfgJrePath(jrePath, &peType))
                {
                        strcpy(launcher.cmd, jrePath);
-               
-                       if (isLauncherPathValid(launcher.cmd))
+                       strcpy(search.foundJavaHome, launcher.cmd);
                        {
-                   search.foundJava = wow64 ? FOUND_BUNDLED | KEY_WOW64_64KEY : FOUND_BUNDLED;
-                               strcpy(search.foundJavaHome, launcher.cmd);
-                               return TRUE;
+                               switch (peType)
+                               {
+                                       case PE_X86:
+                                   search.foundJava = FOUND_BUNDLED;
+                                               return TRUE;
+                                               
+                                       case PE_X64:
+                                   search.foundJava = FOUND_BUNDLED | KEY_WOW64_64KEY;
+                                               return TRUE;
+                               }
                        }
                }
        }
@@ -1074,6 +1260,36 @@ BOOL cfgJreSearch(const char *exePath, int pathLen)
        return FALSE;
 }
 
+BOOL chooseJavaHome(char *path, PE6432 *pPEType)
+{
+       // \83t\83H\83\8b\83_\91I\91ð\83_\83C\83A\83\8d\83O\82É\95\\8e¦\82·\82é\83\81\83b\83Z\81[\83W\82Í\83G\83\89\81[\83\81\83b\83Z\81[\83W\82ð\8eØ\97p\82·\82é 
+       createJreSearchError();
+
+       BROWSEINFO bInfo = { 0 };
+       bInfo.hwndOwner = NULL;
+       bInfo.pidlRoot  = NULL;
+       bInfo.pszDisplayName = path;
+       bInfo.lpszTitle = error.msg;
+       bInfo.ulFlags   = BIF_RETURNONLYFSDIRS | BIF_NEWDIALOGSTYLE;
+
+       for (;;)
+       {
+               LPITEMIDLIST result = SHBrowseForFolder(&bInfo);
+               if (result == NULL)
+               {
+                       // \83L\83\83\83\93\83Z\83\8b 
+                       return FALSE;
+               }
+
+               SHGetPathFromIDList(result, path);
+               
+               if (isValidCfgJrePath(path, pPEType))
+               {
+                       return TRUE;
+               }
+       }
+}
+
 BOOL bundledJreSearch(const char *exePath, const int pathLen)
 {
     debugAll("bundledJreSearch()\n");
@@ -1199,10 +1415,20 @@ BOOL jreSearch(const char *exePath, const int pathLen)
                        // \83o\83\93\83h\83\8b\82Ì\8c\9f\8dõ\82Æ\83\8c\83W\83X\83g\83\8a\82Ì\8c\9f\8dõ\82à\8e¸\94s\82µ\82½\8fê\8d\87
                        // \83\86\81[\83U\81[\82ÉJAVA_HOME\82Ì\91I\91ð\82ð\8b\81\82ß\82é 
                        char jrePath[MAX_PATH] = { 0 };
-                       if (chooseJavaHome(jrePath))
+                       PE6432 peType = PE_UNKNOWN;
+                       if (chooseJavaHome(jrePath, &peType))
                        {
-                               // JAVA_HOME\82ð\91I\91ð\82µ\82½\8fê\8d\87 
-                       search.foundJava = wow64 ? FOUND_BUNDLED | KEY_WOW64_64KEY : FOUND_BUNDLED;
+                               // \97L\8cø\82ÈJAVA_HOME\82ð\91I\91ð\82µ\82½\8fê\8d\87 
+                               switch (peType)
+                               {
+                                       case PE_X86:
+                                       search.foundJava = FOUND_CHOOSED;
+                                               break;
+
+                                       case PE_X64:
+                                       search.foundJava = FOUND_CHOOSED | KEY_WOW64_64KEY;
+                                               break;
+                               }
                                strcpy(launcher.cmd, jrePath);
                                strcpy(search.foundJavaHome, launcher.cmd);
                                
@@ -1390,7 +1616,7 @@ void setCommandLineArgs(const char *lpCmdLine,
        // Constant command line arguments
        if (loadString(CMD_LINE, tmp))
        {
-               char tmp2[MAX_ARGS] = {0};
+               char tmp2[MAX_ARGS] = { 0 };
                expandVars(tmp2, tmp, exePath, pathLen);
                debug("constant commandline args: %s\r\n", tmp2);
 
@@ -1480,7 +1706,7 @@ int prepare(const char *lpCmdLine)
        appendHeapSizes(launcher.args);
 
        char jvmOptions[MAX_ARGS] = {0};
-       setJvmOptions(jvmOptions, exePath);
+       setJvmOptions(jvmOptions, exePath, pathLen);
        expandVars(launcher.args, jvmOptions, exePath, pathLen);
        setMainClassAndClassPath(exePath, pathLen);
        setCommandLineArgs(lpCmdLine, exePath, pathLen);
@@ -1514,35 +1740,40 @@ BOOL execute(const BOOL wait, DWORD *dwExitCode)
        if (CreateProcess(NULL, cmdline, NULL, NULL,
                        TRUE, processPriority, NULL, NULL, &si, &processInformation))
        {
-               // \83v\83\8d\83Z\83X\82ª\8bN\93®\82µ\82Ä\82·\82®\82É\83G\83\89\81[\82ª\97\8e\82¿\82é\82©\82Ç\82¤\82©\82ð\8c©\8bÉ\82ß\82é 
-               WaitForInputIdle(processInformation.hProcess, 10000); // \83\81\83b\83Z\81[\83W\83\8b\81[\83v\82Ì\83A\83C\83h\83\8b\82ð\91Ò\82 
-               WaitForSingleObject(processInformation.hProcess, 3000); // 3\95b\82Ü\82 
-               
-               // \8c»\8e\9e\93_\82Ì\8fI\97¹\83R\81[\83h\82ð\93¾\82é 
-               GetExitCodeProcess(processInformation.hProcess, dwExitCode);
-               debug("Java PreExitCode: %ld\n", *dwExitCode);
-               if (*dwExitCode == STILL_ACTIVE)
-               {
-                       // \82Ü\82¾\8fI\97¹\82µ\82Ä\82¢\82È\82¯\82ê\82Î0\82ð\89¼\90Ý\92è\82·\82é 
-                       *dwExitCode = 0;
-               }
-               
-               if (*dwExitCode == 0)
+               if ((search.foundJava & FOUND_CHOOSED) != 0)
                {
-                       // \8bN\93®\92¼\8cã\82É\83G\83\89\81[\82ª\94­\90\82µ\82Ä\82¢\82é\82Ì\82Å\82È\82¯\82ê\82Î
-                       // JAVA_HOME\82Í\90³\82µ\82©\82Á\82½\82à\82Ì\82Æ\82Ý\82È\82µ\81
-                       // \83o\83\93\83h\83\8b\82Ü\82½\82Í\83\8c\83W\83X\83g\83\8a\82©\82ç\82Ì\8c\9f\8dõ\82É\90¬\8c÷\82µ\82½JAVA_HOME\81A
-                       // \82Ü\82½\82Í\83\86\81[\83U\81[\82ª\91I\91ð\82µ\82½JAVA_HOME\82ð\81A*.cfg\82É\95Û\91\82·\82é
-                       // (\89¼\82É\8f\91\82«\8d\9e\82Ý\8bÖ\8e~\93\99\82Å\8f\91\82«\8d\9e\82ß\82È\82­\82Ä\82à\93Á\92i\96â\91è\82Í\82È\82¢) 
-                       char exePath[MAX_PATH] = { 0 };
-                       char cfgPath[MAX_PATH] = { 0 };
-                       getExePath(exePath);
-                       getCfgPath(exePath, cfgPath);
-                       int saveJavaHome = GetPrivateProfileInt("Settings", "SaveJavaHome", 1, cfgPath);
-                       if (saveJavaHome)
+                       // \83\86\81[\83U\81[\82ªJAVA_HOME\82ð\91I\91ð\82µ\82Ä\8bN\93®\82µ\82½\8fê\8d\87\82Í\81
+                       // \83v\83\8d\83Z\83X\82ª\8bN\93®\82µ\82Ä\82·\82®\82É\83G\83\89\81[\82ª\97\8e\82¿\82é\82©\82Ç\82¤\82©\82ð\8c©\8bÉ\82ß\82é 
+                       WaitForInputIdle(processInformation.hProcess, 10000); // \83\81\83b\83Z\81[\83W\83\8b\81[\83v\82Ì\83A\83C\83h\83\8b\82ð\91Ò\82 
+                       WaitForSingleObject(processInformation.hProcess, 3000); // 3\95b\82Ü\82 
+                       
+                       // \8c»\8e\9e\93_\82Ì\8fI\97¹\83R\81[\83h\82ð\93¾\82é 
+                       GetExitCodeProcess(processInformation.hProcess, dwExitCode);
+                       debug("Java PreExitCode: %ld\n", *dwExitCode);
+                       if (*dwExitCode == STILL_ACTIVE)
                        {
-                               // JAVA_HOME\82Ì\95Û\91\83t\83\89\83O\82ª0\82Å\82È\82¯\82ê\82Î\8eg\97p\82µ\82½JAVA_HOME\82ð\8bL\98^\82·\82é 
-                               WritePrivateProfileString("Settings", "JAVA_HOME", search.foundJavaHome, cfgPath);
+                               // \82Ü\82¾\8fI\97¹\82µ\82Ä\82¢\82È\82¯\82ê\82Î0\82ð\89¼\90Ý\92è\82·\82é 
+                               *dwExitCode = 0;
+                       }
+                       
+                       if (*dwExitCode == 0)
+                       {
+                               // \8bN\93®\92¼\8cã\82É\83G\83\89\81[\82ª\94­\90\82µ\82Ä\82¢\82é\82Ì\82Å\82È\82¯\82ê\82Î
+                               // JAVA_HOME\82Í\90³\82µ\82©\82Á\82½\82à\82Ì\82Æ\82Ý\82È\82µ\81
+                               // \83o\83\93\83h\83\8b\82Ü\82½\82Í\83\8c\83W\83X\83g\83\8a\82©\82ç\82Ì\8c\9f\8dõ\82É\90¬\8c÷\82µ\82½JAVA_HOME\81A
+                               // \82Ü\82½\82Í\83\86\81[\83U\81[\82ª\91I\91ð\82µ\82½JAVA_HOME\82ð\81A*.cfg\82É\95Û\91\82·\82é
+                               // (\89¼\82É\8f\91\82«\8d\9e\82Ý\8bÖ\8e~\93\99\82Å\8f\91\82«\8d\9e\82ß\82È\82­\82Ä\82à\93Á\92i\96â\91è\82Í\82È\82¢) 
+                               char exePath[MAX_PATH] = { 0 };
+                               char cfgPath[MAX_PATH] = { 0 };
+                               getExePath(exePath);
+                               getCfgPath(exePath, cfgPath);
+
+                               int saveJavaHome = GetPrivateProfileInt("Settings", "SaveJavaHome", 1, cfgPath);
+                               if (saveJavaHome)
+                               {
+                                       // JAVA_HOME\82Ì\95Û\91\83t\83\89\83O\82ª0\82Å\82È\82¯\82ê\82Î\8eg\97p\82µ\82½JAVA_HOME\82ð\8bL\98^\82·\82é 
+                                       WritePrivateProfileString("Settings", "JAVA_HOME", search.foundJavaHome, cfgPath);
+                               }
                        }
                }
 
index 348477f..133cb4b 100644 (file)
@@ -64,6 +64,7 @@
 #define FOUND_JRE 1
 #define FOUND_SDK 2
 #define FOUND_BUNDLED 4
+#define FOUND_CHOOSED 8
 
 #define JRE_ONLY 0
 #define PREFER_JRE 1
@@ -94,7 +95,7 @@
 #define FALSE_STR "false"
 
 #define ERROR_FORMAT "Error:\t\t%s\n"
-#define debug(args...) if (hLog != NULL) fprintf(hLog, ## args);
+#define debug(args...) if (hLog != NULL) { fprintf(hLog, ## args); fflush(hLog); }
 #define debugAll(args...) if (debugAll && hLog != NULL) fprintf(hLog, ## args);
 
 typedef void (WINAPI *LPFN_ISWOW64PROCESS) (HANDLE, PBOOL);
@@ -126,7 +127,7 @@ BOOL expandVars(char *dst, const char *src, const char *exePath, const int pathL
 void appendHeapSizes(char *dst);
 void appendHeapSize(char *dst, const int megabytesID, const int percentID,
                const DWORDLONG availableMemory, const char *option);
-void setJvmOptions(char *jvmOptions, const char *exePath);
+void setJvmOptions(char *jvmOptions, const char *exePath, const int pathLen);
 BOOL createMutex();
 void setWorkingDirectory(const char *exePath, const int pathLen);
 BOOL bundledJreSearch(const char *exePath, const int pathLen);