Cara menentukan secara terprogram apakah proses tertentu 32-bit atau 64-bit

102

Bagaimana aplikasi C # saya dapat memeriksa apakah aplikasi / proses tertentu (catatan: bukan proses saat ini) berjalan dalam mode 32-bit atau 64-bit?

Misalnya, saya mungkin ingin menanyakan proses tertentu berdasarkan nama, yaitu, 'abc.exe', atau berdasarkan nomor ID proses.

satya
sumber
Harap selalu masukkan bahasa sebagai tag; Saya akan mengubahnya sekarang di posting ini. :-)
Dean J
3
Harap klarifikasi apakah Anda ingin mengetahui proses saat ini 64 bit atau Anda menanyakan proses lain?
Mehrdad Afshari
Dupelicate: stackoverflow.com/questions/266082/…
Lawrence Johnston

Jawaban:

177

Salah satu cara yang lebih menarik yang pernah saya lihat adalah ini:

if (IntPtr.Size == 4)
{
    // 32-bit
}
else if (IntPtr.Size == 8)
{
    // 64-bit
}
else
{
    // The future is now!
}

Untuk mengetahui apakah proses LAIN sedang berjalan di emulator 64-bit (WOW64), gunakan kode ini:

namespace Is64Bit
{
    using System;
    using System.ComponentModel;
    using System.Diagnostics;
    using System.Runtime.InteropServices;

    internal static class Program
    {
        private static void Main()
        {
            foreach (var p in Process.GetProcesses())
            {
                try
                {
                    Console.WriteLine(p.ProcessName + " is " + (p.IsWin64Emulator() ? string.Empty : "not ") + "32-bit");
                }
                catch (Win32Exception ex)
                {
                    if (ex.NativeErrorCode != 0x00000005)
                    {
                        throw;
                    }
                }
            }

            Console.ReadLine();
        }

        private static bool IsWin64Emulator(this Process process)
        {
            if ((Environment.OSVersion.Version.Major > 5)
                || ((Environment.OSVersion.Version.Major == 5) && (Environment.OSVersion.Version.Minor >= 1)))
            {
                bool retVal;

                return NativeMethods.IsWow64Process(process.Handle, out retVal) && retVal;
            }

            return false; // not on 64-bit Windows Emulator
        }
    }

    internal static class NativeMethods
    {
        [DllImport("kernel32.dll", SetLastError = true, CallingConvention = CallingConvention.Winapi)]
        [return: MarshalAs(UnmanagedType.Bool)]
        internal static extern bool IsWow64Process([In] IntPtr process, [Out] out bool wow64Process);
    }
}
Jesse C. Slicer
sumber
8
(Environment.OSVersion.Version.Major >= 5 && Environment.OSVersion.Version.Minor >= 1) Dan itulah mengapa Microsoft harus membuat versi kebohongan kompatibilitas shims - untuk mengatasi bug dalam kode seperti itu. Apa yang terjadi ketika Windows Vista (6.0) keluar? Dan orang-orang kemudian menjelek-jelekkan Microsoft karena membuat Windows 7 versi 6.1 daripada 7.0, itu memperbaiki begitu banyak bug aplikasi-compat.
Ian Boyd
4
Nama fungsi IsWin64 agak menyesatkan, menurut saya. Ini mengembalikan nilai true jika proses 32-bit berjalan di bawah x64 OS.
Denis The Menace
2
Mengapa menggunakan processHandle = Process.GetProcessById(process.Id).Handle;alih-alih hanya processHandle = process.Handle;?
Jonathon Reinhart
1
@JonathonReinhart baik bukan itu hanya pertanyaan yang bagus. Saya tidak punya ide. Pasti sisa-sisa dari peralihan melakukan sesuatu dari satu cara ke cara lain. Terima kasih telah menemukannya!
Jesse C. Slicer
1
Jawaban ini salah; dan mengembalikan false alih-alih memunculkan pengecualian jika terjadi kesalahan adalah desain yang sangat buruk.
pengguna626528
141

Jika Anda menggunakan .Net 4.0, ini adalah satu baris untuk proses saat ini:

Environment.Is64BitProcess

Lihat Environment.Is64BitProcessProperty (MSDN).

