6

Normally, x86-64 architecture offers compatibility with x86. A 32-bit Windows (or other OS) can run on an x86-64 processor. (Correct me if I am wrong).

I would like to know if it is possible (in C++) for a 32-bit Windows to know that if underlying processor is 64-bit. For example, if Windows 7 32-bit running on Core i5, we should be able to know that processor is 64-bit (although Windows 7 32 bit is running).

You may question the requirement that even if processor is 64 bit and OS is 32 bit, 64 bit processes cannot run (Correct me if I am wrong). But the aim of the program to know the processor, not OS. This question may appear similar to this, but it does not give any hint of C++ program.

4
  • I have a solution in C#, if you like I will post it. Commented Aug 31, 2012 at 9:22
  • 1
    Have you checked if any cpuid flags give you any clue? Commented Aug 31, 2012 at 9:25
  • 1
    How would you deal with a virtualized 32 bits Windows? And with virtualization, the processor that ran your last instruction may not be the same as the one running the current instruction. Commented Aug 31, 2012 at 9:33
  • Steve: I am not good at C#. But post it. It can be give me some clue. Commented Aug 31, 2012 at 9:34

2 Answers 2

7

This is not a C++ solution, but it seems to work in C#.
However should be easily converted to C++ because the key point is in the API structure SYSTEM_INFO and the API GetNativeSystemInfo()

First a reference to the API that gets infos

[DllImport("kernel32.dll")] public static extern void GetNativeSystemInfo ([MarshalAs(UnmanagedType.Struct)] ref SYSTEM_INFO lpSystemInfo); 

then the structure SYSTEM_INFO and the _PROCESSOR_INFO_UNION

[StructLayout(LayoutKind.Sequential)] public struct SYSTEM_INFO { internal _PROCESSOR_INFO_UNION uProcessorInfo; public uint dwPageSize; public IntPtr lpMinimumApplicationAddress; public IntPtr lpMaximumApplicationAddress; public IntPtr dwActiveProcessorMask; public uint dwNumberOfProcessors; public uint dwProcessorType; public uint dwAllocationGranularity; public ushort dwProcessorLevel; public ushort dwProcessorRevision; } [StructLayout(LayoutKind.Explicit)] public struct _PROCESSOR_INFO_UNION { [FieldOffset(0)] internal uint dwOemId; [FieldOffset(0)] internal ushort wProcessorArchitecture; [FieldOffset(2)] internal ushort wReserved; } 

Now an enum to simplify the code and the method that calls the native API

public enum ProcessorArchitecture { Unknown = 0, Bit32 = 1, Bit64 = 2, Itanium64 = 3 } static public ProcessorArchitecture ProcessorBits { get { ProcessorArchitecture pbits = ProcessorArchitecture.Unknown; SYSTEM_INFO l_System_Info = new SYSTEM_INFO(); GetNativeSystemInfo(ref l_System_Info); switch (l_System_Info.uProcessorInfo.wProcessorArchitecture) { case 9: // PROCESSOR_ARCHITECTURE_AMD64 pbits = ProcessorArchitecture.Bit64; break; case 6: // PROCESSOR_ARCHITECTURE_IA64 pbits = ProcessorArchitecture.Itanium64; break; case 0: // PROCESSOR_ARCHITECTURE_INTEL pbits = ProcessorArchitecture.Bit32; break; default: // PROCESSOR_ARCHITECTURE_UNKNOWN pbits = ProcessorArchitecture.Unknown; break; } return pbits; } } 
Sign up to request clarification or add additional context in comments.

9 Comments

Thanks Steve for the solution. It has solved my problem for WOW64 processes.But I also want to detect if the processor is 64 bit when OS is 32-bit. MSDN documentation says "Retrieves information about the current system to an application running under WOW64. If the function is called from a 64-bit application, it is equivalent to the GetSystemInfo function." I was using GetSystemInfo for this.
I don't get it. Changing GetNativeSystemInfo in GetSystemInfo doesn't work in your case?
I think this is the difference between the GetSystemInfo and GetNativeSystemInfo. It should be working according to: msdn.microsoft.com/en-us/library/windows/desktop/…
Steve: I tested my program on Intel Core i5 machine with Windows 7 32 bit version. I got the same processor type by both GetNativeSystemInfo and GetSystemInfo. I would like to say that by program can I detect in Windows 7 32 bit that Intel Core i5 is a 64 bit processor?
@Rolice Thank you for the link. This example is for 64 bit Windows. I am using 32 bit Windows over a 64-bit capable process. I think it works same way because OS is 32-bit.
|
6

Well, as far as I am aware, you can only get this through looking at the CPU information itself. I think it should be enough (for x86 & amd64) to check whether the CPU supports long mode.

For that, you could use the cpuid instruction on x86. By Windows-ness of your post, I'll take a guess you're using the Microsoft C++ compiler. For that, there's a __cpuid intrinsic. Sadly, the description on Microsoft's page ends at PBE flag, while lm flag in my cpuinfo goes three flags later.

Looking at CPUID Modifications for AMD Processors, you can get LM with InfoType = 0x80000001, with the result being at bit 29 of the last returned integer. In CPUID Modifications for Intel Processors the same bit specifies EM64T flag which is equivalent AFAIK.

In both cases, you should be doing InfoType = 0x80000000 first to get maximum meaningful InfoType value. If it's less than 0x80000001, then you should not do the above check and instead assume long mode is not supported.

2 Comments

Thanks Michal for the solution. What does cache line size signifies? Can it also be used to identify 64 bit/32 bit processor?
@dbasic: I don't think that's strictly relevant, and you really shouldn't depend on that. By the way, if you decide to use that and write some code for it, feel free to edit my answer and add it there so others could benefit. I don't have MSVC around to hack it myself.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.