2010-06-29 20 views
10

Me gustaría determinar si mi programa se ejecuta en una versión de Windows Server. Aparentemente, System.Environment no contiene información sobre el hecho de que Windows es una versión de servidor (no existe tal información en el OS version object).Determinar si el programa se está ejecutando en Windows Server

Sé que puedo usar SystemInformation.TerminalServerSession para verificar si mi programa se ejecuta en un escritorio remoto (vea también this question), pero esto también será cierto si el usuario simplemente está accediendo a un equipo Windows de cliente simple de forma remota.

Entonces, ¿hay alguna forma admitida de determinar si el código se está ejecutando en un servidor o en una máquina cliente? No me importa usar P/Invoke si es necesario.

Nota: No deseo buscar la cadena "Server" en el nombre del producto, ya que probablemente no funcione en algunos sistemas debido a la localización.

Respuesta

15

Gracias a los indicadores proporcionados por la respuesta de Nick, finalmente encontré lo que estaba buscando. La función IsOS(OS_ANYSERVER) hace exactamente lo que necesito. Aquí está el código de ejemplo que debería funcionar para cualquier versión del sistema operativo (incluyendo pre-Vista, ya que importamos la función IsOS por ordinal de shlwapi.dll):

class OS 
{ 
    public static bool IsWindowsServer() 
    { 
     return OS.IsOS (OS.OS_ANYSERVER); 
    } 

    const int OS_ANYSERVER = 29; 

    [DllImport("shlwapi.dll", SetLastError=true, EntryPoint="#437")] 
    private static extern bool IsOS(int os); 
} 
+1

Si Nick le dio la respuesta que solía obtener la información que necesita, entonces debe aceptar esa respuesta en lugar de la suya (la información aquí debe ser editada en su pregunta). –

+4

Bueno, Nick no proporcionó la solución IsOS. Por lo tanto, pareció más útil para otros lectores marcar mi propia respuesta como la aceptada. Le he acreditado a Nick un voto positivo. –

+1

Es una buena respuesta gracias por la ayuda. También uso siempre un sitio muy bueno cuando tengo que llamar a métodos externos: http://www.pinvoke.net/ Aquí está el método IsOS: http://www.pinvoke.net/default.aspx/shlwapi/IsOS .html – Major

5

Puede p/invocar las siguientes funciones de Win32:

GetProductInfo para Vista/Windows Server 2008+
GetVersionEx para Windows 2000+

BJ Rollison tiene un good post y sample code sobre esto en su blog.

+0

Gracias por los enlaces. Finalmente resolví el problema llamando a IsOS en su lugar. –

0

No se supone que es un conjunto de de 'Versión Helper Funciones' definido en el archivo de encabezado VersionHelpers.h de WinAPI en el ensamblado Kernel32.DLL. El que, de acuerdo con la documentación, debería funcionar para su caso es IsWindowsServer (void). La descripción es aquí:

http://msdn.microsoft.com/en-us/library/windows/desktop/dn424963%28v=vs.85%29.aspx

en C#, el código sería así (no probado):

using System.Runtime.InteropServices; 

public static class MyClass 
{ 
    [DllImport("Kernel32.dll")] 
    public static extern Boolean IsWindowsServer(); 
} 

Y luego el código de consumo sería simplemente:

bool is_it_a_server = MyClass.IsWindowsServer(); 

I' Nunca he usado ninguna de estas funciones, así que déjame saber cómo funciona ...

+1

no parece funcionar bien para mí – Sauleil

+0

Cuando uso Kernel32.dll o Ntdll.dll para DllImport, aparece un error que no puede encontrar IsWindowsServer() en esos ensamblados. – Brundle

+0

Vea la respuesta de Paul Hoepping; explica por qué 'IsWindowsServer' no se puede encontrar en' kernel32.dll'. –

1

IsWindowsServer es una función en línea en VersionHelpers.h.

Puede encontrar y leer ese archivo de encabezado en su computadora. Utiliza la función API VerifyVersionInfoW. No hay función IswindowsServer en kernel32.dll.

0

Tuve el mismo problema, aunque en scripting.

He encontrado este valor; Yo estoy consultando usando WMI:

https://msdn.microsoft.com/en-us/library/aa394239(v=vs.85).aspx 
Win32_OperatingSystem 
ProductType 
    Data type: uint32 
    Access type: Read-only 
    Additional system information. 
    Work Station (1) 
    Domain Controller (2) 
    Server (3) 

Probé esto por las siguientes versiones del sistema operativo:

  • Windows XP Professional SP3
  • Windows 7 Enterprise
  • de Windows 8.1 Pro
  • de Windows 8.1 Empresa
  • Windows 10 Pro 10.0.16299
  • Windows Server 2003 R2 Standard Edition
  • Windows Server 2003 R2 Standard Edition x64
  • Windows Server 2008 R2 Standard
  • Windows Server 2012 Datacenter
  • Windows Server 2012 R2 Datacenter

Encuentra mi ejemplo por lotes archivo a continuación.

Lucas.

for /f "tokens=2 delims==" %%a in ('wmic.exe os get producttype /value') do (
    set PRODUCT_TYPE=%%a 
) 
if %PRODUCT_TYPE%==1 set PRODUCT_TYPE=Workstation 
if %PRODUCT_TYPE%==2 set PRODUCT_TYPE=DomainController 
if %PRODUCT_TYPE%==3 set PRODUCT_TYPE=Server 
echo %COMPUTERNAME%: %PRODUCT_TYPE% 

Usted puede hacer esto en C#:

using Microsoft.Management.Infrastructure; 
... 
string Namespace = @"root\cimv2"; 
string className = "Win32_OperatingSystem"; 

CimInstance operatingSystem = new CimInstance(className, Namespace); 
Cuestiones relacionadas