Added amd-smi partition as preliminary command.

new command includes following arguments:
  - current - display the current partition information for the selected
    gpu(s)
  - memory - display memory partition information for the selected
    gpu(s)
  - accelerator - display accelerator partition information for the
    selected gpu(s)
additional functionality will be added as more partition APIs are added.

Signed-off-by: gabrpham <Gabriel.Pham@amd.com>
Change-Id: Ica86160139002ef5213d6d4b0e390670aeef01c8
Šī revīzija ir iekļauta:
gabrpham
2024-09-25 22:44:38 -05:00
vecāks 2c8e2060cb
revīzija 4e2fc2d604
6 mainīti faili ar 294 papildinājumiem un 45 dzēšanām
+2 -2
Parādīt failu
@@ -94,7 +94,8 @@ if __name__ == "__main__":
amd_smi_commands.reset,
amd_smi_commands.monitor,
amd_smi_commands.rocm_smi,
amd_smi_commands.xgmi)
amd_smi_commands.xgmi,
amd_smi_commands.partition)
try:
try:
argcomplete.autocomplete(amd_smi_parser)
@@ -128,7 +129,6 @@ if __name__ == "__main__":
sys.tracebacklimit = 10
else:
sys.tracebacklimit = -1
# Execute subcommands
args.func(args)
except amdsmi_cli_exceptions.AmdSmiException as e:
+205
Parādīt failu
@@ -5043,6 +5043,8 @@ class AMDSMICommands():
bitrate = pcie_speed_GTs_value
max_bandwidth = bitrate * pcie_static['max_pcie_width']
except amdsmi_exception.AmdSmiLibraryException as e:
bitrate = "N/A"
max_bandwidth = "N/A"
logging.debug("Failed to get bitrate and bandwidth for GPU %s | %s", src_gpu_id,
e.get_error_info())
@@ -5084,6 +5086,8 @@ class AMDSMICommands():
read = metrics_info['xgmi_read_data_acc'][dest_gpu_id]
write = metrics_info['xgmi_write_data_acc'][dest_gpu_id]
except amdsmi_exception.AmdSmiLibraryException as e:
read = "N/A"
write = "N/A"
logging.debug("Failed to get read data for %s to %s | %s",
self.helpers.get_gpu_id_from_device_handle(src_gpu),
self.helpers.get_gpu_id_from_device_handle(dest_gpu),
@@ -5172,6 +5176,207 @@ class AMDSMICommands():
self.logger.print_output(multiple_device_enabled=True)
def partition(self, args, multiple_devices=False, gpu=None, current=None, memory=None, accelerator=None):
""" Display parition information for the target GPU
param:
args - argparser args to pass to subcommand
multiple_devices (bool) - True if checking for multiple devices
gpu (device_handle) - device_handle for target device
current - boolean which dictates whether the current partition information is shown
memory - boolean which dictates whether the memory partition information is shown
accelerator - boolean which dictates whether the accelerator partition information is shown
returns:
nothing
"""
if gpu:
args.gpu = gpu
if args.gpu == None:
args.gpu = self.device_handles
if not isinstance(args.gpu, list):
args.gpu = [args.gpu]
if current:
args.current = current
if memory:
args.memory = memory
if accelerator:
args.accelerator = accelerator
# if no args are present, then everything should be displayed
if not args.current and not args.memory and not args.accelerator:
args.current = True
args.memory = True
args.accelerator = True
if args.current:
self.logger.table_header = ''.rjust(7)
current_header = "GPU_ID".ljust(13) + \
"MEMORY".ljust(8) + \
"ACCELERATOR_TYPE".ljust(18) + \
"ACCELERATOR_PROFILE_INDEX".ljust(27) + \
"PARTITION_ID".ljust(14)
self.logger.table_header = current_header + self.logger.table_header.strip()
tabular_output = []
for gpu in args.gpu:
gpu_id = self.helpers.get_gpu_id_from_device_handle(gpu)
try:
partition_dict = amdsmi_interface.amdsmi_get_gpu_accelerator_partition_profile(gpu)
profile_type = partition_dict['partition_profile']['profile_type']
profile_index = partition_dict['partition_profile']['profile_index']
partition_id = partition_dict['partition_id']
except amdsmi_exception.AmdSmiLibraryException as e:
profile_type = "N/A"
profile_index = "N/A"
partition_id = "N/A"
logging.debug("Failed to get accelerator partition profile for GPU %s | %s", gpu_id, e.get_error_info())
try:
current_mem_cap = amdsmi_interface.amdsmi_get_gpu_memory_partition(gpu)
except amdsmi_exception.AmdSmiLibraryException as e:
current_mem_cap = "N/A"
logging.debug("Failed to get current memory partition capabilties for GPU %s | %s", gpu_id, e.get_error_info())
tabular_output_dict = {"gpu_id": gpu_id,
"memory": current_mem_cap,
"accelerator_type": profile_type,
"accelerator_profile_index": profile_index,
"partition_id": partition_id}
tabular_output.append(tabular_output_dict)
self.logger.multiple_device_output = tabular_output
self.logger.table_title = "CURRENT_PARTITION"
self.logger.print_output(multiple_device_enabled=True, tabular=True)
self.logger.clear_multiple_devices_ouput()
if args.memory:
for gpu in args.gpu:
gpu_id = self.helpers.get_gpu_id_from_device_handle(gpu)
try:
memory_partition = amdsmi_interface.amdsmi_get_gpu_memory_partition(gpu) # this info likely actually comes from different apis than used here
except amdsmi_exception.AmdSmiLibraryException as e:
memory_partition = "N/A"
logging.debug("Failed to get current memory partition for GPU %s | %s", gpu_id, e.get_error_info())
try:
partition_dict = amdsmi_interface.amdsmi_get_gpu_accelerator_partition_profile(gpu)
temp_mem_caps = partition_dict['partition_profile']['memory_caps']
if temp_mem_caps.amdsmi_nps_flags_t == None:
mem_caps = temp_mem_caps.nps_cap_mask
mem_caps_list = []
if mem_caps & 1 == 1:
mem_caps_list.append("NPS1")
if mem_caps & 2 == 2:
mem_caps_list.append("NPS2")
if mem_caps & 4 == 4:
mem_caps_list.append("NPS4")
if mem_caps & 8 == 8:
mem_caps_list.append("NPS8")
mem_caps_str = str(mem_caps_list).replace("]", "").replace("[", "")
else:
mem_caps = temp_mem_caps.amdsmi_nps_flags_t
mem_caps_list = []
if mem_caps.nps1_cap == 1:
mem_caps_list.append("NPS1")
if mem_caps.nps2_cap == 1:
mem_caps_list.append("NPS2")
if mem_caps.nps4_cap == 1:
mem_caps_list.append("NPS4")
if mem_caps.nps8_cap == 1:
mem_caps_list.append("NPS8")
mem_caps_str = str(mem_caps_list).replace("]", "").replace("[", "")
if mem_caps_str == "":
mem_caps_str = "N/A"
except amdsmi_exception.AmdSmiLibraryException as e:
mem_caps_str = "N/A"
logging.debug("Failed to get accelerator partition profile for GPU %s | %s", gpu_id, e.get_error_info())
memory_dict = {'caps': mem_caps_str, 'current': memory_partition}
self.logger.store_output(gpu, 'memory_partition', memory_dict)
self.logger.store_multiple_device_output()
self.logger.print_output(multiple_device_enabled=True)
self.logger.clear_multiple_devices_ouput()
if args.accelerator:
self.logger.table_header = ''.rjust(7)
current_header = "GPU_ID".ljust(13) + \
"PROFILE_INDEX".ljust(15) + \
"MEMORY_PARTITION_CAPS".ljust(23) + \
"ACCELERATOR_TYPE".ljust(18) + \
"PARTITION_ID".ljust(14) + \
"NUM_PARTITIONS".ljust(16) + \
"NUM_RESOURCES".ljust(15) + \
"RESOURCE_INDEX".ljust(16) + \
"RESOURCE_TYPE".ljust(15) + \
"RESOURCE_INSTANCES".ljust(20) + \
"RESOURCES_SHARED".ljust(18)
self.logger.table_header = current_header + self.logger.table_header.strip()
tabular_output = []
for gpu in args.gpu:
gpu_id = self.helpers.get_gpu_id_from_device_handle(gpu)
try:
partition_dict = amdsmi_interface.amdsmi_get_gpu_accelerator_partition_profile(gpu)
profile_type = partition_dict['partition_profile']['profile_type']
profile_index = partition_dict['partition_profile']['profile_index']
temp_mem_caps = partition_dict['partition_profile']['memory_caps']
parition_id = partition_dict['partition_id']
num_resources = partition_dict['partition_profile']['num_resources']
resources = partition_dict['partition_profile']['resources']
if temp_mem_caps.amdsmi_nps_flags_t == None:
mem_caps = temp_mem_caps.nps_cap_mask
mem_caps_list = []
if mem_caps & 1 == 1:
mem_caps_list.append("NPS1")
if mem_caps & 2 == 2:
mem_caps_list.append("NPS2")
if mem_caps & 4 == 4:
mem_caps_list.append("NPS4")
if mem_caps & 8 == 8:
mem_caps_list.append("NPS8")
mem_caps_str = str(mem_caps_list).replace("]", "").replace("[", "")
else:
mem_caps = temp_mem_caps.amdsmi_nps_flags_t
mem_caps_list = []
if mem_caps.nps1_cap == 1:
mem_caps_list.append("NPS1")
if mem_caps.nps2_cap == 1:
mem_caps_list.append("NPS2")
if mem_caps.nps4_cap == 1:
mem_caps_list.append("NPS4")
if mem_caps.nps8_cap == 1:
mem_caps_list.append("NPS8")
mem_caps_str = str(mem_caps_list).replace("]", "").replace("[", "")
if mem_caps_str == "":
mem_caps_str = "N/A"
except amdsmi_exception.AmdSmiLibraryException as e:
profile_type = "N/A"
profile_index = "N/A"
temp_mem_caps = "N/A"
parition_id = "N/A"
num_resources = "N/A"
resources = "N/A"
mem_caps_str = "N/A"
logging.debug("Failed to get accelerator partition profile for GPU %s | %s", gpu_id, e.get_error_info())
tabular_output_dict = {"gpu_id": gpu_id,
"profile_index": profile_index,
"memory_partition_caps": mem_caps_str,
"accelerator_type": profile_type,
"partition_id": parition_id,
"num_partitions": 0,
"num_resources": num_resources,
"resource_index": resources,
"resource_type": resources,
"resource_instances": resources,
"resources_shared": resources}
tabular_output.append(tabular_output_dict)
self.logger.multiple_device_output = tabular_output
self.logger.table_title = "ACCELERATOR_PARTITION_PROFILES"
self.logger.print_output(multiple_device_enabled=True, tabular=True)
self.logger.clear_multiple_devices_ouput()
def _event_thread(self, commands, i):
devices = commands.device_handles
if len(devices) == 0:
+25 -1
Parādīt failu
@@ -150,8 +150,32 @@ class AMDSMILogger():
table_values += string_value.ljust(14)
elif key == "link_type":
table_values += string_value.ljust(10)
elif key == "memory":
table_values += string_value.ljust(8)
elif key == "accelerator_type":
table_values += string_value.ljust(18)
elif key == "partition_id":
table_values += string_value.ljust(14)
elif key == "accelerator_profile_index":
table_values += string_value.ljust(27)
elif key == "profile_index":
table_values += string_value.ljust(15)
elif key == "memory_partition_caps":
table_values += string_value.ljust(23)
elif key == "num_partitions":
table_values += string_value.ljust(16)
elif key == "num_resources":
table_values += string_value.ljust(15)
elif key == "resource_index":
table_values += string_value.ljust(16)
elif key == "resource_type":
table_values += string_value.ljust(15)
elif key == "resource_instances":
table_values += string_value.ljust(20)
elif key == "resources_shared":
table_values += string_value.ljust(18)
elif key == "RW":
table_values += " " + string_value.ljust(52)
table_values += string_value.ljust(52)
elif key == "process_list":
#Add an additional padding between the first instance of GPU and NAME
table_values += ' '
+37 -2
Parādīt failu
@@ -71,7 +71,7 @@ class AMDSMIParser(argparse.ArgumentParser):
"""
def __init__(self, version, list, static, firmware, bad_pages, metric,
process, profile, event, topology, set_value, reset, monitor,
rocmsmi, xgmi):
rocmsmi, xgmi, partition):
# Helper variables
self.helpers = AMDSMIHelpers()
@@ -117,7 +117,7 @@ class AMDSMIParser(argparse.ArgumentParser):
# Store possible subcommands & aliases for later errors
self.possible_commands = ['version', 'list', 'static', 'firmware', 'ucode', 'bad-pages',
'metric', 'process', 'profile', 'event', 'topology', 'set',
'reset', 'monitor', 'dmon', 'xgmi']
'reset', 'monitor', 'dmon', 'xgmi', 'partition']
# Add all subparsers
self._add_version_parser(self.subparsers, version)
@@ -135,6 +135,7 @@ class AMDSMIParser(argparse.ArgumentParser):
self._add_monitor_parser(self.subparsers, monitor)
self._add_rocm_smi_parser(self.subparsers, rocmsmi)
self._add_xgmi_parser(self.subparsers, xgmi)
self._add_partition_parser(self.subparsers, partition)
def _not_negative_int(self, int_value):
@@ -1286,6 +1287,40 @@ class AMDSMIParser(argparse.ArgumentParser):
xgmi_parser.add_argument('-m', '--metric', action='store_true', required=False, help=metrics_help)
def _add_partition_parser(self, subparsers, func):
if not self.helpers.is_amdgpu_initialized():
# The partition subcommand is only applicable to systems with amdgpu initialized
return
# Subparser help text
partition_help = "Displays partition information of the devices"
partition_subcommand_help = "If no GPU is specified, returns information for all GPUs on the system.\
\nIf no partition argument is provided all partition information will be displayed."
partition_optionals_title = "partition arguments"
# Options help text
current_help = "display the current partition information"
memory_help = "display the current memory partition mode and capabilities"
accelerator_help = "display accelerator partition information"
# Create partition subparser
partition_parser = subparsers.add_parser('partition', help=partition_help, description=partition_subcommand_help)
partition_parser._optionals.title = partition_optionals_title
partition_parser.formatter_class=lambda prog: AMDSMISubparserHelpFormatter(prog)
partition_parser.set_defaults(func=func)
# Add Universal Arguments
self._add_device_arguments(partition_parser, required=False)
# Handle GPU Options
partition_parser.add_argument('-c', '--current', action='store_true', required=False, help=current_help)
partition_parser.add_argument('-m', '--memory', action='store_true', required=False, help=memory_help)
partition_parser.add_argument('-a', '--accelerator', action='store_true', required=False, help=accelerator_help)
# Add command modifiers to the bottom
self._add_command_modifiers(partition_parser)
def error(self, message):
outputformat = self.helpers.get_output_format()