using System;
using System.Reflection;
using System.Xml.Serialization;
namespace NaGet.Packages
{
///
/// PlatformのOSの種類をあらわす
///
public enum PlatformOSType : ushort
{
WIN95 = 40,
WIN98 = 41,
WINME = 42,
WINNT4 = 140,
WIN2K = 150,
WINXP = 151,
WIN2003 = 152,
VISTA = 160,
WIN2008 = 160,
WIN7 = 161,
}
public class Platform
{
///
/// ソフトの動作するアーキテクチャ
///
[XmlAttribute]
public ProcessorArchitecture Arch = ProcessorArchitecture.X86;
///
/// 動作するOSの種類の配列
///
[XmlIgnore]
public PlatformOSType[] OsType;
///
/// OsTypeの文字列表現
///
[XmlAttribute]
public string Os {
get {
if (OsType == null) return null;
string[] strs = new string[OsType.Length];
for (int i = 0; i < OsType.Length; i++) {
strs[i] = OsType[i].ToString("G");
}
return string.Join(",", strs);
}
set {
string[] strs = (value ?? string.Empty).Split(',');
System.Collections.Generic.List list = new System.Collections.Generic.List();
for (int i = 0; i < strs.Length; i++) {
try {
list.Add((PlatformOSType) Enum.Parse(typeof(PlatformOSType), strs[i], true));
} catch (ArgumentException) {
}
}
list.Sort();
OsType = list.ToArray();
}
}
///
/// 現在のプラットホームで動くか否か?
///
/// 動く場合はtrue
public bool IsRunnable()
{
return IsRunnableArch() && IsRunnableOS();
}
///
/// 現在のマシンのアーキテクチャで動くか否か?
///
/// 動く場合はtrue
public bool IsRunnableArch()
{
return Arch == GetArch() ||
Arch == ProcessorArchitecture.None ||
Arch == ProcessorArchitecture.MSIL;
}
///
/// 現在のマシンのアーキテクチャで動かないが、Wow64で動くか否か?
/// 64ビット環境でない場合は常にfalse
///
///
public bool IsRunnableArchOnWow64()
{
if (IntPtr.Size == 8) {
return Arch == ProcessorArchitecture.X86;
} else {
return false;
}
}
///
/// 現在のマシンのアーキテクチャを得る
///
/// 現在のマシンのアーキテクチャ
public static ProcessorArchitecture GetArch()
{
Module[] moduleArray = Assembly.GetExecutingAssembly().GetModules();
Module md = moduleArray[0];
PortableExecutableKinds pekinds;
ImageFileMachine ifm;
md.GetPEKind(out pekinds, out ifm);
switch (ifm) {
case ImageFileMachine.AMD64:
return ProcessorArchitecture.Amd64;
case ImageFileMachine.I386:
return (IntPtr.Size == 4)? ProcessorArchitecture.X86 : ProcessorArchitecture.Amd64;
case ImageFileMachine.IA64:
return ProcessorArchitecture.IA64;
default:
return ProcessorArchitecture.None;
}
}
///
/// 現在のマシンのアーキテクチャを得る
///
/// 現在のマシンのアーキテクチャ
public bool IsRunnableOS()
{
if (OsType == null || OsType.Length <= 0) {
return true; // 記述なしはOS全部で動く扱い
}
PlatformOSType? thisOs = GetOSType();
return thisOs != null && Array.BinarySearch(OsType, (PlatformOSType) thisOs) >= 0;
}
///
/// 現在のマシンのOSを得る
///
/// 現在のマシンのOS
public static PlatformOSType? GetOSType()
{
OperatingSystem os = Environment.OSVersion;
Version osVer = os.Version;
switch (os.Platform) {
case PlatformID.Win32Windows:
if (osVer.Major == 4) {
switch (osVer.Minor) {
case 4:
return PlatformOSType.WIN95;
case 10:
return PlatformOSType.WIN98;
case 99:
return PlatformOSType.WINME;
}
}
break;
case PlatformID.Win32NT:
if (osVer.Major == 4) {
return PlatformOSType.WINNT4;
} else if (osVer.Major == 5) {
switch (osVer.Minor) {
case 0:
return PlatformOSType.WIN2K;
case 1:
return PlatformOSType.WINXP;
case 2:
return PlatformOSType.WIN2003;
}
} else if (osVer.Major == 6) {
switch (osVer.Minor) {
case 0:
return PlatformOSType.VISTA;
case 1:
return PlatformOSType.WIN7;
}
}
break;
// case PlatformID.WinCE:
// return null;
// case PlatformID.Unix:
// return null;
}
return null;
}
}
}