Coverage for cuda / core / system / _field_values.pxi: 66.67%
36 statements
« prev ^ index » next coverage.py v7.14.0, created at 2026-05-22 01:37 +0000
« prev ^ index » next coverage.py v7.14.0, created at 2026-05-22 01:37 +0000
1# SPDX-FileCopyrightText: Copyright (c) 2025-2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
2#
3# SPDX-License-Identifier: Apache-2.0
6cdef class FieldValue:
7 """
8 Represents the data from a single field value.
10 Use :meth:`Device.get_field_values` to get multiple field values at once.
11 """
12 cdef object _field_value
14 def __init__(self, field_value: nvml.FieldValue):
15 assert len(field_value) == 1 1a
16 self._field_value = field_value 1a
18 @property
19 def field_id(self) -> FieldId:
20 """
21 The field ID.
22 """
23 return FieldId(self._field_value.field_id) 1a
25 @property
26 def scope_id(self) -> int:
27 """
28 The scope ID.
29 """
30 # Explicit int() cast required because this is a Numpy type
31 return int(self._field_value.scope_id)
33 @property
34 def timestamp(self) -> int:
35 """
36 The CPU timestamp (in microseconds since 1970) at which the value was
37 sampled.
38 """
39 # Explicit int() cast required because this is a Numpy type
40 return int(self._field_value.timestamp) 1a
42 @property
43 def latency_usec(self) -> int:
44 """
45 How long this field value took to update (in usec) within NVML. This may
46 be averaged across several fields that are serviced by the same driver
47 call.
48 """
49 # Explicit int() cast required because this is a Numpy type
50 return int(self._field_value.latency_usec) 1a
52 @property
53 def value(self) -> int | float:
54 """
55 The field value.
57 Raises
58 ------
59 :class:`cuda.core.system.NvmlError`
60 If there was an error retrieving the field value.
61 """
62 nvml.check_status(self._field_value.nvml_return) 1a
64 cdef int value_type = self._field_value.value_type 1a
65 value = self._field_value.value 1a
67 ValueType = nvml.ValueType 1a
69 if value_type == ValueType.DOUBLE: 1a
70 return float(value.d_val[0])
71 elif value_type == ValueType.UNSIGNED_INT: 1a
72 return int(value.ui_val[0]) 1a
73 elif value_type == ValueType.UNSIGNED_LONG: 1a
74 return int(value.ul_val[0])
75 elif value_type == ValueType.UNSIGNED_LONG_LONG: 1a
76 return int(value.ull_val[0]) 1a
77 elif value_type == ValueType.SIGNED_LONG_LONG:
78 return int(value.ll_val[0])
79 elif value_type == ValueType.SIGNED_INT:
80 return int(value.si_val[0])
81 elif value_type == ValueType.UNSIGNED_SHORT:
82 return int(value.us_val[0])
83 else:
84 raise AssertionError("Unexpected value type")
87cdef class FieldValues:
88 """
89 Container of multiple field values.
90 """
91 cdef object _field_values
93 def __init__(self, field_values: nvml.FieldValue):
94 self._field_values = field_values 1a
96 def __getitem__(self, idx: int) -> FieldValue:
97 return FieldValue(self._field_values[idx]) 1a
99 def __len__(self) -> int:
100 return len(self._field_values) 1a
102 def validate(self) -> None:
103 """
104 Validate that there are no issues in any of the contained field values.
106 Raises an exception for the first issue found, if any.
108 Raises
109 ------
110 :class:`cuda.core.system.NvmlError`
111 If any of the contained field values has an associated exception.
112 """
113 # TODO: This is a classic use case for an `ExceptionGroup`, but those
114 # are only available in Python 3.11+.
115 return_values = self._field_values.nvml_return 1a
116 if len(self._field_values) == 1: 1a
117 return_values = [return_values] 1a
118 for return_value in return_values: 1a
119 nvml.check_status(return_value) 1a
121 def get_all_values(self) -> list[int | float]:
122 """
123 Get all field values as a list.
125 This will validate each of the values and include just the core value in
126 the list.
128 Returns
129 -------
130 list[int | float]
131 List of all field values.
133 Raises
134 ------
135 :class:`cuda.core.system.NvmlError`
136 If any of the contained field values has an associated exception.
137 """
138 return [x.value for x in self] 1a