Nathan Gieseker 9a429d8d25 Windows: Updates Windows Vendoring
Updates windows dependent libraries for vendoing.
2019-01-23 18:43:18 -08:00

113 lines
3.6 KiB
Go

package uvm
import (
"fmt"
"strconv"
"github.com/Microsoft/hcsshim/internal/requesttype"
"github.com/Microsoft/hcsshim/internal/schema2"
"github.com/sirupsen/logrus"
)
// findVSMBShare finds a share by `hostPath`. If not found returns `ErrNotAttached`.
func (uvm *UtilityVM) findVSMBShare(hostPath string) (*vsmbShare, error) {
share, ok := uvm.vsmbShares[hostPath]
if !ok {
return nil, ErrNotAttached
}
return share, nil
}
func (share *vsmbShare) GuestPath() string {
return `\\?\VMSMB\VSMB-{dcc079ae-60ba-4d07-847c-3493609c0870}\` + share.name
}
// AddVSMB adds a VSMB share to a Windows utility VM. Each VSMB share is ref-counted and
// only added if it isn't already. This is used for read-only layers, mapped directories
// to a container, and for mapped pipes.
func (uvm *UtilityVM) AddVSMB(hostPath string, guestRequest interface{}, options *hcsschema.VirtualSmbShareOptions) error {
if uvm.operatingSystem != "windows" {
return errNotSupported
}
logrus.Debugf("uvm::AddVSMB %s %+v %+v id:%s", hostPath, guestRequest, options, uvm.id)
uvm.m.Lock()
defer uvm.m.Unlock()
share, err := uvm.findVSMBShare(hostPath)
if err == ErrNotAttached {
uvm.vsmbCounter++
shareName := "s" + strconv.FormatUint(uvm.vsmbCounter, 16)
modification := &hcsschema.ModifySettingRequest{
RequestType: requesttype.Add,
Settings: hcsschema.VirtualSmbShare{
Name: shareName,
Options: options,
Path: hostPath,
},
ResourcePath: "VirtualMachine/Devices/VirtualSmb/Shares",
}
if err := uvm.Modify(modification); err != nil {
return err
}
share = &vsmbShare{
name: shareName,
guestRequest: guestRequest,
}
uvm.vsmbShares[hostPath] = share
}
share.refCount++
logrus.Debugf("hcsshim::AddVSMB Success %s: refcount=%d %+v", hostPath, share.refCount, share)
return nil
}
// RemoveVSMB removes a VSMB share from a utility VM. Each VSMB share is ref-counted
// and only actually removed when the ref-count drops to zero.
func (uvm *UtilityVM) RemoveVSMB(hostPath string) error {
if uvm.operatingSystem != "windows" {
return errNotSupported
}
logrus.Debugf("uvm::RemoveVSMB %s id:%s", hostPath, uvm.id)
uvm.m.Lock()
defer uvm.m.Unlock()
share, err := uvm.findVSMBShare(hostPath)
if err != nil {
return fmt.Errorf("%s is not present as a VSMB share in %s, cannot remove", hostPath, uvm.id)
}
share.refCount--
if share.refCount > 0 {
logrus.Debugf("uvm::RemoveVSMB Success %s id:%s Ref-count now %d. It is still present in the utility VM", hostPath, uvm.id, share.refCount)
return nil
}
logrus.Debugf("uvm::RemoveVSMB Zero ref-count, removing. %s id:%s", hostPath, uvm.id)
modification := &hcsschema.ModifySettingRequest{
RequestType: requesttype.Remove,
Settings: hcsschema.VirtualSmbShare{Name: share.name},
ResourcePath: "VirtualMachine/Devices/VirtualSmb/Shares",
}
if err := uvm.Modify(modification); err != nil {
return fmt.Errorf("failed to remove vsmb share %s from %s: %+v: %s", hostPath, uvm.id, modification, err)
}
logrus.Debugf("uvm::RemoveVSMB Success %s id:%s successfully removed from utility VM", hostPath, uvm.id)
delete(uvm.vsmbShares, hostPath)
return nil
}
// GetVSMBUvmPath returns the guest path of a VSMB mount.
func (uvm *UtilityVM) GetVSMBUvmPath(hostPath string) (string, error) {
if hostPath == "" {
return "", fmt.Errorf("no hostPath passed to GetVSMBUvmPath")
}
uvm.m.Lock()
defer uvm.m.Unlock()
share, err := uvm.findVSMBShare(hostPath)
if err != nil {
return "", err
}
path := share.GuestPath()
logrus.Debugf("uvm::GetVSMBUvmPath Success %s id:%s path:%s", hostPath, uvm.id, path)
return path, nil
}