64 & 32 bit system directory windows - windows

Trying to find third issue in the database with no luck.
So, I'm developing on a 64bit system (windows seven).
I'm making a simple console programme that check if a dll is present on the windows system. in that case I check in the system32 folder and then, in the sysWOW64 folder.
The pro gramme is 32bit application.
On a 32bit target platform, I can check normally the win32dll, as the SysWOW64 directory doesn't exist, no problem.
Bit when it execute on a 64bit system I can check the win32 directory, but the sysWOW64 directory always me point to the system32 directory.
It seems that on 64bit system there is a kind of redirection.
I'm trying to use the "Wow64DisableWow64FsRedirection" but I have "error C3861: 'Wow64DisableWow64FsRedirection': identifier not found" when I compile.
So there are two questions:
In winbase.h this function is disabled, how to get it work ?
How to determine if I'm currently on a 32 or 64 bit system as programme is running?

You don't have to search for DLLs. LoadLibrary() and LoadLibraryEx() will automatically search all relevant folders for you.
The search order is as follows:
The directory from which the application loaded.
The system directory.
The 16-bit system directory.
The Windows directory
The current directory.
The directories that are listed in the PATH environment variable.
If you're sure that you want to disable the redirection you can do so with Wow64DisableWow64FsRedirection as you mentioned. To make it "work", you have to set
#define _WIN32_WINNT 0x0501 (or higher)
before you include windows.h

About How to determine if i'm currently on a 32 or 64 bit system, I think that you could check the size of an int pointer...
int bits = IntPtr.Size * 8;
Console.WriteLine( "{0}-bit", bits );

While not perhaps what you're looking for, slightly wasteful if you know those are the only two places the file could be located, and possibly wouldn't work if the user has modified them (Although a whole host of other things will have broken for the user too), you could simply use the %Path% environmental variable.

Related

Is my 32 bit & 64 bit installers in the wrong directories?

I'm having trouble installing a 64 bit program on my windows PC.
I'm running windows 7 64 bit.
Looking in regedit after a bit of googling I noticed the files seem to be in the opposite directories to what I think they should be.
Nope, those look correct to me. They are indeed confusing at first, and can be difficult to talk about.
System32 is the native system directory, and happens to be misleadingly named on a 64-bit system.
SysWow64 indicates the system directory for the Windows (32)-on-Windows 64.
Note of course that only a 64-bit application, or one that has disabled redirection, can use a path containing "System32" to reach the 64-bit files it contains.

Is it bad idea to put 64b application into ProgramFiles(x86)?

We are shipping application, that is 32b, and, therefore, put into ProgramFiles(x86) directory. There is x64 'plugin' for it, running as a separate process (service), and now we're deploying it into the main application's subdirectory. The plugin isn't deployed on x86 systems.
Now, the question - isn't this (having x64 exectuable in x86 ProgramFiles) considered as bad idea? Can this solution have negative impact on (something)?
Thanks!
It has no negative impact, and in fact, Visual Studio also does this (it installs its 64-bit native compilers into the (x86) directories).
This is only problematic if it's a "real" 64-bit application that expects to be where it's supposed to be (wrt "Program Files"), as certain WinAPI functions that give you this directory work differently for 64-bit and 32-bit applications.
For an x64 program, the %PROGRAMFILES% environmental variables and their analogues are pointing to the Program Files (no x86) directory. So there may be some problems with locating the files that were put in the wrong directory.
Since your app is 32bit, there shouldn't be any problems.

Opening %SystemRoot%\system32\calc.exe from a 32-bit process redirects to another file. Which, why and how?