Sam
sumber
2
Bisakah Anda memposting kode Is64BitProcess? Mungkin saya dapat menggunakan apa yang dilakukannya untuk mengetahui apakah saya menjalankannya sebagai proses 64-bit.
Ian Boyd
1
@ Ian, saya ragu Sam akan diizinkan secara hukum untuk memposting kode MS di forum ini. Saya tidak yakin dengan konten pasti dari lisensi referensi mereka, tetapi saya cukup yakin itu melarang reproduksi kode di mana saja.
ProfK
3
@Ian seseorang telah melakukan pekerjaan itu untuk Anda: stackoverflow.com/questions/336633/…
Robert MacLean
4
OP secara khusus meminta untuk menanyakan proses lain , bukan proses saat ini.
Harry Johnston
1
Perhatikan bahwa Microsoft memang memposting kode untuk Is64BitProcess( referensiource.microsoft.com/#mscorlib/system/environment.cs ). Namun, itu hanya pernyataan pengembalian hard-code, dikendalikan oleh simbol kompilasi.
Brian
20

Jawaban yang dipilih salah karena tidak sesuai dengan yang diminta. Ia memeriksa apakah suatu proses adalah proses x86 yang berjalan pada x64 OS; sehingga akan mengembalikan "false" untuk proses x64 pada x64 OS atau proses x86 yang berjalan di x86 OS.
Juga, itu tidak menangani kesalahan dengan benar.

Ini metode yang lebih tepat:

internal static class NativeMethods
{
    // see https://msdn.microsoft.com/en-us/library/windows/desktop/ms684139%28v=vs.85%29.aspx
    public static bool Is64Bit(Process process)
    {
        if (!Environment.Is64BitOperatingSystem)
            return false;
        // if this method is not available in your version of .NET, use GetNativeSystemInfo via P/Invoke instead

        bool isWow64;
        if (!IsWow64Process(process.Handle, out isWow64))
            throw new Win32Exception();
        return !isWow64;
    }

    [DllImport("kernel32.dll", SetLastError = true, CallingConvention = CallingConvention.Winapi)]
    [return: MarshalAs(UnmanagedType.Bool)]
    private static extern bool IsWow64Process([In] IntPtr process, [Out] out bool wow64Process);
}
pengguna626528
sumber
1
Environment.GetEnvironmentVariable("PROCESSOR_ARCHITECTURE") == "x86"akan selalu mengembalikan nilai true untuk proses 32bit. Lebih baik digunakan System.Environment.Is64BitOperatingSystemjika .NET4 didukung
Aizzat Suhardi
10

Anda dapat memeriksa ukuran penunjuk untuk menentukan apakah itu 32bits atau 64bits.

int bits = IntPtr.Size * 8;
Console.WriteLine( "{0}-bit", bits );
Console.ReadLine();
Darwyn
sumber
6
Pada saat jawaban ini pertama kali diposting, tidak begitu jelas, tetapi OP ingin tahu bagaimana menanyakan proses lain daripada proses saat ini.
Harry Johnston
3
[DllImport("kernel32.dll", SetLastError = true, CallingConvention = CallingConvention.Winapi)]
[return: MarshalAs(UnmanagedType.Bool)]
public static extern bool IsWow64Process([In] IntPtr hProcess, [Out] out bool lpSystemInfo);

public static bool Is64Bit()
{
    bool retVal;

    IsWow64Process(Process.GetCurrentProcess().Handle, out retVal);

    return retVal;
}
Praveen MB
sumber
5
OP secara khusus menanyakan bagaimana menanyakan proses lain , bukan proses saat ini.
Harry Johnston
1

Ini pemeriksaan satu baris.

bool is64Bit = IntPtr.Size == 8;
Vikram Bose
sumber
6
OP secara khusus menanyakan bagaimana menanyakan proses lain , bukan proses saat ini.
Harry Johnston
0

Saya suka menggunakan ini:

string e = Environment.Is64BitOperatingSystem

Dengan cara ini jika saya perlu mencari atau memverifikasi file, saya dapat dengan mudah menulis:

string e = Environment.Is64BitOperatingSystem

       // If 64 bit locate the 32 bit folder
       ? @"C:\Program Files (x86)\"

       // Else 32 bit
       : @"C:\Program Files\";
pengguna1351333
sumber
13
bagaimana dengan proses 32bit di 64bit OS Machine?
Kiquenet
3
Apakah sangat sulit untuk menggunakan Environment.GetFolderPath(Environment.SpecialFolder.ProgramFilesX86)alih-alih pengkodean keras `C: \ Program Files`?
Luaan
2
Jangan pernah membuat kode keras "file program", karena ini adalah string yang dapat dilokalkan. Αρχεία Εφαρμογών, Arquivos de Programas, dll.
stevieg