//go:build windows package remotevm import ( "context" "net" "os" "github.com/Microsoft/go-winio/pkg/guid" "github.com/Microsoft/hcsshim/internal/vm" "github.com/Microsoft/hcsshim/internal/vmservice" "github.com/pkg/errors" ) func (uvm *utilityVM) VMSocketListen(ctx context.Context, listenType vm.VMSocketType, connID interface{}) (_ net.Listener, err error) { // Make a temp file and delete to "reserve" a unique name for the unix socket f, err := os.CreateTemp("", "") if err != nil { return nil, errors.Wrap(err, "failed to create temp file for unix socket") } if err := f.Close(); err != nil { return nil, errors.Wrap(err, "failed to close temp file") } if err := os.Remove(f.Name()); err != nil { return nil, errors.Wrap(err, "failed to delete temp file to free up name") } l, err := net.Listen("unix", f.Name()) if err != nil { return nil, errors.Wrapf(err, "failed to listen on unix socket %q", f.Name()) } defer func() { if err != nil { _ = l.Close() } }() switch listenType { case vm.HvSocket: serviceGUID, ok := connID.(guid.GUID) if !ok { return nil, errors.New("parameter passed to hvsocketlisten is not a GUID") } if err := uvm.hvSocketListen(ctx, serviceGUID.String(), f.Name()); err != nil { return nil, errors.Wrap(err, "failed to setup relay to hvsocket listener") } case vm.VSock: port, ok := connID.(uint32) if !ok { return nil, errors.New("parameter passed to vsocklisten is not the right type") } if err := uvm.vsockListen(ctx, port, f.Name()); err != nil { return nil, errors.Wrap(err, "failed to setup relay to vsock listener") } default: return nil, errors.New("unknown vmsocket type requested") } return l, nil } func (uvm *utilityVM) hvSocketListen(ctx context.Context, serviceID string, listenerPath string) error { if _, err := uvm.client.VMSocket(ctx, &vmservice.VMSocketRequest{ Type: vmservice.ModifyType_ADD, Config: &vmservice.VMSocketRequest_HvsocketList{ HvsocketList: &vmservice.HVSocketListen{ ServiceID: serviceID, ListenerPath: listenerPath, }, }, }); err != nil { return err } return nil } func (uvm *utilityVM) vsockListen(ctx context.Context, port uint32, listenerPath string) error { if _, err := uvm.client.VMSocket(ctx, &vmservice.VMSocketRequest{ Type: vmservice.ModifyType_ADD, Config: &vmservice.VMSocketRequest_VsockListen{ VsockListen: &vmservice.VSockListen{ Port: port, ListenerPath: listenerPath, }, }, }); err != nil { return err } return nil }