I'm currently writing some test code in C++ that messes around with PE files to understand its file format structure. My project is set to compile to 64 bit. In my code I open %SystemRoot%\system32\calc.exe and read the IMAGE_DOS_HEADER and IMAGE_NT_HEADERS structures. At the same time I have the same calc.exe opened in Notepad++ with the hex editor plugin. I compared the values my code reads with Notepad++ and noticed they were different. I copied calc.exe from System32 to C:\Temp\calc.exe, and now the values match.
Notepad++ seems to be a 32 bit application (haven't checked the PE file, but since it's installed to Program Files (x86) by default, it seems to be a safe assumption to make).
Is this WinSxS at work? Or what else is causing this? And which file is actually fed to 32-bit applications opening %SystemRoot%\system32\calc.exe?
Just curious. Thanks in advance for any light shed on this.
Yes, this is the WOW redirector. You'll see that there is a calc.exe in C:\Windows\SysWOW64 as well. That's the file that is opened when you use the %SystemRoot%\System32\calc.exe path.
This can be temporarily disabled to access the 64-bit version of the file with Wow64DisableWow64FsRedirection
More details can be found at File System Redirector
If I remember well, when a 32bit apps tries to open system32 directory, it's automatically redirected to syswow64 dir.
Disabling WowFs redirection is unnecessary and sometimes is not even an option (for instance, when you are attempting to get Notepad++ to open files in the system32 directory). You can use the virtual directory %windir%\Sysnative instead of %windir%\System32 (you will not see it in explorer, but you can type it in the address bar)
WOW64 is implemented in three DLLs: wow64.dll, wow64cpu.dll, and wow64win.dll (and 32-bit NTDLL). Redirection (among other things) is implemented in wow64.dll, CPU emulation / helper routines in wow64cpu.dll, and wow64win.dll contains thunks to win32k.sys (the kernel mode driver responsible for the windows GUI).

How should my program decide to install under "Program Files (x86)"?

Just out of curiosity, if I am creating a program installer, how should I decide in which "Program Files" directory to install to? On 32-bit systems, the environmental variable "%programfiles%" is good enough. However, on 64-bit systems, 32-bit programs should not install to that folder and instead to "%programfiles(x86)%", which as I understand points to "C:\Program Files (x86)". My question is: How should the installer decide which environment variable to use? Will the value of "%programfiles%" change for a 32-bit application, or should I always check first whether "%programfiles(x86)%" exists before using "%programfiles%", or should I do something entirely different?
Thanks! This is just out of my own curiosity, as I try to get used to 64-bit operating systems.
When the 32-bit program (installer in your case) asks the system to resolve the ProgramFilePath constant (check the exact name in MSDN), the system does not return C:\Program files, but C:\Program files(x86). So it's the system that decides, not the application.
I'm pretty certain that I read somewhere that Windows did this for you automagically. In other words, if your installer was 32-bits, it would be routed to the x86 directory variant even though you were trying to install into Program Files.
I'm sure I read this on The Old New Thing but here's a link that supports the contention until I can find that one.
Ah, yes, here it is, from the ever useful Raymond Chen.
Commenter Koro is writing an installer in the form of a 32-bit program that detects that it's running on a 64-bit system and wants to copy files (and presumably set registry entries and do other installery things) into the 64-bit directories, but the emulation layer redirects the operations into the 32-bit locations. The question is "What is the way of finding the x64 Program Files directory from a 32-bit application?"
The answer is "It is better to work with the system than against it." If you're a 32-bit program, then you're going to be fighting against the emulator each time you try to interact with the outside world. Instead, just recompile your installer as a 64-bit program. Have the 32-bit installer detect that it's running on a 64-bit system and launch the 64-bit installer instead. The 64-bit installer will not run in the 32-bit emulation layer, so when it tries to copy a file or update a registry key, it will see the real 64-bit file system and the real 64-bit registry.

SHGetSpecialFolderPath, how to access 64bit CSIDL from 32bit application

Is there a way from a 32bit application running on a 64bit system to have access to the default folders for 64bit applications?
For example, using SHGetSpecialFolderPath with CSIDL_PROGRAM_FILES from a 32bit application returns "C:\Program Files (x86)' If the same call was used from a 64bit application, I would get "C:\Program Files". Is there a way of getting that "C:\Program Files" from a 32bit application?
A related question here does not help SHGetFolderPath() 32 bit vs 64 bit nor does supressing the wow64 filesystem redirection before calling SHGetSpecialFolderPath
Answering my own question, it seems it is not possible with SHGetSpecialFolderPath. In Vista and later, using the replacement function SHGetKnownFolderPath allows it with FOLDERID_ProgramFilesX64
I believe the whole reason for having separate folders was to prevent 32 and 64 bit applications from mixing. Therefore, you shouldn't need to see a folder belonging to a different bitness from your application.
You may have a very good reason, but I don't see one in your question as posted.

Resources