registry.go 1.61 KB
Newer Older
songlinfeng's avatar
songlinfeng committed
1
2
3
4
5
6
7
/**
# Copyright (c) 2024, HCUOpt CORPORATION.  All rights reserved.
**/

package cdi

import (
8
9
	"dcu-container-toolkit/internal/logger"
	"dcu-container-toolkit/internal/oci"
songlinfeng's avatar
songlinfeng committed
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
	"errors"
	"fmt"

	"github.com/opencontainers/runtime-spec/specs-go"
	"tags.cncf.io/container-device-interface/pkg/cdi"
)

// fromRegistry represents the modifications performed using a CDI registry.
type fromRegistry struct {
	logger   logger.Interface
	registry *cdi.Cache
	devices  []string
}

var _ oci.SpecModifier = (*fromRegistry)(nil)

// Modify applies the modifications defined by the CDI registry to the incoming OCI spec.
func (m fromRegistry) Modify(spec *specs.Spec) error {
	if err := m.registry.Refresh(); err != nil {
		m.logger.Debugf("The following error was triggered when refreshing the CDI registry: %v", err)
	}

	m.logger.Debugf("Injecting devices using CDI: %v", m.devices)
	unresolvedDevices, err := m.registry.InjectDevices(spec, m.devices...)
	if unresolvedDevices != nil {
		m.logger.Warningf("could not resolve CDI devices: %v", unresolvedDevices)
	}
	if err != nil {
		var refreshErrors []error
		for _, rerrs := range m.registry.GetErrors() {
			refreshErrors = append(refreshErrors, rerrs...)
		}
		if rerr := errors.Join(refreshErrors...); rerr != nil {
			// We log the errors that may have been generated while refreshing the CDI registry.
			// These may be due to malformed specifications or device name conflicts that could be
			// the cause of an injection failure.
			m.logger.Warningf("Refreshing the CDI registry generated errors: %v", rerr)
		}

		return fmt.Errorf("failed to inject CDI devices: %v", err)
	}

	return nil
}