Solved

Getting the OS of the pc.

Posted on 2001-07-22
23
179 Views
Last Modified: 2010-04-06
How do I know what Operating System my applications are running on?  Is there a way for this in Delphi?

Thanks!!
0
Comment
Question by:jchua
  • 7
  • 4
  • 3
  • +7
23 Comments
 
LVL 7

Assisted Solution

by:Motaz
Motaz earned 25 total points
ID: 6307314
Use  GetVersionEx API function

0
 
LVL 17

Accepted Solution

by:
inthe earned 25 total points
ID: 6307326
hi,
sure you can use GetVersionEx() api to do it,
below is most complete version ive seen (from madshi):

visit www.madshi.net and get his madbasic package for more stuff.


interface

// types for the "OS" function
type
TOsEnum = (osNone, osWin95, osWin95osr2, osWin98, osWin98se, osWinME, osWin9xNew,
osWinNtOld, osWinNt4, osWin2000, osWinNtNew);
TOS = record
major : cardinal;
minor : cardinal;
build : cardinal;
spStr : string;
win9x : boolean;
win9xEnum : osNone..osWin9xNew;
winNt : boolean;
winNtEnum : osNone..osWinNtNew;
enum : osNone..osWinNtNew;
spNo : cardinal;
end;

// Tests which system is running...
function OS : TOS;

implementation

var os_ : TOS;
osReady : boolean = false;
function OS : TOS;
var vi : TOsVersionInfo;
begin
if not osReady then begin
osReady := true;
ZeroMemory(@vi, sizeOf(TOsVersionInfo));
vi.dwOSVersionInfoSize := sizeOf(TOsVersionInfo);
GetVersionEx(vi);
with os_ do begin
major := vi.dwMajorVersion;
minor := vi.dwMinorVersion;
spStr := vi.szCSDVersion;
win9x := vi.dwPlatformId = VER_PLATFORM_WIN32_WINDOWS;
winNt := vi.dwPlatformId = VER_PLATFORM_WIN32_NT;
if win9x then build := loWord(vi.dwBuildNumber)
else build := vi.dwBuildNumber;
enum := osNone;
spNo := 0;
if win9x then begin
case major of
0..3 : ;
4 : case minor of
00..09 : if build > 1000 then enum := osWin95osr2
else enum := osWin95;
10 : if build > 2000 then enum := osWin98se
else enum := osWin98;
11..90 : enum := osWinME;
else enum := osWin9xNew;
end;
else enum := osWin9xNew;
end;
win9xEnum := enum;
winNtEnum := osNone;
end else if winNt then begin
case major of
0..3 : enum := osWinNtOld;
4 : enum := osWinNt4;
5 : enum := osWin2000;
else enum := osWinNtNew;
end;
win9xEnum := osNone;
winNtEnum := enum;
if Length(spStr) >= 14 then
spNo := StrToIntEx(false, @spStr[14], Length(spStr) - 13);
end;
end;
end;
result := os_;
end;

To test whether you're running on win9x or winNT, you can do:

if OS.win9x
if OS.winNT

To check for winME you can do:
if OS.enum = osWinME

to check for win2000 you can do:
if OS.enum = osWin2000

Or to check whether you're running on winME, win2000 or anything newer you can check:

if OS.enum in [osWinME, osWin2000, osWin9xNew, osWinNtNew]
0
 
LVL 22

Assisted Solution

by:mnasman
mnasman earned 25 total points
ID: 6307329
Hello

  Here's a function will return windows version and if there's service back (if windows nt)

function GetWinVersion: String;
var
 VerInfo: TOSVersionInfo;
 ResultStr: string;
begin
 ResultStr := '';
 VerInfo.dwOSVersionInfoSize := SizeOf(VerInfo);
 GetVersionEx(VerInfo);
 with VerInfo do
   begin
     case dwPlatformID of
       VER_PLATFORM_WIN32S: ResultStr := ResultStr + 'Windows 3.1x running Win32s ';
       VER_PLATFORM_WIN32_WINDOWS:
         begin
           if IntToStr(dwMajorVersion) + '.' + IntToStr(dwMinorVersion) < '4.10' then
             ResultStr := ResultStr + 'Windows 95 ' + szCSDVersion + ' '
           else
             ResultStr := ResultStr + 'Windows 98 ' + szCSDVersion + ' ';
         end;
       VER_PLATFORM_WIN32_NT:
         begin
           if dwMajorVersion = 5 then
             ResultStr := ResultStr + 'Windows 2000 '
           else
             ResultStr := ResultStr + 'Windows NT ';
         end;
     end;
     ResultStr := ResultStr + IntToStr(dwMajorVersion) + '.' + IntToStr(dwMinorVersion) + ' ';
     ResultStr := ResultStr + '(Build ' +  IntToStr(LoWord(dwBuildNumber)) + ') ';
     if dwPlatformID = VER_PLATFORM_WIN32_NT then
       ResultStr := ResultStr + szCSDVersion;
   end;
 Result := ResultStr;
