Как я могу определить, работает ли я в 64-битной JVM или 32-битной JVM (изнутри программы)?

563

Как я могу определить, является ли JVM, в которой выполняется мое приложение, 32-разрядной или 64-разрядной? В частности, какие функции или свойства я могу использовать для обнаружения этого в программе?

BobMcGee
источник
3
Просто из любопытства, зачем вам знать естественный размер системы? Такие детали, как эта, абстрагируются в Java, поэтому вам не нужно (по крайней мере, в теории) знать их.
Патрик Недзельски
3
Это позволяет мне приблизительно оценить требования к памяти для объектов из-за указателей. Любопытство тоже - казалось, что должен быть способ, но я никогда не слышал об этом.
BobMcGee
85
Эта «деталь» не абстрагируется при взаимодействии с собственным интерфейсом Java. 32-битные DLL не могут быть загружены с 64-битной JVM (и наоборот). Так что это очень важная информация для тех, кто использует JNI. Жаль, что, кажется, нет портативного способа получить эту информацию. Один из способов - сначала попытаться загрузить 32-разрядную версию DLL, а в случае сбоя - 64-разрядную версию и т. Д. Ужасно!
Joonas Pulakka
12
Другая ситуация, когда важно различать 32- или 64-битные JVM, связана с отображаемыми файлами. В 32-разрядных системах можно сопоставить только 2 ГБ, поэтому важно соответствующим образом отображать и отображать сегменты файлов, чтобы этот предел не превышался, в то время как в 64-разрядных jvms этот предел намного, намного, намного выше.
Симона Джанни
2
Очень приятно иметь возможность выбирать численный алгоритм, который будет самым быстрым на рассматриваемой машине.
dfeuer

Ответы:

317

Вы получаете системное свойство, которое помечает разрядность этой JVM с помощью:

System.getProperty("sun.arch.data.model");

Возможные результаты:

  • "32" - 32-битная JVM
  • "64" - 64-битная JVM
  • "unknown" - Неизвестная JVM

Как описано в FAQ по HotSpot :

Когда я пишу код Java, как различить 32- и 64-битные операции?

Нет общедоступного API, позволяющего различать 32- и 64-разрядные операции. Подумайте о 64-битной архитектуре как об очередной платформе, которую можно написать один раз, запустить в любом месте. Однако, если вы хотите написать код, который зависит от платформы (позор вам), системное свойство sun.arch.data.model имеет значение «32», «64» или «неизвестно».

Например, это может быть необходимо, если ваш Java-код зависит от собственных библиотек, и вам нужно определить, загружать ли 32- или 64-битную версию библиотек при запуске.

codaddict
источник
22
Я не ожидал бы найти sun.*системные свойства с IBM JVM. Другими словами, это не портативно.
Паскаль Тивент
8
Как вы можете сказать из командной строки? Если вы используете 32-разрядную или 64-разрядную версию? Просто любопытно.
Xonatron
17
Почему принятый ответ зависит от Солнца? «os.arch» выполнит то же самое, не используя собственные пакеты Sun.
b1nary.atr0phy
7
@ b1naryatr0phy, os.arch сообщает об операционной системе или JVM? Я часто запускаю 32-разрядную JVM на своей 64-разрядной рабочей станции для целей разработки.
skiphoppy
7
Это свойство поддерживается в IBM JVM, но не в GCJ. См. Stackoverflow.com/questions/807263/…
Эммануэль Бург
708

Для определенных версий Java вы можете проверить битность JVM из командной строки с флагами -d32и -d64.

$ java -help
...
    -d32          use a 32-bit data model if available
    -d64          use a 64-bit data model if available

Чтобы проверить наличие 64-битной JVM, выполните:

$ java -d64 -version

Если это не 64-битная JVM, вы получите это:

Error: This Java instance does not support a 64-bit JVM.
Please install the desired version.

Аналогично, чтобы проверить 32-битную JVM, запустите:

$ java -d32 -version

Если это не 32-битная JVM, вы получите это:

Error: This Java instance does not support a 32-bit JVM.
Please install the desired version.

Эти флаги были добавлены в Java 7, устарели в Java 9, удалены в Java 10 и больше не доступны в современных версиях Java.

gpampara
источник
3
Хотя это полезно знать, это бесполезно, потому что мне нужно запускать его из-за пределов программы или использовать параметры Java для запуска нового процесса.
BobMcGee
13
Именно то, что я искал. И вы можете запустить, java -d32 -versionчтобы убедиться, что вы не используете 32-разрядную версию. Оба хотят работать дальше Win7.
Xonatron
31
Я нахожусь на Windows 7, и я получаю ошибку 'нераспознанной опции' от java -d32 -version и также от java -d64 -version .
Ely
40
Не используйте «-D64», потому что это делает что-то совершенно другое. Он определяет системное свойство под названием «64». Это определенно не то, что нужно здесь.
Джонатан Хедленд
9
Флаги -d32 или -d64 будут работать только для Java 7 или выше.
darrenmc
188

Просто введите java -versionв вашей консоли.

Если запущена 64-битная версия, вы получите сообщение вроде:

java version "1.6.0_18"
Java(TM) SE Runtime Environment (build 1.6.0_18-b07)
Java HotSpot(TM) 64-Bit Server VM (build 16.0-b13, mixed mode)

32-битная версия покажет что-то похожее на:

java version "1.6.0_41"
Java(TM) SE Runtime Environment (build 1.6.0_41-b02)
Java HotSpot(TM) Client VM (build 20.14-b01, mixed mode, sharing)

Обратите внимание, Clientа не 64-Bit Serverв третьей строке. Client/ServerЧасть не имеет никакого отношения, это отсутствие , 64-Bitчто имеет значение.

