You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by da...@apache.org on 2014/07/28 17:31:14 UTC

[1/3] CLOUDSTACK-6504: removed warnings coming in building hyper-v agent code

Repository: cloudstack
Updated Branches:
  refs/heads/4.4 48f9453a7 -> 8fb89cdc8


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/8fb89cdc/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/Utils.cs
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/Utils.cs b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/Utils.cs
index 07dd78b..b40cb8f 100644
--- a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/Utils.cs
+++ b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/Utils.cs
@@ -1,4 +1,4 @@
-// Licensed to the Apache Software Foundation (ASF) under one
+// Licensed to the Apache Software Foundation (ASF) under one
 // or more contributor license agreements.  See the NOTICE file
 // distributed with this work for additional information
 // regarding copyright ownership.  The ASF licenses this file
@@ -88,7 +88,7 @@ namespace HypervResource
             {
                 IntPtr token = IntPtr.Zero;
 
-                bool isSuccess = LogonUser(cifsShareDetails.User, cifsShareDetails.Domain, cifsShareDetails.Password, LOGON32_LOGON_NEW_CREDENTIALS, LOGON32_PROVIDER_DEFAULT, ref token);
+                LogonUser(cifsShareDetails.User, cifsShareDetails.Domain, cifsShareDetails.Password, LOGON32_LOGON_NEW_CREDENTIALS, LOGON32_PROVIDER_DEFAULT, ref token);
                 using (WindowsImpersonationContext remoteIdentity = new WindowsIdentity(token).Impersonate())
                 {
                     String dest = "";

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/8fb89cdc/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/WmiCallsV2.cs
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/WmiCallsV2.cs b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/WmiCallsV2.cs
index 0214ad8..104ee2d 100644
--- a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/WmiCallsV2.cs
+++ b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/WmiCallsV2.cs
@@ -267,186 +267,180 @@ namespace HypervResource
                 else
                 {
                     errMsg = string.Format("Create VM failing, because there exists a VM with name {0}, state {1}",
-                        vmName,
-                        EnabledState.ToString(vmWmiObj.EnabledState));
-                    var ex = new WmiException(errMsg);
-                    logger.Error(errMsg, ex);
-                    throw ex;
-                }
-            }
-
-            // Create vm carcase
-            logger.DebugFormat("Going ahead with create VM {0}, {1} vcpus, {2}MB RAM", vmName, vcpus, memSize);
-            var newVm = CreateVM(vmName, memSize, vcpus);
-
-            // Add a SCSI controller for attaching/detaching data volumes.
-            AddScsiController(newVm);
-
-            foreach (var diskDrive in diskDrives)
-            {
-                string vhdFile = null;
-                string diskName = null;
-                string isoPath = null;
-                VolumeObjectTO volInfo = VolumeObjectTO.ParseJson(diskDrive.data);
-                TemplateObjectTO templateInfo = TemplateObjectTO.ParseJson(diskDrive.data);
-
-                if (volInfo != null)
-                {
-                    // assert
-                    errMsg = vmName + ": volume missing primaryDataStore for disk " + diskDrive.ToString();
-                    if (volInfo.primaryDataStore == null)
-                    {
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-                    diskName = volInfo.name;
-
-                    // assert
-                    errMsg = vmName + ": can't deal with DataStore type for disk " + diskDrive.ToString();
-                    if (volInfo.primaryDataStore == null)
-                    {
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-                    errMsg = vmName + ": Malformed PrimaryDataStore for disk " + diskDrive.ToString();
-                    if (String.IsNullOrEmpty(volInfo.primaryDataStore.Path))
-                    {
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-                    errMsg = vmName + ": Missing folder PrimaryDataStore for disk " + diskDrive.ToString() + ", missing path: " +  volInfo.primaryDataStore.Path;
-                    if (!Directory.Exists(volInfo.primaryDataStore.Path))
-                    {
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-
-                    vhdFile = volInfo.FullFileName;
-                    if (!System.IO.File.Exists(vhdFile))
-                    {
-                        errMsg = vmName + ": non-existent volume, missing " + vhdFile + " for drive " + diskDrive.ToString();
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-                    logger.Debug("Going to create " + vmName + " with attached voluem " + diskName + " at " + vhdFile);
-                }
-                else if (templateInfo != null && templateInfo.nfsDataStoreTO != null)
-                {
-                    NFSTO share = templateInfo.nfsDataStoreTO;
-                    // The share is mapped, now attach the iso
-                    isoPath = Utils.NormalizePath(Path.Combine(share.UncPath, templateInfo.path));
-                }
-
-                string driveType = diskDrive.type;
-                string ideCtrllr = "0";
-                string driveResourceType = null;
-                switch (driveType) {
-                    case "ROOT":
-                        ideCtrllr = "0";
-                        driveResourceType = HARDDISK_DRIVE;
-                        break;
-                    case "ISO":
-                        ideCtrllr = "1";
-                        driveResourceType = ISO_DRIVE;
-                        break;
-                    case "DATADISK":
-                        break;
-                    default: 
-                        // TODO: double check exception type
-                        errMsg = string.Format("Unknown disk type {0} for disk {1}, vm named {2}", 
-                                string.IsNullOrEmpty(driveType) ? "NULL" : driveType,
-                                string.IsNullOrEmpty(diskName) ? "NULL" : diskName, vmName);
-                        var ex = new WmiException(errMsg);
-                        logger.Error(errMsg, ex);
-                        throw ex;
-                }
-
-                logger.DebugFormat("Create disk type {1} (Named: {0}), on vm {2} {3}", diskName, driveResourceType, vmName,
-                        string.IsNullOrEmpty(vhdFile) ? " no disk to insert" : ", inserting disk" + vhdFile);
-                if (driveType.Equals("DATADISK"))
-                {
-                    AttachDisk(vmName, vhdFile, (string)diskDrive.diskSeq);
-                }
-                else
-                {
-                    AddDiskDriveToIdeController(newVm, vhdFile, ideCtrllr, driveResourceType);
-                    if (isoPath != null)
-                    {
-                        AttachIso(vmName, isoPath);
-                    }
-                }
-            }
-
-            String publicIpAddress = "";
-            int nicCount = 0;
-            int enableState = 2;
-
-            // Add the Nics to the VM in the deviceId order.
-            foreach (var nc in nicInfo)
-            {
-                foreach (var nic in nicInfo)
-                {
-
-                    int nicid = nic.deviceId;
+                        vmName,
+                        EnabledState.ToString(vmWmiObj.EnabledState));
+                    var ex = new WmiException(errMsg);
+                    logger.Error(errMsg, ex);
+                    throw ex;
+                }
+            }
+
+            // Create vm carcase
+            logger.DebugFormat("Going ahead with create VM {0}, {1} vcpus, {2}MB RAM", vmName, vcpus, memSize);
+            var newVm = CreateVM(vmName, memSize, vcpus);
+
+            // Add a SCSI controller for attaching/detaching data volumes.
+            AddScsiController(newVm);
+
+            foreach (var diskDrive in diskDrives)
+            {
+                string vhdFile = null;
+                string diskName = null;
+                string isoPath = null;
+                VolumeObjectTO volInfo = VolumeObjectTO.ParseJson(diskDrive.data);
+                TemplateObjectTO templateInfo = TemplateObjectTO.ParseJson(diskDrive.data);
+
+                if (volInfo != null)
+                {
+                    // assert
+                    errMsg = vmName + ": volume missing primaryDataStore for disk " + diskDrive.ToString();
+                    if (volInfo.primaryDataStore == null)
+                    {
+                        logger.Error(errMsg);
+                        throw new ArgumentException(errMsg);
+                    }
+                    diskName = volInfo.name;
+
+                    // assert
+                    errMsg = vmName + ": can't deal with DataStore type for disk " + diskDrive.ToString();
+                    if (volInfo.primaryDataStore == null)
+                    {
+                        logger.Error(errMsg);
+                        throw new ArgumentException(errMsg);
+                    }
+                    errMsg = vmName + ": Malformed PrimaryDataStore for disk " + diskDrive.ToString();
+                    if (String.IsNullOrEmpty(volInfo.primaryDataStore.Path))
+                    {
+                        logger.Error(errMsg);
+                        throw new ArgumentException(errMsg);
+                    }
+                    errMsg = vmName + ": Missing folder PrimaryDataStore for disk " + diskDrive.ToString() + ", missing path: " +  volInfo.primaryDataStore.Path;
+                    if (!Directory.Exists(volInfo.primaryDataStore.Path))
+                    {
+                        logger.Error(errMsg);
+                        throw new ArgumentException(errMsg);
+                    }
+
+                    vhdFile = volInfo.FullFileName;
+                    if (!System.IO.File.Exists(vhdFile))
+                    {
+                        errMsg = vmName + ": non-existent volume, missing " + vhdFile + " for drive " + diskDrive.ToString();
+                        logger.Error(errMsg);
+                        throw new ArgumentException(errMsg);
+                    }
+                    logger.Debug("Going to create " + vmName + " with attached voluem " + diskName + " at " + vhdFile);
+                }
+                else if (templateInfo != null && templateInfo.nfsDataStoreTO != null)
+                {
+                    NFSTO share = templateInfo.nfsDataStoreTO;
+                    Utils.ConnectToRemote(share.UncPath, share.Domain, share.User, share.Password);
+                    // The share is mapped, now attach the iso
+                    isoPath = Utils.NormalizePath(Path.Combine(share.UncPath, templateInfo.path));
+                }
+
+                string driveType = diskDrive.type;
+                string ideCtrllr = "0";
+                string driveResourceType = null;
+                switch (driveType) {
+                    case "ROOT":
+                        ideCtrllr = "0";
+                        driveResourceType = HARDDISK_DRIVE;
+                        break;
+                    case "ISO":
+                        ideCtrllr = "1";
+                        driveResourceType = ISO_DRIVE;
+                        break;
+                    case "DATADISK":
+                        break;
+                    default: 
+                        // TODO: double check exception type
+                        errMsg = string.Format("Unknown disk type {0} for disk {1}, vm named {2}", 
+                                string.IsNullOrEmpty(driveType) ? "NULL" : driveType,
+                                string.IsNullOrEmpty(diskName) ? "NULL" : diskName, vmName);
+                        var ex = new WmiException(errMsg);
+                        logger.Error(errMsg, ex);
+                        throw ex;
+                }
+
+                logger.DebugFormat("Create disk type {1} (Named: {0}), on vm {2} {3}", diskName, driveResourceType, vmName,
+                        string.IsNullOrEmpty(vhdFile) ? " no disk to insert" : ", inserting disk" + vhdFile);
+                if (driveType.Equals("DATADISK"))
+                {
+                    AttachDisk(vmName, vhdFile, (string)diskDrive.diskSeq);
+                }
+                else
+                {
+                    AddDiskDriveToIdeController(newVm, vhdFile, ideCtrllr, driveResourceType);
+                    if (isoPath != null)
+                    {
+                        AttachIso(vmName, isoPath);
+                    }
+                }
+            }
+
+            int nicCount = 0;
+            // Add the Nics to the VM in the deviceId order.
+            foreach (var nc in nicInfo)
+            {
+                foreach (var nic in nicInfo)
+                {
+
+                    int nicid = nic.deviceId;
                     Int32 networkRateMbps = nic.networkRateMbps;
-                    string mac = nic.mac;
-                    string vlan = null;
-                    string isolationUri = nic.isolationUri;
-                    string broadcastUri = nic.broadcastUri;
+                    string mac = nic.mac;
+                    string vlan = null;
+                    string isolationUri = nic.isolationUri;
+                    string broadcastUri = nic.broadcastUri;
                     string nicIp = nic.ip;
                     string nicNetmask = nic.netmask;
-                    if ( (broadcastUri != null ) || (isolationUri != null && isolationUri.StartsWith("vlan://")))
-                    {
-                        if (broadcastUri != null && broadcastUri.StartsWith("storage"))
-                        {
-                            vlan = broadcastUri.Substring("storage://".Length);
-                        }
-                        else
-                        {
-                            vlan = isolationUri.Substring("vlan://".Length);
-                        }
-                        int tmp;
+                    if ( (broadcastUri != null ) || (isolationUri != null && isolationUri.StartsWith("vlan://")))
+                    {
+                        if (broadcastUri != null && broadcastUri.StartsWith("storage"))
+                        {
+                            vlan = broadcastUri.Substring("storage://".Length);
+                        }
+                        else
+                        {
+                            vlan = isolationUri.Substring("vlan://".Length);
+                        }
+                        int tmp;
                         if (vlan.Equals("untagged", StringComparison.CurrentCultureIgnoreCase) ) {
                             // recevied vlan is untagged, don't parse for the vlan in the isolation uri
                             vlan = null;
                         }
-                        else if (!int.TryParse(vlan, out tmp))
-                        {
-                            // TODO: double check exception type
-                            errMsg = string.Format("Invalid VLAN value {0} for on vm {1} for nic uuid {2}", isolationUri, vmName, nic.uuid);
-                            var ex = new WmiException(errMsg);
-                            logger.Error(errMsg, ex);
-                            throw ex;
-                        }
+                        else if (!int.TryParse(vlan, out tmp))
+                        {
+                            // TODO: double check exception type
+                            errMsg = string.Format("Invalid VLAN value {0} for on vm {1} for nic uuid {2}", isolationUri, vmName, nic.uuid);
+                            var ex = new WmiException(errMsg);
+                            logger.Error(errMsg, ex);
+                            throw ex;
+                        }
+                    }
+                    if(nicIp.Equals("0.0.0.0") && nicNetmask.Equals("255.255.255.255") ) {
+                        // this is the extra nic added to VR.
+                        vlan = defaultvlan;
                     }
-
-                    if (nicid == nicCount)
-                    {
-                        if (nicIp.Equals("0.0.0.0") && nicNetmask.Equals("255.255.255.255"))
-                        {
-                            // this is the extra nic added to VR.
-                            vlan = null;
-                            enableState = 3;
-                        }
-
-                        // Create network adapter
-                        var newAdapter = CreateNICforVm(newVm, mac);
-                        String switchName ="";
-                        if (nic.name != null)
-                        {
-                            switchName =  nic.name;
-                        }
-                        EthernetPortAllocationSettingData portSettings = null;
-                        // connection to vswitch
-                        portSettings = AttachNicToPort(newVm, newAdapter, switchName, enableState);
-                        //reset the flag for other nics
-                        enableState = 2;
-                        // set vlan
-                        if (vlan != null)
-                        {
-                            SetPortVlan(vlan, portSettings);
-                        }
-
+
+                    if (nicid == nicCount)
+                    {
+                        // Create network adapter
+                        var newAdapter = CreateNICforVm(newVm, mac);
+                        String switchName ="";
+                        if (nic.name != null)
+                        {
+                            switchName =  nic.name;
+                        }
+
+                        // connection to vswitch
+                        var portSettings = AttachNicToPort(newVm, newAdapter, switchName);
+
+                        // set vlan
+                        if (vlan != null)
+                        {
+                            SetPortVlan(vlan, portSettings);
+                        }
+
                         if (networkRateMbps > 0)
                         {
                             SetBandWidthLimit((ulong)networkRateMbps, portSettings);
@@ -486,147 +480,574 @@ namespace HypervResource
             SetState(newVm, RequiredState.Enabled);
             // Mark the VM as created by cloudstack tag
             TagVm(newVm);
-
-            // we need to reboot to get the hv kvp daemon get started vr gets configured.
-            if (vmName.StartsWith("r-") || vmName.StartsWith("s-") || vmName.StartsWith("v-"))
-            {
-                System.Threading.Thread.Sleep(90000);
-                // wait for the second boot and then return with sucesss
-                //if publicIPAddress is empty or null don't ping the ip
-              /*if (publicIpAddress.Equals("") == true)
-                {
-                    System.Threading.Thread.Sleep(90000);
-                }
-                else
-                {
-                    pingResource(publicIpAddress);
-                }*/
-            }
-            logger.InfoFormat("Started VM {0}", vmName);
-            return newVm;
-        }
-
-        public static Boolean pingResource(String ip)
-        {
-            PingOptions pingOptions = null;
-            PingReply pingReply = null;
-            IPAddress ipAddress = null;
-            Ping pingSender = new Ping();
-            int numberOfPings = 6;
-            int pingTimeout = 1000;
-            int byteSize = 32;
-            byte[] buffer = new byte[byteSize];
-            ipAddress = IPAddress.Parse(ip);
-            pingOptions = new PingOptions();
-            for (int i = 0; i < numberOfPings; i++)
-            {
-                pingReply = pingSender.Send(ipAddress, pingTimeout, buffer, pingOptions);
-                if (pingReply.Status == IPStatus.Success)
-                {
-                    System.Threading.Thread.Sleep(30000);
-                    return true;
-                }
-                else
-                {
-                    // wait for the second boot and then return with suces
-                    System.Threading.Thread.Sleep(30000);
-                }
-            }
-            return false;
-        }
-
-        private EthernetPortAllocationSettingData AttachNicToPort(ComputerSystem newVm, SyntheticEthernetPortSettingData newAdapter, String vSwitchName, int enableState)
-        {
-            // Get the virtual switch
-            VirtualEthernetSwitch vSwitch = GetExternalVirtSwitch(vSwitchName);
-            //check the the recevied vSwitch is the same as vSwitchName.
-            if (!vSwitchName.Equals("")  && !vSwitch.ElementName.Equals(vSwitchName))
-            {
-               var errMsg = string.Format("Internal error, coudl not find Virtual Switch with the name : " +vSwitchName);
-               var ex = new WmiException(errMsg);
-               logger.Error(errMsg, ex);
-               throw ex;
-            }
-
-            // Create port for adapter
-            var defaultEthernetPortSettings = EthernetPortAllocationSettingData.GetInstances(vSwitch.Scope, "InstanceID LIKE \"%Default\"");
-
-            // assert
-            if (defaultEthernetPortSettings.Count != 1)
-            {
-                var errMsg = string.Format("Internal error, coudl not find default EthernetPortAllocationSettingData instance");
-                var ex = new WmiException(errMsg);
-                logger.Error(errMsg, ex);
-                throw ex;
-            }
-
-            var defaultEthernetPortSettingsObj = defaultEthernetPortSettings.OfType<EthernetPortAllocationSettingData>().First();
-            var newEthernetPortSettings = new EthernetPortAllocationSettingData((ManagementBaseObject)defaultEthernetPortSettingsObj.LateBoundObject.Clone());
-            newEthernetPortSettings.LateBoundObject["Parent"] = newAdapter.Path.Path;
-            newEthernetPortSettings.LateBoundObject["HostResource"] = new string[] { vSwitch.Path.Path };
-            newEthernetPortSettings.LateBoundObject["EnabledState"] = enableState; //3 disabled 2 Enabled
-            // Insert NIC into vm
-            string[] newResources = new string[] { newEthernetPortSettings.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20) };
-            ManagementPath[] newResourcePaths = AddVirtualResource(newResources, newVm);
-
-            // assert
-            if (newResourcePaths.Length != 1)
-            {
-                var errMsg = string.Format(
-                    "Failed to properly insert a single NIC on VM {0} (GUID {1}): number of resource created {2}",
-                    newVm.ElementName,
-                    newVm.Name,
-                    newResourcePaths.Length);
-                var ex = new WmiException(errMsg);
-                logger.Error(errMsg, ex);
-                throw ex;
-            }
-
-            return new EthernetPortAllocationSettingData(newResourcePaths[0]);
-        }
-
-        /// this method is to add a dvd drive and attach the systemvm iso.
-        /// 
-        public void patchSystemVmIso(String vmName, String systemVmIso)
-        {
-            ComputerSystem vmObject = GetComputerSystem(vmName);
-            AddDiskDriveToIdeController(vmObject, "", "1", ISO_DRIVE);
-            AttachIso(vmName, systemVmIso);
-        }
-
-        public void AttachDisk(string vmName, string diskPath, string addressOnController)
-        {
-            logger.DebugFormat("Got request to attach disk {0} to vm {1}", diskPath, vmName);
-
-            ComputerSystem vm = GetComputerSystem(vmName);
-            if (vm == null)
-            {
-                logger.DebugFormat("VM {0} not found", vmName);
-                return;
-            }
-            else
-            {
-                ManagementPath newDrivePath = GetDiskDriveOnScsiController(vm, addressOnController);
-                if (newDrivePath == null)
-                {
-                    newDrivePath = AttachDiskDriveToScsiController(vm, addressOnController);
-                }
-                InsertDiskImage(vm, diskPath, HARDDISK_DISK, newDrivePath);
-            }
-        }
-
-        /// </summary>
-        /// <param name="vm"></param>
-        /// <param name="cntrllerAddr"></param>
-        /// <param name="driveResourceType">IDE_HARDDISK_DRIVE or IDE_ISO_DRIVE</param>
-        public ManagementPath AddDiskDriveToIdeController(ComputerSystem vm, string vhdfile, string cntrllerAddr, string driveResourceType)
-        {
-            logger.DebugFormat("Creating DISK for VM {0} (GUID {1}) by attaching {2}", 
-                        vm.ElementName,
-                        vm.Name,
-                        vhdfile);
-
-            // Determine disk type for drive and assert drive type valid
+
+            // we need to reboot to get the hv kvp daemon get started vr gets configured.
+            if (vmName.StartsWith("r-") || vmName.StartsWith("s-") || vmName.StartsWith("v-"))
+            {
+                System.Threading.Thread.Sleep(90000);
+            }
+            logger.InfoFormat("Started VM {0}", vmName);
+            return newVm;
+        }
+
+        public static Boolean pingResource(String ip)
+        {
+            PingOptions pingOptions = null;
+            PingReply pingReply = null;
+            IPAddress ipAddress = null;
+            Ping pingSender = new Ping();
+            int numberOfPings = 6;
+            int pingTimeout = 1000;
+            int byteSize = 32;
+            byte[] buffer = new byte[byteSize];
+            ipAddress = IPAddress.Parse(ip);
+            pingOptions = new PingOptions();
+            for (int i = 0; i < numberOfPings; i++)
+            {
+                pingReply = pingSender.Send(ipAddress, pingTimeout, buffer, pingOptions);
+                if (pingReply.Status == IPStatus.Success)
+                {
+                    System.Threading.Thread.Sleep(30000);
+                    return true;
+                }
+                else
+                {
+                    // wait for the second boot and then return with suces
+                    System.Threading.Thread.Sleep(30000);
+                }
+            }
+            return false;
+        }
+
+        private EthernetPortAllocationSettingData AttachNicToPort(ComputerSystem newVm, SyntheticEthernetPortSettingData newAdapter, String vSwitchName)
+        {
+            // Get the virtual switch
+            VirtualEthernetSwitch vSwitch = GetExternalVirtSwitch(vSwitchName);
+            //check the the recevied vSwitch is the same as vSwitchName.
+            if (!vSwitchName.Equals("")  && !vSwitch.ElementName.Equals(vSwitchName))
+            {
+               var errMsg = string.Format("Internal error, coudl not find Virtual Switch with the name : " +vSwitchName);
+               var ex = new WmiException(errMsg);
+               logger.Error(errMsg, ex);
+               throw ex;
+            }
+
+            // Create port for adapter
+            var defaultEthernetPortSettings = EthernetPortAllocationSettingData.GetInstances(vSwitch.Scope, "InstanceID LIKE \"%Default\"");
+
+            // assert
+            if (defaultEthernetPortSettings.Count != 1)
+            {
+                var errMsg = string.Format("Internal error, coudl not find default EthernetPortAllocationSettingData instance");
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            var defaultEthernetPortSettingsObj = defaultEthernetPortSettings.OfType<EthernetPortAllocationSettingData>().First();
+            var newEthernetPortSettings = new EthernetPortAllocationSettingData((ManagementBaseObject)defaultEthernetPortSettingsObj.LateBoundObject.Clone());
+            newEthernetPortSettings.LateBoundObject["Parent"] = newAdapter.Path.Path;
+            newEthernetPortSettings.LateBoundObject["HostResource"] = new string[] { vSwitch.Path.Path };
+
+            // Insert NIC into vm
+            string[] newResources = new string[] { newEthernetPortSettings.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20) };
+            ManagementPath[] newResourcePaths = AddVirtualResource(newResources, newVm);
+
+            // assert
+            if (newResourcePaths.Length != 1)
+            {
+                var errMsg = string.Format(
+                    "Failed to properly insert a single NIC on VM {0} (GUID {1}): number of resource created {2}",
+                    newVm.ElementName,
+                    newVm.Name,
+                    newResourcePaths.Length);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            return new EthernetPortAllocationSettingData(newResourcePaths[0]);
+        }
+
+        /// this method is to add a dvd drive and attach the systemvm iso.
+        /// 
+        public void patchSystemVmIso(String vmName, String systemVmIso)
+        {
+            ComputerSystem vmObject = GetComputerSystem(vmName);
+            AddDiskDriveToIdeController(vmObject, "", "1", ISO_DRIVE);
+            AttachIso(vmName, systemVmIso);
+        }
+
+        public void AttachDisk(string vmName, string diskPath, string addressOnController)
+        {
+            logger.DebugFormat("Got request to attach disk {0} to vm {1}", diskPath, vmName);
+
+            ComputerSystem vm = GetComputerSystem(vmName);
+            if (vm == null)
+            {
+                logger.DebugFormat("VM {0} not found", vmName);
+                return;
+            }
+            else
+            {
+                ManagementPath newDrivePath = GetDiskDriveOnScsiController(vm, addressOnController);
+                if (newDrivePath == null)
+                {
+                    newDrivePath = AttachDiskDriveToScsiController(vm, addressOnController);
+                }
+                InsertDiskImage(vm, diskPath, HARDDISK_DISK, newDrivePath);
+            }
+        }
+
+        /// </summary>
+        /// <param name="vm"></param>
+        /// <param name="cntrllerAddr"></param>
+        /// <param name="driveResourceType">IDE_HARDDISK_DRIVE or IDE_ISO_DRIVE</param>
+        public ManagementPath AddDiskDriveToIdeController(ComputerSystem vm, string vhdfile, string cntrllerAddr, string driveResourceType)
+        {
+            logger.DebugFormat("Creating DISK for VM {0} (GUID {1}) by attaching {2}", 
+                        vm.ElementName,
+                        vm.Name,
+                        vhdfile);
+
+            // Determine disk type for drive and assert drive type valid
+            string diskResourceSubType = null;
+            switch(driveResourceType) {
+                case HARDDISK_DRIVE:
+                    diskResourceSubType = HARDDISK_DISK;
+                    break;
+                case ISO_DRIVE: 
+                    diskResourceSubType = ISO_DISK;
+                    break;
+                default:
+                    var errMsg = string.Format(
+                        "Unrecognised disk drive type {0} for VM {1} (GUID {2})",
+                        string.IsNullOrEmpty(driveResourceType) ? "NULL": driveResourceType, 
+                        vm.ElementName,
+                        vm.Name);
+                    var ex = new WmiException(errMsg);
+                    logger.Error(errMsg, ex);
+                    throw ex;
+            }
+
+            ManagementPath newDrivePath = AttachNewDrive(vm, cntrllerAddr, driveResourceType);
+
+            // If there's not disk to insert, we are done.
+            if (String.IsNullOrEmpty(vhdfile))
+            {
+                logger.DebugFormat("No disk to be added to drive, disk drive {0} is complete", newDrivePath.Path);
+            }
+            else
+            {
+                InsertDiskImage(vm, vhdfile, diskResourceSubType, newDrivePath);
+            }
+            return newDrivePath;
+        }
+
+
+        public void DetachDisk(string displayName, string diskFileName)
+        {
+            logger.DebugFormat("Got request to detach virtual disk {0} from vm {1}", diskFileName, displayName);
+
+            ComputerSystem vm = GetComputerSystem(displayName);
+            if (vm == null)
+            {
+                logger.DebugFormat("VM {0} not found", displayName);
+                return;
+            }
+            else
+            {
+                RemoveStorageImage(vm, diskFileName);
+            }
+        }
+
+        /// <summary>
+        /// Removes a disk image from a drive, but does not remove the drive itself.
+        /// </summary>
+        /// <param name="vm"></param>
+        /// <param name="diskFileName"></param>
+        private void RemoveStorageImage(ComputerSystem vm, string diskFileName)
+        {
+            // Obtain StorageAllocationSettingData for disk
+            StorageAllocationSettingData.StorageAllocationSettingDataCollection storageSettingsObjs = StorageAllocationSettingData.GetInstances();
+
+            StorageAllocationSettingData imageToRemove = null;
+            foreach (StorageAllocationSettingData item in storageSettingsObjs)
+            {
+                if (item.HostResource == null || item.HostResource.Length != 1)
+                {
+                    continue;
+                }
+
+                string hostResource = item.HostResource[0];
+                if (Path.Equals(hostResource, diskFileName))
+                {
+                    imageToRemove = item;
+                    break;
+                }
+            }
+
+            // assert
+            if (imageToRemove  == null)
+            {
+                var errMsg = string.Format(
+                    "Failed to remove disk image {0} from VM {1} (GUID {2}): the disk image is not attached.",
+                    diskFileName,
+                    vm.ElementName,
+                    vm.Name);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            RemoveStorageResource(imageToRemove.Path, vm);
+
+            logger.InfoFormat("Removed disk image {0} from VM {1} (GUID {2}): the disk image is not attached.",
+                    diskFileName,
+                    vm.ElementName,
+                    vm.Name);
+        }
+
+        private ManagementPath AttachNewDrive(ComputerSystem vm, string cntrllerAddr, string driveType)
+        {
+            // Disk drives are attached to a 'Parent' IDE controller.  We IDE Controller's settings for the 'Path', which our new Disk drive will use to reference it.
+            VirtualSystemSettingData vmSettings = GetVmSettings(vm);
+            var ctrller = GetIDEControllerSettings(vmSettings, cntrllerAddr);
+
+            // A description of the drive is created by modifying a clone of the default ResourceAllocationSettingData for that drive type
+            string defaultDriveQuery = String.Format("ResourceSubType LIKE \"{0}\" AND InstanceID LIKE \"%Default\"", driveType);
+            var newDiskDriveSettings = CloneResourceAllocationSetting(defaultDriveQuery);
+
+            // Set IDE controller and address on the controller for the new drive
+            newDiskDriveSettings.LateBoundObject["Parent"] = ctrller.Path.ToString();
+            newDiskDriveSettings.LateBoundObject["AddressOnParent"] = "0";
+            newDiskDriveSettings.CommitObject();
+
+            // Add this new disk drive to the VM
+            logger.DebugFormat("Creating disk drive type {0}, parent IDE controller is {1} and address on controller is {2}",
+                newDiskDriveSettings.ResourceSubType,
+                newDiskDriveSettings.Parent,
+                newDiskDriveSettings.AddressOnParent);
+            string[] newDriveResource = new string[] { newDiskDriveSettings.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20) };
+            ManagementPath[] newDrivePaths = AddVirtualResource(newDriveResource, vm);
+
+            // assert
+            if (newDrivePaths.Length != 1)
+            {
+                var errMsg = string.Format(
+                    "Failed to add disk drive type {3} to VM {0} (GUID {1}): number of resource created {2}",
+                    vm.ElementName,
+                    vm.Name,
+                    newDrivePaths.Length,
+                    driveType);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+            logger.DebugFormat("New disk drive type {0} WMI path is {1}s",
+                newDiskDriveSettings.ResourceSubType,
+                newDrivePaths[0].Path);
+            return newDrivePaths[0];
+        }
+
+        private ManagementPath AddScsiController(ComputerSystem vm)
+        {
+            // A description of the controller is created by modifying a clone of the default ResourceAllocationSettingData for scsi controller
+            string scsiQuery = String.Format("ResourceSubType LIKE \"{0}\" AND InstanceID LIKE \"%Default\"", SCSI_CONTROLLER);
+            var scsiSettings = CloneResourceAllocationSetting(scsiQuery);
+
+            scsiSettings.LateBoundObject["ElementName"] = "SCSI Controller";
+            scsiSettings.CommitObject();
+
+            // Insert SCSI controller into vm
+            string[] newResources = new string[] { scsiSettings.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20) };
+            ManagementPath[] newResourcePaths = AddVirtualResource(newResources, vm);
+
+            // assert
+            if (newResourcePaths.Length != 1)
+            {
+                var errMsg = string.Format(
+                    "Failed to add scsi controller to VM {0} (GUID {1}): number of resource created {2}",
+                    vm.ElementName,
+                    vm.Name,
+                    newResourcePaths.Length);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            logger.DebugFormat("New controller type {0} WMI path is {1}s",
+                scsiSettings.ResourceSubType,
+                newResourcePaths[0].Path);
+            return newResourcePaths[0];
+        }
+
+        private ManagementPath GetDiskDriveOnScsiController(ComputerSystem vm, string addrOnController)
+        {
+            VirtualSystemSettingData vmSettings = GetVmSettings(vm);
+            var wmiObjCollection = GetResourceAllocationSettings(vmSettings);
+            foreach (ResourceAllocationSettingData wmiObj in wmiObjCollection)
+            {
+                if (wmiObj.ResourceSubType == HARDDISK_DRIVE)
+                {
+                    ResourceAllocationSettingData parent = new ResourceAllocationSettingData(new ManagementObject(wmiObj.Parent));
+                    if (parent.ResourceSubType == SCSI_CONTROLLER && wmiObj.AddressOnParent == addrOnController)
+                    {
+                        return wmiObj.Path;
+                    }
+                }
+            }
+            return null;
+        }
+
+        private ManagementPath AttachDiskDriveToScsiController(ComputerSystem vm, string addrOnController)
+        {
+            // Disk drives are attached to a 'Parent' Scsi controller.
+            VirtualSystemSettingData vmSettings = GetVmSettings(vm);
+            var ctrller = GetScsiControllerSettings(vmSettings);
+
+            // A description of the drive is created by modifying a clone of the default ResourceAllocationSettingData for that drive type
+            string defaultDriveQuery = String.Format("ResourceSubType LIKE \"{0}\" AND InstanceID LIKE \"%Default\"", HARDDISK_DRIVE);
+            var newDiskDriveSettings = CloneResourceAllocationSetting(defaultDriveQuery);
+
+            // Set IDE controller and address on the controller for the new drive
+            newDiskDriveSettings.LateBoundObject["Parent"] = ctrller.Path.ToString();
+            newDiskDriveSettings.LateBoundObject["AddressOnParent"] = addrOnController;
+            newDiskDriveSettings.CommitObject();
+
+            // Add this new disk drive to the VM
+            logger.DebugFormat("Creating disk drive type {0}, parent IDE controller is {1} and address on controller is {2}",
+                newDiskDriveSettings.ResourceSubType,
+                newDiskDriveSettings.Parent,
+                newDiskDriveSettings.AddressOnParent);
+            string[] newDriveResource = new string[] { newDiskDriveSettings.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20) };
+            ManagementPath[] newDrivePaths = AddVirtualResource(newDriveResource, vm);
+
+            // assert
+            if (newDrivePaths.Length != 1)
+            {
+                var errMsg = string.Format(
+                    "Failed to add disk drive type {3} to VM {0} (GUID {1}): number of resource created {2}",
+                    vm.ElementName,
+                    vm.Name,
+                    newDrivePaths.Length,
+                    HARDDISK_DRIVE);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+            logger.DebugFormat("New disk drive type {0} WMI path is {1}s",
+                newDiskDriveSettings.ResourceSubType,
+                newDrivePaths[0].Path);
+            return newDrivePaths[0];
+        }
+
+
+        private void InsertDiskImage(ComputerSystem vm, string diskImagePath, string diskResourceSubType, ManagementPath drivePath)
+        {
+            // A description of the disk is created by modifying a clone of the default ResourceAllocationSettingData for that disk type
+            string defaultDiskQuery = String.Format("ResourceSubType LIKE \"{0}\" AND InstanceID LIKE \"%Default\"", diskResourceSubType);
+            var newDiskSettings = CloneStorageAllocationSetting(defaultDiskQuery);
+
+            // Set file containing the disk image
+            newDiskSettings.LateBoundObject["Parent"] = drivePath.Path;
+
+            // V2 API uses HostResource to specify image, see http://msdn.microsoft.com/en-us/library/hh859775(v=vs.85).aspx
+            newDiskSettings.LateBoundObject["HostResource"] = new string[] { diskImagePath };
+            newDiskSettings.CommitObject();
+
+            // Add the new Msvm_StorageAllocationSettingData object as a virtual hard disk to the vm.
+            string[] newDiskResource = new string[] { newDiskSettings.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20) };
+            ManagementPath[] newDiskPaths = AddStorageResource(newDiskResource, vm);
+            // assert
+            if (newDiskPaths.Length != 1)
+            {
+                var errMsg = string.Format(
+                    "Failed to add disk image type {3} to VM {0} (GUID {1}): number of resource created {2}",
+                    vm.ElementName,
+                    vm.Name,
+                    newDiskPaths.Length,
+                    diskResourceSubType);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+            logger.InfoFormat("Created disk {2} for VM {0} (GUID {1}), image {3} ",
+                    vm.ElementName,
+                    vm.Name,
+                    newDiskPaths[0].Path,
+                    diskImagePath);
+        }
+
+        /// <summary>
+        /// Create Msvm_StorageAllocationSettingData corresponding to the ISO image, and 
+        /// associate this with the VM's DVD drive.
+        /// </summary>
+        private void AttachIso(ComputerSystem vm, string isoPath)
+        {
+            // Disk drives are attached to a 'Parent' IDE controller.  We IDE Controller's settings for the 'Path', which our new Disk drive will use to reference it.
+            VirtualSystemSettingData vmSettings = GetVmSettings(vm);
+            var driveWmiObj = GetDvdDriveSettings(vmSettings);
+            InsertDiskImage(vm, isoPath, ISO_DISK, driveWmiObj.Path);
+        }
+
+        private static ResourceAllocationSettingData CloneResourceAllocationSetting(string wmiQuery)
+        {
+            var defaultDiskDriveSettingsObjs = ResourceAllocationSettingData.GetInstances(wmiQuery);
+
+            // assert
+            if (defaultDiskDriveSettingsObjs.Count != 1)
+            {
+                var errMsg = string.Format("Failed to find Msvm_ResourceAllocationSettingData for the query {0}", wmiQuery);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            ResourceAllocationSettingData defaultDiskDriveSettings = defaultDiskDriveSettingsObjs.OfType<ResourceAllocationSettingData>().First();
+            return new ResourceAllocationSettingData((ManagementBaseObject)defaultDiskDriveSettings.LateBoundObject.Clone());
+        }
+
+            // we need to reboot to get the hv kvp daemon get started vr gets configured.
+            if (vmName.StartsWith("r-") || vmName.StartsWith("s-") || vmName.StartsWith("v-"))
+            {
+                System.Threading.Thread.Sleep(90000);
+                // wait for the second boot and then return with sucesss
+                //if publicIPAddress is empty or null don't ping the ip
+              /*if (publicIpAddress.Equals("") == true)
+                {
+                    System.Threading.Thread.Sleep(90000);
+                }
+                else
+                {
+                    pingResource(publicIpAddress);
+                }*/
+            }
+            logger.InfoFormat("Started VM {0}", vmName);
+            return newVm;
+        }
+
+        public static Boolean pingResource(String ip)
+        {
+            PingOptions pingOptions = null;
+            PingReply pingReply = null;
+            IPAddress ipAddress = null;
+            Ping pingSender = new Ping();
+            int numberOfPings = 6;
+            int pingTimeout = 1000;
+            int byteSize = 32;
+            byte[] buffer = new byte[byteSize];
+            ipAddress = IPAddress.Parse(ip);
+            pingOptions = new PingOptions();
+            for (int i = 0; i < numberOfPings; i++)
+            {
+                pingReply = pingSender.Send(ipAddress, pingTimeout, buffer, pingOptions);
+                if (pingReply.Status == IPStatus.Success)
+                {
+                    System.Threading.Thread.Sleep(30000);
+                    return true;
+                }
+                else
+                {
+                    // wait for the second boot and then return with suces
+                    System.Threading.Thread.Sleep(30000);
+                }
+            }
+            return false;
+        }
+
+        private EthernetPortAllocationSettingData AttachNicToPort(ComputerSystem newVm, SyntheticEthernetPortSettingData newAdapter, String vSwitchName, int enableState)
+        {
+            // Get the virtual switch
+            VirtualEthernetSwitch vSwitch = GetExternalVirtSwitch(vSwitchName);
+            //check the the recevied vSwitch is the same as vSwitchName.
+            if (!vSwitchName.Equals("")  && !vSwitch.ElementName.Equals(vSwitchName))
+            {
+               var errMsg = string.Format("Internal error, coudl not find Virtual Switch with the name : " +vSwitchName);
+               var ex = new WmiException(errMsg);
+               logger.Error(errMsg, ex);
+               throw ex;
+            }
+
+            // Create port for adapter
+            var defaultEthernetPortSettings = EthernetPortAllocationSettingData.GetInstances(vSwitch.Scope, "InstanceID LIKE \"%Default\"");
+
+            // assert
+            if (defaultEthernetPortSettings.Count != 1)
+            {
+                var errMsg = string.Format("Internal error, coudl not find default EthernetPortAllocationSettingData instance");
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            var defaultEthernetPortSettingsObj = defaultEthernetPortSettings.OfType<EthernetPortAllocationSettingData>().First();
+            var newEthernetPortSettings = new EthernetPortAllocationSettingData((ManagementBaseObject)defaultEthernetPortSettingsObj.LateBoundObject.Clone());
+            newEthernetPortSettings.LateBoundObject["Parent"] = newAdapter.Path.Path;
+            newEthernetPortSettings.LateBoundObject["HostResource"] = new string[] { vSwitch.Path.Path };
+            newEthernetPortSettings.LateBoundObject["EnabledState"] = enableState; //3 disabled 2 Enabled
+            // Insert NIC into vm
+            string[] newResources = new string[] { newEthernetPortSettings.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20) };
+            ManagementPath[] newResourcePaths = AddVirtualResource(newResources, newVm);
+
+            // assert
+            if (newResourcePaths.Length != 1)
+            {
+                var errMsg = string.Format(
+                    "Failed to properly insert a single NIC on VM {0} (GUID {1}): number of resource created {2}",
+                    newVm.ElementName,
+                    newVm.Name,
+                    newResourcePaths.Length);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            return new EthernetPortAllocationSettingData(newResourcePaths[0]);
+        }
+
+        /// this method is to add a dvd drive and attach the systemvm iso.
+        /// 
+        public void patchSystemVmIso(String vmName, String systemVmIso)
+        {
+            ComputerSystem vmObject = GetComputerSystem(vmName);
+            AddDiskDriveToIdeController(vmObject, "", "1", ISO_DRIVE);
+            AttachIso(vmName, systemVmIso);
+        }
+
+        public void AttachDisk(string vmName, string diskPath, string addressOnController)
+        {
+            logger.DebugFormat("Got request to attach disk {0} to vm {1}", diskPath, vmName);
+
+            ComputerSystem vm = GetComputerSystem(vmName);
+            if (vm == null)
+            {
+                logger.DebugFormat("VM {0} not found", vmName);
+                return;
+            }
+            else
+            {
+                ManagementPath newDrivePath = GetDiskDriveOnScsiController(vm, addressOnController);
+                if (newDrivePath == null)
+                {
+                    newDrivePath = AttachDiskDriveToScsiController(vm, addressOnController);
+                }
+                InsertDiskImage(vm, diskPath, HARDDISK_DISK, newDrivePath);
+            }
+        }
+
+        /// </summary>
+        /// <param name="vm"></param>
+        /// <param name="cntrllerAddr"></param>
+        /// <param name="driveResourceType">IDE_HARDDISK_DRIVE or IDE_ISO_DRIVE</param>
+        public ManagementPath AddDiskDriveToIdeController(ComputerSystem vm, string vhdfile, string cntrllerAddr, string driveResourceType)
+        {
+            logger.DebugFormat("Creating DISK for VM {0} (GUID {1}) by attaching {2}", 
+                        vm.ElementName,
+                        vm.Name,
+                        vhdfile);
+
+            // Determine disk type for drive and assert drive type valid
             string diskResourceSubType = null;
             switch(driveResourceType) {
                 case HARDDISK_DRIVE:
@@ -2024,13 +2445,9 @@ namespace HypervResource
 
         public VirtualEthernetSwitchManagementService GetVirtualSwitchManagementService()
         {
-            // VirtualSwitchManagementService is a singleton, most anonymous way of lookup is by asking for the set
-            // of local instances, which should be size 1.
-            var virtSwtichSvcCollection = VirtualEthernetSwitchManagementService.GetInstances();
-            foreach (VirtualEthernetSwitchManagementService item in virtSwtichSvcCollection)
-            {
-                return item;
-            }
+            ComputerSystem vm = GetComputerSystem(vmName);
+            // Obtain controller for Hyper-V virtualisation subsystem
+            VirtualSystemManagementService vmMgmtSvc = GetVirtualisationSystemManagementService();
 
             var errMsg = string.Format("No Hyper-V subsystem on server");
             var ex = new WmiException(errMsg);
@@ -2183,195 +2600,259 @@ namespace HypervResource
                 System.Threading.Thread.Sleep(1000);
             }
 
-            if (jobObj.JobState != JobState.Completed)
-            {
-                var errMsg = string.Format(
-                    "Hyper-V Job failed, Error Code:{0}, Description: {1}",
-                    jobObj.ErrorCode,
-                    jobObj.ErrorDescription);
-                var ex = new WmiException(errMsg);
-                logger.Error(errMsg, ex);
-                throw ex;
-            }
-        }
-
-        private static void StorageJobCompleted(ManagementPath jobPath)
-        {
-            StorageJob jobObj = null;
-            for (; ; )
-            {
-                jobObj = new StorageJob(jobPath);
-                if (jobObj.JobState != JobState.Starting && jobObj.JobState != JobState.Running)
-                {
-                    break;
-                }
-                logger.InfoFormat("In progress... {0}% completed.", jobObj.PercentComplete);
-                System.Threading.Thread.Sleep(1000);
-            }
-
-            if (jobObj.JobState != JobState.Completed)
-            {
-                var errMsg = string.Format(
-                    "Hyper-V Job failed, Error Code:{0}, Description: {1}",
-                    jobObj.ErrorCode,
-                    jobObj.ErrorDescription);
-                var ex = new WmiException(errMsg);
-                logger.Error(errMsg, ex);
-                throw ex;
-            }
-        }
-
-        public void GetProcessorResources(out uint sockets, out uint cores, out uint mhz)
-        {
-            //  Processor processors
-            cores = 0;
-            mhz = 0;
-            sockets = 0;
-            Processor.ProcessorCollection procCol = Processor.GetInstances();
-            foreach (Processor procInfo in procCol)
-            {
-                cores += procInfo.NumberOfCores;
-                mhz = procInfo.MaxClockSpeed;
-                sockets++;
-           }
-        }
-        
-        public void GetProcessorUsageInfo(out double cpuUtilization)
-        {
-            PerfFormattedData_Counters_ProcessorInformation.PerfFormattedData_Counters_ProcessorInformationCollection coll = 
-                            PerfFormattedData_Counters_ProcessorInformation.GetInstances("Name=\"_Total\"");
-            cpuUtilization = 100;
-            // Use the first one
-            foreach (PerfFormattedData_Counters_ProcessorInformation procInfo in coll)
-            {
-                // Idle during a given internal 
-                // See http://library.wmifun.net/cimv2/win32_perfformatteddata_counters_processorinformation.html
-                cpuUtilization = 100.0 - (double)procInfo.PercentIdleTime;            
-            }
-        }
-
-
-        public void GetMemoryResources(out ulong physicalRamKBs, out ulong freeMemoryKBs)
-        {
-            OperatingSystem0 os = new OperatingSystem0();
-            physicalRamKBs = os.TotalVisibleMemorySize;
-            freeMemoryKBs = os.FreePhysicalMemory;
-        }
-
-        public string GetDefaultVirtualDiskFolder()
-        {
-            VirtualSystemManagementServiceSettingData.VirtualSystemManagementServiceSettingDataCollection coll = VirtualSystemManagementServiceSettingData.GetInstances();
-            string defaultVirtualHardDiskPath = null;
-            foreach (VirtualSystemManagementServiceSettingData settings in coll)
-            {
-                defaultVirtualHardDiskPath = settings.DefaultVirtualHardDiskPath;
-            }
-
-            // assert
-            if (!System.IO.Directory.Exists(defaultVirtualHardDiskPath) ){
-                var errMsg = string.Format(
-                    "Hyper-V DefaultVirtualHardDiskPath is invalid!");
-                logger.Error(errMsg);
-                return null;
-            }
-            
-            return defaultVirtualHardDiskPath;
-        }
-
-        public ComputerSystem GetComputerSystem(string displayName)
-        {
-            var wmiQuery = String.Format("ElementName=\"{0}\"", displayName);
-            ComputerSystem.ComputerSystemCollection vmCollection = ComputerSystem.GetInstances(wmiQuery);
-
-            // Return the first one
-            foreach (ComputerSystem vm in vmCollection)
-            {
-                return vm;
-            }
-            return null;
-        }
-
-        public ComputerSystem.ComputerSystemCollection GetComputerSystemCollection()
-        {
-            var wmiQuery = String.Format("Caption=\"Virtual Machine\"");
-            return ComputerSystem.GetInstances(wmiQuery);
-        }
-
-        public Dictionary<String, VmState> GetVmSync(String privateIpAddress)
-        {
-            List<String> vms = GetVmElementNames();
-            Dictionary<String, VmState> vmSyncStates = new Dictionary<string, VmState>();
-            String vmState;
-            foreach (String vm in vms)
-            {
-                 vmState = EnabledState.ToCloudStackState(GetComputerSystem(vm).EnabledState);
-                 vmSyncStates.Add(vm, new VmState(vmState, privateIpAddress));
-            }
-            return vmSyncStates;
-        }
-
-        public List<string> GetVmElementNames()
-        {
-            List<string> result = new List<string>();
-            ComputerSystem.ComputerSystemCollection vmCollection = ComputerSystem.GetInstances();
-
-            // Return the first one
-            foreach (ComputerSystem vm in vmCollection)
-            {
-                if (vm.Caption.StartsWith("Hosting Computer System") )
-                {
-                    continue;
-                }
-                result.Add(vm.ElementName);
-            }
-            return result;
-        }
-
-        public ProcessorSettingData GetProcSettings(VirtualSystemSettingData vmSettings)
-        {
-            // An ASSOCIATOR object provides the cross reference from the VirtualSystemSettingData and the 
-            // ProcessorSettingData, but generated wrappers do not expose a ASSOCIATOR OF query as a method.
-            // Instead, we use the System.Management to code the equivalant of 
-            //  string query = string.Format( "ASSOCIATORS OF {{{0}}} WHERE ResultClass = {1}", vmSettings.path, resultclassName);
-            //
-            var wmiObjQuery = new RelatedObjectQuery(vmSettings.Path.Path, ProcessorSettingData.CreatedClassName);
-
-            // NB: default scope of ManagementObjectSearcher is '\\.\root\cimv2', which does not contain
-            // the virtualisation objects.
-            var wmiObjectSearch = new ManagementObjectSearcher(vmSettings.Scope, wmiObjQuery);
-            var wmiObjCollection = new ProcessorSettingData.ProcessorSettingDataCollection(wmiObjectSearch.Get());
-
-            foreach (ProcessorSettingData wmiObj in wmiObjCollection)
+            if (jobObj.JobState != JobState.Completed)
             {
-                return wmiObj;
+                var errMsg = string.Format(
+                    "Hyper-V Job failed, Error Code:{0}, Description: {1}",
+                    jobObj.ErrorCode,
+                    jobObj.ErrorDescription);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
             }
-
-            var errMsg = string.Format("No ProcessorSettingData in VirtualSystemSettingData {0}", vmSettings.Path.Path);
-            var ex = new WmiException(errMsg);
-            logger.Error(errMsg, ex);
-            throw ex;
         }
 
-        public MemorySettingData GetMemSettings(VirtualSystemSettingData vmSettings)
+        private static void StorageJobCompleted(ManagementPath jobPath)
         {
-            // An ASSOCIATOR object provides the cross reference from the VirtualSystemSettingData and the 
-            // MemorySettingData, but generated wrappers do not expose a ASSOCIATOR OF query as a method.
-            // Instead, we use the System.Management to code the equivalant of 
-            //  string query = string.Format( "ASSOCIATORS OF {{{0}}} WHERE ResultClass = {1}", vmSettings.path, resultclassName);
-            //
-            var wmiObjQuery = new RelatedObjectQuery(vmSettings.Path.Path, MemorySettingData.CreatedClassName);
-
-            EthernetPortAllocationSettingData[] ethernetConnections = GetEthernetConnections(vm);
-            EthernetSwitchPortVlanSettingData vlanSettings = GetVlanSettings(ethernetConnections[pos]);
+            StorageJob jobObj = null;
+            for (; ; )
+            {
+                jobObj = new StorageJob(jobPath);
+                if (jobObj.JobState != JobState.Starting && jobObj.JobState != JobState.Running)
+                {
+                    break;
+                }
+                logger.InfoFormat("In progress... {0}% completed.", jobObj.PercentComplete);
+                System.Threading.Thread.Sleep(1000);
+            }
 
-            //Assign configuration to new NIC
-            vlanSettings.LateBoundObject["AccessVlanId"] = vlanid;
-            vlanSettings.LateBoundObject["OperationMode"] = 1;
-            ModifyFeatureVmResources(vmMgmtSvc, vm, new String[] {
-                vlanSettings.LateBoundObject.GetText(TextFormat.CimDtd20)});
+            if (jobObj.JobState != JobState.Completed)
+            {
+                var errMsg = string.Format(
+                    "Hyper-V Job failed, Error Code:{0}, Description: {1}",
+                    jobObj.ErrorCode,
+                    jobObj.ErrorDescription);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
         }
 
-        public void AttachIso(string displayName, string iso)
+        /// <summary>
+        /// Migrates a vm to the given destination host
+        /// </summary>
+        /// <param name="desplayName"></param>
+        /// <param name="destination host"></param>
+        public void MigrateVm(string vmName, string destination)
+        {
+            ComputerSystem vm = GetComputerSystem(vmName);
+            VirtualSystemMigrationSettingData migrationSettingData = VirtualSystemMigrationSettingData.CreateInstance();
+            VirtualSystemMigrationService service = GetVirtualisationSystemMigrationService();
+
+            IPAddress addr = IPAddress.Parse(destination);
+            IPHostEntry entry = Dns.GetHostEntry(addr);
+            string[] destinationHost = new string[] { destination };
+
+            migrationSettingData.LateBoundObject["MigrationType"] = MigrationType.VirtualSystem;
+            migrationSettingData.LateBoundObject["TransportType"] = TransportType.TCP;
+            migrationSettingData.LateBoundObject["DestinationIPAddressList"] = destinationHost;
+            string migrationSettings = migrationSettingData.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20);
+
+            ManagementPath jobPath;
+            var ret_val = service.MigrateVirtualSystemToHost(vm.Path, entry.HostName, migrationSettings, null, null, out jobPath);
+            if (ret_val == ReturnCode.Started)
+            {
+                MigrationJobCompleted(jobPath);
+            }
+            else if (ret_val != ReturnCode.Completed)
+            {
+                var errMsg = string.Format(
+                    "Failed migrating VM {0} (GUID {1}) due to {2}",
+                    vm.ElementName,
+                    vm.Name,
+                    ReturnCode.ToString(ret_val));
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+        }
+
+        /// <summary>
+        /// Migrates the volume of a vm to a given destination storage
+        /// </summary>
+        /// <param name="displayName"></param>
+        /// <param name="volume"></param>
+        /// <param name="destination storage pool"></param>
+        public void MigrateVolume(string vmName, string volume, string destination)
+        {
+            ComputerSystem vm = GetComputerSystem(vmName);
+            VirtualSystemMigrationSettingData migrationSettingData = VirtualSystemMigrationSettingData.CreateInstance();
+            VirtualSystemMigrationService service = GetVirtualisationSystemMigrationService();
+            StorageAllocationSettingData[] sasd = GetStorageSettings(vm);
+
+            string[] rasds = null;
+            if (sasd != null)
+            {
+                rasds = new string[1];
+                foreach (StorageAllocationSettingData item in sasd)
+                {
+                    string vhdFileName = Path.GetFileNameWithoutExtension(item.HostResource[0]);
+                    if (!String.IsNullOrEmpty(vhdFileName) && vhdFileName.Equals(volume))
+                    {
+                        string newVhdPath = Path.Combine(destination, Path.GetFileName(item.HostResource[0]));
+                        item.LateBoundObject["HostResource"] = new string[] { newVhdPath };
+                        item.LateBoundObject["PoolId"] = "";
+                        rasds[0] = item.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20);
+                        break;
+                    }
+                }
+            }
+
+            migrationSettingData.LateBoundObject["MigrationType"] = MigrationType.Storage;
+            migrationSettingData.LateBoundObject["TransportType"] = TransportType.TCP;
+            string migrationSettings = migrationSettingData.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20);
+
+            ManagementPath jobPath;
+            var ret_val = service.MigrateVirtualSystemToHost(vm.Path, null, migrationSettings, rasds, null, out jobPath);
+            if (ret_val == ReturnCode.Started)
+            {
+                MigrationJobCompleted(jobPath);
+            }
+            else if (ret_val != ReturnCode.Completed)
+            {
+                var errMsg = string.Format(
+                    "Failed migrating volume {0} of VM {1} (GUID {2}) due to {3}",
+                    volume,
+                    vm.ElementName,
+                    vm.Name,
+                    ReturnCode.ToString(ret_val));
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+        }
+
+        /// <summary>
+        /// Migrates the volume of a vm to a given destination storage
+        /// </summary>
+        /// <param name="displayName"></param>
+        /// <param name="destination host"></param>
+        /// <param name="volumeToPool"> volume to me migrated to which pool</param>
+        public void MigrateVmWithVolume(string vmName, string destination, Dictionary<string, string> volumeToPool)
+        {
+            ComputerSystem vm = GetComputerSystem(vmName);
+            VirtualSystemMigrationSettingData migrationSettingData = VirtualSystemMigrationSettingData.CreateInstance();
+            VirtualSystemMigrationService service = GetVirtualisationSystemMigrationService();
+            StorageAllocationSettingData[] sasd = GetStorageSettings(vm);
+
+            string[] rasds = null;
+            if (sasd != null)
+            {
+                rasds = new string[sasd.Length];
+                uint index = 0;
+                foreach (StorageAllocationSettingData item in sasd)
+                {
+                    string vhdFileName = Path.GetFileNameWithoutExtension(item.HostResource[0]);
+                    if (!String.IsNullOrEmpty(vhdFileName) && volumeToPool.ContainsKey(vhdFileName))
+                    {
+                        string newVhdPath = Path.Combine(volumeToPool[vhdFileName], Path.GetFileName(item.HostResource[0]));
+                        item.LateBoundObject["HostResource"] = new string[] { newVhdPath };
+                        item.LateBoundObject["PoolId"] = "";
+                    }
+
+                    rasds[index++] = item.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20);
+                }
+            }
+
+            IPAddress addr = IPAddress.Parse(destination);
+            IPHostEntry entry = Dns.GetHostEntry(addr);
+            string[] destinationHost = new string[] { destination };
+
+            migrationSettingData.LateBoundObject["MigrationType"] = MigrationType.VirtualSystemAndStorage;
+            migrationSettingData.LateBoundObject["TransportType"] = TransportType.TCP;
+            migrationSettingData.LateBoundObject["DestinationIPAddressList"] = destinationHost;
+            string migrationSettings = migrationSettingData.LateBoundObject.GetText(System.Management.TextFormat.CimDtd20);
+
+            ManagementPath jobPath;
+            var ret_val = service.MigrateVirtualSystemToHost(vm.Path, entry.HostName, migrationSettings, rasds, null, out jobPath);
+            if (ret_val == ReturnCode.Started)
+            {
+                MigrationJobCompleted(jobPath);
+            }
+            else if (ret_val != ReturnCode.Completed)
+            {
+                var errMsg = string.Format(
+                    "Failed migrating VM {0} and its volumes to destination {1} (GUID {2}) due to {3}",
+                    vm.ElementName,
+                    destination,
+                    vm.Name,
+                    ReturnCode.ToString(ret_val));
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+        }
+
+        /// <summary>
+        /// Create new storage media resources, e.g. hard disk images and ISO disk images
+        /// see http://msdn.microsoft.com/en-us/library/hh859775(v=vs.85).aspx
+        /// </summary>
+        /// <param name="wmiQuery"></param>
+        /// <returns></returns>
+        private static StorageAllocationSettingData CloneStorageAllocationSetting(string wmiQuery)
+        {
+            var defaultDiskImageSettingsObjs = StorageAllocationSettingData.GetInstances(wmiQuery);
+
+            // assert
+            if (defaultDiskImageSettingsObjs.Count != 1)
+            {
+                var errMsg = string.Format("Failed to find Msvm_StorageAllocationSettingData for the query {0}", wmiQuery);
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+
+            StorageAllocationSettingData defaultDiskDriveSettings = defaultDiskImageSettingsObjs.OfType<StorageAllocationSettingData>().First();
+            return new StorageAllocationSettingData((ManagementBaseObject)defaultDiskDriveSettings.LateBoundObject.Clone());
+        }
+
+        /// < summary>
+        /// Removes a storage resource from a computer system.
+        /// </summary>
+        /// <param name="storageSettings">Path that uniquely identifies the resource.</param>
+        /// <param name="vm">VM to which the disk image will be attached.</param>
+        // Add new 
+        private void RemoveNetworkResource(ManagementPath resourcePath)
+        {
+            var virtSwitchMgmtSvc = GetVirtualSwitchManagementService();
+            ManagementPath jobPath;
+            var ret_val = virtSwitchMgmtSvc.RemoveResourceSettings(
+                new ManagementPath[] { resourcePath },
+                out jobPath);
+
+            // If the Job is done asynchronously
+            if (ret_val == ReturnCode.Started)
+            {
+                JobCompleted(jobPath);
+            }
+            else if (ret_val != ReturnCode.Completed)
+            {
+                var errMsg = string.Format(
+                    "Failed to remove network resources {0} from switch due to {1}",
+                    resourcePath.Path,
+                    ReturnCode.ToString(ret_val));
+                var ex = new WmiException(errMsg);
+                logger.Error(errMsg, ex);
+                throw ex;
+            }
+        }
+
+        /// < summary>
+        /// Removes a storage resource from a computer system.
+        /// </summary>
+        /// <param name="storageSettings">Path that uniquely identifies the resource.</param>
+        /// <param name="vm">VM to which the disk image will be attached.</param>
+        private void RemoveStorageResource(ManagementPath resourcePath, ComputerSystem vm)
         {
             logger.DebugFormat("Got request to attach iso {0} to vm {1}", iso, displayName);
 


[2/3] CLOUDSTACK-6504: removed warnings coming in building hyper-v agent code

Posted by da...@apache.org.
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/8fb89cdc/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/HypervResourceController.cs
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/HypervResourceController.cs b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/HypervResourceController.cs
index 1a46b50..41a3a8a 100644
--- a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/HypervResourceController.cs
+++ b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/HypervResourceController.cs
@@ -189,1867 +189,607 @@ namespace HypervResource
             using (log4net.NDC.Push(Guid.NewGuid().ToString()))
             {
                 logger.Info(CloudStackTypes.SetupCommand + Utils.CleanString(cmd.ToString()));
-
-                string details = null;
-                bool result = false;
-
-                try
-                {
-                    result = true;
-                }
-                catch (Exception sysEx)
-                {
-                    details = CloudStackTypes.SetupCommand + " failed due to " + sysEx.Message;
-                    logger.Error(details, sysEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = "success - NOP",
-                    _reconnect = false,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.SetupAnswer);
-            }
-        }
-
-        // POST api/HypervResource/AttachCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.AttachCommand)]
-        public JContainer AttachCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.AttachCommand + Utils.CleanString(cmd.ToString()));
-
-                string details = null;
-                bool result = false;
-
-                try
-                {
-                    string vmName = (string)cmd.vmName;
-                    DiskTO disk = DiskTO.ParseJson(cmd.disk);
-
-                    if (disk.type.Equals("ISO"))
-                    {
-                        TemplateObjectTO dataStore = disk.templateObjectTO;
-                        NFSTO share = dataStore.nfsDataStoreTO;
-                        string diskPath = Utils.NormalizePath(Path.Combine(share.UncPath, dataStore.path));
-                        wmiCallsV2.AttachIso(vmName, diskPath);
-                        result = true;
-                    }
-                    else if (disk.type.Equals("DATADISK"))
-                    {
-                        VolumeObjectTO volume = disk.volumeObjectTO;
-                        string diskPath = Utils.NormalizePath(volume.FullFileName);
-                        wmiCallsV2.AttachDisk(vmName, diskPath, disk.diskSequence);
-                        result = true;
-                    }
-                    else
-                    {
-                        details = "Invalid disk type to be attached to vm " + vmName;
-                    }
-                }
-                catch (Exception sysEx)
-                {
-                    details = CloudStackTypes.AttachCommand + " failed due to " + sysEx.Message;
-                    logger.Error(details, sysEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    disk = cmd.disk,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.AttachAnswer);
-            }
-        }
-
-        // POST api/HypervResource/DetachCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.DettachCommand)]
-        public JContainer DetachCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.DettachCommand + Utils.CleanString(cmd.ToString()));
-
-                string details = null;
-                bool result = false;
-
-                try
-                {
-                    string vmName = (string)cmd.vmName;
-                    DiskTO disk = DiskTO.ParseJson(cmd.disk);
-
-                    if (disk.type.Equals("ISO"))
-                    {
-                        TemplateObjectTO dataStore = disk.templateObjectTO;
-                        NFSTO share = dataStore.nfsDataStoreTO;
-                        string diskPath = Utils.NormalizePath(Path.Combine(share.UncPath, dataStore.path));
-                        wmiCallsV2.DetachDisk(vmName, diskPath);
-                        result = true;
-                    }
-                    else if (disk.type.Equals("DATADISK"))
-                    {
-                        VolumeObjectTO volume = disk.volumeObjectTO;
-                        PrimaryDataStoreTO primary = volume.primaryDataStore;
-                        string diskPath = Utils.NormalizePath(volume.FullFileName);
-                        wmiCallsV2.DetachDisk(vmName, diskPath);
-                        result = true;
-                    }
-                    else
-                    {
-                        details = "Invalid disk type to be dettached from vm " + vmName;
-                    }
-                }
-                catch (Exception sysEx)
-                {
-                    details = CloudStackTypes.DettachCommand + " failed due to " + sysEx.Message;
-                    logger.Error(details, sysEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.DettachAnswer);
-            }
-        }
-
-        // POST api/HypervResource/RebootCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.RebootCommand)]
-        public JContainer RebootCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
+
+                string details = null;
+                bool result = false;
+
+                try
+                {
+                    result = true;
+                }
+                catch (Exception sysEx)
+                {
+                    details = CloudStackTypes.SetupCommand + " failed due to " + sysEx.Message;
+                    logger.Error(details, sysEx);
+                }
+
+                object ansContent = new
+                {
+                    result = result,
+                    details = "success - NOP",
+                    _reconnect = false,
+                    contextMap = contextMap
+                };
+
+                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.SetupAnswer);
+            }
+        }
+
+        // POST api/HypervResource/AttachCommand
+        [HttpPost]
+        [ActionName(CloudStackTypes.AttachCommand)]
+        public JContainer AttachCommand([FromBody]dynamic cmd)
+        {
+            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
+            {
+                logger.Info(CloudStackTypes.AttachCommand + Utils.CleanString(cmd.ToString()));
+
+                string details = null;
+                bool result = false;
+
+                try
+                {
+                    string vmName = (string)cmd.vmName;
+                    DiskTO disk = DiskTO.ParseJson(cmd.disk);
+
+                    if (disk.type.Equals("ISO"))
+                    {
+                        TemplateObjectTO dataStore = disk.templateObjectTO;
+                        NFSTO share = dataStore.nfsDataStoreTO;
+                        Utils.ConnectToRemote(share.UncPath, share.Domain, share.User, share.Password);
+                        string diskPath = Utils.NormalizePath(Path.Combine(share.UncPath, dataStore.path));
+                        wmiCallsV2.AttachIso(vmName, diskPath);
+                        result = true;
+                    }
+                    else if (disk.type.Equals("DATADISK"))
+                    {
+                        VolumeObjectTO volume = disk.volumeObjectTO;
+                        PrimaryDataStoreTO primary = volume.primaryDataStore;
+                        if (!primary.isLocal)
+                        {
+                            Utils.ConnectToRemote(primary.UncPath, primary.Domain, primary.User, primary.Password);
+                        }
+                        string diskPath = Utils.NormalizePath(volume.FullFileName);
+                        wmiCallsV2.AttachDisk(vmName, diskPath, disk.diskSequence);
+                        result = true;
+                    }
+                    else
+                    {
+                        details = "Invalid disk type to be attached to vm " + vmName;
+                    }
+                }
+                catch (Exception sysEx)
+                {
+                    details = CloudStackTypes.AttachCommand + " failed due to " + sysEx.Message;
+                    logger.Error(details, sysEx);
+                }
+
+                object ansContent = new
+                {
+                    result = result,
+                    details = details,
+                    disk = cmd.disk,
+                    contextMap = contextMap
+                };
+
+                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.AttachAnswer);
+            }
+        }
+
+        // POST api/HypervResource/DetachCommand
+        [HttpPost]
+        [ActionName(CloudStackTypes.DettachCommand)]
+        public JContainer DetachCommand([FromBody]dynamic cmd)
+        {
+            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
+            {
+                logger.Info(CloudStackTypes.DettachCommand + Utils.CleanString(cmd.ToString()));
+
+                string details = null;
+                bool result = false;
+
+                try
+                {
+                    string vmName = (string)cmd.vmName;
+                    DiskTO disk = DiskTO.ParseJson(cmd.disk);
+
+                    if (disk.type.Equals("ISO"))
+                    {
+                        TemplateObjectTO dataStore = disk.templateObjectTO;
+                        NFSTO share = dataStore.nfsDataStoreTO;
+                        string diskPath = Utils.NormalizePath(Path.Combine(share.UncPath, dataStore.path));
+                        wmiCallsV2.DetachDisk(vmName, diskPath);
+                        result = true;
+                    }
+                    else if (disk.type.Equals("DATADISK"))
+                    {
+                        VolumeObjectTO volume = disk.volumeObjectTO;
+                        string diskPath = Utils.NormalizePath(volume.FullFileName);
+                        wmiCallsV2.DetachDisk(vmName, diskPath);
+                        result = true;
+                    }
+                    else
+                    {
+                        details = "Invalid disk type to be dettached from vm " + vmName;
+                    }
+                }
+                catch (Exception sysEx)
+                {
+                    details = CloudStackTypes.DettachCommand + " failed due to " + sysEx.Message;
+                    logger.Error(details, sysEx);
+                }
+
+                object ansContent = new
+                {
+                    result = result,
+                    details = details,
+                    contextMap = contextMap
+                };
+
+                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.DettachAnswer);
+            }
+        }
+
+        // POST api/HypervResource/RebootCommand
+        [HttpPost]
+        [ActionName(CloudStackTypes.RebootCommand)]
+        public JContainer RebootCommand([FromBody]dynamic cmd)
+        {
+            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
+            {
                 logger.Info(CloudStackTypes.RebootCommand + Utils.CleanString(cmd.ToString()));
 
-                string details = null;
-                bool result = false;
-
-                try
-                {
-                    string vmName = (string)cmd.vmName;
-                    var sys = wmiCallsV2.GetComputerSystem(vmName);
-                    if (sys == null)
-                    {
-                        details = CloudStackTypes.RebootCommand + " requested unknown VM " + vmName;
-                        logger.Error(details);
-                    }
-                    else
-                    {
-                        wmiCallsV2.SetState(sys, RequiredState.Reset);
-                        result = true;
-                    }
-                }
-                catch (Exception sysEx)
-                {
-                    details = CloudStackTypes.RebootCommand + " failed due to " + sysEx.Message;
-                    logger.Error(details, sysEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.RebootAnswer);
-            }
-        }
-
-        // POST api/HypervResource/DestroyCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.DestroyCommand)]
-        public JContainer DestroyCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.DestroyCommand + Utils.CleanString(cmd.ToString()));
-
-                string details = null;
-                bool result = false;
-
-                try
-                {
-                    // Assert
-                    String errMsg = "No 'volume' details in " + CloudStackTypes.DestroyCommand + " " + Utils.CleanString(cmd.ToString());
-                    if (cmd.volume == null)
-                    {
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-
-                    // Assert
-                    errMsg = "No valide path in DestroyCommand in " + CloudStackTypes.DestroyCommand + " " + (String)cmd.ToString();
-                    if (cmd.volume.path == null)
-                    {
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-
-                    String path = (string)cmd.volume.path;
-                    if (!File.Exists(path))
-                    {
-                        logger.Info(CloudStackTypes.DestroyCommand + ", but volume at pass already deleted " + path);
-                    }
-
-                    string vmName = (string)cmd.vmName;
-                    if (!string.IsNullOrEmpty(vmName) && File.Exists(path))
-                    {
-                        // Make sure that this resource is removed from the VM
-                        wmiCallsV2.DetachDisk(vmName, path);
-                    }
-
-                    File.Delete(path);
-                    result = true;
-                }
-                catch (Exception sysEx)
-                {
-                    details = CloudStackTypes.DestroyCommand + " failed due to " + sysEx.Message;
-                    logger.Error(details, sysEx);
-                }
-
-                object ansContent = new
-                    {
-                        result = result,
-                        details = details,
-                        contextMap = contextMap
-                    };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-            }
-        }
-
-        // POST api/HypervResource/DeleteCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.DeleteCommand)]
-        public JContainer DeleteCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.DestroyCommand + Utils.CleanString(cmd.ToString()));
-
-                string details = null;
-                bool result = false;
-
-                try
-                {
-                    // Assert
-                    String errMsg = "No 'volume' details in " + CloudStackTypes.DestroyCommand + " " + Utils.CleanString(cmd.ToString());
-                    VolumeObjectTO destVolumeObjectTO = VolumeObjectTO.ParseJson(cmd.data);
-
-                    if (destVolumeObjectTO.name == null)
-                    {
-                        logger.Error(errMsg);
-                        throw new ArgumentException(errMsg);
-                    }
-
-                    String path = destVolumeObjectTO.FullFileName;
-                    if (!File.Exists(path))
-                    {
-                        logger.Info(CloudStackTypes.DestroyCommand + ", but volume at pass already deleted " + path);
-                    }
-
-                    string vmName = (string)cmd.vmName;
-                    if (!string.IsNullOrEmpty(vmName) && File.Exists(path))
-                    {
-                        // Make sure that this resource is removed from the VM
-                        wmiCallsV2.DetachDisk(vmName, path);
-                    }
-
-                    File.Delete(path);
-                    result = true;
-                }
-                catch (Exception sysEx)
-                {
-                    details = CloudStackTypes.DestroyCommand + " failed due to " + sysEx.Message;
-                    logger.Error(details, sysEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-            }
-        }
-
-        
-        private static JArray ReturnCloudStackTypedJArray(object ansContent, string ansType)
-        {
-            JObject ansObj = Utils.CreateCloudStackObject(ansType, ansContent);
-            JArray answer = new JArray(ansObj);
-            logger.Info(Utils.CleanString(ansObj.ToString()));
-            return answer;
-        }
-
-        // POST api/HypervResource/CreateCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.CreateCommand)]
-        public JContainer CreateCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CreateCommand + Utils.CleanString(cmd.ToString()));
-
-                string details = null;
-                bool result = false;
-                VolumeInfo volume = new VolumeInfo();
-
-                try
-                {
-                    string diskType = cmd.diskCharacteristics.type;
-                    ulong disksize = cmd.diskCharacteristics.size;
-                    string templateUri = cmd.templateUrl;
-
-                    // assert: valid storagepool?
-                    string poolTypeStr = cmd.pool.type;
-                    string poolLocalPath = cmd.pool.path;
-                    string poolUuid = cmd.pool.uuid;
-                    string newVolPath = null;
-                    long volId = cmd.volId;
-                    string newVolName = null;
-
-                    if (ValidStoragePool(poolTypeStr, poolLocalPath, poolUuid, ref details))
-                    {
-                        // No template URI?  Its a blank disk.
-                        if (string.IsNullOrEmpty(templateUri))
-                        {
-                            // assert
-                            VolumeType volType;
-                            if (!Enum.TryParse<VolumeType>(diskType, out volType) && volType != VolumeType.DATADISK)
-                            {
-                                details = "Cannot create volumes of type " + (string.IsNullOrEmpty(diskType) ? "NULL" : diskType);
-                            }
-                            else
-                            {
-                                newVolName = cmd.diskCharacteristics.name;
-                                newVolPath = Path.Combine(poolLocalPath, newVolName, diskType.ToLower());
-                                // TODO: make volume format and block size configurable
-                                wmiCallsV2.CreateDynamicVirtualHardDisk(disksize, newVolPath);
-                                if (File.Exists(newVolPath))
-                                {
-                                    result = true;
-                                }
-                                else
-                                {
-                                    details = "Failed to create DATADISK with name " + newVolName;
-                                }
-                            }
-                        }
-                        else
-                        {
-                            // TODO:  Does this always work, or do I need to download template at times?
-                            if (templateUri.Contains("/") || templateUri.Contains("\\"))
-                            {
-                                details = "Problem with templateURL " + templateUri +
-                                                " the URL should be volume UUID in primary storage created by previous PrimaryStorageDownloadCommand";
-                                logger.Error(details);
-                            }
-                            else
-                            {
-                                logger.Debug("Template's name in primary store should be " + templateUri);
-                                //            HypervPhysicalDisk BaseVol = primaryPool.getPhysicalDisk(tmplturl);
-                                FileInfo srcFileInfo = new FileInfo(templateUri);
-                                newVolName = Guid.NewGuid() + srcFileInfo.Extension;
-                                newVolPath = Path.Combine(poolLocalPath, newVolName);
-                                logger.Debug("New volume will be at " + newVolPath);
-                                string oldVolPath = Path.Combine(poolLocalPath, templateUri);
-                                File.Copy(oldVolPath, newVolPath);
-                                if (File.Exists(newVolPath))
-                                {
-                                    result = true;
-                                }
-                                else
-                                {
-                                    details = "Failed to create DATADISK with name " + newVolName;
-                                }
-                            }
-                            volume = new VolumeInfo(
-                                      volId, diskType,
-                                    poolTypeStr, poolUuid, newVolName,
-                                    newVolPath, newVolPath, (long)disksize, null);
-                        }
-                    }
-                }
-                catch (Exception sysEx)
-                {
-                    // TODO: consider this as model for error processing in all commands
-                    details = CloudStackTypes.CreateCommand + " failed due to " + sysEx.Message;
-                    logger.Error(details, sysEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    volume = volume,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CreateAnswer);
-            }
-        }
-
-        // POST api/HypervResource/PrimaryStorageDownloadCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.PrimaryStorageDownloadCommand)]
-        public JContainer PrimaryStorageDownloadCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.PrimaryStorageDownloadCommand + Utils.CleanString(cmd.ToString()));
-                string details = null;
-                bool result = false;
-                long size = 0;
-                string newCopyFileName = null;
-
-                string poolLocalPath = cmd.localPath;
-                string poolUuid = cmd.poolUuid;
-                if (!Directory.Exists(poolLocalPath))
-                {
-                    details = "None existent local path " + poolLocalPath;
-                }
-                else
-                {
-                    // Compose name for downloaded file.
-                    string sourceUrl = cmd.url;
-                    if (sourceUrl.ToLower().EndsWith(".vhd"))
-                    {
-                        newCopyFileName = Guid.NewGuid() + ".vhd";
-                    }
-                    if (sourceUrl.ToLower().EndsWith(".vhdx"))
-                    {
-                        newCopyFileName = Guid.NewGuid() + ".vhdx";
-                    }
-
-                    // assert
-                    if (newCopyFileName == null)
-                    {
-                        details = CloudStackTypes.PrimaryStorageDownloadCommand + " Invalid file extension for hypervisor type in source URL " + sourceUrl;
-                        logger.Error(details);
-                    }
-                    else
-                    {
-                        try
-                        {
-                            FileInfo newFile;
-                            if (CopyURI(sourceUrl, newCopyFileName, poolLocalPath, out newFile, ref details))
-                            {
-                                size = newFile.Length;
-                                result = true;
-                            }
-                        }
-                        catch (System.Exception ex)
-                        {
-                            details = CloudStackTypes.PrimaryStorageDownloadCommand + " Cannot download source URL " + sourceUrl + " due to " + ex.Message;
-                            logger.Error(details, ex);
-                        }
-                    }
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    templateSize = size,
-                    installPath = newCopyFileName,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.PrimaryStorageDownloadAnswer);
-            }
-        }
-
-        private static bool ValidStoragePool(string poolTypeStr, string poolLocalPath, string poolUuid, ref string details)
-        {
-            StoragePoolType poolType;
-            if (!Enum.TryParse<StoragePoolType>(poolTypeStr, out poolType) || poolType != StoragePoolType.Filesystem)
-            {
-                details = "Primary storage pool " + poolUuid + " type " + poolType + " local path " + poolLocalPath + " has invalid StoragePoolType";
-                logger.Error(details);
-                return false;
-            }
-            else if (!Directory.Exists(poolLocalPath))
-            {
-                details = "Primary storage pool " + poolUuid + " type " + poolType + " local path " + poolLocalPath + " has invalid local path";
-                logger.Error(details);
-                return false;
-            }
-            return true;
-        }
-
-        /// <summary>
-        /// Exceptions to watch out for:
-        /// Exceptions related to URI creation
-        /// System.SystemException
-        /// +-System.ArgumentNullException
-        /// +-System.FormatException
-        ///   +-System.UriFormatException
-        ///
-        /// Exceptions related to NFS URIs
-        /// System.SystemException
-        /// +-System.NotSupportedException
-        /// +-System.ArgumentException
-        /// +-System.ArgumentNullException
-        ///   +-System.Security.SecurityException;
-        /// +-System.UnauthorizedAccessException
-        /// +-System.IO.IOException
-        ///   +-System.IO.PathTooLongException
-        ///   
-        /// Exceptions related to HTTP URIs
-        /// System.SystemException
-        /// +-System.InvalidOperationException
-        ///    +-System.Net.WebException
-        /// +-System.NotSupportedException
-        /// +-System.ArgumentNullException
-        /// </summary>
-        /// <param name="sourceUri"></param>
-        /// <param name="newCopyFileName"></param>
-        /// <param name="poolLocalPath"></param>
-        /// <returns></returns>
-        private bool CopyURI(string sourceUri, string newCopyFileName, string poolLocalPath, out FileInfo newFile, ref string details)
-        {
-            Uri source = new Uri(sourceUri);
-            String destFilePath = Path.Combine(poolLocalPath, newCopyFileName);
-            string[] pathSegments = source.Segments;
-            String templateUUIDandExtension = pathSegments[pathSegments.Length - 1];
-            newFile = new FileInfo(destFilePath);
-
-            // NFS URI assumed to already be mounted locally.  Mount location given by settings.
-            if (source.Scheme.ToLower().Equals("nfs"))
-            {
-                String srcDiskPath = Path.Combine(HypervResourceController.config.LocalSecondaryStoragePath, templateUUIDandExtension);
-                String taskMsg = "Copy NFS url in " + sourceUri + " at " + srcDiskPath + " to pool " + poolLocalPath;
-                logger.Debug(taskMsg);
-                File.Copy(srcDiskPath, destFilePath);
-            }
-            else if (source.Scheme.ToLower().Equals("http") || source.Scheme.ToLower().Equals("https"))
-            {
-                System.Net.WebClient webclient = new WebClient();
-                webclient.DownloadFile(source, destFilePath);
-            }
-            else
-            {
-                details = "Unsupported URI scheme " + source.Scheme.ToLower() + " in source URI " + sourceUri;
-                logger.Error(details);
-                return false;
-            }
-
-            if (!File.Exists(destFilePath))
-            {
-                details = "Filed to copy " + sourceUri + " to primary pool destination " + destFilePath;
-                logger.Error(details);
-                return false;
-            }
-            return true;
-        }
-
-        // POST api/HypervResource/CheckHealthCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.CheckHealthCommand)]
-        public JContainer CheckHealthCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CheckHealthCommand + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                {
-                    result = true,
-                    details = "resource is alive",
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CheckHealthAnswer);
-            }
-        }
-
-        // POST api/HypervResource/CheckOnHostCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.CheckOnHostCommand)]
-        public JContainer CheckOnHostCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CheckOnHostCommand + Utils.CleanString(cmd.ToString()));
-                string details = "host is not alive";
-                bool result = true;
-                try
-                {
-                    foreach (string poolPath in config.getAllPrimaryStorages())
-                    {
-                        if (IsHostAlive(poolPath, (string)cmd.host.privateNetwork.ip))
-                        {
-                            result = false;
-                            details = "host is alive";
-                            break;
-                        }
-                    }
-                }
-                catch (Exception e)
-                {
-                    logger.Error("Error Occurred in " + CloudStackTypes.CheckOnHostCommand + " : " + e.Message);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CheckOnHostAnswer);
-            }
-        }
-
-        private bool IsHostAlive(string poolPath, string privateIp)
-        {
-            bool hostAlive = false;
-            try
-            {
-                string hbFile = Path.Combine(poolPath, "hb-" + privateIp);
-                FileInfo file = new FileInfo(hbFile);
-                using (StreamReader sr = file.OpenText())
-                {
-                    string epoch = sr.ReadLine();
-                    string[] dateTime = epoch.Split('@');
-                    string[] date = dateTime[0].Split('-');
-                    string[] time = dateTime[1].Split(':');
-                    DateTime epochTime = new DateTime(Convert.ToInt32(date[0]), Convert.ToInt32(date[1]), Convert.ToInt32(date[2]), Convert.ToInt32(time[0]),
-                        Convert.ToInt32(time[1]), Convert.ToInt32(time[2]), DateTimeKind.Utc);
-                    DateTime currentTime = DateTime.UtcNow;
-                    DateTime ThreeMinuteLaterEpoch = epochTime.AddMinutes(3);
-                    if (currentTime.CompareTo(ThreeMinuteLaterEpoch) < 0)
-                    {
-                        hostAlive = true;
-                    }
-                    sr.Close();
-                }
-            }
-            catch (Exception e)
-            {
-                logger.Info("Exception occurred in verifying host " + e.Message);
-            }
-
-            return hostAlive;
-        }
-
-        // POST api/HypervResource/CheckSshCommand
-        // TODO: create test
-        [HttpPost]
-        [ActionName(CloudStackTypes.CheckSshCommand)]
-        public JContainer CheckSshCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CheckSshCommand + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                {
-                    result = true,
-                    details = "NOP, TODO: implement properly",
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CheckSshAnswer);
-            }
-        }
-
-        // POST api/HypervResource/CheckVirtualMachineCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.CheckVirtualMachineCommand)]
-        public JContainer CheckVirtualMachineCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CheckVirtualMachineCommand + Utils.CleanString(cmd.ToString()));
-                string details = null;
-                bool result = false;
-                string vmName = cmd.vmName;
-                string state = null;
-
-                // TODO: Look up the VM, convert Hyper-V state to CloudStack version.
-                var sys = wmiCallsV2.GetComputerSystem(vmName);
-                if (sys == null)
-                {
-                    details = CloudStackTypes.CheckVirtualMachineCommand + " requested unknown VM " + vmName;
-                    logger.Error(details);
-                }
-                else
-                {
-                    state = EnabledState.ToCloudStackState(sys.EnabledState); // TODO: V2 changes?
-                    result = true;
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    state = state,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CheckVirtualMachineAnswer);
-            }
-        }
-
-        // POST api/HypervResource/DeleteStoragePoolCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.DeleteStoragePoolCommand)]
-        public JContainer DeleteStoragePoolCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.DeleteStoragePoolCommand + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                {
-                    result = true,
-                    details = "Current implementation does not delete local path corresponding to storage pool!",
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-            }
-        }
-
-        /// <summary>
-        /// NOP - legacy command -
-        /// POST api/HypervResource/CreateStoragePoolCommand
-        /// </summary>
-        /// <param name="cmd"></param>
-        /// <returns></returns>
-        [HttpPost]
-        [ActionName(CloudStackTypes.CreateStoragePoolCommand)]
-        public JContainer CreateStoragePoolCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CreateStoragePoolCommand + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                {
-                    result = true,
-                    details = "success - NOP",
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-            }
-        }
-
-        // POST api/HypervResource/ModifyStoragePoolCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.ModifyStoragePoolCommand)]
-        public JContainer ModifyStoragePoolCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.ModifyStoragePoolCommand + Utils.CleanString(cmd.ToString()));
-                string details = null;
-                string localPath;
-                StoragePoolType poolType;
-                object ansContent;
-
-                bool result = ValidateStoragePoolCommand(cmd, out localPath, out poolType, ref details);
-                if (!result)
-                {
-                    ansContent = new
-                    {
-                        result = result,
-                        details = details,
-                        contextMap = contextMap
-                    };
-                    return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-                }
-
-                var tInfo = new Dictionary<string, string>();
-                long capacityBytes = 0;
-                long availableBytes = 0;
-                string hostPath = null;
-                if (poolType == StoragePoolType.Filesystem)
-                {
-                    GetCapacityForLocalPath(localPath, out capacityBytes, out availableBytes);
-                    hostPath = localPath;
-                }
-                else if (poolType == StoragePoolType.NetworkFilesystem ||
-                    poolType == StoragePoolType.SMB)
-                {
-                    NFSTO share = new NFSTO();
-                    String uriStr = "cifs://" + (string)cmd.pool.host + (string)cmd.pool.path;
-                    share.uri = new Uri(uriStr);
-                    hostPath = Utils.NormalizePath(share.UncPath);
-
-                    // Check access to share.
-                    Utils.GetShareDetails(share.UncPath, out capacityBytes, out availableBytes);
-                    config.setPrimaryStorage((string)cmd.pool.uuid, hostPath);
-                }
-                else
-                {
-                    result = false;
-                }
-
-                String uuid = null;
-                var poolInfo = new
-                {
-                    uuid = uuid,
-                    host = cmd.pool.host,
-                    hostPath = cmd.pool.path,
-                    localPath = hostPath,
-                    poolType = cmd.pool.type,
-                    capacityBytes = capacityBytes,
-                    availableBytes = availableBytes
-                };
-
-                ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    localPath = hostPath,
-                    templateInfo = tInfo,
-                    poolInfo = poolInfo,
-                    contextMap = contextMap
-                };
-
-                if (result)
-                {
-                    try
-                    {
-                        if ((bool)cmd.add)
-                        {
-                            logger.Info("Adding HeartBeat Task to task scheduler for pool " + (string)cmd.pool.uuid);
-                            Utils.AddHeartBeatTask((string)cmd.pool.uuid, hostPath, config.PrivateIpAddress);
-                        }
-                        else
-                        {
-                            logger.Info("Deleting HeartBeat Task from task scheduler for pool " + (string)cmd.pool.uuid);
-                            Utils.RemoveHeartBeatTask(cmd.pool.uuid);
-                        }
-                    }
-                    catch (Exception e)
-                    {
-                        logger.Error("Error occurred in adding/delete HeartBeat Task to/from Task Scheduler : " + e.Message);
-                    }
-                }
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.ModifyStoragePoolAnswer);
-            }
-        }
-
-        private bool ValidateStoragePoolCommand(dynamic cmd, out string localPath, out StoragePoolType poolType, ref string details)
-        {
-            dynamic pool = cmd.pool;
-            string poolTypeStr = pool.type;
-            localPath = cmd.localPath;
-            if (!Enum.TryParse<StoragePoolType>(poolTypeStr, out poolType))
-            {
-                details = "Request to create / modify unsupported pool type: " + (poolTypeStr == null ? "NULL" : poolTypeStr) + "in cmd " + JsonConvert.SerializeObject(cmd);
-                logger.Error(details);
-                return false;
-            }
-
-            if (poolType != StoragePoolType.Filesystem &&
-                poolType != StoragePoolType.NetworkFilesystem &&
-                poolType != StoragePoolType.SMB)
-            {
-                details = "Request to create / modify unsupported pool type: " + (poolTypeStr == null ? "NULL" : poolTypeStr) + "in cmd " + JsonConvert.SerializeObject(cmd);
-                logger.Error(details);
-                return false;
-            }
-
-            return true;
-        }
-
-        // POST api/HypervResource/PlugNicCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.PlugNicCommand)]
-        public JContainer PlugNicCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.PlugNicCommand + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                {
-                    result = true,
-                    details = "Hot Nic plug not supported, change any empty virtual network adapter network settings",
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.PlugNicAnswer);
-            }
-        }
-
-
-        // POST api/HypervResource/CleanupNetworkRulesCmd
-        [HttpPost]
-        [ActionName(CloudStackTypes.CleanupNetworkRulesCmd)]
-        public JContainer CleanupNetworkRulesCmd([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CleanupNetworkRulesCmd + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                 {
-                     result = false,
-                     details = "nothing to cleanup in our current implementation",
-                     contextMap = contextMap
-                 };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-            }
-        }
-
-        // POST api/HypervResource/CheckNetworkCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.CheckNetworkCommand)]
-        public JContainer CheckNetworkCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CheckNetworkCommand + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                {
-                    result = true,
-                    details = (string)null,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CheckNetworkAnswer);
-            }
-        }
-
-        // POST api/HypervResource/ReadyCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.ReadyCommand)]
-        public JContainer ReadyCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.ReadyCommand + Utils.CleanString(cmd.ToString()));
-                object ansContent = new
-                {
-                    result = true,
-                    details = (string)null,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.ReadyAnswer);
-            }
-
-        }
-
-        // POST api/HypervResource/StartCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.StartCommand)]
-        public JContainer StartCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.StartCommand + Utils.CleanString(cmd.ToString()));
-                string details = null;
-                bool result = false;
-
-                try
-                {
-                    string systemVmIsoPath = systemVmIso;
-                    lock (systemVmIso)
-                    {
-                        systemVmIsoPath = systemVmIso;
-                        String uriStr = (String)cmd.secondaryStorage;
-                        if (!String.IsNullOrEmpty(uriStr))
-                        {
-                            if (String.IsNullOrEmpty(systemVmIsoPath) || !File.Exists(systemVmIsoPath))
-                            {
-                                NFSTO share = new NFSTO();
-                                share.uri = new Uri(uriStr);
-                                string defaultDataPath = wmiCallsV2.GetDefaultDataRoot();
-
-                                string secondaryPath = Utils.NormalizePath(Path.Combine(share.UncPath, "systemvm"));
-                                string[] choices = Directory.GetFiles(secondaryPath, "systemvm*.iso");
-                                if (choices.Length != 1)
-                                {
-                                    String errMsg = "Couldn't locate the systemvm iso on " + secondaryPath;
-                                    logger.Debug(errMsg);
-                                }
-                                else
-                                {
-                                    systemVmIsoPath = Utils.NormalizePath(Path.Combine(defaultDataPath, Path.GetFileName(choices[0])));
-                                    if (!File.Exists(systemVmIsoPath))
-                                    {
-                                        Utils.DownloadCifsFileToLocalFile(choices[0], share, systemVmIsoPath);
-                                    }
-                                    systemVmIso = systemVmIsoPath;
-                                }
-                            }
-                        }
-                    }
-
-                    wmiCallsV2.DeployVirtualMachine(cmd, systemVmIsoPath);
-                    result = true;
-                }
-                catch (Exception wmiEx)
-                {
-                    details = CloudStackTypes.StartCommand + " fail on exception" + wmiEx.Message;
-                    logger.Error(details, wmiEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    vm = cmd.vm,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.StartAnswer);
-            }
-        }
-
-        // POST api/HypervResource/StopCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.StopCommand)]
-        public JContainer StopCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.StopCommand + Utils.CleanString(cmd.ToString()));
-                string details = null;
-                bool result = false;
-                bool checkBeforeCleanup = cmd.checkBeforeCleanup;
-                String vmName = cmd.vmName;
-
-                if (checkBeforeCleanup == true)
-                {
-                    ComputerSystem vm = wmiCallsV2.GetComputerSystem(vmName);
-                    if (vm == null || vm.EnabledState == 2)
-                    {
-                        // VM is not available or vm in running state
-                        return ReturnCloudStackTypedJArray(new { result = false, details = "VM is running on host, bailing out", vm = vmName, contextMap = contextMap }, CloudStackTypes.StopAnswer);
-                    }
-                }
-                try
-                {
-                    wmiCallsV2.DestroyVm(cmd);
-                    result = true;
-                }
-                catch (Exception wmiEx)
-                {
-                    details = CloudStackTypes.StopCommand + " fail on exception" + wmiEx.Message;
-                    logger.Error(details, wmiEx);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    vm = cmd.vm,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.StopAnswer);
-            }
-        }
-
-        // POST api/HypervResource/CreateObjectCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.CreateObjectCommand)]
-        public JContainer CreateObjectCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.CreateObjectCommand + Utils.CleanString(cmd.ToString()));
-
-                bool result = false;
-                string details = null;
-                object newData = null;
-                try
-                {
-                    VolumeObjectTO volume = VolumeObjectTO.ParseJson(cmd.data);
-                    PrimaryDataStoreTO primary = volume.primaryDataStore;
-                    ulong volumeSize = volume.size;
-                    string volumeName = volume.uuid + ".vhdx";
-                    string volumePath = null;
-
-                    if (primary.isLocal)
-                    {
-                        volumePath = Path.Combine(primary.Path, volumeName);
-                    }
-                    else
-                    {
-                        volumePath = @"\\" + primary.uri.Host + primary.uri.LocalPath + @"\" + volumeName;
-                        volumePath = Utils.NormalizePath(volumePath);
-                    }
-                    volume.path = volume.uuid;
-                    wmiCallsV2.CreateDynamicVirtualHardDisk(volumeSize, volumePath);
-                    if (File.Exists(volumePath))
-                    {
-                        result = true;
-                        JObject ansObj = Utils.CreateCloudStackObject(CloudStackTypes.VolumeObjectTO, volume);
-                        newData = ansObj;
-                    }
-                    else
-                    {
-                        details = "Failed to create disk with name " + volumePath;
-                    }
-                }
-                catch (Exception ex)
-                {
-                    // Test by providing wrong key
-                    details = CloudStackTypes.CreateObjectCommand + " failed on exception, " + ex.Message;
-                    logger.Error(details, ex);
-                }
-
-                object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    data = newData,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CreateObjectAnswer);
-            }
-        }
-
-        // POST api/HypervResource/MaintainCommand
-        // TODO: should this be a NOP?
-        [HttpPost]
-        [ActionName(CloudStackTypes.MaintainCommand)]
-        public JContainer MaintainCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.MaintainCommand + Utils.CleanString(cmd.ToString()));
-
-                object ansContent = new
-                {
-                    result = true,
-                    willMigrate = true,
-                    details = "success - NOP for MaintainCommand",
-                    _reconnect = false,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.MaintainAnswer);
-            }
-        }
-
-        // POST api/HypervResource/PingRoutingCommand
-        // TODO: should this be a NOP?
-        [HttpPost]
-        [ActionName(CloudStackTypes.PingRoutingCommand)]
-        public JContainer PingRoutingCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.PingRoutingCommand + Utils.CleanString(cmd.ToString()));
-
-                object ansContent = new
-                {
-                    result = true,
-                    details = "success - NOP for PingRoutingCommand",
-                    _reconnect = false,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-            }
-        }
-
-        // POST api/HypervResource/PingCommand
-        // TODO: should this be a NOP?
-        [HttpPost]
-        [ActionName(CloudStackTypes.PingCommand)]
-        public JContainer PingCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.PingCommand + Utils.CleanString(cmd.ToString()));
-
-                object ansContent = new
-                {
-                    result = true,
-                    details = "success - NOP for PingCommand",
-                    _reconnect = false,
-                    contextMap = contextMap
-                };
-
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.Answer);
-            }
-        }
-
-        // POST api/HypervResource/ModifyVmVnicVlanCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.ModifyVmNicConfigCommand)]
-        public JContainer ModifyVmNicConfigCommand([FromBody]dynamic cmd)
-        {
-
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.ModifyVmNicConfigCommand + Utils.CleanString(cmd.ToString()));
-                bool result = false;
-                String vmName = cmd.vmName;
-                String vlan = cmd.vlan;
-                string macAddress = cmd.macAddress;
-                uint pos = cmd.index;
-                bool enable = cmd.enable;
-                string switchLableName = cmd.switchLableName;
-                if (macAddress != null)
-                {
-                    wmiCallsV2.ModifyVmVLan(vmName, vlan, macAddress);
-                    result = true;
-                }
-                else if (pos >= 1)
-                {
-                    wmiCallsV2.ModifyVmVLan(vmName, vlan, pos, enable, switchLableName);
-                    result = true;
-                }
-
-                object ansContent = new
-                {
-                    vmName = vmName,
-                    result = result,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.ModifyVmNicConfigAnswer);
-            }
-
-        }
-
-        // POST api/HypervResource/GetVmConfigCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.GetVmConfigCommand)]
-        public JContainer GetVmConfigCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.GetVmConfigCommand + Utils.CleanString(cmd.ToString()));
-                bool result = false;
-                String vmName = cmd.vmName;
-                ComputerSystem vm = wmiCallsV2.GetComputerSystem(vmName);
-                List<NicDetails> nicDetails = new List<NicDetails>();
-                var nicSettingsViaVm = wmiCallsV2.GetEthernetPortSettings(vm);
-                NicDetails nic = null;
-                int index = 0;
-                int[] nicStates = new int[8];
-                int[] nicVlan = new int[8];
-                int vlanid = 1;
-
-                var ethernetConnections = wmiCallsV2.GetEthernetConnections(vm);
-                foreach (EthernetPortAllocationSettingData item in ethernetConnections)
-                {
-                    EthernetSwitchPortVlanSettingData vlanSettings = wmiCallsV2.GetVlanSettings(item);
-                    if (vlanSettings == null)
-                    {
-                        vlanid = -1;
-                    }
-                    else
-                    {
-                        vlanid = vlanSettings.AccessVlanId;
-                    }
-                    nicStates[index] = (Int32)(item.EnabledState);
-                    nicVlan[index] = vlanid;
-                    index++;
-                }
-
-                index = 0;
-                foreach (SyntheticEthernetPortSettingData item in nicSettingsViaVm)
-                {
-                    nic = new NicDetails(item.Address, nicVlan[index], nicStates[index]);
-                    index++;
-                    nicDetails.Add(nic);
-                }
-
-
-                result = true;
-
-                object ansContent = new
-                {
-                    vmName = vmName,
-                    nics = nicDetails,
-                    result = result,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.GetVmConfigAnswer);
-            }
-        }
-
-
-
-        // POST api/HypervResource/GetVmStatsCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.GetVmStatsCommand)]
-        public JContainer GetVmStatsCommand([FromBody]dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                logger.Info(CloudStackTypes.GetVmStatsCommand + Utils.CleanString(cmd.ToString()));
-                bool result = false;
-                JArray vmNamesJson = cmd.vmNames;
-                string[] vmNames = vmNamesJson.ToObject<string[]>();
-                Dictionary<string, VmStatsEntry> vmProcessorInfo = new Dictionary<string, VmStatsEntry>(vmNames.Length);
-
-                var vmsToInspect = new List<System.Management.ManagementPath>();
-                foreach (var vmName in vmNames)
-                {
-                    var sys = wmiCallsV2.GetComputerSystem(vmName);
-                    if (sys == null)
-                    {
-                        logger.InfoFormat("GetVmStatsCommand requested unknown VM {0}", vmNames);
-                        continue;
-                    }
-                    var sysInfo = wmiCallsV2.GetVmSettings(sys);
-                    vmsToInspect.Add(sysInfo.Path);
-                }
-
-                wmiCallsV2.GetSummaryInfo(vmProcessorInfo, vmsToInspect);
-
-                // TODO: Network usage comes from Performance Counter API; however it is only available in kb/s, and not in total terms.
-                // Curious about these?  Use perfmon to inspect them, e.g. http://msdn.microsoft.com/en-us/library/xhcx5a20%28v=vs.100%29.aspx
-                // Recent post on these counter at http://blogs.technet.com/b/cedward/archive/2011/07/19/hyper-v-networking-optimizations-part-6-of-6-monitoring-hyper-v-network-consumption.aspx
-                result = true;
-
-                object ansContent = new
-                {
-                    vmStatsMap = vmProcessorInfo,
-                    result = result,
-                    contextMap = contextMap
-                };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.GetVmStatsAnswer);
-            }
-        }
-
-        // POST api/HypervResource/CopyCommand
-        [HttpPost]
-        [ActionName(CloudStackTypes.CopyCommand)]
-        public JContainer CopyCommand(dynamic cmd)
-        {
-            using (log4net.NDC.Push(Guid.NewGuid().ToString()))
-            {
-                // Log command *after* we've removed security details from the command.
-                logger.Info(CloudStackTypes.CopyCommand + Utils.CleanString(cmd.ToString()));
-
-                bool result = false;
-                string details = null;
-                object newData = null;
-                TemplateObjectTO destTemplateObjectTO = null;
-                VolumeObjectTO destVolumeObjectTO = null;
-                VolumeObjectTO srcVolumeObjectTO = null;
-                TemplateObjectTO srcTemplateObjectTO = null;
-
-                try
-                {
-                    dynamic timeout = cmd.wait;  // TODO: Useful?
-
-                    srcTemplateObjectTO = TemplateObjectTO.ParseJson(cmd.srcTO);
-                    destTemplateObjectTO = TemplateObjectTO.ParseJson(cmd.destTO);
-                    srcVolumeObjectTO = VolumeObjectTO.ParseJson(cmd.srcTO);
-                    destVolumeObjectTO = VolumeObjectTO.ParseJson(cmd.destTO);
-
-                    string destFile = null;
-                    if (destTemplateObjectTO != null)
-                    {
-                        if (destTemplateObjectTO.primaryDataStore != null)
-                        {
-                            destFile = destTemplateObjectTO.FullFileName;
-                        }
-                        else if (destTemplateObjectTO.nfsDataStoreTO != null)
-                        {
-                            destFile = destTemplateObjectTO.FullFileName;
-                        }
-                    }
-
-                    // Template already downloaded?
-                    if (destFile != null && File.Exists(destFile) &&
-                        !String.IsNullOrEmpty(destTemplateObjectTO.checksum))
+                string details = null;
+                bool result = false;
+
+                try
+                {
+                    string vmName = (string)cmd.vmName;
+                    var sys = wmiCallsV2.GetComputerSystem(vmName);
+                    if (sys == null)
                     {
-                        // TODO: checksum fails us, because it is of the compressed image.
-                        // ASK: should we store the compressed or uncompressed version or is the checksum not calculated correctly?
-                        logger.Debug(CloudStackTypes.CopyCommand + " calling VerifyChecksum to see if we already have the file at " + destFile);
-                        result = VerifyChecksum(destFile, destTemplateObjectTO.checksum);
-                        if (!result)
-                        {
-                            result = true;
-                            logger.Debug(CloudStackTypes.CopyCommand + " existing file has different checksum " + destFile);
-                        }
+                        details = CloudStackTypes.RebootCommand + " requested unknown VM " + vmName;
+                        logger.Error(details);
                     }
-
-                    // Do we have to create a new one?
-                    if (!result)
+                    else
                     {
-                        // Create local copy of a template?
-                        if (srcTemplateObjectTO != null && destTemplateObjectTO != null)
-                        {
-                            // S3 download to primary storage?
-                            // NFS provider download to primary storage?
-                            if ((srcTemplateObjectTO.s3DataStoreTO != null || srcTemplateObjectTO.nfsDataStoreTO != null) && destTemplateObjectTO.primaryDataStore != null)
-                            {
-                                if (File.Exists(destFile))
-                                {
-                                    logger.Info("Deleting existing file " + destFile);
-                                    File.Delete(destFile);
-                                }
-
-                                if (srcTemplateObjectTO.s3DataStoreTO != null)
-                                {
-                                    // Download from S3 to destination data storage
-                                    DownloadS3ObjectToFile(srcTemplateObjectTO.path, srcTemplateObjectTO.s3DataStoreTO, destFile);
-                                }
-                                else if (srcTemplateObjectTO.nfsDataStoreTO != null)
-                                {
-                                    // Download from S3 to destination data storage
-                                    Utils.DownloadCifsFileToLocalFile(srcTemplateObjectTO.path, srcTemplateObjectTO.nfsDataStoreTO, destFile);
-                                }
-
-                                // Uncompress, as required
-                                if (srcTemplateObjectTO.path.EndsWith(".bz2"))
-                                {
-                                    String uncompressedFile = destFile + ".tmp";
-                                    String compressedFile = destFile;
-                                    using (var uncompressedOutStrm = new FileStream(uncompressedFile, FileMode.CreateNew, FileAccess.Write))
-                                    {
-                                        using (var compressedInStrm = new FileStream(destFile, FileMode.Open, FileAccess.Read))
-                                        {
-                                            using (var bz2UncompressorStrm = new Ionic.BZip2.BZip2InputStream(compressedInStrm, true) /* outer 'using' statement will close FileStream*/ )
-                                            {
-                                                int count = 0;
-                                                int bufsize = 1024 * 1024;
-                                                byte[] buf = new byte[bufsize];
-
-                                                // EOF returns -1, see http://dotnetzip.codeplex.com/workitem/16069 
-                                                while (0 < (count = bz2UncompressorStrm.Read(buf, 0, bufsize)))
-                                                {
-                                                    uncompressedOutStrm.Write(buf, 0, count);
-                                                }
-                                            }
-                                        }
-                                    }
-                                    File.Delete(compressedFile);
-                                    File.Move(uncompressedFile, compressedFile);
-                                    if (File.Exists(uncompressedFile))
-                                    {
-                                        String errMsg = "Extra file left around called " + uncompressedFile + " when creating " + destFile;
-                                        logger.Error(errMsg);
-                                        throw new IOException(errMsg);
-                                    }
-                                }
-
-                                // assert
-                                if (!File.Exists(destFile))
-                                {
-                                    String errMsg = "Failed to create " + destFile + " , because the file is missing";
-                                    logger.Error(errMsg);
-                                    throw new IOException(errMsg);
-                                }
-
-                                newData = cmd.destTO;
-                                result = true;
-                            }
-                            else
-                            {
-                                details = "Data store combination not supported";
-                            }
-                        }
-                        // Create volume from a template?
-                        else if (srcTemplateObjectTO != null && destVolumeObjectTO != null)
-                        {
-                            // VolumeObjectTO guesses file extension based on existing files
-                            // this can be wrong if the previous file had a different file type
-                            var guessedDestFile = destVolumeObjectTO.FullFileName;
-                            if (File.Exists(guessedDestFile))
-                            {
-                                logger.Info("Deleting existing file " + guessedDestFile);
-                                File.Delete(guessedDestFile);
-                            }
-
-                            destVolumeObjectTO.format = srcTemplateObjectTO.format;
-                            destFile = destVolumeObjectTO.FullFileName;
-                            if (File.Exists(destFile))
-                            {
-                                logger.Info("Deleting existing file " + destFile);
-                                File.Delete(destFile);
-                            }
-
-                            string srcFile = srcTemplateObjectTO.FullFileName;
-                            if (!File.Exists(srcFile))
-                            {
-                                details = "Local template file missing from " + srcFile;
-                            }
-                            else
-                            {
-                                // TODO: thin provision instead of copying the full file.
-                                File.Copy(srcFile, destFile);
-                                destVolumeObjectTO.path = destVolumeObjectTO.uuid;
-                                JObject ansObj = Utils.CreateCloudStackObject(CloudStackTypes.VolumeObjectTO, destVolumeObjectTO);
-                                newData = ansObj;
-                                result = true;
-                            }
-                        }
-                        else if (srcVolumeObjectTO != null && destVolumeObjectTO != null)
-                        {
-                            var guessedDestFile = destVolumeObjectTO.FullFileName;
-                            if (File.Exists(guessedDestFile))
-                            {
-                                logger.Info("Deleting existing file " + guessedDestFile);
-                                File.Delete(guessedDestFile);
-                            }
-
-                            destVolumeObjectTO.format = srcVolumeObjectTO.format;
-                            destFile = destVolumeObjectTO.FullFileName;
-                            if (File.Exists(destFile))
-                            {
-                                logger.Info("Deleting existing file " + destFile);
-                                File.Delete(destFile);
-                            }
-
-                            string srcFile = srcVolumeObjectTO.FullFileName;
-                            if (!File.Exists(srcFile))
-                            {
-                                details = "Local template file missing from " + srcFile;
-                            }
-                            else
-                            {
-                                // Create the directory before copying the files. CreateDirectory
-                                // doesn't do anything if the directory is already present.
-                                Directory.CreateDirectory(Path.GetDirectoryName(destFile));
-                                File.Copy(srcFile, destFile);
-
-                                if (srcVolumeObjectTO.nfsDataStore != null && srcVolumeObjectTO.primaryDataStore == null)
-                                {
-                                    logger.Info("Copied volume from secondary data store to primary. Path: " + destVolumeObjectTO.path);
-                                }
-                                else if (srcVolumeObjectTO.primaryDataStore != null && srcVolumeObjectTO.nfsDataStore == null)
-                                {
-                                    destVolumeObjectTO.path = destVolumeObjectTO.path + "/" + destVolumeObjectTO.uuid;
-                                    if (destVolumeObjectTO.format != null)
-                                    {
-                                        destVolumeObjectTO.path += "." + destVolumeObjectTO.format.ToLower();
-                                    }
-                                }
-                                else
-                                {
-                                    logger.Error("Destination volume path wasn't set. Unsupported source volume data store.");
-                                }
-
-                                // Create volumeto object deserialize and send it
-                                JObject ansObj = Utils.CreateCloudStackObject(CloudStackTypes.VolumeObjectTO, destVolumeObjectTO);
-                                newData = ansObj;
-                                result = true;
-                            }
-                        }
-                        else if (srcVolumeObjectTO != null && destTemplateObjectTO != null)
-                        {
-                            var guessedDestFile = destTemplateObjectTO.FullFileName;
-                            if (File.Exists(guessedDestFile))
-                            {
-                                logger.Info("Deleting existing file " + guessedDestFile);
-                                File.Delete(guessedDestFile);
-                            }
-
-                            destTemplateObjectTO.format = srcVolumeObjectTO.format;
-                            destFile = destTemplateObjectTO.FullFileName;
-                            if (File.Exists(destFile))
-                            {
-                                logger.Info("Deleting existing file " + destFile);
-                                File.Delete(destFile);
-                            }
-
-                            string srcFile = srcVolumeObjectTO.FullFileName;
-                            if (!File.Exists(srcFile))
-                            {
-                                details = "Local template file missing from " + srcFile;
-                            }
-                            else
-                            {
-                                // Create the directory before copying the files. CreateDirectory
-                                // doesn't do anything if the directory is already present.
-                                Directory.CreateDirectory(Path.GetDirectoryName(destFile));
-                                File.Copy(srcFile, destFile);
-
-                                FileInfo destFileInfo = new FileInfo(destFile);
-                                // Write the template.properties file
-                                PostCreateTemplate(Path.GetDirectoryName(destFile), destTemplateObjectTO.id, destTemplateObjectTO.name,
-                                    destFileInfo.Length.ToString(), srcVolumeObjectTO.size.ToString(), destTemplateObjectTO.format);
-
-                                TemplateObjectTO destTemplateObject = new TemplateObjectTO();
-                                destTemplateObject.size = srcVolumeObjectTO.size.ToString();
-                                destTemplateObject.format = srcVolumeObjectTO.format;
-                                destTemplateObject.path = destTemplateObjectTO.path + "/" + destTemplateObjectTO.uuid;
-                                if (destTemplateObject.format != null)
-                                {
-                                    destTemplateObject.path += "." + destTemplateObject.format.ToLower();
-                                }
-                                destTemplateObject.nfsDataStoreTO = destTemplateObjectTO.nfsDataStoreTO;
-                                destTemplateObject.checksum = destTemplateObjectTO.checksum;
-                                newData = destTemplateObject;
-                                JObject ansObj = Utils.CreateCloudStackObject(CloudStackTypes.TemplateObjectTO, destTemplateObject);
-                                newData = ansObj;
-                                result = true;
-                            }
-                        }
-                        else
-                        {
-                            details = "Data store combination not supported";
-                        }
+                        wmiCallsV2.SetState(sys, RequiredState.Reset);
+                        result = true;
                     }
                 }
-                catch (Exception ex)
+                catch (Exception sysEx)
                 {
-                    // Test by providing wrong key
-                    details = CloudStackTypes.CopyCommand + " failed on exception, " + ex.Message;
-                    logger.Error(details, ex);
+                    details = CloudStackTypes.RebootCommand + " failed due to " + sysEx.Message;
+                    logger.Error(details, sysEx);
                 }
 
                 object ansContent = new
                 {
                     result = result,
                     details = details,
-                    newData = newData,
                     contextMap = contextMap
                 };
-                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.CopyCmdAnswer);
-            }
-        }
-
-        private static void PostCreateTemplate(string path, string templateId, string templateUuid, string physicalSize, string virtualSize, string format)
-        {
-            string templatePropFile = Path.Combine(path, "template.properties");
-            using (StreamWriter sw = new StreamWriter(File.Open(templatePropFile, FileMode.Create), Encoding.GetEncoding("iso-8859-1")))
-            {
-                if (format != null)
-                {
-                    format = format.ToLower();
-                }
-
-                sw.NewLine = "\n";
-                sw.WriteLine("id=" + templateId);
-                sw.WriteLine("filename=" + templateUuid + "." + format);
-                sw.WriteLine(format + ".filename=" + templateUuid + "." + format);
-                sw.WriteLine("uniquename=" + templateUuid);
-                sw.WriteLine(format + "=true");
-                sw.WriteLine("virtualsize=" + virtualSize);
-                sw.WriteLine(format + ".virtualsize=" + virtualSize);
-                sw.WriteLine("size=" + physicalSize);
-                sw.WriteLine(format + ".size=" + physicalSize);
-                sw.WriteLine("public=false");
-            }
-        }
-
-        private static bool VerifyChecksum(string destFile, string checksum)
-        {
-            string localChecksum = BitConverter.ToString(CalcFileChecksum(destFile)).Replace("-", "").ToLower();
-            logger.Debug("Checksum of " + destFile + " is " + checksum);
-            if (checksum.Equals(localChecksum))
-            {
-                return true;
-            }
-            return false;
-        }
-
-        /// <summary>
-        /// Match implmentation of DownloadManagerImpl.computeCheckSum
-        /// </summary>
-        /// <param name="destFile"></param>
-        /// <returns></returns>
-        private static byte[] CalcFileChecksum(string destFile)
-        {
-            // TODO:  Add unit test to verify that checksum algorithm has not changed.
-            using (MD5 md5 = MD5.Create())
-            {
-                using (FileStream stream = File.OpenRead(destFile))
-                {
-                    return md5.ComputeHash(stream);
-                }
-            }
-        }
-
-        private static void DownloadS3ObjectToFile(string srcObjectKey, S3TO srcS3TO, string destFile)
-        {
-            AmazonS3Config S3Config = new AmazonS3Config
-            {
-                ServiceURL = srcS3TO.endpoint,
-                CommunicationProtocol = Amazon.S3.Model.Protocol.HTTP
-            };
-
-            if (srcS3TO.httpsFlag)
-            {
-                S3Config.CommunicationProtocol = Protocol.HTTPS;
-            }
-
-            try
-            {
-                using (AmazonS3 client = Amazon.AWSClientFactory.CreateAmazonS3Client(srcS3TO.accessKey, srcS3TO.secretKey, S3Config))
-                {
-                    GetObjectRequest getObjectRequest = new GetObjectRequest().WithBucketName(srcS3TO.bucketName).WithKey(srcObjectKey);
 
-                    using (S3Response getObjectResponse = client.GetObject(getObjectRequest))
-                    {
-                        using (Stream s = getObjectResponse.ResponseStream)
-                        {
-                            using (FileStream fs = new FileStream(destFile, FileMode.Create, FileAccess.Write))
-                            {
-                                byte[] data = new byte[524288];
-                                int bytesRead = 0;
-                                do
-                                {
-                                    bytesRead = s.Read(data, 0, data.Length);
-                                    fs.Write(data, 0, bytesRead);
-                                }
-                                while (bytesRead > 0);
-                                fs.Flush();
-                            }
-                        }
-                    }
-                }
-            }
-            catch (Exception ex)
-            {
-                string errMsg = "Download from S3 url" + srcS3TO.endpoint + " said: " + ex.Message;
-                logger.Error(errMsg, ex);
-                throw new Exception(errMsg, ex);
+                return ReturnCloudStackTypedJArray(ansContent, CloudStackTypes.RebootAnswer);
             }
         }
 