end;


procedure TForm1.Button1Click(Sender: TObject);
begin
  ShowMessage(GetWinVersion);
end;

Best regards
Mohammed Nasman
0
 
LVL 11

Assisted Solution

by:robert_marquardt
robert_marquardt earned 25 total points
ID: 6307337
Madshi's version does not check for "Setup.exe" on ME.
ME fakes a Win98 if the program is named "Setup.exe".
0
 
LVL 5

Expert Comment

by:Gwena
ID: 6307343
Listening :-)
0
 
LVL 7

Expert Comment

by:Motaz
ID: 6307349
I write this example for you:

procedure TForm1.Button1Click(Sender: TObject);
const Plateforms: array [0 .. 2] of string[12] = ('Win 3.1', 'Win 95', 'Win NT');
var
  Info: _OSVERSIONINFO;

begin
  info.dwOSVersionInfoSize:= SizeOf(Info);
  GetVersionEx(Info);
  Memo1.Lines.Add('Plateform: ' + Plateforms[Info.dwPlatformId]);
  Memo1.Lines.Add('Major Version: ' + IntToStr(Info.dwMajorVersion));
  Memo1.Lines.Add('Minor Version: ' + IntToStr(Info.dwMinorVersion));
  Memo1.Lines.Add('Builder number: ' + IntToStr(Info.dwBuildNumber));
  Memo1.Lines.Add('Information : ' + Info.szCSDVersion);
end;

Motaz
0
 
LVL 17

Expert Comment

by:inthe
ID: 6307351
hi robert,

what program ,the executable containing getversionex?
thats a strange one ,do you know why ?
Regards Barry
0
 
LVL 20

Expert Comment

by:Madshi
ID: 6307400
Hi guys...  :-)

Thanx Barry...

Robert, I didn't know that. Could you tell me more about the problem? Is there an official way to come around that? Or do we have to do ugly things again?

Regards, Madshi.
0
 
LVL 11

Expert Comment

by:robert_marquardt
ID: 6307408
inthe, yes.

Here is the current workaround of the Jedi Code Library.
It seems a compatibility trick of WinME to make older Game CDs install on WinME. Maybe even some older Microsoft CDs fail. AFAIK it is not documented.

function GetWindowsVersion: TWindowsVersion;
begin
  Result := wvUnknown;
  case Win32Platform of
    VER_PLATFORM_WIN32_WINDOWS:
      case Win32MinorVersion of
        0..9:
          if Trim(Win32CSDVersion) = 'B' then
            Result := wvWin95OSR2
          else
            Result := wvWin95;
        10..89:
          // On Windows ME Win32MinorVersion can be 10 (indicating Windows 98
          // under certain circumstances (image name is setup.exe). Checking
          // the kernel version is one way of working around that.
          if KernelVersionHi = $0004005A then // 4.90.x.x
            Result := wvWinME
          else if Trim(Win32CSDVersion) = 'A' then
            Result := wvWin98SE
          else
            Result := wvWin98;
        90:
          Result := wvWinME;
      end;
    VER_PLATFORM_WIN32_NT:
      case Win32MajorVersion of
        3:
          Result := wvWinNT3;
        4:
          Result := wvWinNT4;
        5:
          Result := wvWin2000;
      end;
  end;
end;
0
 
LVL 20

Expert Comment

by:Madshi
ID: 6307412
Thanx Robert for the hint, I'll add that fix in my stuff. I think I should check winXP again, maybe there's such a thing, too...
0
 
LVL 17

Expert Comment

by:inthe
ID: 6307449
thanks also,
or if your function returns win98 then can also doublecheck by reading Productname and versionnumber from registry under SOFTWARE\Microsoft\Windows\CurrentVersion and check if are "MICROSOFT WINDOWS ME" or 4.9 ..
a quick search on google revealed this is causing problems for hundreds of people ,and as rob said it's not documented anywhere officially.
0
Maximize Your Threat Intelligence Reporting

Reporting is one of the most important and least talked about aspects of a world-class threat intelligence program. Here’s how to do it right.

 
LVL 20

Expert Comment

by:Madshi
ID: 6307459
Hmmm... I checked it, Robert is right. If your exe is called "setup.exe", GetVersionEx returns minor 10, which is Windows98SE. It doesn't happen for "install.exe", only for "setup.exe".

But I've found a different solution for the problem, which I like better than to check the kernel version: The build number! This number grows independently from the minor number. E.g. for win95 it is < 1000, for win95osr2 it is > 1000. For win98se it's 2222, for winME it's 3000. And it's the same, regardless whether the exe is called "setup.exe" or not. So my solution looks like this:

case minor of
  00..09 : if      build > 1000 then enum := osWin95osr2
           else                      enum := osWin95;
  10     : if      build > 2700 then enum := osWinME
           else if build > 2000 then enum := osWin98se
           else                      enum := osWin98;
  11..90 : enum := osWinME;
  else     enum := osWin9xNew;
