Come si determina l'architettura a 32 o 64 bit di Windows utilizzando Java?
Come si determina l'architettura a 32 o 64 bit di Windows utilizzando Java?
Grazie.
9 answers
Si noti che la proprietà os.arch
fornirà solo l'architettura di JRE , non del sistema operativo sottostante.
Se si installa un jre a 32 bit su un sistema a 64 bit, System.getProperty("os.arch")
restituirà x86
Per determinare effettivamente l'architettura sottostante, sarà necessario scrivere del codice nativo. Vedi questo post per maggiori informazioni (e un link al codice nativo di esempio)
Non mi fido esattamente di leggere il sistema operativo.variabile di sistema ad arco. Mentre funziona se un utente esegue una JVM a 64 bit su un sistema a 64 bit. Non funziona se l'utente sta eseguendo una JVM a 32 bit su un sistema a 64 bit.
Il seguente codice funziona per rilevare correttamente i sistemi operativi Windows a 64 bit. Su un sistema Windows a 64 bit la variabile di ambiente "Programfiles(x86)" sarà impostato. NON verrà impostato su un sistema a 32 bit e java lo leggerà come null.
boolean is64bit = false;
if (System.getProperty("os.name").contains("Windows")) {
is64bit = (System.getenv("ProgramFiles(x86)") != null);
} else {
is64bit = (System.getProperty("os.arch").indexOf("64") != -1);
}
Destinato ad altre operazioni sistemi come Linux o Solaris o Mac potremmo vedere anche questo problema. Quindi questa non è una soluzione completa. Per Mac probabilmente sei al sicuro perché Apple blocca la JVM in modo che corrisponda al sistema operativo. Ma Linux e Solaris, ecc.. possono ancora utilizzare una JVM a 32 bit sul loro sistema a 64 bit. Quindi usa questo con cautela.
Ho usato il prompt dei comandi (comando > > wmic OS get OSArchitecture) per ottenere l'architettura del sistema operativo. Il seguente programma aiuta a ottenere tutti i parametri richiesti:
import java.io.*;
public class User {
public static void main(String[] args) throws Exception {
System.out.println("OS --> "+System.getProperty("os.name")); //OS Name such as Windows/Linux
System.out.println("JRE Architecture --> "+System.getProperty("sun.arch.data.model")+" bit."); // JRE architecture i.e 64 bit or 32 bit JRE
ProcessBuilder builder = new ProcessBuilder(
"cmd.exe", "/c","wmic OS get OSArchitecture");
builder.redirectErrorStream(true);
Process p = builder.start();
String result = getStringFromInputStream(p.getInputStream());
if(result.contains("64"))
System.out.println("OS Architecture --> is 64 bit"); //The OS Architecture
else
System.out.println("OS Architecture --> is 32 bit");
}
private static String getStringFromInputStream(InputStream is) {
BufferedReader br = null;
StringBuilder sb = new StringBuilder();
String line;
try {
br = new BufferedReader(new InputStreamReader(is));
while ((line = br.readLine()) != null) {
sb.append(line);
}
} catch (IOException e) {
e.printStackTrace();
} finally {
if (br != null) {
try {
br.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return sb.toString();
}
}
Puoi provare questo codice, penso che sia meglio rilevare il modello di JVM
boolean is64bit = System.getProperty("sun.arch.data.model").contains("64");
Forse non è il modo migliore, ma funziona.
Tutto quello che faccio è ottenere la "Variabile Ambiente" che Windows ha configurato per la cartella Program Files x86. Voglio dire che Windows x64 ha la cartella (Programmi x86) e x86 no. Poiché un utente può cambiare il percorso di File di programma in Enviroment Variables
, o può fare una directory " Program Files (x86)" in C:\, non userò il rilevamento della cartella ma il "Percorso di ambiente" di " Program Files (x86)" con la variabile in Windows registro.
public class getSystemInfo {
static void suckOsInfo(){
// Get OS Name (Like: Windows 7, Windows 8, Windows XP, etc.)
String osVersion = System.getProperty("os.name");
System.out.print(osVersion);
String pFilesX86 = System.getenv("ProgramFiles(X86)");
if (pFilesX86 !=(null)){
// Put here the code to execute when Windows x64 are Detected
System.out.println(" 64bit");
}
else{
// Put here the code to execute when Windows x32 are Detected
System.out.println(" 32bit");
}
System.out.println("Now getSystemInfo class will EXIT");
System.exit(0);
}
}
(Solo per Windows) Controlla se C:\Windows\SysWOW64 esistere. se la directory esiste, è un processo a 64 bit. Altrimenti, è un processo a 32 bit.
Disclaimer: per favore non downvote questo come una risposta duplicata, dal momento che volevo condividere la mia soluzione di codice Java a questo (quello allo stesso modo è un codice nativo).
Vorrei aggiungere la risposta dell'onorevole James Van Huis;
Dal momento che la proprietà os.arco:
System.getProperty("os.arch");
restituisce il bitness di JRE, questo può effettivamente essere molto utile.
Dall'articolo:
Nel tuo codice, devi prima controllare la dimensione di IntPtr, se restituisce 8 allora sei in esecuzione su un sistema operativo a 64 bit. Se restituisce 4, sei esecuzione di un'applicazione a 32 bit, quindi ora è necessario sapere se si sta eseguendo in modo nativo o sotto WOW64.
Pertanto, il controllo delle dimensioni IntPtr è lo stesso controllo che si esegue guardando il "sistema operativo.arco". Dopo questo è possibile procedere con capire se il processo è in esecuzione in modo nativo o in WOW64.
Questo può essere fatto usando la libreria jna(ad esempio NativeLibrary) che offre l'uso delle funzioni native necessarie.
//test the JRE here by checking the os.arch property
//go into the try block if JRE is 32bit
try {
NativeLibrary kernel32Library = NativeLibrary.getInstance("kernel32");
Function isWow64Function = kernel32Library.getFunction("IsWow64Process");
WinNT.HANDLE hProcess = Kernel32.INSTANCE.GetCurrentProcess();
IntByReference isWow64 = new IntByReference(0);
Boolean returnType = false;
Object[] inArgs = {
hProcess,
isWow64
};
if ((Boolean) isWow64Function.invoke(returnType.getClass(), inArgs)) {
if (isWow64.getValue() == 1) {
//32bit JRE on x64OS
}
}
} catch (UnsatisfiedLinkError e) { //thrown by getFunction
}
Qualcosa di simile potrebbe anche funziona, ma consiglierei la prima versione, dato che è quella che ho provato su x64 e 32bit JRE su x64 OS. Inoltre dovrebbe essere il modo più sicuro, perché nel seguito non si controlla effettivamente se esiste o meno la funzione "IsWow64Process".
Qui sto aggiungendo un esempio del controllo JRE, solo così è completo, anche se non è difficile da trovare.
Map<String, Integer> archMap = new HashMap<String, Integer>();
archMap.put("x86", 32);
archMap.put("i386", 32);
archMap.put("i486", 32);
archMap.put("i586", 32);
archMap.put("i686", 32);
archMap.put("x86_64", 64);
archMap.put("amd64", 64);
//archMap.put("powerpc", 3);
this.arch = archMap.get(SystemUtils.OS_ARCH);
if (this.arch == null) {
throw new IllegalArgumentException("Unknown architecture " + SystemUtils.OS_ARCH);
}
System.getProperty("os.arch");
È possibile utilizzare il sistema operativo.proprietà arch nelle proprietà del sistema per scoprirlo.
Properties pr = System.getProperties();
System.out.println(pr.getProperty("os.arch"));
Se sei su 32 bit, dovrebbe mostrare i386 o qualcosa del genere