From 078a38a906185761a985ec18431e9ad551d7d839 Mon Sep 17 00:00:00 2001 From: Richard Yan Date: Thu, 30 Jan 2025 02:54:57 -0800 Subject: [PATCH] scripts to compile and run experiments --- sims/vcs/scripts/compile_designs.sh | 19 ++++ sims/vcs/scripts/env.sh | 1 + sims/vcs/scripts/pprint | 163 ++++++++++++++++++++++++++++ sims/vcs/scripts/run_sims.sh | 61 +++++++++++ sims/vcs/scripts/sram_util.sh | 42 +++++++ 5 files changed, 286 insertions(+) create mode 100755 sims/vcs/scripts/compile_designs.sh create mode 100755 sims/vcs/scripts/env.sh create mode 100755 sims/vcs/scripts/pprint create mode 100755 sims/vcs/scripts/run_sims.sh create mode 100755 sims/vcs/scripts/sram_util.sh diff --git a/sims/vcs/scripts/compile_designs.sh b/sims/vcs/scripts/compile_designs.sh new file mode 100755 index 00000000..5ddcb3c1 --- /dev/null +++ b/sims/vcs/scripts/compile_designs.sh @@ -0,0 +1,19 @@ +#!/bin/bash + +set -e + +CURRENT_DIR="${PWD##*/}" +if [[ "$CURRENT_DIR" != "vcs" ]]; then + echo "Error: This script must be run from chipyard/sims/vcs." + exit 1 +fi + +source ./scripts/env.sh + +echo -e "\nCompiling volta & ampere designs" +make CONFIG=VirgoFP16Config +make CONFIG=VirgoFP16Config debug +echo -e "\nCompiling hopper & virgo designs" +make CONFIG=VirgoHopperConfig +make CONFIG=VirgoHopperConfig debug +echo -e "\nCompilation completed" diff --git a/sims/vcs/scripts/env.sh b/sims/vcs/scripts/env.sh new file mode 100755 index 00000000..2eace979 --- /dev/null +++ b/sims/vcs/scripts/env.sh @@ -0,0 +1 @@ +export KERNELS_PATH="/scratch/yrh/vxsw/kernels" diff --git a/sims/vcs/scripts/pprint b/sims/vcs/scripts/pprint new file mode 100755 index 00000000..1c0aa85d --- /dev/null +++ b/sims/vcs/scripts/pprint @@ -0,0 +1,163 @@ +#!/usr/bin/env python3 + +import sys +import signal +import re +import time + +PRINT_BUF = 0x20000 / 4 + +def translator(line): + if 'core-req-wr' in line: + # Check rs1_data's last element condition + rs1_data_start = line.find('addr={') + len('addr={') + rs1_data_end = line.find('}', rs1_data_start) + rs1_data_elts = line[rs1_data_start:rs1_data_end].split(', ') + + byteen_start = line.find('byteen={') + len('byteen={') + byteen_end = line.find('}', byteen_start) + byteen_elts = line[byteen_start:byteen_end].split(', ') + + rs2_data_start = line.find('data={') + len('data={') + rs2_data_end = line.find('}', rs2_data_start) + rs2_data_elts = line[rs2_data_start:rs2_data_end].split(', ') + + # print(rs1_data_last_element) + for rs1, rs2, byteen in zip(rs1_data_elts, rs2_data_elts, byteen_elts): + if int(rs1, 16) >> 18 == 0xff0: + offset = (int(rs1, 16) - PRINT_BUF) % 65536 + if offset < 0 or offset >= 1024: + continue + else: + offset = offset % 16384 + # Extract rs2_data's last element + + hex_value = rs2[2:] # Remove the '0x' prefix + if "x" in hex_value: + continue + byteen_int = int(byteen, 16) + hex_value = "0" * (8 - len(hex_value)) + hex_value + bytes_object = bytes.fromhex(hex_value) # .replace(b"\x00", b"") + + masked_bytes_list = [] + + assert(len(bytes_object) == 4) + + for i, byte in enumerate(bytes_object[::-1]): + if byteen_int & (1 << i): + masked_bytes_list.append(byte) + + reversed_bytes = bytes(masked_bytes_list) + # print(reversed_bytes.decode('utf-8', errors="ignore")) + try: + return reversed_bytes.decode('ascii', errors="ignore") + except UnicodeDecodeError: + return "" + +def timestamp_parser(line): + match = re.match(r"^\s*(\d+):", line) + if match: + return match.group(1) + else: + return "" + +sim_started = False +sim_ended = False + +def signal_handler(sig, frame): + if sim_started: + print("\033[B") + sys.exit(0) + +def main(): + signal.signal(signal.SIGINT, signal_handler) + + curr_timestamp = -1 + prev_timestamp = -1 + curr_clock = time.time() + prev_clock = time.time() + re_start_num = re.compile(r"^\s*[0-9]+:") + + ts_countdown = 100 + global sim_started, sim_ended + perf_counters = False + hang_detector = 0 + + # if (len(sys.argv) > 1) and (sys.argv[1] == "started"): + # sim_started = True + run_label = sys.argv[1] + lineno = int(sys.argv[2]) + + print("\033[2J\033[H") + + for line in sys.stdin: + line = line.rstrip('\n') + + if "Chronologic VCS simulator" in line: + sim_started = True + + sim_nontrace = re.match(re_start_num, line) is None + + if "====================CORE" in line: + perf_counters = True + if hang_detector >= 8: + pass + # print("\n\033[3mpossible hang detected\033[0m\n") + + if "has no more active warps" in line: + sim_ended = True + + if (not sim_started): + print(line) + continue + + if sim_ended: + if "has no more active warps" not in line: + sim_ended = False + else: + continue + + if sim_started and (not sim_ended): + if sim_nontrace: + if not perf_counters: + print(line) + elif line.startswith("dcache stores:"): + perf_counters = False + hang_detector += 1 + continue + else: + hang_detector = 0 + + if ts_countdown == 0: + match = re.match(r"^\s*(\d+):", line) + if match: + prev_clock = curr_clock + prev_timestamp = curr_timestamp + curr_clock = time.time() + curr_timestamp = match.group(1) + speed_in_hz = (int(curr_timestamp) - int(prev_timestamp)) / (curr_clock - prev_clock) if curr_clock - prev_clock > 0 else 0 + + # Save cursor position + print("\033[s", end='') + # Move cursor to top-left corner, clear line, bold, timestamp, unbold + print("\033[" + str(lineno) + "H\033[2K\033[1m" + run_label, + "[TIME]", curr_timestamp, "[SPEED]", int(speed_in_hz), "\033[0m", end='') + # Restore cursor position + print("\033[u", end='', flush=True) + + ts_countdown = 200 + else: + ts_countdown = 10 + + ts_countdown -= 1 + translated_line = translator(line) + + if translated_line: + print(translated_line, end='') + sys.stdout.flush() + + print("") + +if __name__ == '__main__': + main() + diff --git a/sims/vcs/scripts/run_sims.sh b/sims/vcs/scripts/run_sims.sh new file mode 100755 index 00000000..bb5e38a0 --- /dev/null +++ b/sims/vcs/scripts/run_sims.sh @@ -0,0 +1,61 @@ +#!/bin/bash + +set -e + +CURRENT_DIR="${PWD##*/}" +if [[ "$CURRENT_DIR" != "vcs" ]]; then + echo "Error: This script must be run from chipyard/sims/vcs." + exit 1 +fi + +if [[ -z "${TMUX}" ]]; then + echo "Error: you must be in a tmux session to run simulations." +fi + +source ./scripts/env.sh + +lineno=0 + +start_run() { + echo "kickoff elf $KERNELS_PATH/$2 on config $1" + lineno=$((lineno+1)) + make CONFIG=$1 BINARY="$KERNELS_PATH/$2" LOADMEM=1 run-binary"$4" 2>&1 | ./scripts/pprint "$3" $lineno & +} + +check_exists() { + if ! [ -f "$1" ]; then + echo "Error: looked for file $1 that does not exist." + exit 1 + fi +} + +check_exists "simv-chipyard.harness-VirgoFP16Config" +check_exists "simv-chipyard.harness-VirgoHopperConfig" +check_exists "simv-chipyard.harness-VirgoFP16Config-debug" +check_exists "simv-chipyard.harness-VirgoHopperConfig-debug" + +# sanity check that the kernels have been compiled +check_exists "$KERNELS_PATH/sgemm_tcore/kernel.radiance.gemm.tcore.volta.dim256.elf" +check_exists "$KERNELS_PATH/sgemm_tcore/kernel.radiance.gemm.tcore.hopper.dim512.elf" +check_exists "$KERNELS_PATH/sgemm_gemmini_dma/kernel.radiance.gemm.virgo.hopper.dim1024.elf" + +echo "Simulations will be started in parallel in 5 seconds. Please do not Ctrl+C as it kills all subprocesses." + +sleep 5 + +suffix="-debug" + +# dims=(256 512 1024) +dims=(256 512) +for dim in "${dims[@]}"; do + echo "$element" + start_run VirgoFP16Config sgemm_tcore/kernel.radiance.gemm.tcore.volta.dim${dim}.elf "volta${dim} " "${suffix}" + start_run VirgoFP16Config sgemm_tcore/kernel.radiance.gemm.tcore.ampere.dim${dim}.elf "ampere${dim}" "${suffix}" + start_run VirgoHopperConfig sgemm_tcore/kernel.radiance.gemm.tcore.hopper.dim${dim}.elf "hopper${dim}" "${suffix}" + start_run VirgoHopperConfig sgemm_gemmini_dma/kernel.radiance.gemm.virgo.hopper.dim${dim}.elf "virgo${dim} " "${suffix}" + suffix="" +done + +wait + +echo "All simulations have finished!" diff --git a/sims/vcs/scripts/sram_util.sh b/sims/vcs/scripts/sram_util.sh new file mode 100755 index 00000000..5d913c49 --- /dev/null +++ b/sims/vcs/scripts/sram_util.sh @@ -0,0 +1,42 @@ +#!/bin/bash + +# Define file names and corresponding n values +declare -A files_and_n_values +files_and_n_values=( + ["output/chipyard.harness.TestHarness.VirgoFP16Config/kernel.radiance.gemm.tcore.volta.dim256.fsdb"]=256 + ["output/chipyard.harness.TestHarness.VirgoFP16Config/kernel.radiance.gemm.tcore.volta.dim512.fsdb"]=512 + ["output/chipyard.harness.TestHarness.VirgoFP16Config/kernel.radiance.gemm.tcore.volta.dim1024.fsdb"]=1024 + ["output/chipyard.harness.TestHarness.VirgoFP16Config/kernel.radiance.gemm.tcore.ampere.dim256.fsdb"]=256 + ["output/chipyard.harness.TestHarness.VirgoFP16Config/kernel.radiance.gemm.tcore.ampere.dim512.fsdb"]=512 + ["output/chipyard.harness.TestHarness.VirgoFP16Config/kernel.radiance.gemm.tcore.ampere.dim1024.fsdb"]=1024 + ["output/chipyard.harness.TestHarness.VirgoHopperConfig/kernel.radiance.gemm.tcore.hopper.dim256.fsdb"]=256 + ["output/chipyard.harness.TestHarness.VirgoHopperConfig/kernel.radiance.gemm.tcore.hopper.dim512.fsdb"]=512 + ["output/chipyard.harness.TestHarness.VirgoHopperConfig/kernel.radiance.gemm.tcore.hopper.dim1024.fsdb"]=1024 + ["output/chipyard.harness.TestHarness.VirgoHopperConfig/kernel.radiance.gemm.virgo.hopper.dim256.fsdb"]=256 + ["output/chipyard.harness.TestHarness.VirgoHopperConfig/kernel.radiance.gemm.virgo.hopper.dim512.fsdb"]=512 + ["output/chipyard.harness.TestHarness.VirgoHopperConfig/kernel.radiance.gemm.virgo.hopper.dim1024.fsdb"]=1024 +) + +for fsdb_file in "${!files_and_n_values[@]}"; do + n=${files_and_n_values[$fsdb_file]} + + echo "parsing sharedmem reads for file $fsdb_file" + + # Run fsdbreport command + fsdbreport "$fsdb_file" -s "/TestDriver/testHarness/chiptop0/system/cluster_prci_domain/element_reset_domain_element/shared_mem/smemReadCounter" -of d -nolog -o /tmp/smem_activity.log + + # Extract last line and parse the second number + last_line=$(tail -n 1 /tmp/smem_activity.log) + reads=$(echo "$last_line" | awk '{print $2}') + + # Clean up temp file + rm -f /tmp/smem_activity.log + + echo "reads: $reads" + + # Calculate final value + result=$(echo "scale=6; $reads / ($n * $n / 64)" | bc) + + echo "multiple of input data size: $result" +done +