Хостинг серверов Minecraft playvds.com
  1. Вы находитесь в русском сообществе Bukkit. Мы - администраторы серверов Minecraft, разрабатываем собственные плагины и переводим на русский язык плагины наших собратьев из других стран.
    Скрыть объявление
  2. Данный раздел создан исключительно для релизов! Вопросы по лаунчеру или обвязке задавайте ТОЛЬКО в соответсвующей теме автора. Любые другие темы будут удалены, а авторы понесут наказание.

Лаунчер MLU Launcher C#, UPDATE # 1

Тема в разделе "Веб-обвязки и лаунчеры", создана пользователем DevilEz_Mc, 17 дек 2013.

  1. Racvol

    Racvol Старожил Пользователь

    Баллы:
    123
    Для поиска Java я бы написал что нибудь вроде этого:
    PHP:
                var key Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall");
                foreach (
    String keyName in key.GetSubKeyNames())
                {
                    
    RegistryKey subkey key.OpenSubKey(keyName);
                    if (
    subkey != null)
                    {
                        
    String name subkey.GetValue("DisplayName") as String ?? String.Empty;
                        
    String publisher subkey.GetValue("Publisher") as String ?? String.Empty;
                        
    String displayVersion subkey.GetValue("DisplayVersion") as String ?? String.Empty;
                        if (
    name.Contains("Java") && publisher.Contains("Oracle") && displayVersion.Contains("7.0."))
                        {
                            
    Trace.WriteLine("DisplayName: " name ", DisplayVersion:" displayVersion);
                            
    Trace.WriteLine("  InstallLocation: " subkey.GetValue("InstallLocation").ToString());
                        }
                    }
                }
    И вместо дикой конкатенации строк лучше использовать StringBuilder
     
  2. Хостинг MineCraft
    <
  3. Leonfuerst

    Leonfuerst Активный участник Пользователь

    Баллы:
    58
    Имя в Minecraft:
    Leonfuerst
    Так лучше
    Код:
    using System;
    using System.Collections.Generic;
    using System.Diagnostics;
    using System.IO;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    
    namespace Minecraft_Launcher
    {
        class JavaCheck
        {
            private const string JavaClass =
                @"public class JavaBit
                  {
                      public static void main (String[] args)
                      {
                          System.out.print
                              (System.getProperty(""sun.arch.data.model"") );
                      }
                  }";
    
            private static void DeleteFiles(params string[] files)
            {
                foreach (var fileName in files)
                {
                    try
                    {
                        if (File.Exists(fileName))
                            File.Delete(fileName);
                    }
                    catch (IOException)
                    {
                    }
                }
            }
    
            public static int JavaBit()
            {
                var tempPath = Path.GetTempPath();
                var tempClassPath = Path.Combine(tempPath, "JavaBit.java");
                var tempJarPath = Path.Combine(tempPath, "JavaBit.class");
    
                DeleteFiles(tempClassPath, tempJarPath);
    
                File.WriteAllText(tempClassPath, JavaClass);
    
                using (var javaCompiler = new Process())
                {
                    javaCompiler.StartInfo.Arguments = "JavaBit.java";
                    javaCompiler.StartInfo.CreateNoWindow = true;
                    javaCompiler.StartInfo.FileName = "javac.exe";
                    javaCompiler.StartInfo.UseShellExecute = false;
                    javaCompiler.StartInfo.WorkingDirectory = tempPath;
                    javaCompiler.Start();
                    javaCompiler.WaitForExit();
                }
    
                using (var javaProcess = new Process())
                {
                    javaProcess.StartInfo.Arguments = "JavaBit";
                    javaProcess.StartInfo.CreateNoWindow = true;
                    javaProcess.StartInfo.FileName = "java.exe";
                    javaProcess.StartInfo.RedirectStandardOutput = true;
                    javaProcess.StartInfo.UseShellExecute = false;
                    javaProcess.StartInfo.WorkingDirectory = tempPath;
                    javaProcess.Start();
                    javaProcess.WaitForExit();
                    var line = javaProcess.StandardOutput.ReadLine();
                    line = line.Trim();
    
                    DeleteFiles(tempClassPath, tempJarPath);
    
                    return int.Parse(line);
                }
            }
        }
    }
    
     
  4. Racvol

    Racvol Старожил Пользователь

    Баллы:
    123
    Поздравляю, вы выиграли конкурс "Самый бесполезный код руведра"!!!

    Ну действительно, каким же образом мы можем опредилить битность запускаемого процесса кроме как созданием двух временных файлов, компиляцией их, потом запуск уже скомпилированного файла. И это все ради того чтобы получить число 32 или 64.

    Мало того что этот код решает тока одну задачу это определение, какая битность процесса будет запущен если указать не полный путь к исполняемому файлу java.exe, а просто имя исполняемого файла java.exe. Так делает это настолько не эффективно что просто ужас.

    Код:
            public static Int32 JavaBit()
            {
                //Ищем путь где находится java.exe
                const string exe = "java.exe";
                var environmentVariable = Environment.GetEnvironmentVariable("PATH");
                if (environmentVariable == null) throw new ApplicationException("Переменной окружения PATH не существует???");
                var exeFilePath = environmentVariable
                    .Split(';').FirstOrDefault(s => File.Exists(Path.Combine(s, exe)));
    
                if (exeFilePath == null) throw new ApplicationException("Java.exe не найден");
                using (var fs = new FileStream(Path.Combine(exeFilePath, exe), FileMode.Open, FileAccess.Read, FileShare.Read))
                {
                    var binReader = new BinaryReader(fs);
                       
                    //Получаем смещение где хранится структура с битностью
                    fs.Position = 0x3C;
                    var headerOffset = binReader.ReadUInt32();
    
                    //Так можно проверить смещение
                    if (headerOffset > fs.Length - 5)
                    {
                        //И сделать чтонибудь умное
                        throw new ApplicationException("Неверный формат образа");
                    }
    
                    //Далее читаем сигнатуру PE файла
                    fs.Position = headerOffset;
                    var signature = binReader.ReadUInt32();
                    if (signature != 0x00004550) //Проверяем сигнатуру
                    {
                        throw new ApplicationException("Неверный формат образа");
                    }
    
                    //Далее в следающих 16 битах хранится наше число архитектуры
                    /*Дальше пошли магические цыфры =) и плохой код лучше конечно через перечисление или структуру*/
                    switch(binReader.ReadUInt16())
                    {
                        case 332: //Если равно 0x014c то это под архитектуру I386
                            return 32;                       
                        case 34404: //Если равно 0x8664 то это под архитектуру x64
                            return 64;
                        default:
                            return 0;
                    }
                }               
            }
        }
    Так будет раз в 10 быстрее и правильней
     
    Последнее редактирование: 9 янв 2014
  5. Sirse

    Sirse Старожил Пользователь

    Баллы:
    173
    Имя в Minecraft:
    Sirse
    Зачем искать яву, если по умолчанию бинарник всегда лежит в C:\Windows\System32\java.exe ?
     
  6. Leonfuerst

    Leonfuerst Активный участник Пользователь

    Баллы:
    58
    Имя в Minecraft:
    Leonfuerst
    А если у пользователя нет прав для просмотра данного каталога?
     
  7. Sirse

    Sirse Старожил Пользователь

    Баллы:
    173
    Имя в Minecraft:
    Sirse
    Не подумал об этом...[DOUBLEPOST=1389343940,1389343754][/DOUBLEPOST]Хотя опять же, существует ветвь SOFTWARE\\JavaSoft\\Java Runtime Environment\\, брать путь к бинарникам можно оттуда, а не копаться в SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall
     
    Racvol нравится это.
  8. Leonfuerst

    Leonfuerst Активный участник Пользователь

    Баллы:
    58
    Имя в Minecraft:
    Leonfuerst
    Вообще можно просто определить разрядность системы и уповать на правильность пользователя(чтобы он установил Java x64),но...
     
  9. Sirse

    Sirse Старожил Пользователь

    Баллы:
    173
    Имя в Minecraft:
    Sirse
    ... школьники умудряются качать .net с порнобаннерами.
     
  10. Leonfuerst

    Leonfuerst Активный участник Пользователь

    Баллы:
    58
    Имя в Minecraft:
    Leonfuerst
    Тогда просто проверить в реестре некоторые ключи.Если нужно могу скинуть
     
  11. Sirse

    Sirse Старожил Пользователь

    Баллы:
    173
    Имя в Minecraft:
    Sirse
    Хм, не откажусь. Желательно кидать в эту тему, для сообщества.
     
  12. Leonfuerst

    Leonfuerst Активный участник Пользователь

    Баллы:
    58
    Имя в Minecraft:
    Leonfuerst
    Если есть в разделе HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\JavaSoft - то java 32-х битная
    Если есть в разделе HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft - тогда разрядность java совпадает с разрядностью Windows.
     
  13. Racvol

    Racvol Старожил Пользователь

    Баллы:
    123
    Не знал[DOUBLEPOST=1389346553][/DOUBLEPOST]
    Определить разрядность ОС? Есть же метод Environment.Is64BitOperatingSystem
     
  14. Leonfuerst

    Leonfuerst Активный участник Пользователь

    Баллы:
    58
    Имя в Minecraft:
    Leonfuerst
    Я про него и говорил.
     
  15. Racvol

    Racvol Старожил Пользователь

    Баллы:
    123
    Ну а если у меня установлено две версии Java 64 и 32 битных как их отличить в SOFTWARE\\JavaSoft\\Java Runtime Environment?
     
  16. Sirse

    Sirse Старожил Пользователь

    Баллы:
    173
    Имя в Minecraft:
    Sirse
    Определить битность файлов. Однако я сейчас подумал, если поставить и 32 битную, и 64 битную версии, то как они вообще будут разделяться в SOFTWARE\\JavaSoft\\Java Runtime Environment\\версия\\ ?
    И ещё вопрос, скорее не по теме: никто не знает, почему не рисуются формы в Xamarin Studio, Gtk# проекте? Под Ubuntu всё рисовалось, под Win не хочет.
     
  17. Racvol

    Racvol Старожил Пользователь

    Баллы:
    123
    В 64 битной ОС, для 32 битной Java создается другая ветка реестра.[DOUBLEPOST=1389454442,1389431820][/DOUBLEPOST]Переработал алгоритм поиска Java согласно вашим подсказкам, теперь он выглядит так

    PHP:
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Runtime.InteropServices;
    using Microsoft.Win32;
    using NLog;


    namespace 
    Launcher
    {

        
    unsafe abstract class Java
        
    {
            protected static 
    readonly Logger Log LogManager.GetCurrentClassLogger();
            public 
    String Version get; private set; }
            public 
    String FullVersion get; private set; }
            public 
    String JavaHome get; private set; }
            public 
    String ImageCkSum get; private set; }
            public 
    String RuntimeLib get; private set; }
            public 
    UInt16 BitArchitecture get; private set; }

            protected 
    Java()
            {
                var 
    key Registry.LocalMachine.OpenSubKey(@"SOFTWARE\JavaSoft\Java Runtime Environment");
                if (
    Environment.Is64BitProcess != Environment.Is64BitOperatingSystem)
                {
                    
    key Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Wow6432Node\JavaSoft\Java Runtime Environment");
                }
                if (
    key != null)
                {
                    var 
    jreDictionary =
                        
    key.GetSubKeyNames()
                            .
    Select(keyName => key.OpenSubKey(keyName))
                            .
    Where(versionKey =>
                                    
    versionKey != null &&
                                    
    versionKey.Name == key.Name "\\" key.GetValue("Java" key.GetValue("CurrentVersion").ToString().Split('.')[1] + "FamilyVersion"))
                            .
    Select(versionKey => versionKey.OpenSubKey("MSI"))
                            .
    Where(javaMsiKey => javaMsiKey != null)
                            .
    Select(javaMsiKey => new Dictionary<StringString>
                            {
                                {
    "PRODUCTVERSION"javaMsiKey.GetValue("PRODUCTVERSION") as String},
                                {
    "JavaHome"javaMsiKey.GetValue("INSTALLDIR") as String},
                                {
    "ImageCkSum"javaMsiKey.GetValue("ImageCkSum") as String},
                                {
    "FullVersion"javaMsiKey.GetValue("FullVersion") as String}
                            }).
    FirstOrDefault();

                    if (
    jreDictionary != null)
                    {
                        
    FullVersion jreDictionary["FullVersion"];
                        
    Version jreDictionary["PRODUCTVERSION"];
                        
    JavaHome jreDictionary["JavaHome"];
                        
    ImageCkSum jreDictionary["ImageCkSum"];
                        
    RuntimeLib jreDictionary["JavaHome"] + @"bin\server\jvm.dll";
                        
    BitArchitecture = (UInt16)(Environment.Is64BitProcess 64 32);
                    }
                }
            }     
        }
    }
     
    Hephest, Sirse и Leonfuerst нравится это.
  18. Sirse

    Sirse Старожил Пользователь

    Баллы:
    173
    Имя в Minecraft:
    Sirse
    Пруф? Да и если человек использовал open-source лаунчер как базу - ничего страшного.
     
  19. Sirse

    Sirse Старожил Пользователь

    Баллы:
    173
    Имя в Minecraft:
    Sirse
    @Racvol, вы случаем не решали проблему с утилиткой "Универсальный обход"? Есть ли что-то более-менее адекватное, чем проверка чексумм Java?
     
  20. Racvol

    Racvol Старожил Пользователь

    Баллы:
    123
    Это тот где подменяется стандартная библиотека Java rt.jar?

    Если не охота тащить c Launcher-ом и проверять всю библиотеку Java, можно проверять какие библиотеки были загружены и откуда, например если они загружены не из папки minecraft и не входят в список исключений (такие как стандартные библиотеки) клиент должен автоматически отправляться в бан с логом до разбирательства
     
    Последнее редактирование: 18 янв 2014
  21. xhome

    xhome Старожил Пользователь

    Баллы:
    103
    Skype:
    xhomee
    Имя в Minecraft:
    xhomee
    А зачем ячейка под введение логина и пароля?
     

Поделиться этой страницей