dantmnf / WSLAttachSwitch

Attach the WSL2 virtual machine to a Hyper-V virtual switch.
The Unlicense
107 stars 12 forks source link

Can't delete VMSwitch after connecting with WSLAttach #10

Open nrclark opened 6 months ago

nrclark commented 6 months ago

I can attach a VMSwitch to WSL using WSLAttachSwitch.exe, and everything works fine. But when I try to delete the VMSwitch afterwords, this operation fails. It fails if I do it using the Hyper-V Manager GUI, and also if I try to do it in Powershell.

Here's a Powershell script that demonstrates the failure:

New-VMSwitch -Name "Testbench VMSwitch" -NetAdapterName MyAdapter

#ensure that WSL is running
wsl.exe sleep 0

WSLAttachSwitch.exe "Testbench VMSwitch"
wsl.exe --shutdown
Start-Sleep -Seconds 10
Remove-VMSwitch "Testbench VMSwitch" -Force

Everything works fine until my call to Remove-VMSwitch. But when I run that, it hangs at 0% until I kill the operation. After I've killed the operation, my machine is in an error-state where I can't modify, overwrite, or remove the VMSwitch instance.

What can I do to kill a switch before trying to delete it?

dantmnf commented 6 months ago

After wsl --shutdown, find the orphaned endpoint with hcsdiag list endpoints -d

> hcsdiag list endpoints -d
{
    "ID":"373d79f3-8aff-2b1f-e39e-1d5e6778e085",
    "Name":"Ethernet",
    "Version":64424509440,
    "AdditionalParams":{
        "SwitchId":"05712AA4-F8BD-4C7B-A6EE-1D5E6778E085",
        "SwitchPortId":"373D79F3-8AFF-2B1F-E39E-1D5E6778E085",
        "VmSwitchNicName":"F9B87977-8D0D-4CB9-803A-2E9C3A01A3C5--B6E33AEF-2D04-5717-A760-2E6278FB8F93"
    },
    "Resources":{
        "AdditionalParams":{

        },
        "AllocationOrder":1,
        "Allocators":[
            {
                "AdditionalParams":{

                },
                "AllocationOrder":0,
                "Connected":true,
                "EndpointId":"373D79F3-8AFF-2B1F-E39E-1D5E6778E085",
                "EndpointPortGuid":"373D79F3-8AFF-2B1F-E39E-1D5E6778E085",
                "Flags":0,
                "Health":{
                    "LastErrorCode":0,
                    "LastUpdateTime":133515791944042565
                },
                "ID":"F13A93E9-61D2-41D3-B8AF-33E22ADEA7C9",
                "IsPolicy":false,
                "IsolationId":0,
                "MacAddress":"00-15-5D-55-A8-40",
                "ManagementPort":false,
                "NetworkId":"05712AA4-F8BD-4C7B-A6EE-1D5E6778E085",
                "NicId":"F9B87977-8D0D-4CB9-803A-2E9C3A01A3C5--B6E33AEF-2D04-5717-A760-2E6278FB8F93",
                "PortFriendlyNamePrefix":"Endpoint Port",
                "PreferredPortFriendlyName":"373D79F3-8AFF-2B1F-E39E-1D5E6778E085",
                "State":3,
                "SwitchId":"05712AA4-F8BD-4C7B-A6EE-1D5E6778E085",
                "Tag":"VM Port",
                "VmPort":true,
                "nonPersistentPort":true
            }
        ],
        "CompartmentOperationTime":0,
        "Flags":0,
        "Health":{
            "LastErrorCode":0,
            "LastUpdateTime":133515791944032554
        },
        "ID":"0BC72CD6-41AD-418B-99E5-3CB353F16400",
        "PortOperationTime":0,
        "State":1,
        "SwitchOperationTime":0,
        "VfpOperationTime":0,
        "parentId":"F781002E-2B97-4C20-8981-99771FBEF38F"
    },
    "State":2,
    "VirtualNetwork":"05712aa4-f8bd-4c7b-a6ee-1d5e6778e085",
    "VirtualNetworkName":"Testbench VMSwitch",  <-- look at this
    "Policies":[
        {
            "Settings":{
                "IsolationId":4294967295
            },
            "Type":"VLAN"
        }
    ],
    "MacAddress":"00-15-5D-55-A8-40",
    "Flags":32,
    "SharedContainers":[

    ],
    "VirtualMachine":"F9B87977-8D0D-4CB9-803A-2E9C3A01A3C5" <-- find a VirtualMachine not present in `hcsdiag list`
}

Then remove the endpoint with hnsdiag remove endpoints $ID

hnsdiag remove endpoints 373d79f3-8aff-2b1f-e39e-1d5e6778e085

Now the virtual switch could be removed without issues. Maybe we can add some cleanup functionality to this tool.