end;

Has someone Windows2000 running? Or even XP? My NT based partitions are all broken in the moment. Could someone check the version info for "setup.exe" in these systems? Would be great...

Regards, Madshi.
0
 
LVL 20

Expert Comment

by:Madshi
ID: 6307469
P.S: If anyone is interested, here comes the part for detecting XP:

case major of
  0..3 : enum := osWinNtOld;
  4    : enum := osWinNt4;
  5    : case minor of
           0  : enum := osWin2k;
           1  : enum := osWinXP
           else enum := osWinNtNew;
         end;
  else   enum := osWinNtNew;
end;

Interesting, for Microsoft win2000 is NT5 and winXP is only something like NT5.1.
0
 
LVL 17

Expert Comment

by:geobul
ID: 6307513
To Madshi:
My Win2000 reports Minor = 0 and Major = 5 for both setup.exe and other name. Is that what you wanted to be checked?

Regards, Geo
0
 
LVL 20

Expert Comment

by:Madshi
ID: 6307529
Great! Thank you very much, Geo!  :-)  So it seems that winME is the only system with such a "compatibility" mode for "setup.exe". Well, don't know about XP right now, will check that later...
0
 
LVL 11

Expert Comment

by:robert_marquardt
ID: 6307551
Madshi, can we use your code in the JCL?
0
 
LVL 14

Expert Comment

by:DragonSlayer
ID: 6307627
how can we differentiate the diff. versions of an operating system? i.e. Win2k Pro Edition, Server Edition, and the upcoming WinXP which will have several editions?
0
 
LVL 20

Expert Comment

by:Madshi
ID: 6307915
Hi Robert, do you mean only the few "build" and XP lines? Or do you mean my whole OS type & function? Both is okay for me. If you want to use the whole type & function, a one-line comment pointing to my homepage would be nice. If you only want to use the few lines, just copy them without a comment.

Hi DragonSlayer, to be honest: I don't know. I would have to install both editions in order to test that. Don't they only differ by the number of available services? I don't know whether the version info is not exactly the same?

Regards, Madshi.
0
 
LVL 14

Expert Comment

by:DragonSlayer
ID: 6307971
Madshi,

Umm... I don't know... but I suppose for WinNT they only differ by the tools (or services as you'd put them)... not sure about Win2k and XP.

But what if I want to enable an application to only be run in Win2k Server Ed.? Well, not that I really want to do that... it's just as an example.

Also, there's the 64-bit version of XP...
0
 
LVL 20

Expert Comment

by:Madshi
ID: 6308145
>> But what if I want to enable an application to only be run in Win2k Server Ed.?

Yeah, no question that it would make sense to know on which edition you run, I just don't know how to solve that in the moment.
0
 
LVL 11

Expert Comment

by:robert_marquardt
ID: 6308286
I recall that WinNT 4.0 Workstation vs Server was only two registry keys which were monitored by a system thread to prevent changes (not counting the server tools).

The trick to change a worstation to a server was to patch the key names in a kernel copy so that the thread monitored the wrong keys. Then do a restart with the new kernel, change the keys and restart to the original kernel.
The monitoring did not check the keys itself. It only prevented key changes.
0
 
LVL 1

Expert Comment

by:Madmarlin
ID: 6321817

I thought it was stored in the registry..
Sorry cant fin specific path at present..
0
 
LVL 26

Expert Comment

by:Russell Libby
ID: 8711351
No comment has been added lately, so it's time to clean up this TA.
I will leave a recommendation in the Cleanup topic area that this question is:

To split between motaz, inthe, madshi, mnasman and robert_marquardt

Please leave any comments here within the next seven days.
 
PLEASE DO NOT ACCEPT THIS COMMENT AS AN ANSWER!
 
Thank you,
Russell

EE Cleanup Volunteer
0

Featured Post

Do You Know the 4 Main Threat Actor Types?

Do you know the main threat actor types? Most attackers fall into one of four categories, each with their own favored tactics, techniques, and procedures.

Join & Write a Comment

Suggested Solutions

This article explains how to create forms/units independent of other forms/units object names in a delphi project. Have you ever created a form for user input in a Delphi project and then had the need to have that same form in a other Delphi proj…
In my programming career I have only very rarely run into situations where operator overloading would be of any use in my work.  Normally those situations involved math with either overly large numbers (hundreds of thousands of digits or accuracy re…
In this seventh video of the Xpdf series, we discuss and demonstrate the PDFfonts utility, which lists all the fonts used in a PDF file. It does this via a command line interface, making it suitable for use in programs, scripts, batch files — any pl…
Get a first impression of how PRTG looks and learn how it works.   This video is a short introduction to PRTG, as an initial overview or as a quick start for new PRTG users.

706 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

13 Experts available now in Live!

Get 1:1 Help Now