Thread: How to detect the operating system at runtime?

  1. #1
    Registered User
    Join Date
    Jul 2007
    Posts
    88

    How to detect the operating system at runtime?

    I ask this because I learned the ability to compile an exe to run on more then one operating system at the same time. Imho it's pretty cool.

    Do you know a common way to detect the operating system at runtime (not compile time)?

    I know there is no standard C or C++ feature for that. Is there a prefab library available?

    Or do I need to implement these checks myself for all supported operating systems myself?

  2. #2
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Assuming "OS" here means things like Linux, Windows, MacOS X, etc rather than Windows 98, Windows NT or Linux 2.4 and Linux 2.6, then it's not possible to have ONE executable file for different OS's, since these use different executable file formats [well, I think MacOS and Linux actually use the same format files, but they have different shared libraries and OS interfaces].

    So you need to compile your application for the OS (and processor type) that you are wanting to use. Yes, you can make it work with different OS's at runtime if you really want, but they need to be close enough in relation to each other [e.g different versions of Windows or Linux]. For most cases, those different versions are close enough that MOST things can be done the same way anyway, so knowing the difference only matters in some small detail things.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  3. #3
    Woof, woof! zacs7's Avatar
    Join Date
    Mar 2007
    Location
    Australia
    Posts
    3,459
    For most cases, those different versions are close enough that MOST things can be done the same way anyway.
    ... including some sort of API or other method of getting the OS name or type.

  4. #4
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by zacs7 View Post
    ... including some sort of API or other method of getting the OS name or type.
    Sure, but the point was more that "if the OS is so different that you need to know which one it for anything but very special operating system calls, then it's probable that you need to know before you compile which OS it is".

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  5. #5
    Woof, woof! zacs7's Avatar
    Join Date
    Mar 2007
    Location
    Australia
    Posts
    3,459
    Sigh, I've been missing the point of your posts all day (don't worry it's me, not you)... sorry

  6. #6
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by zacs7 View Post
    Sigh, I've been missing the point of your posts all day (don't worry it's me, not you)... sorry
    Well, maybe I should have been more clear - if you misunderstand it, someone else may also misunderstand it - and I'd rather that you asked for a clarificiation point than that someone else is misunderstanding the point and using that misunderstanding in some way to get even deeper into the world of misunderstanding. Sometimes I read my own posts and think "did I really say that - I should have mentioned <something> to make it clearer".

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  7. #7
    Registered User
    Join Date
    Jul 2007
    Posts
    88
    Quote Originally Posted by matsp View Post
    Assuming "OS" here means things like Linux, Windows, MacOS X, etc rather than Windows 98, Windows NT or Linux 2.4 and Linux 2.6, then it's not possible to have ONE executable file for different OS's, since these use different executable file formats [well, I think MacOS and Linux actually use the same format files, but they have different shared libraries and OS interfaces].

    So you need to compile your application for the OS (and processor type) that you are wanting to use. Yes, you can make it work with different OS's at runtime if you really want, but they need to be close enough in relation to each other [e.g different versions of Windows or Linux]. For most cases, those different versions are close enough that MOST things can be done the same way anyway, so knowing the difference only matters in some small detail things.

    --
    Mats
    OS means in my personal association also older OS, not just recent ones. Also more different ones, NT, Linux and DOS. This was also the thing I was talking about.

    Indeed, currently I was only testing on i386. No other hardware. Guess this will be really impossible on different hardware to use the same executable (without emulator, patching, runtime environment or other tricks).

    Currently my exe can run on:
    (from HX DOS Extender, \hx\SAMPLES\OW4\THREADW.EXE)
    - WinNT (tested only XP and Vista) (native win32 console, no NTVDM)
    - Win9x (tested only Win98)
    - DOS (tested only MS-DOS and FreeDOS)

    And I know another exe running on:
    (from grub4dos, bootlace.com)
    - WinNT (tested only XP 32 and Vista 32) (unfortunately only NTVDM)
    - Win9x (tested only on Win98)
    - DOS (tested only MS-DOS and FreeDOS)
    - and finally also on Linux 2.6 (tested only Ubuntu Hardy)

    (I am trying to understand and both all two processes and combine them but that's another story.)

    Isn't this amazing? Both exe are Open Source if you are interested. It did take me a long time to get aware of this software. It was always my dream to have uber portable software.

    Seams I am the first gui here interested in this? Probable to solve my original question I need to write this from scratch, try to execute some operating system function while error catching for all operating systems.

  8. #8
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Well, a windows executable is actually a DOS executable, but it has a special marker in it that tells the OS that it "knows about protected mode". If you start the same application in "real mode", it runs a stub. Applications that can run in both DOS and Windows environments use this stub part to implement their own way to do the same things that Windows does when run in Windows [such as setting up a 32-bit environment]. It is either a complete duplicate of the same applicaiton, or it links together the 32-bit application with the Windows environment.

    I'm pretty sure [although it would probably take me a few hours to prove] that the dos extender has it's own little set of compatibility functions that are EITHER Windows 32-bit API or compatible with old-fashioned DOS.

    The grub4dos when used with Linux uses kexec, which is not quite the same as "running an executable file in Linux" - becasue kexec really replaces the kernel with the executable file you load. Once grub4dos has been loaded, it's not executing inside the Linux environment, it is executing in it's own environment [A boot loader is such a task that you can't really use any OS anyways, so the boot-loader has to understand some basics in itself, and not rely on the OS to solve those things - grub for example has complete filesystem support to read from the disk in various types of filessystems, such as the more popular Linux and Windows filesystems].

    Writing code for either of the above examples is relying on "you either put a layer in to translate, or you make the function yourself", which is not really "working on several OS's" as such.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  9. #9
    Registered User
    Join Date
    Jul 2007
    Posts
    88
    Quote Originally Posted by matsp View Post
    Well, a windows executable is actually a DOS executable
    Before I thought NT and DOS are pretty much different.


    I'm pretty sure [although it would probably take me a few hours to prove] that the dos extender has it's own little set of compatibility functions that are EITHER Windows 32-bit API or compatible with old-fashioned DOS.
    The HX website says it has win32 console emulation, no more need to prove it.

    The grub4dos when used with Linux uses kexec, which is not quite the same as "running an executable file in Linux" - becasue kexec really replaces the kernel with the executable file you load.
    After booting Ubuntu I can go to console, join the folder and type .\bootlace.com.

    You mean kexec is installed by default and Ubuntu is automatically starting bootlace.com without typing kexec?

    While writing this I started my test Ubuntu and wanted to remove kexec. But it's not even installed. When typing kexec Ubuntu suggest to install the kexec-tools. So kexec can not be the explanation.

    Once grub4dos has been loaded, it's not executing inside the Linux environment, it is executing in it's own environment [A boot loader is such a task that you can't really use any OS anyways, so the boot-loader has to understand some basics in itself, and not rely on the OS to solve those things - grub for example has complete filesystem support to read from the disk in various types of filessystems, such as the more popular Linux and Windows filesystems].
    I wasn't talking about the bootmanager part. Only about the service tool bootlace.com which is a tool to write the bootcode into MBR AFTER an operating system such as Linux or DOS has been started.

    Writing code for either of the above examples is relying on "you either put a layer in to translate, or you make the function yourself", which is not really "working on several OS's" as such.
    Well, dunno how to call it. In the end I want an exe with the ability to run on the major operating systems I've mentioned here.

    bootlace.com is a good model because Linux and DOS are very different and it can install the bootcode into MBR with the same tool (very probable that very different system calls are needed).

  10. #10
    C++まいる!Cをこわせ!
    Join Date
    Oct 2007
    Location
    Inside my computer
    Posts
    24,654
    Quote Originally Posted by sept View Post
    Before I thought NT and DOS are pretty much different.
    Of course, but they are.
    But AFAIK, Windows executables also contain a little stub of DOS code to prevent them from executing from DOS.
    The rest of the executable format is totally different from DOS.
    Quote Originally Posted by Adak View Post
    io.h certainly IS included in some modern compilers. It is no longer part of the standard for C, but it is nevertheless, included in the very latest Pelles C versions.
    Quote Originally Posted by Salem View Post
    You mean it's included as a crutch to help ancient programmers limp along without them having to relearn too much.

    Outside of your DOS world, your header file is meaningless.

  11. #11
    Registered User
    Join Date
    Jul 2007
    Posts
    88
    Quote Originally Posted by Elysia View Post
    Of course, but they are.
    But AFAIK, Windows executables also contain a little stub of DOS code to prevent them from executing from DOS.
    The usual "this program can not be run in DOS mode".

  12. #12
    Algorithm Dissector iMalc's Avatar
    Join Date
    Dec 2005
    Location
    New Zealand
    Posts
    6,318
    If it were possible then everyone would be doing it already. That's all you need to know.
    My homepage
    Advice: Take only as directed - If symptoms persist, please see your debugger

    Linus Torvalds: "But it clearly is the only right way. The fact that everybody else does it some other way only means that they are wrong"

  13. #13
    and the hat of sweating
    Join Date
    Aug 2007
    Location
    Toronto, ON
    Posts
    3,545
    Quote Originally Posted by sept View Post
    I ask this because I learned the ability to compile an exe to run on more then one operating system at the same time. Imho it's pretty cool.
    It's called Java.

    Quote Originally Posted by sept View Post
    Do you know a common way to detect the operating system at runtime (not compile time)?
    Yes, call the appropriate OS API function, which is different on every OS.

  14. #14
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    And looking at bootlace.com, it seems to be an ELF executable for Linux. It probably just happens to also have a suitable piece of code to work as a DOS executable - after all, a .com file is just a binary file with no "markings", so ANY file can be made into a .com file - write "aaaaaa" into a text file, rename it to ".com", and you can execute it. It won't do anything meaningful, and it will probably crash, but the OS will accept it as an executable file.

    If circumstances are right, then the first "instruction" in bootlace will be executable. In this case, it's 7F 45, which translates to JG (JNLE). I don't know for sure, but I expect that to be true when a .com file starts, so it will jump 41 hex bytes forward. Then it sets up an environment which resembles Linux [sufficiently to do the work of writing one sector to the hard-disk - and it may not even do it in Linux style at all, I can't find the source, but it wouldn't be hard to use BIOS calls from the DOS-side, and use Linux code when running under Linux.

    But this is not your average programming type things - it's tricky stuff to solve particularly tricky situations.

    As to the executable files for Windows and DOS: You _CAN_ if you like replace the stub with your own executable by /STUB:filename when linking your executable (that is, if you are using MS tools).

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  15. #15
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by cpjust View Post
    Yes, call the appropriate OS API function, which is different on every OS.
    This is obviously said in jest, since how do you find out which OS it is BEFORE you call the OS-specific function. There is no way to set up a signal handler to handle the "bad system call" or "invalid instruction" or whatever happens when you try to call a Linux system call on Windows or vice versa. Now, if we use tricks like the bootlace above, it is POSSIBLE to set a flag somewhere in a known good memory location [.com files are modifiable after loading - otherwise you couldn't use initialized arrays], and then from that know whether it was started one way or the other.

    Likewise, replacing certain parts of Windows API with your own API is entirely possible - it's hard work, but possible.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. What is a Microsoft Operating System Like?
    By Troll_King in forum A Brief History of Cprogramming.com
    Replies: 35
    Last Post: 10-21-2002, 07:36 AM
  2. Operating system
    By sopranosomega in forum C Programming
    Replies: 6
    Last Post: 10-07-2002, 06:12 AM
  3. What operating system are YOU useing?
    By RoD in forum A Brief History of Cprogramming.com
    Replies: 36
    Last Post: 09-14-2002, 10:02 AM
  4. My favourite operating system
    By techie in forum A Brief History of Cprogramming.com
    Replies: 15
    Last Post: 07-19-2002, 06:29 AM
  5. A New Operating System
    By commanderrulz in forum A Brief History of Cprogramming.com
    Replies: 21
    Last Post: 01-24-2002, 01:36 PM