Repository: vmware/govmomi
Pull request #3175 (2023-07-10 20:38:06)

fix: check the error chain when validating if it's x509 error
## Description

Please include a summary of the change and which issue is fixed. Please also
include relevant motivation and context. List any dependencies that are required
for this change.

Check the error chain when checking if error is x509 related. This should be compatible with both golang 1.20 and 1.19

Closes: #https://github.com/vmware/govmomi/issues/3174

## Type of change

Please mark options that are relevant:

- [x] Bug fix (non-breaking change which fixes an issue)
- [ ] New feature (non-breaking change which adds functionality)
- [ ] Breaking change (fix or feature that would cause existing functionality to
  not work as expected)
- [ ] This change requires a documentation update
- [ ] Build related change

## How Has This Been Tested?

Please describe the tests that you ran to verify your changes. Provide
instructions so we can reproduce. If applicable, please also list any relevant
details for your test configuration.

- [x] Test Description 1
Compiles CPI with 1.20 and configures CPI with tlsthumbprint, and the error doesn't appear.
- [ ] Test Description 2


## Checklist:

- [x] My code follows the `CONTRIBUTION`
  [guidelines](https://github.com/vmware/govmomi/blob/main/CONTRIBUTING.md) of
  this project
- [x] I have commented my code, particularly in hard-to-understand areas
- [ ] I have made corresponding changes to the documentation
- [ ] I have added tests that prove my fix is effective or that my feature works
- [ ] New and existing unit tests pass locally with my changes
- [ ] Any dependent changes have been merged

sbueringer: cc @dougm 
lubronzhan: I think Doug is on PTO this week, he should be able to review this next week
sbueringer: Perfect!

Patch:
diff --git a/object/virtual_device_list.go b/object/virtual_device_list.go
index 92797dcd..37655065 100644
--- a/object/virtual_device_list.go
+++ b/object/virtual_device_list.go
@@ -404,13 +404,9 @@ func (l VirtualDeviceList) PickController(kind types.BaseVirtualController) type
 }
 
 // newUnitNumber returns the unit number to use for attaching a new device to the given controller.
-func (l VirtualDeviceList) newUnitNumber(c types.BaseVirtualController, offset int) int32 {
+func (l VirtualDeviceList) newUnitNumber(c types.BaseVirtualController) int32 {
 	units := make([]bool, 30)
 
-	for i := 0; i < offset; i++ {
-		units[i] = true
-	}
-
 	switch sc := c.(type) {
 	case types.BaseVirtualSCSIController:
 		//  The SCSI controller sits on its own bus
@@ -459,14 +455,7 @@ func (l VirtualDeviceList) AssignController(device types.BaseVirtualDevice, c ty
 	d := device.GetVirtualDevice()
 	d.ControllerKey = c.GetVirtualController().Key
 	d.UnitNumber = new(int32)
-
-	offset := 0
-	switch device.(type) {
-	case types.BaseVirtualEthernetCard:
-		offset = 7
-	}
-	*d.UnitNumber = l.newUnitNumber(c, offset)
-
+	*d.UnitNumber = l.newUnitNumber(c)
 	if d.Key == 0 {
 		d.Key = l.newRandomKey()
 	}
diff --git a/vim25/soap/error.go b/vim25/soap/error.go
index cdf0a66b..fd30e3ff 100644
--- a/vim25/soap/error.go
+++ b/vim25/soap/error.go
@@ -19,6 +19,7 @@ package soap
 import (
 	"crypto/x509"
 	"encoding/json"
+	"errors"
 	"fmt"
 	"reflect"
 	"strings"
@@ -131,8 +132,18 @@ func ToVimFault(err error) types.BaseMethodFault {
 }
 
 func IsCertificateUntrusted(err error) bool {
-	switch err.(type) {
-	case x509.UnknownAuthorityError, x509.HostnameError:
+	// golang 1.20 introduce a new type to wrap 509 errors. So instead of
+	// casting the type, now we check the error chain contains the
+	// x509 error or not.
+	x509UnknownAuthorityErr := &x509.UnknownAuthorityError{}
+	ok := errors.As(err, x509UnknownAuthorityErr)
+	if ok {
+		return true
+	}
+
+	x509HostNameErr := &x509.HostnameError{}
+	ok = errors.As(err, x509HostNameErr)
+	if ok {
 		return true
 	}
 


Test patch:
diff --git a/object/virtual_device_list_test.go b/object/virtual_device_list_test.go
index 466fb02d..fef4db9e 100644
--- a/object/virtual_device_list_test.go
+++ b/object/virtual_device_list_test.go
@@ -698,7 +698,7 @@ func TestPickController(t *testing.T) {
 			t.Errorf("expected controller key: %d, got: %d\n", test.key, key)
 		}
 
-		unit := list.newUnitNumber(c, 0)
+		unit := list.newUnitNumber(c)
 		if unit != test.unit {
 			t.Errorf("expected unit number: %d, got: %d\n", test.unit, unit)
 		}