Enabling Standalone GUI on 2.x (#214)

* Initial overhaul of Analyze mode. Basic CLI is enabled.

Signed-off-by: colramos-amd <colramos@amd.com>

* Merge branch '2.x' of github.com:AMDResearch/omniperf into 2.x-dev

Signed-off-by: colramos-amd <colramos@amd.com>

* fix comment typo

Signed-off-by: Karl W Schulz <karl.schulz@amd.com>

* Move error logging to util.py

Signed-off-by: colramos-amd <colramos@amd.com>

* Move perfmon_configs dir into omniperf_soc dir. Rename config dirs for clarity

Signed-off-by: colramos-amd <colramos@amd.com>

* Add a supported_archs property to Omniperf base class

Signed-off-by: colramos-amd <colramos@amd.com>

* Add css assets for GUI styling

Signed-off-by: colramos-amd <colramos@amd.com>

* Re-organize roofline class. Improved useability

Signed-off-by: colramos-amd <colramos@amd.com>

* Enable standalone GUI

Signed-off-by: colramos-amd <colramos@amd.com>

* Remove outdated metric_configs. This was moved to omniperf_soc dir

Signed-off-by: colramos-amd <colramos@amd.com>

* Fix small bug in GUI to enable Mi100 visualization

Signed-off-by: colramos-amd <colramos@amd.com>

---------

Signed-off-by: colramos-amd <colramos@amd.com>
Signed-off-by: Karl W Schulz <karl.schulz@amd.com>
Signed-off-by: Cole Ramos <colramos@amd.com>
Co-authored-by: Karl W Schulz <karl.schulz@amd.com>

[ROCm/rocprofiler-compute commit: 7d93a086c2]
Cette révision appartient à :
Cole Ramos
2023-12-18 16:37:01 -06:00
révisé par GitHub
Parent 4719fa0e3b
révision c73bd2bf91
165 fichiers modifiés avec 37024 ajouts et 14772 suppressions
+379
Voir le fichier
@@ -0,0 +1,379 @@
##############################################################################bl
# MIT License
#
# Copyright (c) 2021 - 2023 Advanced Micro Devices, Inc. All Rights Reserved.
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in 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:
#
# The above copyright notice and this permission notice shall be included in all
# copies or substantial portions of the Software.
#
# 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
# AUTHORS 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 IN THE
# SOFTWARE.
##############################################################################el
import sys
import pandas as pd
from dash import html, dash_table
import plotly.express as px
import colorlover
from utils import schema
pd.set_option(
"mode.chained_assignment", None
) # ignore SettingWithCopyWarning pandas warning
IS_DARK = True #TODO: Remove hardcoded in favor of class property
##################
# HELPER FUNCTIONS
##################
def filter_df(column, df, filt):
filt_df = df
if filt != []:
filt_df = df.loc[df[schema.pmc_perf_file_prefix][column].astype(str).isin(filt)]
return filt_df
def multi_bar_chart(table_id, display_df):
if table_id == 1604:
nested_bar = {"NC": {}, "UC": {}, "RW": {}, "CC": {}}
for index, row in display_df.iterrows():
nested_bar[row["Coherency"]][row["Xfer"]] = row["Avg"]
if table_id == 1704:
nested_bar = {"Read": {}, "Write": {}}
for index, row in display_df.iterrows():
nested_bar[row["Transaction"]][row["Type"]] = row["Avg"]
return nested_bar
def discrete_background_color_bins(df, n_bins=5, columns="all"):
bounds = [i * (1.0 / n_bins) for i in range(n_bins + 1)]
if columns == "all":
if "id" in df:
df_numeric_columns = df.select_dtypes("number").drop(["id"], axis=1)
else:
df_numeric_columns = df.select_dtypes("number")
else:
df_numeric_columns = df[columns]
df_max = df_numeric_columns.max().max()
df_min = df_numeric_columns.min().min()
ranges = [((df_max - df_min) * i) + df_min for i in bounds]
styles = []
legend = []
for i in range(1, len(bounds)):
min_bound = ranges[i - 1]
max_bound = ranges[i]
backgroundColor = colorlover.scales[str(n_bins)]["seq"]["Blues"][i - 1]
color = "white" if i > len(bounds) / 2.0 else "inherit"
for column in df_numeric_columns:
styles.append(
{
"if": {
"filter_query": (
"{{{column}}} >= {min_bound}"
+ (
" && {{{column}}} < {max_bound}"
if (i < len(bounds) - 1)
else ""
)
).format(column=column, min_bound=min_bound, max_bound=max_bound),
"column_id": column,
},
"backgroundColor": backgroundColor,
"color": color,
}
)
legend.append(
html.Div(
style={"display": "inline-block", "width": "60px"},
children=[
html.Div(
style={
"backgroundColor": backgroundColor,
"borderLeft": "1px rgb(50, 50, 50) solid",
"height": "10px",
}
),
html.Small(round(min_bound, 2), style={"paddingLeft": "2px"}),
],
)
)
return (styles, html.Div(legend, style={"padding": "5px 0 5px 0"}))
####################
# GRAPHICAL ELEMENTS
####################
def build_bar_chart(display_df, table_config, barchart_elements, norm_filt):
"""
Read data into a bar chart. ID will determine which subtype of barchart.
"""
d_figs = []
# Insr Mix bar chart
if table_config["id"] in barchart_elements["instr_mix"]:
display_df["Avg"] = [
x.astype(int) if x != "" else int(0) for x in display_df["Avg"]
]
df_unit = display_df["Unit"][0]
d_figs.append(
px.bar(
display_df,
x="Avg",
y="Metric",
color="Avg",
labels={"Avg": "# of {}".format(df_unit.lower())},
height=400,
orientation="h",
)
)
# Multi bar chart
elif table_config["id"] in barchart_elements["multi_bar"]:
display_df["Avg"] = [
x.astype(int) if x != "" else int(0) for x in display_df["Avg"]
]
df_unit = display_df["Unit"][0]
nested_bar = multi_bar_chart(table_config["id"], display_df)
# generate chart for each coherency
for group, metric in nested_bar.items():
d_figs.append(
px.bar(
title=group,
x=metric.values(),
y=metric.keys(),
labels={"x": df_unit, "y": ""},
text=metric.values(),
orientation="h",
height=200,
)
.update_xaxes(showgrid=False, rangemode="nonnegative")
.update_yaxes(showgrid=False)
.update_layout(title_x=0.5)
)
# L2 Cache per channel
elif table_config["id"] in barchart_elements["l2_cache_per_chan"]:
nested_bar = {}
channels = []
for colName, colData in display_df.items():
if colName == "Channel":
channels = list(colData.values)
else:
display_df[colName] = [
x.astype(float) if x != "" and x != None else float(0)
for x in display_df[colName]
]
nested_bar[colName] = list(display_df[colName])
for group, metric in nested_bar.items():
d_figs.append(
px.bar(
title=group[0 : group.rfind("(")],
x=channels,
y=metric,
labels={
"x": "Channel",
"y": group[group.rfind("(") + 1 : len(group) - 1].replace(
"per", norm_filt
),
},
).update_yaxes(rangemode="nonnegative")
)
# Speed-of-light bar chart
elif table_config["id"] in barchart_elements["sol"]:
display_df["Value"] = [
x.astype(float) if x != "" else float(0) for x in display_df["Value"]
]
if table_config["id"] == 1701:
# special layout for L2 Cache SOL
d_figs.append(
px.bar(
display_df[display_df["Unit"] == "Pct"],
x="Value",
y="Metric",
color="Value",
range_color=[0, 100],
labels={"Value": "%"},
height=220,
orientation="h",
).update_xaxes(range=[0, 110], ticks="inside")
) # append first % chart
d_figs.append(
px.bar(
display_df[display_df["Unit"] == "Gb/s"],
x="Value",
y="Metric",
color="Value",
range_color=[0, 1638],
labels={"Value": "GB/s"},
height=220,
orientation="h",
).update_xaxes(range=[0, 1638])
) # append second GB/s chart
else:
d_figs.append(
px.bar(
display_df,
x="Value",
y="Metric",
color="Value",
range_color=[0, 100],
labels={"Value": "%"},
height=400,
orientation="h",
).update_xaxes(range=[0, 110])
)
else:
print(
"ERROR: Table id {}. Cannot determine barchart type.".format(
table_config["id"]
)
)
sys.exit(-1)
# update layout for each of the charts
for fig in d_figs:
fig.update_layout(
margin=dict(l=50, r=50, b=50, t=50, pad=4),
paper_bgcolor="rgba(0,0,0,0)",
plot_bgcolor="rgba(0,0,0,0)",
font={"color": "#ffffff"},
)
return d_figs
def build_table_chart(
display_df, table_config, original_df, display_columns, comparable_columns, decimal
):
"""
Read data into a DashTable
"""
d_figs = []
# build comlumns/header with formatting
formatted_columns = []
for col in display_df.columns:
if (
str(col).lower() == "pct"
or str(col).lower() == "pop"
or str(col).lower() == "percentage"
):
formatted_columns.append(
dict(
id=col,
name=col,
type="numeric",
format={"specifier": ".{}f".format(decimal)},
)
)
elif col in comparable_columns:
formatted_columns.append(
dict(
id=col,
name=col,
type="numeric",
format={"specifier": ".{}f".format(decimal)},
)
)
else:
formatted_columns.append(dict(id=col, name=col, type="text"))
# tooltip shows only on the 1st col for now if 'Tips' available
table_tooltip = (
[
{
column: {
"value": str(row["Tips"])
if column == display_columns[0] and row["Tips"]
else "",
"type": "markdown",
}
for column, value in row.items()
}
for row in original_df.to_dict("records")
]
if "Tips" in original_df.columns.values.tolist()
else None
)
# build data table with columns, tooltip, df and other properties
d_t = dash_table.DataTable(
id=str(table_config["id"]),
sort_action="native",
sort_mode="multi",
columns=formatted_columns,
tooltip_data=table_tooltip,
# left-aligning the text of the 1st col
style_cell_conditional=[
{"if": {"column_id": display_columns[0]}, "textAlign": "left"}
],
# style cell
style_cell={"maxWidth": "500px"},
# display style
style_header={
"backgroundColor": "rgb(30, 30, 30)",
"color": "white",
"fontWeight": "bold",
}
if IS_DARK
else {},
style_data={
"backgroundColor": "rgb(50, 50, 50)",
"color": "white",
"whiteSpace": "normal",
"height": "auto",
}
if IS_DARK
else {},
style_data_conditional=[
{"if": {"row_index": "odd"}, "backgroundColor": "rgb(60, 60, 60)"},
{
"if": {"column_id": "PoP", "filter_query": "{PoP} > 50"},
"backgroundColor": "#ffa90a",
"color": "white",
},
{
"if": {"column_id": "PoP", "filter_query": "{PoP} > 80"},
"backgroundColor": "#ff120a",
"color": "white",
},
{
"if": {
"column_id": "Avg",
"filter_query": "{Unit} = Pct && {Avg} > 50",
},
"backgroundColor": "#ffa90a",
"color": "white",
},
{
"if": {
"column_id": "Avg",
"filter_query": "{Unit} = Pct && {Avg} > 80",
},
"backgroundColor": "#ff120a",
"color": "white",
},
]
if IS_DARK
else [],
# the df to display
data=display_df.to_dict("records"),
)
# print("DATA: \n", display_df.to_dict('records'))
d_figs.append(d_t)
return d_figs
# print(d_t.columns)
+341
Voir le fichier
@@ -0,0 +1,341 @@
##############################################################################bl
# MIT License
#
# Copyright (c) 2021 - 2023 Advanced Micro Devices, Inc. All Rights Reserved.
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in 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:
#
# The above copyright notice and this permission notice shall be included in all
# copies or substantial portions of the Software.
#
# 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
# AUTHORS 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 IN THE
# SOFTWARE.
##############################################################################el
from dash import html, dcc
import dash_bootstrap_components as dbc
from utils import schema
avail_normalizations = ["per_wave", "per_cycle", "per_second", "per_kernel"]
# List all the unique column values for desired column in df, 'target_col'
def list_unique(orig_list, is_numeric):
list_set = set(orig_list)
unique_list = list(list_set)
if is_numeric:
unique_list.sort()
return unique_list
def create_span(input):
elmt = {}
elmt["label"] = (html.Span(str(input), title=str(input)),)
elmt["value"] = str(input)
return elmt
def get_header(raw_pmc, input_filters, kernel_names):
return html.Header(
id="home",
children=[
html.Nav(
id="nav-wrap",
children=[
html.Ul(
id="nav",
children=[
html.Div(
className="nav-left",
children=[
dbc.DropdownMenu(
[
dbc.DropdownMenuItem("Overview", header=True),
dbc.DropdownMenuItem(
"Roofline",
href="#roofline",
external_link=True,
),
dbc.DropdownMenuItem(
"Top Stat",
href="#top_stat",
external_link=True,
),
dbc.DropdownMenuItem(
"System Info",
href="#system_info",
external_link=True,
),
dbc.DropdownMenuItem(
"System Speed-of-Light",
href="#system_speed-of-light",
external_link=True,
),
dbc.DropdownMenuItem("Compute", header=True),
dbc.DropdownMenuItem(
"Command Processor (CPF/CPC)",
href="#command_processor_cpccpf",
external_link=True,
),
dbc.DropdownMenuItem(
"Shader Processor Input (SPI)",
href="#shader_processor_input_spi",
external_link=True,
),
dbc.DropdownMenuItem(
"Wavefront",
href="#wavefront",
external_link=True,
),
dbc.DropdownMenuItem(
"Compute Units - Instruction Mix",
href="#compute_units_-_instruction_mix",
external_link=True,
),
dbc.DropdownMenuItem(
"Compute Units - Compute Pipeline",
href="#compute_units_-_compute_pipeline",
external_link=True,
),
dbc.DropdownMenuItem("Cache", header=True),
dbc.DropdownMenuItem(
"Local Data Share (LDS)",
href="#local_data_share_lds",
external_link=True,
),
dbc.DropdownMenuItem(
"Instruction Cache",
href="#instruction_cache",
external_link=True,
),
dbc.DropdownMenuItem(
"Scalar L1 Data Cache",
href="#scalar_l1_data_cache",
external_link=True,
),
dbc.DropdownMenuItem(
"Texture Addresser & Texture Data (TA/TD)",
href="#texture_addresser_and_texture_data_tatd",
external_link=True,
),
dbc.DropdownMenuItem(
"Vector L1 Data Cache",
href="#vector_l1_data_cache",
external_link=True,
),
dbc.DropdownMenuItem(
"L2 Cache",
href="#l2_cache",
external_link=True,
),
dbc.DropdownMenuItem(
"L2 Cache (per channel)",
href="#l2_cache_per_channel",
external_link=True,
),
],
label="Menu",
menu_variant="dark",
),
],
),
html.Li(
className="filter",
children=[
html.Div(
children=[
html.A(
className="smoothscroll",
children=["Normalization:"],
),
dcc.Dropdown(
avail_normalizations,
id="norm-filt",
value=input_filters["normalization"],
clearable=False,
style={"width": "150px"},
),
]
)
],
),
html.Li(
className="filter",
children=[
html.Div(
children=[
html.A(
className="smoothscroll",
children=["GCD:"],
),
dcc.Dropdown(
list_unique(
list(
map(
str,
raw_pmc[
schema.pmc_perf_file_prefix
]["gpu-id"],
)
),
True,
), # list avail gcd ids
id="gcd-filt",
multi=True,
value=input_filters[
"gpu"
], # default to any gpu filters passed as args
placeholder="ALL",
clearable=False,
style={"width": "60px"},
),
]
)
],
),
html.Li(
className="filter",
children=[
html.Div(
children=[
html.A(
className="smoothscroll",
children=["Dispatch Filter:"],
),
dcc.Dropdown(
list(
map(
str,
raw_pmc[
schema.pmc_perf_file_prefix
]["Index"],
)
),
id="disp-filt",
multi=True,
value=input_filters[
"dispatch"
], # default to any dispatch filters passed as args
placeholder="ALL",
style={"width": "150px"},
),
]
)
],
),
html.Li(
className="filter",
children=[
html.Div(
children=[
html.A(
className="smoothscroll",
children=["Top N:"],
),
dcc.Dropdown(
[1, 5, 10, 15, 20, 50, 100],
id="top-n-filt",
value=input_filters[
"top_n"
], # default to any dispatch filters passed as args
clearable=False,
style={"width": "50px"},
),
]
)
],
),
html.Li(
className="filter",
children=[
html.Div(
children=[
html.A(
className="smoothscroll",
children=["Kernels:"],
),
dcc.Dropdown(
list(
map(
create_span,
list_unique(
list(
map(
str,
raw_pmc[
schema.pmc_perf_file_prefix
]["KernelName"],
)
),
False,
), # list avail kernel names
)
),
id="kernel-filt",
multi=True,
value=kernel_names,
optionHeight=150,
placeholder="ALL",
style={
"width": "600px", # TODO: Change these widths to % rather than fixed value
},
),
]
)
],
),
html.Div(
className="nav-right",
children=[
html.Li(
children=[
# Report bug button
html.A(
href="",
children=[
html.Button(
className="report",
children=["Report Bug"],
)
],
)
]
)
],
),
],
)
],
),
html.Div(
className="row banner",
children=[
html.H3(
children=["Placeholder. Guided Analysis coming soon..."],
style={"color": "white"},
),
],
),
html.P(
className="scrolldown",
children=[
html.A(
className="smoothscroll",
href="#roofline",
children=[html.I(className="icon-down-circle")],
)
],
),
],
)
Fichier diff supprimé car celui-ci est trop grand Voir la Diff
+37 -49
Voir le fichier
@@ -22,9 +22,10 @@
# SOFTWARE.
##############################################################################el
import sys
import os
from dataclasses import dataclass
import logging
import csv
################################################
@@ -94,43 +95,42 @@ def get_color(catagory):
# -------------------------------------------------------------------------------------
# Plot BW at each cache level
# -------------------------------------------------------------------------------------
def calc_ceilings(roof_specs, benchmark_data, targ_mem_level, verbose):
def calc_ceilings(roofline_parameters, dtype, benchmark_data):
"""Given benchmarking data, calculate ceilings (or peak performance) for empirical roofline
"""
# TODO: This is where filtering by memory level will need to occur for standalone
graphPoints = {"hbm": [], "l2": [], "l1": [], "lds": [], "valu": [], "mfma": []}
if targ_mem_level == "ALL":
if roofline_parameters['mem_level'] == "ALL":
cacheHierarchy = ["HBM", "L2", "L1", "LDS"]
else:
cacheHierarchy = targ_mem_level
cacheHierarchy = roofline_parameters['mem_level']
x1 = y1 = x2 = y2 = -1
x1_mfma = y1_mfma = x2_mfma = y2_mfma = -1
target_precision = roof_specs["dtype"][2:]
target_precision = dtype[2:]
if roof_specs["dtype"] != "FP16" and roof_specs["dtype"] != "I8":
if dtype != "FP16" and dtype != "I8":
peakOps = float(
benchmark_data[roof_specs["dtype"] + "Flops"][roof_specs["device"]]
benchmark_data[dtype + "Flops"][roofline_parameters['device_id']]
)
for i in range(0, len(cacheHierarchy)):
# Plot BW line
if verbose >= 3:
print("Current cache level is ", cacheHierarchy[i])
# Plot BW line
logging.debug("[roofline] Current cache level is ", cacheHierarchy[i])
curr_bw = cacheHierarchy[i] + "Bw"
peakBw = float(benchmark_data[curr_bw][roof_specs["device"]])
peakBw = float(benchmark_data[curr_bw][roofline_parameters['device_id']])
if roof_specs["dtype"] == "I8":
peakMFMA = float(benchmark_data["MFMAI8Ops"][roof_specs["device"]])
if dtype == "I8":
peakMFMA = float(benchmark_data["MFMAI8Ops"][roofline_parameters['device_id']])
else:
peakMFMA = float(
benchmark_data["MFMAF{}Flops".format(target_precision)][roof_specs["device"]]
benchmark_data["MFMAF{}Flops".format(target_precision)][roofline_parameters['device_id']]
)
x1 = float(XMIN)
y1 = float(XMIN) * peakBw
# Note: No reg peakOps for FP16 or INT8
if roof_specs["dtype"] != "FP16" and roof_specs["dtype"] != "I8":
if dtype != "FP16" and dtype != "I8":
x2 = peakOps / peakBw
y2 = peakOps
@@ -142,9 +142,9 @@ def calc_ceilings(roof_specs, benchmark_data, targ_mem_level, verbose):
y2_mfma = peakMFMA
# These are the points to use:
if verbose >= 3:
print("x = [{}, {}]".format(x1, x2_mfma))
print("y = [{}, {}]".format(y1, y2_mfma))
logging.debug("[roofline] coordinate points:")
logging.debug("x = [{}, {}]".format(x1, x2_mfma))
logging.debug("y = [{}, {}]".format(y1, y2_mfma))
graphPoints[cacheHierarchy[i].lower()].append([x1, x2_mfma])
graphPoints[cacheHierarchy[i].lower()].append([y1, y2_mfma])
@@ -154,28 +154,26 @@ def calc_ceilings(roof_specs, benchmark_data, targ_mem_level, verbose):
# Plot computing roof
# -------------------------------------------------------------------------------------
# Note: No FMA roof for FP16 or INT8
if roof_specs["dtype"] != "FP16" and roof_specs["dtype"] != "I8":
if dtype != "FP16" and dtype != "I8":
# Plot FMA roof
x0 = XMAX
if x2 < x0:
x0 = x2
if verbose >= 3:
print("FMA ROOF [{}, {}], [{},{}]".format(x0, XMAX, peakOps, peakOps))
logging.debug("FMA ROOF [{}, {}], [{},{}]".format(x0, XMAX, peakOps, peakOps))
graphPoints["valu"].append([x0, XMAX])
graphPoints["valu"].append([peakOps, peakOps])
graphPoints["valu"].append(peakOps)
# Plot MFMA roof
if (
x1_mfma != -1 or roof_specs["dtype"] == "FP16" or roof_specs["dtype"] == "I8"
x1_mfma != -1 or dtype == "FP16" or dtype == "I8"
): # assert that mfma has been assigned
x0_mfma = XMAX
if x2_mfma < x0_mfma:
x0_mfma = x2_mfma
if verbose >= 3:
print("MFMA ROOF [{}, {}], [{},{}]".format(x0_mfma, XMAX, peakMFMA, peakMFMA))
logging.debug("MFMA ROOF [{}, {}], [{},{}]".format(x0_mfma, XMAX, peakMFMA, peakMFMA))
graphPoints["mfma"].append([x0_mfma, XMAX])
graphPoints["mfma"].append([peakMFMA, peakMFMA])
graphPoints["mfma"].append(peakMFMA)
@@ -187,7 +185,7 @@ def calc_ceilings(roof_specs, benchmark_data, targ_mem_level, verbose):
# Overlay application performance
# -------------------------------------------------------------------------------------
# Calculate relevent metrics for ai calculation
def calc_ai(sort_type, ret_df, verbose):
def calc_ai(sort_type, ret_df):
"""Given counter data, caclulate arithmetic intensity for each kernel in the application.
"""
df = ret_df["pmc_perf"]
@@ -263,8 +261,7 @@ def calc_ai(sort_type, ret_df, verbose):
+ (df["SQ_INSTS_VALU_MFMA_MOPS_F64"][idx] * 512)
)
except KeyError:
if verbose >= 3:
print("{}: Skipped total_flops at index {}".format(kernelName[:35], idx))
logging.debug("[roofline] {}: Skipped total_flops at index {}".format(kernelName[:35], idx))
pass
try:
valu_flops += (
@@ -291,8 +288,7 @@ def calc_ai(sort_type, ret_df, verbose):
)
)
except KeyError:
if verbose >= 3:
print("{}: Skipped valu_flops at index {}".format(kernelName[:35], idx))
logging.debug("{}: Skipped valu_flops at index {}".format(kernelName[:35], idx))
pass
try:
@@ -302,8 +298,7 @@ def calc_ai(sort_type, ret_df, verbose):
mfma_flops_f64 += df["SQ_INSTS_VALU_MFMA_MOPS_F64"][idx] * 512
mfma_iops_i8 += df["SQ_INSTS_VALU_MFMA_MOPS_I8"][idx] * 512
except KeyError:
if verbose >= 3:
print("{}: Skipped mfma ops at index {}".format(kernelName[:35], idx))
logging.debug("[roofline] {}: Skipped mfma ops at index {}".format(kernelName[:35], idx))
pass
try:
@@ -313,15 +308,13 @@ def calc_ai(sort_type, ret_df, verbose):
* L2_BANKS
) # L2_BANKS = 32 (since assuming mi200)
except KeyError:
if verbose >= 3:
print("{}: Skipped lds_data at index {}".format(kernelName[:35], idx))
logging.debug("[roofline] {}: Skipped lds_data at index {}".format(kernelName[:35], idx))
pass
try:
L1cache_data += df["TCP_TOTAL_CACHE_ACCESSES_sum"][idx] * 64
except KeyError:
if verbose >= 3:
print("{}: Skipped L1cache_data at index {}".format(kernelName[:35], idx))
logging.debug("[roofline] {}: Skipped L1cache_data at index {}".format(kernelName[:35], idx))
pass
try:
@@ -332,8 +325,7 @@ def calc_ai(sort_type, ret_df, verbose):
+ df["TCP_TCC_READ_REQ_sum"][idx] * 64
)
except KeyError:
if verbose >= 3:
print("{}: Skipped L2cache_data at index {}".format(kernelName[:35], idx))
logging.debug("[roofline] {}: Skipped L2cache_data at index {}".format(kernelName[:35], idx))
pass
try:
hbm_data += (
@@ -343,8 +335,7 @@ def calc_ai(sort_type, ret_df, verbose):
+ ((df["TCC_EA_WRREQ_sum"][idx] - df["TCC_EA_WRREQ_64B_sum"][idx]) * 32)
)
except KeyError:
if verbose >= 3:
print("{}: Skipped hbm_data at index {}".format(kernelName[:35], idx))
logging.debug("[roofline] {}: Skipped hbm_data at index {}".format(kernelName[:35], idx))
pass
totalDuration += df["EndNs"][idx] - df["BeginNs"][idx]
@@ -372,12 +363,11 @@ def calc_ai(sort_type, ret_df, verbose):
avgDuration / calls,
)
)
if verbose >= 2:
print(
"Just added {} to AI_Data at index {}. # of calls: {}".format(
kernelName, idx, calls
)
logging.debug(
"Just added {} to AI_Data at index {}. # of calls: {}".format(
kernelName, idx, calls
)
)
total_flops = (
valu_flops
) = (
@@ -487,8 +477,8 @@ def calc_ai(sort_type, ret_df, verbose):
return intensityPoints
def constuct_roof(roof_specs, targ_mem_level, verbose):
benchmark_results = roof_specs["path"] + "/roofline.csv"
def constuct_roof(roofline_parameters, dtype):
benchmark_results = os.path.join(roofline_parameters["path_to_dir"], "roofline.csv")
# -----------------------------------------------------
# Initialize roofline data dictionary from roofline.csv
# -----------------------------------------------------
@@ -526,8 +516,6 @@ def constuct_roof(roof_specs, targ_mem_level, verbose):
# ------------------
# Generate Roofline
# ------------------
results = calc_ceilings(roof_specs, benchmark_data, targ_mem_level, verbose)
# for key in results:
# print(key, "->", results[key])
results = calc_ceilings(roofline_parameters, dtype, benchmark_data)
return results
-1
Voir le fichier
@@ -135,7 +135,6 @@ def show_all(args, runs, archConfigs, output):
)
# show value + percentage
# TODO: better alignment
t_df = (
cur_df[header]
.astype(float)