Files
derek.holloway 7502bf64a4
CodeQL / Analyze (actions) (push) Canceled after 0s
CodeQL / Analyze (python) (push) Canceled after 0s
pre-commit / pre-commit (push) Canceled after 0s
Multi-Arch CI / setup (push) Canceled after 0s
Publish build_manylinux_x86_64 images / publish_build_manylinux_x86_64 (push) Canceled after 0s
Setup (Multi-Arch) / setup (push) Canceled after 0s
Multi-Arch CI / Linux::${{ fromJSON(needs.setup.outputs.linux_build_config || '{}').build_variant_label || 'skip' }} (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish no_rocm_image_ubi10 image / publish_no_rocm_image_ubi10 (push) Canceled after 0s
Multi-Arch CI / Windows::${{ fromJSON(needs.setup.outputs.windows_build_config || '{}').build_variant_label || 'skip' }} (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Multi-Arch CI / Manifest Diff (push) Canceled after 0s
TheRock Manifest Diff Report / Generate Manifest Diff Report (push) Canceled after 0s
Multi-Arch CI / CI Summary (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04 (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04_ocl_rt images / publish_no_rocm_image_ubuntu24_04_ocl_rt (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_rocgdb (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04_rocgdb images / publish_no_rocm_image_ubuntu24_04_rocgdb (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_ocl_rt (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Unit Tests / Unit Tests :: ubuntu-24.04 (push) Canceled after 0s
Unit Tests / Unit Tests :: windows-2022 (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_media (push) Canceled after 0s
Unit Tests / Unit Tests Summary (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_openmpi (push) Canceled after 0s
Flatten subprojects into a single base monorepo
2026-09-02 16:34:47 -07:00

221 lines
10 KiB
C++

/*******************************************************************************
*
* MIT License
*
* Copyright (C) 2019-2022 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.
*
*******************************************************************************/
#include <gtest/gtest.h>
#include <Tensile/AMDGPU.hpp>
#include <Tensile/AMDGPUPredicates.hpp>
#include <Tensile/ContractionLibrary.hpp>
#include <Tensile/ContractionProblemPredicates.hpp>
#include <Tensile/ContractionProblemProperties.hpp>
#include <Tensile/Distance.hpp>
#include <Tensile/ExactLogicLibrary.hpp>
using namespace Tensile;
TEST(ContractionSelectionLibraryTest, Single)
{
std::shared_ptr<Hardware> hardware = std::make_shared<AMDGPU>(
AMDGPU::Processor::gfx900, 64, 0, "AMD Radeon Vega Frontier Edition");
SingleContractionLibrary lib;
lib.solution = std::make_shared<ContractionSolution>();
auto problem = std::make_shared<ContractionProblem>();
EXPECT_EQ(lib.findBestSolution(*problem, *hardware), lib.solution);
}
TEST(ContractionSelectionLibraryTest, GPUSelection)
{
std::shared_ptr<Hardware> v10 = std::make_shared<AMDGPU>(
AMDGPU::Processor::gfx900, 64, 0, "AMD Radeon Vega Frontier Edition");
std::shared_ptr<Hardware> v20
= std::make_shared<AMDGPU>(AMDGPU::Processor::gfx906, 60, 0, "AMD Radeon Vega 7");
std::shared_ptr<Hardware> v20_64CU
= std::make_shared<AMDGPU>(AMDGPU::Processor::gfx906, 64, 0, "AMD Radeon Vega 7");
// Create solutions
auto v20Solution = std::make_shared<ContractionSolution>();
auto v20Solution_64CU = std::make_shared<ContractionSolution>();
auto genericSolution = std::make_shared<ContractionSolution>();
// Create libraries
std::shared_ptr<ContractionLibrary> v20Lib
= std::make_shared<SingleContractionLibrary>(v20Solution);
std::shared_ptr<ContractionLibrary> v20Lib_64CU
= std::make_shared<SingleContractionLibrary>(v20Solution_64CU);
auto genericLib = std::make_shared<SingleContractionLibrary>(genericSolution);
// Create hardware predicate for a generic "V20"
auto isV20 = std::make_shared<Predicates::GPU::ProcessorEqual>(AMDGPU::Processor::gfx906);
std::shared_ptr<Predicates::Predicate<Hardware>> isAMDGPUV20
= std::make_shared<Predicates::IsSubclass<Hardware, AMDGPU>>(isV20);
HardwarePredicate hardwareIsAMDGPUV20(isAMDGPUV20);
// Create hardware predicate for a "V20" with 64 CU
std::shared_ptr<Predicates::Predicate<AMDGPU>> isV20Proc
= std::make_shared<Predicates::GPU::ProcessorEqual>(AMDGPU::Processor::gfx906);
std::shared_ptr<Predicates::Predicate<AMDGPU>> is64CU
= std::make_shared<Predicates::GPU::CUCountEqual>(64);
std::shared_ptr<Predicates::Predicate<AMDGPU>> isAMDGPUV20_64CU
= std::make_shared<Predicates::And<AMDGPU>>(
std::initializer_list<std::shared_ptr<Predicates::Predicate<AMDGPU>>>{isV20Proc,
is64CU});
HardwarePredicate hardwareIsAMDGPUV20_64CU(
std::make_shared<Predicates::IsSubclass<Hardware, AMDGPU>>(isAMDGPUV20_64CU));
// Create hierarchy for hardware selection
ContractionHardwareSelectionLibrary::Row v20Row(hardwareIsAMDGPUV20, v20Lib);
ContractionHardwareSelectionLibrary::Row v20Row_64CU(hardwareIsAMDGPUV20_64CU, v20Lib_64CU);
ContractionHardwareSelectionLibrary lib({v20Row_64CU, v20Row});
auto problem = std::make_shared<ContractionProblem>();
EXPECT_EQ(lib.findBestSolution(*problem, *v20), v20Solution);
EXPECT_EQ(lib.findBestSolution(*problem, *v20_64CU), v20Solution_64CU);
EXPECT_EQ(lib.findBestSolution(*problem, *v10), std::shared_ptr<ContractionSolution>());
HardwarePredicate allHardware(std::make_shared<Predicates::True<Hardware>>());
lib.rows.push_back(std::make_pair(allHardware, genericLib));
EXPECT_EQ(lib.findBestSolution(*problem, *v20), v20Solution);
EXPECT_EQ(lib.findBestSolution(*problem, *v20_64CU), v20Solution_64CU);
EXPECT_EQ(lib.findBestSolution(*problem, *v10), genericSolution);
}
TEST(ContractionSelectionLibraryTest, RegionSelection)
{
// Create solutions
auto region1Solution = std::make_shared<ContractionSolution>();
auto region2Solution = std::make_shared<ContractionSolution>();
auto genericSolution = std::make_shared<ContractionSolution>();
// Create libraries
auto region1Lib = std::make_shared<SingleContractionLibrary>(region1Solution);
auto region2Lib = std::make_shared<SingleContractionLibrary>(region2Solution);
auto genericLib = std::make_shared<SingleContractionLibrary>(genericSolution);
// Create region predicate for (6000 <= M < 8000), (0 <= N < 7000)
using Predicate = Predicates::Predicate<ContractionProblem>;
using SizeInRange = Predicates::Contraction::SizeInRange;
using Range = Predicates::Contraction::Range;
using And = Predicates::And<ContractionProblem>;
size_t max_size = std::numeric_limits<size_t>::max();
std::shared_ptr<Predicate> regionM = std::make_shared<SizeInRange>(0, Range{6000, 8000});
std::shared_ptr<Predicate> regionN1 = std::make_shared<SizeInRange>(1, Range{0, 7000});
std::shared_ptr<Predicate> regionN2 = std::make_shared<SizeInRange>(1, Range{7000, max_size});
// Create region predicate for (6000 <= M < 8000), (0 <= N < 7000)
auto preds1 = {regionM, regionN1};
auto isRegion1 = std::make_shared<And>(preds1);
// Create region predicate for (6000 <= M < 8000), (7000 <= N < max)
auto preds2 = {regionM, regionN2};
auto isRegion2 = std::make_shared<And>(preds2);
// Create fallthrough predicate (i.e. default)
ContractionProblemPredicate allProbs(std::make_shared<Predicates::True<ContractionProblem>>());
// Create hierarchy for region selection
ContractionProblemSelectionLibrary::Row Region1Row(isRegion1, region1Lib);
ContractionProblemSelectionLibrary::Row Region2Row(isRegion2, region2Lib);
ContractionProblemSelectionLibrary::Row GenericRow(allProbs, genericLib);
ContractionProblemSelectionLibrary lib({Region1Row, Region2Row, GenericRow});
auto Region1Problem
= ContractionProblem::GEMM(false, false, 7000, 6500, 1000, 7000, 1000, 7000, 1.0, false, 1);
auto Region2Problem
= ContractionProblem::GEMM(false, false, 7000, 7500, 1000, 7000, 1000, 7000, 1.0, false, 1);
auto OutRegionProblem
= ContractionProblem::GEMM(false, false, 5000, 2000, 1000, 5000, 1000, 5000, 1.0, false, 1);
AMDGPU gpu;
EXPECT_EQ(lib.findBestSolution(Region1Problem, gpu), region1Solution);
EXPECT_EQ(lib.findBestSolution(Region2Problem, gpu), region2Solution);
EXPECT_EQ(lib.findBestSolution(OutRegionProblem, gpu), genericSolution);
}
TEST(ContractionSelectionLibraryTest, TransposeSelection)
{
auto NNSolution = std::make_shared<ContractionSolution>();
auto NTSolution = std::make_shared<ContractionSolution>();
auto TNSolution = std::make_shared<ContractionSolution>();
auto TTSolution = std::make_shared<ContractionSolution>();
NNSolution->index = 0;
NTSolution->index = 1;
TNSolution->index = 2;
TTSolution->index = 3;
SolutionMap<ContractionSolution> map(
{{0, NNSolution}, {1, NTSolution}, {2, TNSolution}, {3, TTSolution}});
std::shared_ptr<ContractionLibrary> NNLibrary
= std::make_shared<SingleContractionLibrary>(NNSolution);
std::shared_ptr<ContractionLibrary> NTLibrary
= std::make_shared<SingleContractionLibrary>(NTSolution);
std::shared_ptr<ContractionLibrary> TNLibrary
= std::make_shared<SingleContractionLibrary>(TNSolution);
std::shared_ptr<ContractionLibrary> TTLibrary
= std::make_shared<SingleContractionLibrary>(TTSolution);
auto lib = std::make_shared<ContractionProblemMapLibrary>();
lib->property = std::make_shared<Contraction::OperationIdentifier>();
lib->map["Contraction_l_Ailk_Bljk_Cijk_Dijk"] = NNLibrary;
lib->map["Contraction_l_Ailk_Bjlk_Cijk_Dijk"] = NTLibrary;
lib->map["Contraction_l_Alik_Bljk_Cijk_Dijk"] = TNLibrary;
lib->map["Contraction_l_Alik_Bjlk_Cijk_Dijk"] = TTLibrary;
AMDGPU gpu;
auto NNProblem = ContractionProblem::GEMM(false, false, 4, 4, 4, 4, 4, 4, 1.2, false, 1);
auto NTProblem = ContractionProblem::GEMM(false, true, 4, 4, 4, 4, 4, 4, 1.2, false, 1);
auto TNProblem = ContractionProblem::GEMM(true, false, 4, 4, 4, 4, 4, 4, 1.2, false, 1);
auto TTProblem = ContractionProblem::GEMM(true, true, 4, 4, 4, 4, 4, 4, 1.2, false, 1);
// auto WeirdProblemC = ContractionProblem::FromBLAS( true, true, 4,4,4,
// 4,4,4, false, false, 1); WeirdProblemC.c.transpose(0,1);
// auto WeirdProblemD = ContractionProblem::FromBLAS( true, true, 4,4,4,
// 4,4,4, false, false, 1); WeirdProblemD.d.transpose(0,1);
EXPECT_EQ(lib->findBestSolution(NNProblem, gpu), NNSolution);
EXPECT_EQ(lib->findBestSolution(NTProblem, gpu), NTSolution);
EXPECT_EQ(lib->findBestSolution(TNProblem, gpu), TNSolution);
EXPECT_EQ(lib->findBestSolution(TTProblem, gpu), TTSolution);
// EXPECT_EQ(lib->findBestSolution(WeirdProblemC, gpu), nullptr);
// EXPECT_EQ(lib->findBestSolution(WeirdProblemD, gpu), nullptr);
MasterContractionLibrary mlib;
mlib.solutions = map;
mlib.library = lib;
}