github.com/vmware/govmomi@v0.37.2/vim25/types/helpers.go (about)

     1  /*
     2  Copyright (c) 2015-2022 VMware, Inc. All Rights Reserved.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8      http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package types
    18  
    19  import (
    20  	"net/url"
    21  	"reflect"
    22  	"strings"
    23  	"time"
    24  )
    25  
    26  func NewBool(v bool) *bool {
    27  	return &v
    28  }
    29  
    30  func NewInt32(v int32) *int32 {
    31  	return &v
    32  }
    33  
    34  func NewInt64(v int64) *int64 {
    35  	return &v
    36  }
    37  
    38  func NewTime(v time.Time) *time.Time {
    39  	return &v
    40  }
    41  
    42  func NewReference(r ManagedObjectReference) *ManagedObjectReference {
    43  	return &r
    44  }
    45  
    46  func (r ManagedObjectReference) Reference() ManagedObjectReference {
    47  	return r
    48  }
    49  
    50  func (r ManagedObjectReference) String() string {
    51  	return strings.Join([]string{r.Type, r.Value}, ":")
    52  }
    53  
    54  func (r *ManagedObjectReference) FromString(o string) bool {
    55  	s := strings.SplitN(o, ":", 2)
    56  
    57  	if len(s) != 2 {
    58  		return false
    59  	}
    60  
    61  	r.Type = s[0]
    62  	r.Value = s[1]
    63  
    64  	return true
    65  }
    66  
    67  // Encode ManagedObjectReference for use with URL and File paths
    68  func (r ManagedObjectReference) Encode() string {
    69  	return strings.Join([]string{r.Type, url.QueryEscape(r.Value)}, "-")
    70  }
    71  
    72  func (c *PerfCounterInfo) Name() string {
    73  	return c.GroupInfo.GetElementDescription().Key + "." + c.NameInfo.GetElementDescription().Key + "." + string(c.RollupType)
    74  }
    75  
    76  func defaultResourceAllocationInfo() ResourceAllocationInfo {
    77  	return ResourceAllocationInfo{
    78  		Reservation:           NewInt64(0),
    79  		ExpandableReservation: NewBool(true),
    80  		Limit:                 NewInt64(-1),
    81  		Shares: &SharesInfo{
    82  			Level: SharesLevelNormal,
    83  		},
    84  	}
    85  }
    86  
    87  // DefaultResourceConfigSpec returns a ResourceConfigSpec populated with the same default field values as vCenter.
    88  // Note that the wsdl marks these fields as optional, but they are required to be set when creating a resource pool.
    89  // They are only optional when updating a resource pool.
    90  func DefaultResourceConfigSpec() ResourceConfigSpec {
    91  	return ResourceConfigSpec{
    92  		CpuAllocation:    defaultResourceAllocationInfo(),
    93  		MemoryAllocation: defaultResourceAllocationInfo(),
    94  	}
    95  }
    96  
    97  // ToConfigSpec returns a VirtualMachineConfigSpec based on the
    98  // VirtualMachineConfigInfo.
    99  func (ci VirtualMachineConfigInfo) ToConfigSpec() VirtualMachineConfigSpec {
   100  	cs := VirtualMachineConfigSpec{
   101  		ChangeVersion:                ci.ChangeVersion,
   102  		Name:                         ci.Name,
   103  		Version:                      ci.Version,
   104  		CreateDate:                   ci.CreateDate,
   105  		Uuid:                         ci.Uuid,
   106  		InstanceUuid:                 ci.InstanceUuid,
   107  		NpivNodeWorldWideName:        ci.NpivNodeWorldWideName,
   108  		NpivPortWorldWideName:        ci.NpivPortWorldWideName,
   109  		NpivWorldWideNameType:        ci.NpivWorldWideNameType,
   110  		NpivDesiredNodeWwns:          ci.NpivDesiredNodeWwns,
   111  		NpivDesiredPortWwns:          ci.NpivDesiredPortWwns,
   112  		NpivTemporaryDisabled:        ci.NpivTemporaryDisabled,
   113  		NpivOnNonRdmDisks:            ci.NpivOnNonRdmDisks,
   114  		LocationId:                   ci.LocationId,
   115  		GuestId:                      ci.GuestId,
   116  		AlternateGuestName:           ci.AlternateGuestName,
   117  		Annotation:                   ci.Annotation,
   118  		Files:                        &ci.Files,
   119  		Tools:                        ci.Tools,
   120  		Flags:                        &ci.Flags,
   121  		ConsolePreferences:           ci.ConsolePreferences,
   122  		PowerOpInfo:                  &ci.DefaultPowerOps,
   123  		NumCPUs:                      ci.Hardware.NumCPU,
   124  		VcpuConfig:                   ci.VcpuConfig,
   125  		NumCoresPerSocket:            ci.Hardware.NumCoresPerSocket,
   126  		MemoryMB:                     int64(ci.Hardware.MemoryMB),
   127  		MemoryHotAddEnabled:          ci.MemoryHotAddEnabled,
   128  		CpuHotAddEnabled:             ci.CpuHotAddEnabled,
   129  		CpuHotRemoveEnabled:          ci.CpuHotRemoveEnabled,
   130  		VirtualICH7MPresent:          ci.Hardware.VirtualICH7MPresent,
   131  		VirtualSMCPresent:            ci.Hardware.VirtualSMCPresent,
   132  		DeviceChange:                 make([]BaseVirtualDeviceConfigSpec, len(ci.Hardware.Device)),
   133  		CpuAllocation:                ci.CpuAllocation,
   134  		MemoryAllocation:             ci.MemoryAllocation,
   135  		LatencySensitivity:           ci.LatencySensitivity,
   136  		CpuAffinity:                  ci.CpuAffinity,
   137  		MemoryAffinity:               ci.MemoryAffinity,
   138  		NetworkShaper:                ci.NetworkShaper,
   139  		CpuFeatureMask:               make([]VirtualMachineCpuIdInfoSpec, len(ci.CpuFeatureMask)),
   140  		ExtraConfig:                  ci.ExtraConfig,
   141  		SwapPlacement:                ci.SwapPlacement,
   142  		BootOptions:                  ci.BootOptions,
   143  		FtInfo:                       ci.FtInfo,
   144  		RepConfig:                    ci.RepConfig,
   145  		VAssertsEnabled:              ci.VAssertsEnabled,
   146  		ChangeTrackingEnabled:        ci.ChangeTrackingEnabled,
   147  		Firmware:                     ci.Firmware,
   148  		MaxMksConnections:            ci.MaxMksConnections,
   149  		GuestAutoLockEnabled:         ci.GuestAutoLockEnabled,
   150  		ManagedBy:                    ci.ManagedBy,
   151  		MemoryReservationLockedToMax: ci.MemoryReservationLockedToMax,
   152  		NestedHVEnabled:              ci.NestedHVEnabled,
   153  		VPMCEnabled:                  ci.VPMCEnabled,
   154  		MessageBusTunnelEnabled:      ci.MessageBusTunnelEnabled,
   155  		MigrateEncryption:            ci.MigrateEncryption,
   156  		FtEncryptionMode:             ci.FtEncryptionMode,
   157  		SevEnabled:                   ci.SevEnabled,
   158  		PmemFailoverEnabled:          ci.PmemFailoverEnabled,
   159  		Pmem:                         ci.Pmem,
   160  		NpivWorldWideNameOp:          ci.NpivWorldWideNameType,
   161  		RebootPowerOff:               ci.RebootPowerOff,
   162  		ScheduledHardwareUpgradeInfo: ci.ScheduledHardwareUpgradeInfo,
   163  		SgxInfo:                      ci.SgxInfo,
   164  		GuestMonitoringModeInfo:      ci.GuestMonitoringModeInfo,
   165  		VmxStatsCollectionEnabled:    ci.VmxStatsCollectionEnabled,
   166  		VmOpNotificationToAppEnabled: ci.VmOpNotificationToAppEnabled,
   167  		VmOpNotificationTimeout:      ci.VmOpNotificationTimeout,
   168  		DeviceSwap:                   ci.DeviceSwap,
   169  		SimultaneousThreads:          ci.Hardware.SimultaneousThreads,
   170  		DeviceGroups:                 ci.DeviceGroups,
   171  		MotherboardLayout:            ci.Hardware.MotherboardLayout,
   172  	}
   173  
   174  	// Unassign the Files field if all of its fields are empty.
   175  	if ci.Files.FtMetadataDirectory == "" && ci.Files.LogDirectory == "" &&
   176  		ci.Files.SnapshotDirectory == "" && ci.Files.SuspendDirectory == "" &&
   177  		ci.Files.VmPathName == "" {
   178  		cs.Files = nil
   179  	}
   180  
   181  	// Unassign the Flags field if all of its fields are empty.
   182  	if ci.Flags.CbrcCacheEnabled == nil &&
   183  		ci.Flags.DisableAcceleration == nil &&
   184  		ci.Flags.DiskUuidEnabled == nil &&
   185  		ci.Flags.EnableLogging == nil &&
   186  		ci.Flags.FaultToleranceType == "" &&
   187  		ci.Flags.HtSharing == "" &&
   188  		ci.Flags.MonitorType == "" &&
   189  		ci.Flags.RecordReplayEnabled == nil &&
   190  		ci.Flags.RunWithDebugInfo == nil &&
   191  		ci.Flags.SnapshotDisabled == nil &&
   192  		ci.Flags.SnapshotLocked == nil &&
   193  		ci.Flags.SnapshotPowerOffBehavior == "" &&
   194  		ci.Flags.UseToe == nil &&
   195  		ci.Flags.VbsEnabled == nil &&
   196  		ci.Flags.VirtualExecUsage == "" &&
   197  		ci.Flags.VirtualMmuUsage == "" &&
   198  		ci.Flags.VvtdEnabled == nil {
   199  		cs.Flags = nil
   200  	}
   201  
   202  	// Unassign the PowerOps field if all of its fields are empty.
   203  	if ci.DefaultPowerOps.DefaultPowerOffType == "" &&
   204  		ci.DefaultPowerOps.DefaultResetType == "" &&
   205  		ci.DefaultPowerOps.DefaultSuspendType == "" &&
   206  		ci.DefaultPowerOps.PowerOffType == "" &&
   207  		ci.DefaultPowerOps.ResetType == "" &&
   208  		ci.DefaultPowerOps.StandbyAction == "" &&
   209  		ci.DefaultPowerOps.SuspendType == "" {
   210  		cs.PowerOpInfo = nil
   211  	}
   212  
   213  	for i := 0; i < len(cs.CpuFeatureMask); i++ {
   214  		cs.CpuFeatureMask[i] = VirtualMachineCpuIdInfoSpec{
   215  			ArrayUpdateSpec: ArrayUpdateSpec{
   216  				Operation: ArrayUpdateOperationAdd,
   217  			},
   218  			Info: &HostCpuIdInfo{
   219  				// TODO: Does DynamicData need to be copied?
   220  				//       It is an empty struct...
   221  				Level:  ci.CpuFeatureMask[i].Level,
   222  				Vendor: ci.CpuFeatureMask[i].Vendor,
   223  				Eax:    ci.CpuFeatureMask[i].Eax,
   224  				Ebx:    ci.CpuFeatureMask[i].Ebx,
   225  				Ecx:    ci.CpuFeatureMask[i].Ecx,
   226  				Edx:    ci.CpuFeatureMask[i].Edx,
   227  			},
   228  		}
   229  	}
   230  
   231  	for i := 0; i < len(cs.DeviceChange); i++ {
   232  		cs.DeviceChange[i] = &VirtualDeviceConfigSpec{
   233  			// TODO: Does DynamicData need to be copied?
   234  			//       It is an empty struct...
   235  			Operation:     VirtualDeviceConfigSpecOperationAdd,
   236  			FileOperation: VirtualDeviceConfigSpecFileOperationCreate,
   237  			Device:        ci.Hardware.Device[i],
   238  			// TODO: It is unclear how the profiles associated with the VM or
   239  			//       its hardware can be reintroduced/persisted in the
   240  			//       ConfigSpec.
   241  			Profile: nil,
   242  			// The backing will come from the device.
   243  			Backing: nil,
   244  			// TODO: Investigate futher.
   245  			FilterSpec: nil,
   246  		}
   247  	}
   248  
   249  	if ni := ci.NumaInfo; ni != nil {
   250  		cs.VirtualNuma = &VirtualMachineVirtualNuma{
   251  			CoresPerNumaNode:       ni.CoresPerNumaNode,
   252  			ExposeVnumaOnCpuHotadd: ni.VnumaOnCpuHotaddExposed,
   253  		}
   254  	}
   255  
   256  	if civa, ok := ci.VAppConfig.(*VmConfigInfo); ok {
   257  		var csva VmConfigSpec
   258  
   259  		csva.Eula = civa.Eula
   260  		csva.InstallBootRequired = &civa.InstallBootRequired
   261  		csva.InstallBootStopDelay = civa.InstallBootStopDelay
   262  
   263  		ipAssignment := civa.IpAssignment
   264  		csva.IpAssignment = &ipAssignment
   265  
   266  		csva.OvfEnvironmentTransport = civa.OvfEnvironmentTransport
   267  		for i := range civa.OvfSection {
   268  			s := civa.OvfSection[i]
   269  			csva.OvfSection = append(
   270  				csva.OvfSection,
   271  				VAppOvfSectionSpec{
   272  					ArrayUpdateSpec: ArrayUpdateSpec{
   273  						Operation: ArrayUpdateOperationAdd,
   274  					},
   275  					Info: &s,
   276  				},
   277  			)
   278  		}
   279  
   280  		for i := range civa.Product {
   281  			p := civa.Product[i]
   282  			csva.Product = append(
   283  				csva.Product,
   284  				VAppProductSpec{
   285  					ArrayUpdateSpec: ArrayUpdateSpec{
   286  						Operation: ArrayUpdateOperationAdd,
   287  					},
   288  					Info: &p,
   289  				},
   290  			)
   291  		}
   292  
   293  		for i := range civa.Property {
   294  			p := civa.Property[i]
   295  			csva.Property = append(
   296  				csva.Property,
   297  				VAppPropertySpec{
   298  					ArrayUpdateSpec: ArrayUpdateSpec{
   299  						Operation: ArrayUpdateOperationAdd,
   300  					},
   301  					Info: &p,
   302  				},
   303  			)
   304  		}
   305  
   306  		cs.VAppConfig = &csva
   307  	}
   308  
   309  	return cs
   310  }
   311  
   312  func init() {
   313  	// Known 6.5 issue where this event type is sent even though it is internal.
   314  	// This workaround allows us to unmarshal and avoid NPEs.
   315  	t["HostSubSpecificationUpdateEvent"] = reflect.TypeOf((*HostEvent)(nil)).Elem()
   316  }