Forum:Please port to older Windows versions

From NetHackWiki
Revision as of 12:35, 16 December 2015 by Yetisyny (talk | contribs) (turns out it's actually an incompatibility with non-SSE2 CPUs, but I figured out how to fix it and posted directions on what to change in the .vcxproj files in the /win/win32/vs2013 directory of NetHack 3.6.0's source code)
Jump to navigation Jump to search


Hi, could someone please port the newly released vanilla NetHack 3.6.0 to older Windows versions such as Windows XP, and have it also work on older CPUs (my CPU is an AMD Sempron 2800+ which doesn't support the SSE2 instruction set)? If you use the GNU GCC compiler for Windows (I recommend MinGW instead of Cygwin, and in particular recommend the MinGW distribution called TDM-GCC and suggest the 32-bit version), well that will produce executables that work as far back as Windows 98 and Windows NT 4.0 on CPUs as far back as the 386, while still being perfectly compatible with the newest 64-bit Windows 10. The best IDE for C/C++ on either Windows or Linux (not Mac OS X though sorry) is Code::Blocks and its Windows version integrates very well with TDM-GCC. In fact Code::Blocks provides builds that have TDM-GCC bundled with it (if you use an older version of Code::Blocks with a newer version of TDM-GCC you'll have problems). Right now other than the nightly builds there is also a release candidate out right now for the latest Code::Blocks which should work fine with the latest TDM-GCC (the last stable Code::Blocks from 2013 obviously doesn't work with the latest TDM-GCC from 2015). I'd suggest the latest Code::Blocks 15.12 Release Candidate 1 (WITHOUT bundled MinGW) as the IDE, used with the latest TDM-GCC 32-bit bundle 5.1.0-3 distribution of MinGW-GCC as the compiler. That oughta be able to compile NetHack 3.6.0 or anything else written in C or C++, even stuff using the latest language features like C11 or C++14, and compile it so it works even on really old computers.

Anyway someone please compile and build a NetHack 3.6.0 port for older 32-bit Windows versions, for people who aren't using Windows 7 yet. With the above instructions you ought to be able to build NetHack 3.6.0 to run on any Windows version as far back as Windows 98 (maybe even 95?) or Windows NT 4.0 on any CPU as far back as a 386. That'll be fine not just for me with my early-2005 32-bit AMD CPU running Windows XP, but people on computers from back in the 1990s still running Windows 9x if there are still any of those around (I've seen stuff online from Windows 98 enthusiasts who apparently still exist and still use Windows 98 even today in 2015, so if you think I am out of date using Windows XP just think about the Windows 98 enthusiast community, or for that matter, the people who still use DOS).

Porting NetHack to all sorts of platforms has always been a big part of its history so not even having a version that works on 32-bit Windows XP is kinda ridiculous. Anyway I think it's likely plenty of NetHack developers or developers of various NetHack variants might read this and have the programming skills to pull it off (there might be some compiler warnings and/or errors and only folks like you who know the NetHack code inside and out would have an easy time of getting things to work). I'm more of a C++ developer than a vanilla C developer and I have a tough time with memory management in vanilla C plus I don't know the NetHack source code and it takes awhile to get up to speed on a project so I figured someone else might be better suited to getting this compiled correctly than me. Anyway thanks for reading this everyone, I hope one of ya manages to port this to older versions of 32-bit Windows. Oh, and for the people who program variants... it'd also be nice if you compiled your variants to work on older versions of Windows and work with older CPUs, and didn't use Microsoft's compilers, instead using the trusty MinGW-GCC compilers, specifically the handy TDM-GCC distribution which is all-in-one and works quite well.

Oh and hopefully NetHack 3.6.0 doesn't use any APIs that require Windows 7 or later or Vista or later such as DirectX 11. If so that would make things tougher as the last version of DirectX supported by Windows XP (as well as Windows 98, ME, and 2000) is DirectX 9.0c. That's just one example of a new API in the Windows NT 6.x kernel that might possibly be used in NetHack 3.6.0 and prevent it from being compatible with Windows XP or even older versions. Hopefully NetHack 3.6.0 uses as few new APIs as possible... it's still written in vanilla C, I think, and it's written to be cross-platform, so I don't expect they would use too many new APIs from Windows.

--Yetisyny (talk) 11:17, 15 December 2015 (UTC)

Open source developers, as a rule, are more easily persuaded by neat ideas and some code than by just neat ideas. You furthermore have something very important to such an effort that I don't -- access to a box running the targeted version of Windows. I have nothing functional that runs Windows XP.
I don't know if NetHack uses anything much other than the bare-bones Win32 API. It certainly doesn't use any version of DirectX.
The fix for W343-3 is to call a Unicode API instead of the ANSI one. When I composed the patch, I still had Windows 98 handy, and put in a check for Windows 9x to avoid calling that Unicode API on Windows 9x. The check is present in NetHack 3.6.0: search sys/winnt/nttty.c for the variable name has_unicode. I conclude that the DevTeam has not intentionally broken compatibility with older versions of Windows.
Perhaps the binary distribution will work just fine. Or you might try compiling from source, and posting any errors here.--Ray Chason (talk) 01:50, 16 December 2015 (UTC)
Aha, I've tested it on another Windows XP computer with a more modern CPU and found out the REAL source of this problem. Actually the incompatibility wasn't the operating system at all. It works perfectly fine on Windows XP computers if their CPUs support the SSE2 instruction set. The reason it wasn't working was that the computer I usually use not only runs Windows XP but has a 32-bit AMD Sempron 2800+ CPU (equivalent to an AMD Athlon XP 2800+ and supposedly equivalent to a Pentium 4 2.8 GHz, except for the fact that Pentium 4's support the SSE2 instruction set and Athlon XPs and 32-bit Semprons don't).
Microsoft Visual C and Visual C++ prior to the 2012 version (i.e. the 2010 version and earlier) by default target the IA32/Pentium Pro/i686 CPU architecture. See here for architecture targeting in Microsoft Visual C and C++ 2010, the last version whose default CPU target was IA32/Pentium Pro/i686. Microsoft Visual C and C++ in the 2012 and later versions (including the 2013 version that it seems NetHack 3.6.0 is compiled with) by default target the SSE2/Pentium IV/pentium4 architecture (and AMD chips didn't support all of the instruction sets of this architecture until AMD64 chips came out, with SSE2 introduced at the same time as 64-bit instructions to the AMD product line, meaning no 32-bit AMD chip supports SSE2, and AMD began its transition from 32-bit to 64-bit in late 2003 and finished it in early 2005). See here for architecture targeting in Microsoft Visual C and C++ 2013 version, which is the version that the DevTeam used to compile NetHack 3.6.0.
So what is necessary is to use the "/arch:IA32" option as specified here for the Microsoft Visual C 2013 project... and to NOT specify any architecture to target for the Microsoft Visual C 2010 project since if you do specify one it will require newer CPUs and Visual C 2010 didn't have "/arch:IA32" as an option since it was the default prior to the 2012 version.
The easiest, safest way to do it is through the GUI of Microsoft Visual Studio 2013 and is explained here. Specifically, to do it from the IDE of Microsoft Visual Studio 2013, open the Property Pages dialog box for the project, select the Configuration Properties, C/C++ folder, select the Code Generation property page, and modify the Enable Enhanced Instruction Set property so that it is set to IA32, and do that with every single one of the Visual C 2013 project files in /win/win32/vs2013.
A more difficult method that can be done through any text editor can be done by modifying the .vcxproj files in the /win/win32/vs2013 directory and making sure that every time there is a <ClCompile> for a 32-bit build (not 64-bit), inside that there is an <AdditionalOptions> that has "/arch:IA32" as one of the options prior to the "%" at the end of the list of additional options. So for example, under a <ClCompile>, if you find an <AdditionalOptions> such as "<AdditionalOptions>/FS %(AdditionalOptions)</AdditionalOptions>", you would change it to "<AdditionalOptions>/arch:IA32 /FS %(AdditionalOptions)</AdditionalOptions>", by adding in "/arch:IA32 " right after <AdditionalOptions>. And if you find a <ClCompile> that doesn't have an <AdditionalOptions> element inside it, you'd put in a line that says "<AdditionalOptions>/arch:IA32 %(AdditionalOptions)</AdditionalOptions>". There are also <AdditionalOptions> sections inside <Link> sections but in those you shouldn't add the "/arch:IA32"... it only goes in the <ClCompile> sections. And this is only for the Visual C 2013 project files in /win/win32/vs2013, not the Visual C 2010 project files in /win/win32/vs2010. The Visual C 2010 project files in /win/win32/vs2010 are fine the way they are already and don't need modifications. For an example of a .vcxproj file that has the correct "/arch:IA32" option in all the right places, this code from another open-source project's .vcxproj file has it done correctly in the way it is done in Visual Studio 2012, 2013, and 2015.
Anyway this is what is needed to fix the incompatibility with older CPUs (such as ALL 32-bit AMD chips ever made, along with pre-Pentium IV Intel chips). It just requires those simple changes to the Visual C 2013 project files, either through the IDE of Microsoft Visual Studio 2013 or by making the edits I specified above to the .vcxproj files in the /win/win32/vs2013 directory of NetHack 3.6.0's source code. Doing this using the IDE of Microsoft Visual Studio 2013 is probably safer than doing it by hand-editing the .vcxproj files in a text editor so I'd recommend that method as the preferred one out of the 2 I described. The only advantage of hand-editing the .vcxproj files is that it doesn't require Microsoft Visual Studio 2013 and can be done simply by using a text editor, although you have to be a lot more careful with that method not to mess anything else up in those files.
In some good news, there isn't any operating system incompatibility AT ALL with the latest NetHack 3.6.0 and Windows XP or Windows Vista. It is a CPU incompatibility, not an operating system incompatibility, according to some testing I have done on various computers. The current NetHack 3.6.0 binaries work perfectly fine on any computer with Windows XP or later, as long as the computer has an Intel or AMD CPU that supports the SSE2 instruction set. And if the fix I propose here is adopted, the SSE2 instruction set won't be required anymore and all that'll be required is Windows XP or later. By the way, the SSE2 instruction set didn't become a system requirement for Windows itself until Windows 8.1. All versions of Windows up through the original 8.0 do not require SSE2. So making it a requirement for NetHack is not a good idea. Anyway, the ACTUAL system requirements for the current binaries aren't Windows 7 or later, they're Windows XP or later plus a CPU that supports the SSE2 instruction set.
Well I'd like to submit this as a bugfix to the official NetHack DevTeam. I think with this amount of information they can take care of the rest of it themselves, and then it won't require SSE2 anymore and will work on ANY computer with Windows XP or later.
As far as compiling a build that would work on even older versions of Windows that are pre-XP, I think that's obviously a lower priority than getting this incompatibility problem fixed, since reducing the CPU requirement from SSE2 to just 32-bit x86 doesn't require anyone to switch compilers, it just means fixing the .vcxproj files to have the right options for the compiler, which is pretty simple to do from the IDE of Microsoft Visual Studio 2013.
Sorry about initially getting the cause of the incompatibility wrong in my first post... there's no operating system incompatibility with Windows XP at all, it's a CPU incompatibility with CPUs that don't support the SSE2 instruction set. I was mostly misled into thinking it was an OS incompatibility because I was going by what the NetHack website said about system requirements, rather than actually testing it out on different computers to find out for real what the actual requirements are, something I've done since then.
--Yetisyny (talk) 12:34, 16 December 2015 (UTC)