How to check if a binary is 16 bit on Windows
Windows has extended the old DOS executable format multiple times, so if you look at a 'modern' Windows executable, right near the beginning there will be a MZ
(or possibly ZM
if the executable is for a system that uses the opposite bit order). This designates the header for the second DOS executable format, known simply as the MZ format.
Beyond that, you'll see some apparent gibberish, followed by something along the lines of 'This program can't be run in DOS mode.'. That gibberish is actually a really simple DOS program that prints out a message to tell the user that that program can't be run in DOS.
After that, you have the header for the actual executable, which may start with one of four pairs of letters, NE
, LX
, LE
, or PE
. If you don't see one of these and the above mentioned message, it's a 16-bit DOS application.
NE
executables (known as 'New Executables') are currently deprecated. They were the first 'new' format extended form MZ, and were originally developed for Windows 1.0. They are always invariably 16-bit Windows executables, and were officially used with Windows 1.0-3.x, MS-DOS 4.0 (but not later versions), OS/2 1.x, and the OS/2 versions of Windows up through NT 5.0 (Windows 2000). These can not be run natively on 64-bit Windows, and will not properly display an application icon on 32-bit versions of Windows since Vista.
LX
executables (one of two varieties of 'Linear Executables') are 32-bit executables in a format that was used by OS/2 2.x and newer, and by some DOS Extenders. These are not supported under any modern version of Windows (and I think they may never have been supported, though I'm not sure).
LE
executables (the other type of 'Linear Executable') are an odd case, and may even technically contain 64-bit code. They were also introduced with OS/2 2.0 (just like LX
executables), but were designed to be used for hardware drivers. The VxD driver model used in Windows 3.x and 9x utilized this format. They were never used for user applications, and thus are not at all supported on newer versions of Windows.
PE
executables, more commonly known as 'Portable Executables' are the format used by modern Windows systems, and were designed for 32-bit code (and thus never supported 16-bit code). There is also an extension called 'PE32+', which is used for 64-bit Windows binaries, .NET CIL binaries (which are bit-width agnostic), and a number of other things which use different extensions (for example, UEFI drivers and applications, which use a .efi
extension, are PE32+ format).
Using this information, you can use the same general check suggested in the answer you linked to in your question. If you just see the MZ
and not the short message followed by some gibberish and then one of the four above letter pairs within the first 4kB of the file, it's just a DOS executable, otherwise, it's one of those four formats. The only one of those formats that should work natively on Windows 10 is the PE format.
As an example, here's a hexdump of the first 512 bytes of a 64-bit Windows executable (specifically, one of the components of the BOINC client software):
00000000: 4d5a 9000 0300 0000 0400 0000 ffff 0000 MZ..............
00000010: b800 0000 0000 0000 4000 0000 0000 0000 ........@.......
00000020: 0000 0000 0000 0000 0000 0000 0000 0000 ................
00000030: 0000 0000 0000 0000 0000 0000 1801 0000 ................
00000040: 0e1f ba0e 00b4 09cd 21b8 014c cd21 5468 ........!..L.!Th
00000050: 6973 2070 726f 6772 616d 2063 616e 6e6f is program canno
00000060: 7420 6265 2072 756e 2069 6e20 444f 5320 t be run in DOS
00000070: 6d6f 6465 2e0d 0d0a 2400 0000 0000 0000 mode....$.......
00000080: c88d b31c 8cec dd4f 8cec dd4f 8cec dd4f .......O...O...O
00000090: 8594 4e4f 9aec dd4f e39a 414f 88ec dd4f ..NO...O..AO...O
000000a0: 1fa2 454f 8eec dd4f e39a 434f 8eec dd4f ..EO...O..CO...O
000000b0: e39a 774f 9fec dd4f e39a 764f 89ec dd4f ..wO...O..vO...O
000000c0: 8594 5e4f 8dec dd4f 8594 594f 8dec dd4f ..^O...O..YO...O
000000d0: 9771 414f 85ec dd4f 8cec dc4f 14ed dd4f .qAO...O...O...O
000000e0: 9771 764f d0ec dd4f 9771 474f 8dec dd4f .qvO...O.qGO...O
000000f0: 9771 404f 8dec dd4f 5269 6368 8cec dd4f [email protected]
00000100: 0000 0000 0000 0000 0000 0000 0000 0000 ................
00000110: 0000 0000 0000 0000 5045 0000 6486 0600 ........PE..d...
00000120: 4c88 ea5a 0000 0000 0000 0000 f000 2200 L..Z..........".
00000130: 0b02 0a00 00fe 0a00 0092 0b00 0000 0000 ................
00000140: c0e4 0800 0010 0000 0000 0040 0100 0000 ...........@....
00000150: 0010 0000 0002 0000 0500 0200 0000 0000 ................
00000160: 0500 0200 0000 0000 0020 1b00 0004 0000 ......... ......
00000170: 489f 1700 0300 4081 0000 1000 0000 0000 H.....@.........
00000180: 0010 0000 0000 0000 0000 1000 0000 0000 ................
00000190: 0010 0000 0000 0000 0000 0000 1000 0000 ................
000001a0: 0000 0000 0000 0000 8cc6 0e00 6801 0000 ............h...
000001b0: 0030 1400 9cd6 0600 00a0 1300 a884 0000 .0..............
000001c0: 0094 1600 2019 0000 0010 1b00 2001 0000 .... ....... ...
000001d0: e01c 0b00 1c00 0000 0000 0000 0000 0000 ................
000001e0: 0000 0000 0000 0000 0000 0000 0000 0000 ................
000001f0: 0000 0000 0000 0000 0000 0000 0000 0000 ................
Notice first the MZ
in the first two bytes, followed by the data for the DOS program that tells you that it can't be run under DOS if you try to run it there, followed by the PE
signature in bytes 280 and 281. You can also see these particular elements in a text editor, though it's a lot harder to read.
Note however that there is also the very real possibility that it's not a Windows executable at all, and someone just gave it the wrong name. Windows will usually recognize something as being a 16-bit executable and say that that's why it can't run it.
If Windows can't run your application because it's 16-bit, it will tell you this explicitly. There's no need to guess.
Windows 10 retains the same compatibility policy that previous versions have had; the 64-bit versions cannot run 16-bit software. The 32-bit version can run 16-bit software, but unlike previous versions, you'll need to add NTVDM support via Windows Features.