Если в вашей системе установлено несколько версий Java, перейдите в папку / bin той версии Java, которую вы хотите проверить, и введите ее java -versionтам.

Седат Килинк
источник
но в hp нон-стоп oss env я не получаю 64 бит или 32 бит
vels4j
28
ОП конкретно говорит в рамках программы .
Томаш Зато - Восстановить Монику
34

Я установил 32-битную JVM и повторил попытку, похоже, что следующее говорит вам о битности JVM, а не об ОС:

System.getProperty("os.arch");
#
# on a 64-bit Linux box:
# "x86" when using 32-bit JVM
# "amd64" when using 64-bit JVM

Это было проверено как на SUN, так и на IBM JVM (32- и 64-разрядной). Понятно, что системное свойство - это не просто арка операционной системы.

bryantsai
источник
7
Это дает информацию об архитектуре операционной системы. Если я не ошибаюсь, это не должно быть таким же, как у JVM.
codaddict
2
@codaddict, похоже, это действительно битность JVM.
брянцай
20
@codaddict Это полностью неверно (и я не знаю, почему шесть человек проголосовали за этот комментарий.) «os.arch» предназначен для возврата версии JVM. Проверьте это сами, и Бог поможет вам, если вы действительно полагаетесь на это для обнаружения ОС.
b1nary.atr0phy
6
os.archимеет много возможных значений, трудно сказать, 32-х или 64-х битные. См. Lopica.sourceforge.net/os.html
Эммануэль Бург
2
Это строка, предназначенная для человеческого глаза, и без строгого определения допустимых значений полагаться на это не очень хорошая идея - вместо этого напишите код, который проверяет фактическую функциональность.
Турбьёрн Равн Андерсен
15

Дополнительная информация:

На работающем процессе вы можете использовать (по крайней мере, с некоторыми последними версиями Sun JDK5 / 6):

$ /opt/java1.5/bin/jinfo -sysprops 14680 | grep sun.arch.data.model
Attaching to process ID 14680, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 1.5.0_16-b02
sun.arch.data.model = 32

где 14680 - PID jvm, выполняющего приложение. "os.arch" тоже работает.

Также поддерживаются другие сценарии:

jinfo [ option ] pid
jinfo [ option ] executable core
jinfo [ option ] [server-id@]remote-hostname-or-IP 

Однако учтите также это примечание:

« ПРИМЕЧАНИЕ. - Эта утилита не поддерживается и может или не может быть доступна в будущих версиях JDK. В системах Windows, где отсутствует dbgent.dll, необходимо установить« Средства отладки для Windows », чтобы эти инструменты работали. Переменная среды PATH должна содержать местоположение jvm.dll, используемое целевым процессом, или местоположение, из которого был создан файл аварийного дампа. "

тусклый
источник
7

В Linux вы можете получить информацию заголовка ELF с помощью одной из следующих двух команд:

file {YOUR_JRE_LOCATION_HERE}/bin/java

o / p: исполняемый 64-разрядный LSB ELF , AMD x86-64, версия 1 (SYSV), для GNU / Linux 2.4.0, динамически связанный (использует общие библиотеки), для GNU / Linux 2.4.0, не удален

или

readelf -h {YOUR_JRE_LOCATION_HERE}/bin/java | grep 'Class'

о / п: Класс: ELF 64

jawsnnn
источник
6

Если вы используете JNA, вы можете проверить com.sun.jna.Native.POINTER_SIZE == 4(32 бит) или com.sun.jna.Native.POINTER_SIZE == 8(64 бит).

Энтони Хейворд
источник
Это разумно, но доступ к размеру указателя значительно медленнее, чем к другим решениям (требуется некоторое время для инициализации).
BullyWiiPlaza
1

Под Windows 7 в " Панели управления » в разделе « Программы | Программы и компоненты » 64-разрядные варианты JRE & JDK перечислены с « 64-разрядными » в скобках (например, « Java SE Development Kit 7 Update 65 (64-разрядные»). ) "), тогда как для 32-битных вариантов вариант не упоминается в скобках (например, просто" Java SE Development Kit 8 Update 60 ").

user1364368
источник
1

Если вы используете JNA, вы можете сделать это Platform.is64Bit().

鹞 之 神 乐
источник
-1

Для Windows, вы можете проверить Javaместоположение дома. Если это содержит (x86)это 32-bitиначе 64-bit:

public static boolean is32Bit()
{
    val javaHome = System.getProperty("java.home");
    return javaHome.contains("(x86)");
}

public static boolean is64Bit()
{
    return !is32Bit();
}

Примеры путей:

C:\Program Files (x86)\Java\jdk1.8.0_181\bin\java.exe # 32-bit
C:\Program Files\Java\jdk-10.0.2\bin\java.exe # 64-bit

Зачем заботиться о Windowsединственном решении?

Если вам нужно знать, на какой битовой версии вы работаете, вы, скорее всего, возитесь с собственным кодом, Windowsтак что независимость от платформы в любом случае не учитывается.

BullyWiiPlaza
источник
-2

Чтобы получить версию JVM, в которой работает программа

System.out.println(Runtime.class.getPackage().getImplementationVersion());
Олу Смит
источник
Будет ли это отчет для JVM или операционной системы? Вы можете запустить 32-разрядную JVM в 64-разрядной операционной системе.
Турбьёрн Равн Андерсен
Это не использует JMX?
Турбьерн Равн Андерсен
2
Это возвращает что-то вроде 1.8.0_172или nullна Java 10и не отвечает на вопрос в любом случае.
BullyWiiPlaza