-        // POST api/HypervResource/GetStorageStatsCommand
+        // POST api/HypervResource/DestroyCommand
         [HttpPost]
-        [ActionName(CloudStackTypes.GetStorageStatsCommand)]
-        public JContainer GetStorageStatsCommand([FromBody]dynamic cmd)
+        [ActionName(CloudStackTypes.DestroyCommand)]
+        public JContainer DestroyCommand([FromBody]dynamic cmd)
         {
             using (log4net.NDC.Push(Guid.NewGuid().ToString()))
             {
-                logger.Info(CloudStackTypes.GetStorageStatsCommand + Utils.CleanString(cmd.ToString()));
-                bool result = false;
+                logger.Info(CloudStackTypes.DestroyCommand + Utils.CleanString(cmd.ToString()));
+
                 string details = null;
-                long capacity = 0;
-                long available = 0;
-                long used = 0;
+                bool result = false;
+
                 try
                 {
-                    StoragePoolType poolType;
-                    string poolId = (string)cmd.id;
-                    string hostPath = null;
-                    if (!Enum.TryParse<StoragePoolType>((string)cmd.pooltype, out poolType))
-                    {
-                        details = "Request to get unsupported pool type: " + ((string)cmd.pooltype == null ? "NULL" : (string)cmd.pooltype) + "in cmd " +
-                            JsonConvert.SerializeObject(cmd);
-                        logger.Error(details);
-                    }
-                    else if (poolType == StoragePoolType.Filesystem)
+                    // Assert
+                    String errMsg = "No 'volume' details in " + CloudStackTypes.DestroyCommand + " " + Utils.CleanString(cmd.ToString());
+                    if (cmd.volume == null)
                     {
-                        hostPath = (string)cmd.localPath;;
-                        GetCapacityForLocalPath(hostPath, out capacity, out available);
-                        used = capacity - available;
-                        result = true;
+                        logger.Error(errMsg);
+                        throw new ArgumentException(errMsg);
                     }
-                    else if (poolType == StoragePoolType.NetworkFilesystem || poolType == StoragePoolType.SMB)
+
+                    // Assert
+                    errMsg = "No valide path in DestroyCommand in " + CloudStackTypes.DestroyCommand + " " + (String)cmd.ToString();
+                    if (cmd.volume.path == null)
                     {
-                        string sharePath = config.getPrimaryStorage((string)cmd.id);
-                        if (sharePath != null)
-                        {
-                            hostPath = sharePath;
-                            Utils.GetShareDetails(sharePath, out capacity, out available);
-                            used = capacity - available;
-                            result = true;
-                        }
+                        logger.Error(errMsg);
+                        throw new ArgumentException(errMsg);
                     }
-                    else
+
+                    String path = (string)cmd.volume.path;
+                    if (!File.Exists(path))
                     {
-                        result = false;
+                        logger.Info(CloudStackTypes.DestroyCommand + ", but volume at pass already deleted " + path);
                     }
 
-                    if (result)
+                    string vmName = (string)cmd.vmName;
+                    if (!string.IsNullOrEmpty(vmName) && File.Exists(path))
                     {
-                        logger.Debug(CloudStackTypes.GetStorageStatsCommand + " set used bytes for " + hostPath + " to " + used);
+                        // Make sure that this resource is removed from the VM
+                        wmiCallsV2.DetachDisk(vmName, path);
                     }
+
+                    File.Delete(path);
+                    result = true;
                 }
-                catch (Exception ex)
+                catch (Exception sysEx)
                 {
-                    details = CloudStackTypes.GetStorageStatsCommand + " failed on exception" + ex.Message;
-                    logger.Error(details, ex);
+                    details = CloudStackTypes.DestroyCommand + " failed due to " + sysEx.Message;
+                    logger.Error(details, sysEx);
                 }
 
                 object ansContent = new
-                {
-                    result = result,
-                    details = details,
-                    capacity = capacity,

<TRUNCATED>

[3/3] git commit: updated refs/heads/4.4 to 8fb89cd

Posted by da...@apache.org.
CLOUDSTACK-6504: removed warnings coming in building hyper-v agent code

(cherry picked from commit 66f8e0e1b5c81cbfde926c0c65c4d5969767cab9)

Conflicts:
	plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/HypervResourceController.cs
	plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/WmiCallsV2.cs


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/8fb89cdc
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/8fb89cdc
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/8fb89cdc

Branch: refs/heads/4.4
Commit: 8fb89cdc8e2dff60d49fecd3e51a9bf997061035
Parents: 48f9453
Author: Anshul Gangwar <an...@citrix.com>
Authored: Thu Apr 24 22:30:12 2014 -0700
Committer: Daan Hoogland <da...@onecht.net>
Committed: Mon Jul 28 17:31:03 2014 +0200

----------------------------------------------------------------------
 .../HypervResource/CloudStackTypes.cs           |    8 +-
 .../HypervResource/HypervResourceController.cs  | 3558 +++++++++---------
 .../ServerResource/HypervResource/Utils.cs      |    4 +-
 .../ServerResource/HypervResource/WmiCallsV2.cs | 1483 +++++---
 4 files changed, 2740 insertions(+), 2313 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/8fb89cdc/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/CloudStackTypes.cs
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/CloudStackTypes.cs b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/CloudStackTypes.cs
index ef24c79..4516191 100644
--- a/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/CloudStackTypes.cs
+++ b/plugins/hypervisors/hyperv/DotNet/ServerResource/HypervResource/CloudStackTypes.cs
@@ -302,7 +302,7 @@ namespace HypervResource
                 path = Utils.NormalizePath(path);
                 if (Directory.Exists(path))
                 {
-                    string[] choices = choices = Directory.GetFiles(path, volInfo.uuid + ".vhd*");
+                    string[] choices = Directory.GetFiles(path, volInfo.uuid + ".vhd*");
                     if (choices.Length != 1)
                     {
                         String errMsg = "Tried to guess file extension, but cannot find file corresponding to " +
@@ -609,6 +609,7 @@ namespace HypervResource
 
     public struct VolumeInfo
     {
+#pragma warning disable 0414
         public long id;
         public string type;
         public string storagePoolType;
@@ -618,6 +619,7 @@ namespace HypervResource
         public string path;
         long size;
         string chainInfo;
+#pragma warning restore 0414
 
         public VolumeInfo(long id, string type, string poolType, String poolUuid, String name, String mountPoint, String path, long size, String chainInfo)
         {
@@ -635,10 +637,12 @@ namespace HypervResource
 
     public class VmState
     {
+#pragma warning disable 0414
         [JsonProperty("state")]
         public String state;
         [JsonProperty("host")]
         String host;
+#pragma warning restore 0414
         public VmState() { }
         public VmState(String vmState, String host)
         {
@@ -649,6 +653,7 @@ namespace HypervResource
 
     public struct StoragePoolInfo
     {
+#pragma warning disable 0414
         [JsonProperty("uuid")]
         public String uuid;
         [JsonProperty("host")]
@@ -667,6 +672,7 @@ namespace HypervResource
         long availableBytes;
         [JsonProperty("details")]
         Dictionary<String, String> details;
+#pragma warning restore 0414
 
         public StoragePoolInfo(String uuid, String host, String hostPath,
                 String localPath, string poolType, long capacityBytes,