Add APIs for PM table and register table
Read the PM table and register table as the name value pair.
Change-Id: Ie44fe67a28af3341bd6beb90d809e90f280351ac
[ROCm/amdsmi commit: ac1ba33371]
Этот коммит содержится в:
коммит произвёл
Shuzhou Liu
родитель
09125ca639
Коммит
c7f9cff2cb
@@ -141,6 +141,7 @@ set(CMN_SRC_LIST
|
||||
"${ROCM_SRC_DIR}/rocm_smi_counters.cc"
|
||||
"${ROCM_SRC_DIR}/rocm_smi_device.cc"
|
||||
"${ROCM_SRC_DIR}/rocm_smi_gpu_metrics.cc"
|
||||
"${ROCM_SRC_DIR}/rocm_smi_binary_parser.cc"
|
||||
"${ROCM_SRC_DIR}/rocm_smi_io_link.cc"
|
||||
"${ROCM_SRC_DIR}/rocm_smi_kfd.cc"
|
||||
"${ROCM_SRC_DIR}/rocm_smi_main.cc"
|
||||
@@ -163,6 +164,7 @@ set(CMN_INC_LIST
|
||||
"${ROCM_INC_DIR}/rocm_smi_counters.h"
|
||||
"${ROCM_INC_DIR}/rocm_smi_device.h"
|
||||
"${ROCM_INC_DIR}/rocm_smi_gpu_metrics.h"
|
||||
"${ROCM_INC_DIR}/rocm_smi_binary_parser.h"
|
||||
"${ROCM_INC_DIR}/rocm_smi_exception.h"
|
||||
"${ROCM_INC_DIR}/rocm_smi_io_link.h"
|
||||
"${ROCM_INC_DIR}/rocm_smi_kfd.h"
|
||||
|
||||
@@ -1213,6 +1213,28 @@ typedef struct {
|
||||
/// @endcond
|
||||
} amdsmi_gpu_metrics_t;
|
||||
|
||||
|
||||
#define MAX_AMDSMI_NAME_LENGTH 64
|
||||
|
||||
/**
|
||||
* @brief This structure holds the name value pairs
|
||||
*/
|
||||
typedef struct {
|
||||
char name[MAX_AMDSMI_NAME_LENGTH]; //!< Name
|
||||
uint64_t value; //!< Use uint64_t to make it universal
|
||||
} amdsmi_name_value_t;
|
||||
|
||||
/**
|
||||
* @brief This register type for register table
|
||||
*/
|
||||
typedef enum {
|
||||
AMDSMI_REG_XGMI,
|
||||
AMDSMI_REG_WAFL,
|
||||
AMDSMI_REG_PCIE,
|
||||
AMDSMI_REG_USR,
|
||||
AMDSMI_REG_USR1,
|
||||
} amdsmi_reg_type_t;
|
||||
|
||||
/**
|
||||
* @brief This structure holds ras feature
|
||||
*/
|
||||
@@ -2585,6 +2607,77 @@ amdsmi_status_t amdsmi_get_gpu_od_volt_info(amdsmi_processor_handle processor_ha
|
||||
amdsmi_status_t amdsmi_get_gpu_metrics_info(amdsmi_processor_handle processor_handle,
|
||||
amdsmi_gpu_metrics_t *pgpu_metrics);
|
||||
|
||||
/**
|
||||
* @brief Get the pm metrics table with provided device index.
|
||||
*
|
||||
* @details Given a device handle @p processor_handle, @p pm_metrics pointer,
|
||||
* and @p num_of_metrics pointer,
|
||||
* this function will write the pm metrics name value pair
|
||||
* to the array at @p pm_metrics and the number of metrics retreived to @p num_of_metrics
|
||||
* Note: the library allocated memory for pm_metrics, and user must call
|
||||
* free(pm_metrics) to free it after use.
|
||||
*
|
||||
* @param[in] processor_handle a processor handle
|
||||
*
|
||||
* @param[inout] pm_metrics A pointerto an array to hold multiple PM metrics. On successs,
|
||||
* the library will allocate memory of pm_metrics and write metrics to this array.
|
||||
* The caller must free this memory after usage to avoid memory leak.
|
||||
*
|
||||
* @param[inout] num_of_metrics a pointer to uint32_t to which the number of
|
||||
* metrics is allocated for pm_metrics array as input, and the number of metrics retreived
|
||||
* as output. If this parameter is NULL, this function will return
|
||||
* ::AMDSMI_STATUS_INVALID_ARGS if the function is supported with the provided,
|
||||
* arguments and ::AMDSMI_STATUS_NOT_SUPPORTED if it is not supported with the
|
||||
* provided arguments.
|
||||
*
|
||||
* @retval ::AMDSMI_STATUS_SUCCESS call was successful
|
||||
* @retval ::AMDSMI_STATUS_NOT_SUPPORTED installed software or hardware does not
|
||||
* support this function with the given arguments
|
||||
* @retval ::AMDSMI_STATUS_INVALID_ARGS the provided arguments are not valid
|
||||
*
|
||||
*/
|
||||
amdsmi_status_t amdsmi_get_gpu_pm_metrics_info(
|
||||
amdsmi_processor_handle processor_handle,
|
||||
amdsmi_name_value_t** pm_metrics,
|
||||
uint32_t *num_of_metrics);
|
||||
|
||||
/**
|
||||
* @brief Get the register metrics table with provided device index and register type.
|
||||
*
|
||||
* @details Given a device handle @p processor_handle, @p reg_type, @p reg_metrics pointer,
|
||||
* and @p num_of_metrics pointer,
|
||||
* this function will write the register metrics name value pair
|
||||
* to the array at @p reg_metrics and the number of metrics retreived to @p num_of_metrics
|
||||
* Note: the library allocated memory for reg_metrics, and user must call
|
||||
* free(reg_metrics) to free it after use.
|
||||
*
|
||||
* @param[in] processor_handle a processor handle
|
||||
*
|
||||
* @param[in] reg_type The register type
|
||||
*
|
||||
* @param[inout] reg_metrics A pointerto an array to hold multiple register metrics. On successs,
|
||||
* the library will allocate memory of reg_metrics and write metrics to this array.
|
||||
* The caller must free this memory after usage to avoid memory leak.
|
||||
*
|
||||
* @param[inout] num_of_metrics a pointer to uint32_t to which the number of
|
||||
* metrics is allocated for reg_metrics array as input, and the number of metrics retreived
|
||||
* as output. If this parameter is NULL, this function will return
|
||||
* ::AMDSMI_STATUS_INVALID_ARGS if the function is supported with the provided,
|
||||
* arguments and ::AMDSMI_STATUS_NOT_SUPPORTED if it is not supported with the
|
||||
* provided arguments.
|
||||
*
|
||||
* @retval ::AMDSMI_STATUS_SUCCESS call was successful
|
||||
* @retval ::AMDSMI_STATUS_NOT_SUPPORTED installed software or hardware does not
|
||||
* support this function with the given arguments
|
||||
* @retval ::AMDSMI_STATUS_INVALID_ARGS the provided arguments are not valid
|
||||
*
|
||||
*/
|
||||
amdsmi_status_t amdsmi_get_gpu_reg_table_info(
|
||||
amdsmi_processor_handle processor_handle,
|
||||
amdsmi_reg_type_t reg_type,
|
||||
amdsmi_name_value_t** reg_metrics,
|
||||
uint32_t *num_of_metrics);
|
||||
|
||||
/**
|
||||
* @brief This function sets the clock range information. It is not supported on virtual
|
||||
* machine guest
|
||||
|
||||
@@ -1063,6 +1063,28 @@ typedef struct {
|
||||
/// \endcond
|
||||
} rsmi_gpu_metrics_t;
|
||||
|
||||
|
||||
#define MAX_RSMI_NAME_LENGTH 64
|
||||
|
||||
/**
|
||||
* @brief This structure holds the name value pairs
|
||||
*/
|
||||
typedef struct {
|
||||
char name[MAX_RSMI_NAME_LENGTH]; //!< Name
|
||||
uint64_t value; //!< Use uint64_t to make it universal
|
||||
} rsmi_name_value_t;
|
||||
|
||||
/**
|
||||
* @brief This register type for register table
|
||||
*/
|
||||
typedef enum {
|
||||
RSMI_REG_XGMI,
|
||||
RSMI_REG_WAFL,
|
||||
RSMI_REG_PCIE,
|
||||
RSMI_REG_USR,
|
||||
RSMI_REG_USR1,
|
||||
} rsmi_reg_type_t;
|
||||
|
||||
/**
|
||||
* @brief This structure holds error counts.
|
||||
*/
|
||||
@@ -2765,6 +2787,76 @@ rsmi_status_t rsmi_dev_od_volt_info_get(uint32_t dv_ind,
|
||||
rsmi_status_t rsmi_dev_gpu_metrics_info_get(uint32_t dv_ind,
|
||||
rsmi_gpu_metrics_t *pgpu_metrics);
|
||||
|
||||
/**
|
||||
* @brief Get the pm metrics table with provided device index.
|
||||
*
|
||||
* @details Given a device index @p dv_ind, @p pm_metrics pointer,
|
||||
* and @p num_of_metrics pointer,
|
||||
* this function will write the pm metrics name value pair
|
||||
* to the array at @p pm_metrics and the number of metrics retreived to @p num_of_metrics
|
||||
* Note: the library allocated memory for pm_metrics, and user must call
|
||||
* free(pm_metrics) to free it after use.
|
||||
*
|
||||
* @param[in] dv_ind a device index
|
||||
*
|
||||
* @param[inout] pm_metrics A pointerto an array to hold multiple PM metrics. On successs,
|
||||
* the library will allocate memory of pm_metrics and write metrics to this array.
|
||||
* The caller must free this memory after usage to avoid memory leak.
|
||||
*
|
||||
* @param[inout] num_of_metrics a pointer to uint32_t to which the number of
|
||||
* metrics is allocated for pm_metrics array as input, and the number of metrics retreived
|
||||
* as output. If this parameter is NULL, this function will return
|
||||
* ::RSMI_STATUS_INVALID_ARGS if the function is supported with the provided,
|
||||
* arguments and ::RSMI_STATUS_NOT_SUPPORTED if it is not supported with the
|
||||
* provided arguments.
|
||||
*
|
||||
* @retval ::RSMI_STATUS_SUCCESS call was successful
|
||||
* @retval ::RSMI_STATUS_NOT_SUPPORTED installed software or hardware does not
|
||||
* support this function with the given arguments
|
||||
* @retval ::RSMI_STATUS_INVALID_ARGS the provided arguments are not valid
|
||||
*
|
||||
*/
|
||||
rsmi_status_t rsmi_dev_pm_metrics_info_get(uint32_t dv_ind,
|
||||
rsmi_name_value_t** pm_metrics,
|
||||
uint32_t *num_of_metrics);
|
||||
|
||||
|
||||
/**
|
||||
* @brief Get the register metrics table with provided device index and registertype.
|
||||
*
|
||||
* @details Given a device index @p dv_ind, @p reg_type, @p reg_metrics pointer,
|
||||
* and @p num_of_metrics pointer,
|
||||
* this function will write the register metrics name value pair
|
||||
* to the array at @p reg_metrics and the number of metrics retreived to @p num_of_metrics
|
||||
* Note: the library allocated memory for reg_metrics, and user must call
|
||||
* free(reg_metrics) to free it after use.
|
||||
*
|
||||
* @param[in] dv_ind a device index
|
||||
*
|
||||
* @param[in] reg_type The register type
|
||||
*
|
||||
* @param[inout] reg_metrics A pointerto an array to hold multiple register metrics. On successs,
|
||||
* the library will allocate memory of reg_metrics and write metrics to this array.
|
||||
* The caller must free this memory after usage to avoid memory leak.
|
||||
*
|
||||
* @param[inout] num_of_metrics a pointer to uint32_t to which the number of
|
||||
* metrics is allocated for reg_metrics array as input, and the number of metrics retreived
|
||||
* as output. If this parameter is NULL, this function will return
|
||||
* ::RSMI_STATUS_INVALID_ARGS if the function is supported with the provided,
|
||||
* arguments and ::RSMI_STATUS_NOT_SUPPORTED if it is not supported with the
|
||||
* provided arguments.
|
||||
*
|
||||
* @retval ::RSMI_STATUS_SUCCESS call was successful
|
||||
* @retval ::RSMI_STATUS_NOT_SUPPORTED installed software or hardware does not
|
||||
* support this function with the given arguments
|
||||
* @retval ::RSMI_STATUS_INVALID_ARGS the provided arguments are not valid
|
||||
*
|
||||
*/
|
||||
rsmi_status_t rsmi_dev_reg_table_info_get(uint32_t dv_ind,
|
||||
rsmi_reg_type_t reg_type,
|
||||
rsmi_name_value_t** reg_metrics,
|
||||
uint32_t *num_of_metrics);
|
||||
|
||||
/**
|
||||
* @brief This function sets the clock range information
|
||||
*
|
||||
|
||||
@@ -0,0 +1,262 @@
|
||||
/*
|
||||
* =============================================================================
|
||||
* The University of Illinois/NCSA
|
||||
* Open Source License (NCSA)
|
||||
*
|
||||
* Copyright (c) 2017-2023, Advanced Micro Devices, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Developed by:
|
||||
*
|
||||
* AMD Research and AMD ROC Software Development
|
||||
*
|
||||
* Advanced Micro Devices, Inc.
|
||||
*
|
||||
* www.amd.com
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to
|
||||
* deal with the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* - Redistributions of source code must retain the above copyright notice,
|
||||
* this list of conditions and the following disclaimers.
|
||||
* - Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimers in
|
||||
* the documentation and/or other materials provided with the distribution.
|
||||
* - Neither the names of <Name of Development Group, Name of Institution>,
|
||||
* nor the names of its contributors may be used to endorse or promote
|
||||
* products derived from this Software without specific prior written
|
||||
* permission.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
||||
* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
||||
* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
* DEALINGS WITH THE SOFTWARE.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef ROCM_SMI_ROCM_SMI_BINARY_PARSER_H_
|
||||
#define ROCM_SMI_ROCM_SMI_BINARY_PARSER_H_
|
||||
|
||||
#include "rocm_smi/rocm_smi_common.h"
|
||||
#include "rocm_smi/rocm_smi.h"
|
||||
|
||||
#include <cstdint>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <tuple>
|
||||
#include <vector>
|
||||
|
||||
/**
|
||||
* A binary parser to read the pm table and register table
|
||||
*
|
||||
*/
|
||||
namespace amd::smi {
|
||||
|
||||
// definition for register table
|
||||
enum amdgpu_sysfs_reg_offset {
|
||||
AMDGPU_SYS_REG_STATE_XGMI = 0x0000,
|
||||
AMDGPU_SYS_REG_STATE_WAFL = 0x1000,
|
||||
AMDGPU_SYS_REG_STATE_PCIE = 0x2000,
|
||||
AMDGPU_SYS_REG_STATE_USR = 0x3000,
|
||||
AMDGPU_SYS_REG_STATE_USR_1 = 0x4000,
|
||||
AMDGPU_SYS_REG_STATE_END = 0x5000,
|
||||
};
|
||||
|
||||
#define FIELD_FLAG_NUM_INSTANCE 0x01
|
||||
#define FIELD_FLAG_NUM_SMN 0x02
|
||||
#define FIELD_FLAG_INSTANCE_START 0x04
|
||||
#define FIELD_FLAG_SMN_START 0x08
|
||||
|
||||
#define FIELD_TYPE_U8 0x01
|
||||
#define FIELD_TYPE_U16 0x02
|
||||
#define FIELD_TYPE_U32 0x04
|
||||
#define FIELD_TYPE_U64 0x08
|
||||
|
||||
struct metric_field {
|
||||
uint8_t field_type;
|
||||
int field_arr_size;
|
||||
const char *field_name;
|
||||
uint8_t field_flag;
|
||||
};
|
||||
|
||||
struct metric_field xgmi_regs[] = {
|
||||
{ FIELD_TYPE_U16, 1, "structure_size", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "format_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "content_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "state_type", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "num_instances", FIELD_FLAG_NUM_INSTANCE },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U16, 1, "instance", FIELD_FLAG_INSTANCE_START },
|
||||
{ FIELD_TYPE_U16, 1, "state", 0 },
|
||||
{ FIELD_TYPE_U16, 1, "num_smn_regs", FIELD_FLAG_NUM_SMN },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U64, 1, "addr", FIELD_FLAG_SMN_START },
|
||||
{ FIELD_TYPE_U32, 1, "value", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pad", 0 },
|
||||
{ 0, 0, NULL, 0 },
|
||||
};
|
||||
|
||||
// check me!
|
||||
struct metric_field wafl_regs[] = {
|
||||
{ FIELD_TYPE_U16, 1, "structure_size", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "format_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "content_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "state_type", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "num_instances", FIELD_FLAG_NUM_INSTANCE },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U16, 1, "instance", FIELD_FLAG_INSTANCE_START },
|
||||
{ FIELD_TYPE_U16, 1, "state", 0 },
|
||||
{ FIELD_TYPE_U16, 1, "num_smn_regs", FIELD_FLAG_NUM_SMN },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U64, 1, "addr", FIELD_FLAG_SMN_START },
|
||||
{ FIELD_TYPE_U32, 1, "value", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pad", 0 },
|
||||
{ 0, 0, NULL, 0 },
|
||||
};
|
||||
|
||||
struct metric_field pcie_regs[] = {
|
||||
{ FIELD_TYPE_U16, 1, "structure_size", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "format_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "content_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "state_type", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "num_instances", FIELD_FLAG_NUM_INSTANCE },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U16, 1, "instance", FIELD_FLAG_INSTANCE_START },
|
||||
{ FIELD_TYPE_U16, 1, "state", 0 },
|
||||
{ FIELD_TYPE_U16, 1, "num_smn_regs", FIELD_FLAG_NUM_SMN },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U16, 1, "device_status", 0 },
|
||||
{ FIELD_TYPE_U16, 1, "link_status", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "sub_bus_number_latency", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pcie_corr_err_status", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pcie_uncorr_err_status", 0 },
|
||||
|
||||
{ FIELD_TYPE_U64, 1, "addr", FIELD_FLAG_SMN_START },
|
||||
{ FIELD_TYPE_U32, 1, "value", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pad", 0 },
|
||||
{ 0, 0, NULL, 0 },
|
||||
};
|
||||
|
||||
struct metric_field usr_regs[] = {
|
||||
{ FIELD_TYPE_U16, 1, "structure_size", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "format_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "content_revision", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "state_type", 0 },
|
||||
{ FIELD_TYPE_U8, 1, "num_instances", FIELD_FLAG_NUM_INSTANCE },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U16, 1, "instance", FIELD_FLAG_INSTANCE_START },
|
||||
{ FIELD_TYPE_U16, 1, "state", 0 },
|
||||
{ FIELD_TYPE_U16, 1, "num_smn_regs", FIELD_FLAG_NUM_SMN },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
|
||||
{ FIELD_TYPE_U64, 1, "addr", FIELD_FLAG_SMN_START },
|
||||
{ FIELD_TYPE_U32, 1, "value", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pad", 0 },
|
||||
{ 0, 0, NULL, 0 },
|
||||
};
|
||||
|
||||
// definition for pm metrics table
|
||||
#define FIELD_FLAG_ACCUMULATOR 0x01
|
||||
|
||||
struct metric_field smu_13_0_6_v8[] = {
|
||||
{ FIELD_TYPE_U16, 1, "structure_size", 0 },
|
||||
{ FIELD_TYPE_U16, 1, "pad", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "mp1_ip_discovery_version", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pmfw_version", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "pmmetrics_version", 0 },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "AccumulationCounter", 0 },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "MaxSocketTemperature", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MaxVrTemperature", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MaxHbmTemperature", 0 },
|
||||
{ FIELD_TYPE_U64, 1, "MaxSocketTemperatureAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "MaxVrTemperatureAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "MaxHbmTemperatureAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "SocketPowerLimit", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MaxSocketPowerLimit", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "SocketPower", 0 },
|
||||
|
||||
{ FIELD_TYPE_U64, 1, "Timestamp", 0 },
|
||||
{ FIELD_TYPE_U64, 1, "SocketEnergyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "CcdEnergyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "XcdEnergyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "AidEnergyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "HbmEnergyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "CclkFrequencyLimit", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "GfxclkFrequencyLimit", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "FclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "UclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "SocclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "VclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "DclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "LclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U64, 8, "GfxclkFrequencyAcc", FIELD_FLAG_ACCUMULATOR},
|
||||
{ FIELD_TYPE_U64, 96, "CclkFrequencyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "MaxCclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MinCclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MaxGfxclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MinGfxclkFrequency", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "FclkFrequencyTable", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "UclkFrequencyTable", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "SocclkFrequencyTable", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "VclkFrequencyTable", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "DclkFrequencyTable", 0 },
|
||||
{ FIELD_TYPE_U32, 4, "LclkFrequencyTable", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MaxLclkDpmRange", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "MinLclkDpmRange", 0 },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "XgmiWidth", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "XgmiBitrate", 0 },
|
||||
{ FIELD_TYPE_U64, 8, "XgmiReadBandwidthAcc", 0 },
|
||||
{ FIELD_TYPE_U64, 8, "XgmiWriteBandwidthAcc", 0 },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "SocketC0Residency", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "SocketGfxBusy", 0 },
|
||||
{ FIELD_TYPE_U32, 1, "DramBandwidthUtilization", 0 },
|
||||
{ FIELD_TYPE_U64, 1, "SocketC0ResidencyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "SocketGfxBusyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 1, "DramBandwidthAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U32, 1, "MaxDramBandwidth", 0 },
|
||||
{ FIELD_TYPE_U64, 1, "DramBandwidthUtilizationAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 4, "PcieBandwidthAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
|
||||
{ FIELD_TYPE_U32, 1, "ProchotResidencyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U32, 1, "PptResidencyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U32, 1, "SocketThmResidencyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U32, 1, "VrThmResidencyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U32, 1, "HbmThmResidencyAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U32, 1, "GfxLockXCDMak", 0 },
|
||||
|
||||
{ FIELD_TYPE_U32, 8, "GfxclkFrequency", 0 },
|
||||
|
||||
{ FIELD_TYPE_U64, 4, "PublicSerialNumber_AID", 0 },
|
||||
{ FIELD_TYPE_U64, 8, "PublicSerialNumber_XCD", 0 },
|
||||
{ FIELD_TYPE_U64, 12, "PublicSerialNumber_CCD", 0 },
|
||||
|
||||
{ FIELD_TYPE_U64, 8, "XgmiReadDataSizeAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ FIELD_TYPE_U64, 8, "XgmiWriteDataSizeAcc", FIELD_FLAG_ACCUMULATOR },
|
||||
{ 0, 0, NULL, 0 },
|
||||
};
|
||||
|
||||
} // namespace amd::smi
|
||||
|
||||
#endif // ROCM_SMI_ROCM_SMI_BINARY_PARSER_H_
|
||||
|
||||
@@ -171,6 +171,8 @@ enum DevInfoTypes {
|
||||
kDevMemPageBad,
|
||||
kDevNumaNode,
|
||||
kDevGpuMetrics,
|
||||
kDevPmMetrics,
|
||||
kDevRegMetrics,
|
||||
kDevGpuReset,
|
||||
kDevAvailableComputePartition,
|
||||
kDevComputePartition,
|
||||
@@ -205,6 +207,7 @@ class Device {
|
||||
int readDevInfo(DevInfoTypes type, std::vector<std::string> *retVec);
|
||||
int readDevInfo(DevInfoTypes type, std::size_t b_size,
|
||||
void *p_binary_data);
|
||||
std::string get_sys_file_path_by_type(DevInfoTypes type) const;
|
||||
// Get the property from a file which may contain multiple properties.
|
||||
int readDevInfo(DevInfoTypes type, const std::string& property,
|
||||
std::string& value);
|
||||
|
||||
@@ -106,6 +106,14 @@ static const std::map<rsmi_clk_type_t, amd::smi::DevInfoTypes> kClkTypeMap = {
|
||||
#define TRY try {
|
||||
#define CATCH } catch (...) {return amd::smi::handleException();}
|
||||
|
||||
// declare pm metrics and register table function
|
||||
namespace amd::smi {
|
||||
int present_pmmetrics(const char* sysfs_file_name,
|
||||
rsmi_name_value_t **kv, uint32_t *kvnum);
|
||||
int present_reg_state(const char* fname, rsmi_reg_type_t reg_type,
|
||||
rsmi_name_value_t **kv, uint32_t *kvnum);
|
||||
}
|
||||
|
||||
static uint64_t get_multiplier_from_str(char units_char) {
|
||||
uint32_t multiplier = 0;
|
||||
|
||||
@@ -2479,6 +2487,40 @@ rsmi_dev_vendor_name_get(uint32_t dv_ind, char *name, size_t len) {
|
||||
CATCH
|
||||
}
|
||||
|
||||
rsmi_status_t rsmi_dev_pm_metrics_info_get(uint32_t dv_ind,
|
||||
rsmi_name_value_t** pm_metrics,
|
||||
uint32_t *num_of_metrics) {
|
||||
TRY
|
||||
DEVICE_MUTEX
|
||||
CHK_SUPPORT_NAME_ONLY(num_of_metrics)
|
||||
std::string file_path = dev->
|
||||
get_sys_file_path_by_type(amd::smi::kDevPmMetrics);
|
||||
|
||||
int ret = amd::smi::present_pmmetrics(
|
||||
file_path.c_str(), pm_metrics, num_of_metrics);
|
||||
if (ret == 0) return RSMI_STATUS_SUCCESS;
|
||||
return RSMI_STATUS_NOT_SUPPORTED;
|
||||
|
||||
CATCH
|
||||
}
|
||||
|
||||
rsmi_status_t rsmi_dev_reg_table_info_get(uint32_t dv_ind,
|
||||
rsmi_reg_type_t reg_type,
|
||||
rsmi_name_value_t** reg_metrics,
|
||||
uint32_t *num_of_metrics) {
|
||||
TRY
|
||||
DEVICE_MUTEX
|
||||
CHK_SUPPORT_NAME_ONLY(num_of_metrics)
|
||||
std::string file_path = dev->
|
||||
get_sys_file_path_by_type(amd::smi::kDevRegMetrics);
|
||||
|
||||
int ret = amd::smi::present_reg_state(
|
||||
file_path.c_str(), reg_type, reg_metrics, num_of_metrics);
|
||||
if (ret == 0) return RSMI_STATUS_SUCCESS;
|
||||
return RSMI_STATUS_NOT_SUPPORTED;
|
||||
|
||||
CATCH
|
||||
}
|
||||
|
||||
rsmi_status_t
|
||||
rsmi_dev_pci_bandwidth_get(uint32_t dv_ind, rsmi_pcie_bandwidth_t *b) {
|
||||
|
||||
Исполняемый файл
+320
@@ -0,0 +1,320 @@
|
||||
/*
|
||||
* =============================================================================
|
||||
* The University of Illinois/NCSA
|
||||
* Open Source License (NCSA)
|
||||
*
|
||||
* Copyright (c) 2017-2023, Advanced Micro Devices, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Developed by:
|
||||
*
|
||||
* AMD Research and AMD ROC Software Development
|
||||
*
|
||||
* Advanced Micro Devices, Inc.
|
||||
*
|
||||
* www.amd.com
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to
|
||||
* deal with the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* - Redistributions of source code must retain the above copyright notice,
|
||||
* this list of conditions and the following disclaimers.
|
||||
* - Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimers in
|
||||
* the documentation and/or other materials provided with the distribution.
|
||||
* - Neither the names of <Name of Development Group, Name of Institution>,
|
||||
* nor the names of its contributors may be used to endorse or promote
|
||||
* products derived from this Software without specific prior written
|
||||
* permission.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
||||
* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
||||
* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
* DEALINGS WITH THE SOFTWARE.
|
||||
*
|
||||
*/
|
||||
|
||||
#include "rocm_smi/rocm_smi_binary_parser.h"
|
||||
#include "rocm_smi/rocm_smi_common.h" // Should go before rocm_smi.h
|
||||
#include "rocm_smi/rocm_smi.h"
|
||||
#include "rocm_smi/rocm_smi_main.h"
|
||||
#include "rocm_smi/rocm_smi_utils.h"
|
||||
#include "rocm_smi/rocm_smi_exception.h"
|
||||
#include "rocm_smi/rocm_smi_device.h"
|
||||
#include "rocm_smi/rocm_smi_logger.h"
|
||||
|
||||
#include <dirent.h>
|
||||
#include <pthread.h>
|
||||
|
||||
#include <algorithm>
|
||||
#include <cassert>
|
||||
#include <cstdint>
|
||||
#include <cstring>
|
||||
#include <fstream>
|
||||
#include <iostream>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <utility>
|
||||
#include <variant>
|
||||
#include <vector>
|
||||
|
||||
namespace amd::smi {
|
||||
static uint64_t get_value(uint8_t **ptr, struct metric_field *field) {
|
||||
uint64_t v;
|
||||
switch (field->field_type) {
|
||||
case FIELD_TYPE_U8:
|
||||
v = *(uint8_t*)(*ptr);
|
||||
++(*ptr);
|
||||
break;
|
||||
case FIELD_TYPE_U16:
|
||||
v = *(uint16_t*)(*ptr);
|
||||
(*ptr) += 2;
|
||||
break;
|
||||
case FIELD_TYPE_U32:
|
||||
v = *(uint32_t*)(*ptr);
|
||||
(*ptr) += 4;
|
||||
break;
|
||||
case FIELD_TYPE_U64:
|
||||
v = *(uint64_t*)(*ptr);
|
||||
(*ptr) += 8;
|
||||
break;
|
||||
}
|
||||
return v;
|
||||
}
|
||||
|
||||
static int parse_pmmetric_table(uint8_t *buf, struct metric_field *table,
|
||||
int32_t buflen, rsmi_name_value_t **kv, uint32_t *kvnum) {
|
||||
uint64_t v1;
|
||||
int x, y;
|
||||
uint8_t *origbuf = buf;
|
||||
uint32_t kvsize = 64;
|
||||
|
||||
*kv = reinterpret_cast<rsmi_name_value_t*>(calloc(kvsize, sizeof **kv));
|
||||
*kvnum = 0;
|
||||
|
||||
for (x = 0; table[x].field_name; x++) {
|
||||
for (y = 0; y < table[x].field_arr_size; y++) {
|
||||
v1 = get_value(&buf, &table[x]);
|
||||
if ((intptr_t)(buf - origbuf) > buflen) {
|
||||
fprintf(stderr,
|
||||
"[ERROR]: Invalid buffer as buffer length exceeded\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (*kvnum == kvsize) {
|
||||
kvsize += 64;
|
||||
*kv = reinterpret_cast<rsmi_name_value_t*>
|
||||
(realloc(*kv,kvsize * (sizeof **kv)));
|
||||
}
|
||||
if (table[x].field_arr_size == 1) {
|
||||
sprintf((*kv)[*kvnum].name, "%s", table[x].field_name);
|
||||
} else {
|
||||
sprintf((*kv)[*kvnum].name, "%s[%d]", table[x].field_name, y);
|
||||
}
|
||||
(*kv)[*kvnum].value = v1;
|
||||
|
||||
++(*kvnum);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/** present the PM metrics data
|
||||
*
|
||||
* @dri_instance: which card to pick under /sys/class/drm/card${instance}/device/
|
||||
* @kv: pointer to pointer of rsmi_name_value pairs
|
||||
* @kvnum: pointer to number of used rsmi_name_value pairs
|
||||
*/
|
||||
int present_pmmetrics(const char* fname,
|
||||
rsmi_name_value_t **kv, uint32_t *kvnum)
|
||||
{
|
||||
uint8_t *buf1;
|
||||
FILE *infile;
|
||||
uint32_t pmmetrics_version;
|
||||
metric_field *table;
|
||||
int r;
|
||||
int32_t len;
|
||||
|
||||
infile = fopen(fname, "rb");
|
||||
if (!infile) {
|
||||
fprintf(stderr, "[ERROR]: pm_metrics file not found \n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
buf1 = reinterpret_cast<uint8_t *>(calloc(1, 65536));
|
||||
if (!buf1) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
table = NULL;
|
||||
len = fread(buf1, 1, 65536, infile);
|
||||
fseek(infile, 0, SEEK_SET);
|
||||
memcpy(&pmmetrics_version, &buf1[12], 4);
|
||||
|
||||
switch (pmmetrics_version) {
|
||||
case 4: // ??? why 4?
|
||||
table = &smu_13_0_6_v8[0];
|
||||
break;
|
||||
default:
|
||||
fprintf(stderr, "Metrics version %d not supported\n"
|
||||
, pmmetrics_version);
|
||||
return -1;
|
||||
}
|
||||
r = parse_pmmetric_table(buf1, table, len, kv, kvnum);
|
||||
fclose(infile);
|
||||
free(buf1);
|
||||
return r;
|
||||
}
|
||||
|
||||
static int parse_reg_state_table(uint8_t *buf, int32_t buflen,
|
||||
struct metric_field *table,
|
||||
rsmi_name_value_t **kv, uint32_t *kvnum) {
|
||||
int skip_smn, x, y, cur_instance, cur_smn,
|
||||
num_instance, num_smn, instance_start, smn_start;
|
||||
uint64_t v;
|
||||
uint8_t *obuf, *origbuf;
|
||||
int kvsize = 64;
|
||||
|
||||
*kv = reinterpret_cast<rsmi_name_value_t*>(calloc(kvsize, sizeof **kv));
|
||||
*kvnum = 0;
|
||||
|
||||
skip_smn = cur_instance = num_instance = num_smn = 0;
|
||||
instance_start = smn_start = 0x1000;
|
||||
x = 0;
|
||||
origbuf = buf;
|
||||
top:
|
||||
while (table[x].field_name != NULL) {
|
||||
for (y = 0; y < table[x].field_arr_size; y++) {
|
||||
obuf = buf;
|
||||
v = get_value(&buf, &table[x]);
|
||||
if ((intptr_t)(buf - origbuf) > buflen) {
|
||||
fprintf(stderr,
|
||||
"[ERROR] Invalid buffer as read length was exceeded\n");
|
||||
return -1;
|
||||
}
|
||||
switch (table[x].field_flag) {
|
||||
case FIELD_FLAG_INSTANCE_START:
|
||||
instance_start = x;
|
||||
num_smn = cur_smn = 0;
|
||||
break;
|
||||
case FIELD_FLAG_SMN_START:
|
||||
// if we hit an SMN start but there are no registers then skip back to the start
|
||||
// of the instance block
|
||||
if (skip_smn) {
|
||||
// out of instances we're done so bail!
|
||||
if (!num_instance)
|
||||
return 0;
|
||||
x = instance_start;
|
||||
--num_instance;
|
||||
++cur_instance;
|
||||
// rewind the buffer since we didn't actually consume
|
||||
// this word
|
||||
buf = obuf;
|
||||
goto top;
|
||||
} else {
|
||||
smn_start = x;
|
||||
}
|
||||
break;
|
||||
case FIELD_FLAG_NUM_INSTANCE:
|
||||
num_instance = v;
|
||||
break;
|
||||
case FIELD_FLAG_NUM_SMN:
|
||||
num_smn = v;
|
||||
if (v)
|
||||
skip_smn = 0;
|
||||
else
|
||||
skip_smn = 1;
|
||||
break;
|
||||
}
|
||||
if (*kvnum == kvsize) {
|
||||
kvsize += 64;
|
||||
*kv = reinterpret_cast<rsmi_name_value_t*>(
|
||||
realloc(*kv, kvsize * (sizeof **kv)));
|
||||
}
|
||||
sprintf((*kv)[*kvnum].name, "%s", table[x].field_name);
|
||||
if (table[x].field_arr_size > 1) {
|
||||
sprintf((*kv)[*kvnum].name + strlen((*kv)[*kvnum].name), "[%d]", y);
|
||||
}
|
||||
if (x >= instance_start)
|
||||
sprintf((*kv)[*kvnum].name + strlen((*kv)[*kvnum].name), ".instance[%d]", cur_instance);
|
||||
if (x >= smn_start)
|
||||
sprintf((*kv)[*kvnum].name + strlen((*kv)[*kvnum].name), ".smn[%d]", cur_smn);
|
||||
(*kv)[*kvnum].value = v;
|
||||
++(*kvnum);
|
||||
}
|
||||
|
||||
// done move to next or loop
|
||||
++x;
|
||||
if (table[x].field_name == NULL && --num_smn) {
|
||||
x = smn_start;
|
||||
++cur_smn;
|
||||
} else if (table[x].field_name == NULL && --num_instance) {
|
||||
x = instance_start;
|
||||
++cur_instance;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/** present_reg_state: present register state data
|
||||
*
|
||||
* @dri_instance: The DRI instance to select under /sys/class/drm/card${instance}/device
|
||||
* @table: Name of the table to read {"xgmi', "wafl", "pcie", "usr", "usr_1"}
|
||||
* @kv: pointer to pointer of rsmi_name_value pairs
|
||||
* @kvnum: pointer to number of used rsmi_name_value pairs
|
||||
*/
|
||||
int present_reg_state(const char* fname,
|
||||
rsmi_reg_type_t reg_type, rsmi_name_value_t **kv, uint32_t *kvnum) {
|
||||
uint8_t buf[4096];
|
||||
FILE *infile;
|
||||
struct metric_field *tab;
|
||||
int32_t len;
|
||||
|
||||
infile = fopen(fname, "rb");
|
||||
if (!infile) {
|
||||
fprintf(stderr, "[ERROR]: reg_state file not found\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
tab = NULL;
|
||||
if (reg_type == RSMI_REG_XGMI) {
|
||||
fseek(infile, AMDGPU_SYS_REG_STATE_XGMI, SEEK_SET);
|
||||
tab = &xgmi_regs[0];
|
||||
}
|
||||
if (reg_type == RSMI_REG_WAFL) {
|
||||
fseek(infile, AMDGPU_SYS_REG_STATE_WAFL, SEEK_SET);
|
||||
tab = &wafl_regs[0];
|
||||
}
|
||||
if (reg_type == RSMI_REG_PCIE) {
|
||||
fseek(infile, AMDGPU_SYS_REG_STATE_PCIE, SEEK_SET);
|
||||
tab = &pcie_regs[0];
|
||||
}
|
||||
if (reg_type == RSMI_REG_USR) {
|
||||
fseek(infile, AMDGPU_SYS_REG_STATE_USR, SEEK_SET);
|
||||
tab = &usr_regs[0];
|
||||
}
|
||||
if (reg_type == RSMI_REG_USR1) {
|
||||
fseek(infile, AMDGPU_SYS_REG_STATE_USR_1, SEEK_SET);
|
||||
tab = &usr_regs[0];
|
||||
}
|
||||
if (!tab) {
|
||||
fprintf(stderr, "[ERROR]: Invalid register space named <%d>\n", reg_type);
|
||||
fclose(infile);
|
||||
return -2;
|
||||
}
|
||||
|
||||
len = fread(buf, 1, sizeof buf, infile);
|
||||
fclose(infile);
|
||||
return parse_reg_state_table(buf, len, tab, kv, kvnum);
|
||||
}
|
||||
|
||||
|
||||
} // namespace amd::smi
|
||||
@@ -130,6 +130,8 @@ static const char *kDevXGMIErrorFName = "xgmi_error";
|
||||
static const char *kDevSerialNumberFName = "serial_number";
|
||||
static const char *kDevNumaNodeFName = "numa_node";
|
||||
static const char *kDevGpuMetricsFName = "gpu_metrics";
|
||||
static const char *kDevPmMetricsFName = "pm_metrics"; // PM log
|
||||
static const char *kDevRegMetricsFName = "reg_state"; // register table
|
||||
static const char *kDevAvailableComputePartitionFName =
|
||||
"available_compute_partition";
|
||||
static const char *kDevComputePartitionFName = "current_compute_partition";
|
||||
@@ -312,6 +314,8 @@ static const std::map<DevInfoTypes, const char *> kDevAttribNameMap = {
|
||||
{kDevMemPageBad, kDevMemPageBadFName},
|
||||
{kDevNumaNode, kDevNumaNodeFName},
|
||||
{kDevGpuMetrics, kDevGpuMetricsFName},
|
||||
{kDevPmMetrics, kDevPmMetricsFName},
|
||||
{kDevRegMetrics, kDevRegMetricsFName},
|
||||
{kDevGpuReset, kDevGpuResetFName},
|
||||
{kDevAvailableComputePartition, kDevAvailableComputePartitionFName},
|
||||
{kDevComputePartition, kDevComputePartitionFName},
|
||||
@@ -445,6 +449,8 @@ static const std::map<const char *, dev_depends_t> kDevFuncDependsMap = {
|
||||
{"rsmi_dev_memory_reserved_pages_get", {{kDevMemPageBadFName}, {}}},
|
||||
{"rsmi_topo_numa_affinity_get", {{kDevNumaNodeFName}, {}}},
|
||||
{"rsmi_dev_gpu_metrics_info_get", {{kDevGpuMetricsFName}, {}}},
|
||||
{"rsmi_dev_pm_metrics_info_get", {{kDevPmMetricsFName}, {}}},
|
||||
{"rsmi_dev_reg_table_info_get", {{kDevRegMetricsFName}, {}}},
|
||||
{"rsmi_dev_gpu_reset", {{kDevGpuResetFName}, {}}},
|
||||
{"rsmi_dev_compute_partition_get", {{kDevComputePartitionFName}, {}}},
|
||||
{"rsmi_dev_compute_partition_set", {{kDevComputePartitionFName}, {}}},
|
||||
@@ -594,6 +600,14 @@ int Device::openDebugFileStream(DevInfoTypes type, T *fs, const char *str) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
std::string Device::get_sys_file_path_by_type(DevInfoTypes type) const {
|
||||
auto sysfs_path = path_;
|
||||
sysfs_path += "/device/";
|
||||
sysfs_path += kDevAttribNameMap.at(type);
|
||||
|
||||
return sysfs_path;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
int Device::openSysfsFileStream(DevInfoTypes type, T *fs, const char *str) {
|
||||
auto sysfs_path = path_;
|
||||
|
||||
@@ -154,6 +154,8 @@ amd::smi::RocmSMI::devInfoTypesStrings = {
|
||||
{amd::smi::kDevMemPageBad, amdSMI + "kDevMemPageBad"},
|
||||
{amd::smi::kDevNumaNode, amdSMI + "kDevNumaNode"},
|
||||
{amd::smi::kDevGpuMetrics, amdSMI + "kDevGpuMetrics"},
|
||||
{amd::smi::kDevPmMetrics, amdSMI + "kDevPmMetrics"},
|
||||
{amd::smi::kDevRegMetrics, amdSMI + "kDevRegMetrics"},
|
||||
{amd::smi::kDevGpuReset, amdSMI + "kDevGpuReset"},
|
||||
{amd::smi::kDevAvailableComputePartition, amdSMI +
|
||||
"kDevAvailableComputePartition"},
|
||||
|
||||
@@ -1157,6 +1157,31 @@ amdsmi_status_t amdsmi_get_gpu_metrics_info(
|
||||
reinterpret_cast<rsmi_gpu_metrics_t*>(pgpu_metrics));
|
||||
}
|
||||
|
||||
|
||||
amdsmi_status_t amdsmi_get_gpu_pm_metrics_info(
|
||||
amdsmi_processor_handle processor_handle,
|
||||
amdsmi_name_value_t** pm_metrics,
|
||||
uint32_t *num_of_metrics) {
|
||||
AMDSMI_CHECK_INIT();
|
||||
|
||||
return rsmi_wrapper(rsmi_dev_pm_metrics_info_get, processor_handle,
|
||||
reinterpret_cast<rsmi_name_value_t**>(pm_metrics),
|
||||
num_of_metrics);
|
||||
}
|
||||
|
||||
amdsmi_status_t amdsmi_get_gpu_reg_table_info(
|
||||
amdsmi_processor_handle processor_handle,
|
||||
amdsmi_reg_type_t reg_type,
|
||||
amdsmi_name_value_t** reg_metrics,
|
||||
uint32_t *num_of_metrics) {
|
||||
AMDSMI_CHECK_INIT();
|
||||
|
||||
return rsmi_wrapper(rsmi_dev_reg_table_info_get, processor_handle,
|
||||
static_cast<rsmi_reg_type_t>(reg_type),
|
||||
reinterpret_cast<rsmi_name_value_t**>(reg_metrics),
|
||||
num_of_metrics);
|
||||
}
|
||||
|
||||
amdsmi_status_t
|
||||
amdsmi_get_power_cap_info(amdsmi_processor_handle processor_handle,
|
||||
uint32_t sensor_ind,
|
||||
|
||||
Ссылка в новой задаче
Block a user