forked from Qortal/Brooklyn
215 lines
6.0 KiB
C++
215 lines
6.0 KiB
C++
//
|
|
// Copyright © 2021 Arm Ltd and Contributors. All rights reserved.
|
|
// SPDX-License-Identifier: MIT
|
|
//
|
|
#include "TestBlocks.hpp"
|
|
#include "TestStrategy.hpp"
|
|
|
|
#include <IMemoryOptimizerStrategy.hpp>
|
|
#include <MemoryOptimizerStrategyLibrary.hpp>
|
|
#include <strategies/StrategyValidator.hpp>
|
|
|
|
|
|
#include <cxxopts.hpp>
|
|
|
|
#include <iostream>
|
|
#include <algorithm>
|
|
#include <iomanip>
|
|
|
|
std::vector<TestBlock> testBlocks
|
|
{
|
|
{"fsrcnn", fsrcnn},
|
|
{"inceptionv4", inceptionv4},
|
|
{"deeplabv3", deeplabv3},
|
|
{"deepspeechv1", deepspeechv1},
|
|
{"mobilebert", mobilebert},
|
|
{"ssd_mobilenetv2", ssd_mobilenetv2},
|
|
{"resnetv2", resnetv2},
|
|
{"yolov3",yolov3}
|
|
};
|
|
|
|
void PrintModels()
|
|
{
|
|
std::cout << "Available models:\n";
|
|
for (const auto& model : testBlocks)
|
|
{
|
|
std::cout << model.m_Name << "\n";
|
|
}
|
|
std::cout << "\n";
|
|
}
|
|
|
|
size_t GetMinPossibleMemorySize(const std::vector<armnn::MemBlock>& blocks)
|
|
{
|
|
unsigned int maxLifetime = 0;
|
|
for (auto& block: blocks)
|
|
{
|
|
maxLifetime = std::max(maxLifetime, block.m_EndOfLife);
|
|
}
|
|
maxLifetime++;
|
|
|
|
std::vector<size_t> lifetimes(maxLifetime);
|
|
for (const auto& block : blocks)
|
|
{
|
|
for (auto lifetime = block.m_StartOfLife; lifetime <= block.m_EndOfLife; ++lifetime)
|
|
{
|
|
lifetimes[lifetime] += block.m_MemSize;
|
|
}
|
|
}
|
|
return *std::max_element(lifetimes.begin(), lifetimes.end());
|
|
}
|
|
|
|
void RunBenchmark(armnn::IMemoryOptimizerStrategy* strategy, std::vector<TestBlock>* models)
|
|
{
|
|
using Clock = std::chrono::high_resolution_clock;
|
|
float avgEfficiency = 0;
|
|
std::chrono::duration<double, std::milli> avgDuration{};
|
|
std::cout << "\nMemory Strategy: " << strategy->GetName()<< "\n";
|
|
std::cout << "===============================================\n";
|
|
for (auto& model : *models)
|
|
{
|
|
auto now = Clock::now();
|
|
const std::vector<armnn::MemBin> result = strategy->Optimize(model.m_Blocks);
|
|
auto duration = std::chrono::duration<double, std::milli>(Clock::now() - now);
|
|
|
|
avgDuration += duration;
|
|
size_t memoryUsage = 0;
|
|
for (auto bin : result)
|
|
{
|
|
memoryUsage += bin.m_MemSize;
|
|
}
|
|
size_t minSize = GetMinPossibleMemorySize(model.m_Blocks);
|
|
|
|
float efficiency = static_cast<float>(minSize) / static_cast<float>(memoryUsage);
|
|
efficiency*=100;
|
|
avgEfficiency += efficiency;
|
|
std::cout << "\nModel: " << model.m_Name << "\n";
|
|
|
|
std::cout << "Strategy execution time: " << std::setprecision(4) << duration.count() << " milliseconds\n";
|
|
|
|
std::cout << "Memory usage: " << memoryUsage/1024 << " kb\n";
|
|
|
|
std::cout << "Minimum possible usage: " << minSize/1024 << " kb\n";
|
|
|
|
std::cout << "Memory efficiency: " << std::setprecision(3) << efficiency << "%\n";
|
|
}
|
|
|
|
avgDuration/= static_cast<double>(models->size());
|
|
avgEfficiency/= static_cast<float>(models->size());
|
|
|
|
std::cout << "\n===============================================\n";
|
|
std::cout << "Average memory duration: " << std::setprecision(4) << avgDuration.count() << " milliseconds\n";
|
|
std::cout << "Average memory efficiency: " << std::setprecision(3) << avgEfficiency << "%\n";
|
|
}
|
|
|
|
struct BenchmarkOptions
|
|
{
|
|
std::string m_StrategyName;
|
|
std::string m_ModelName;
|
|
bool m_UseDefaultStrategy = false;
|
|
bool m_Validate = false;
|
|
};
|
|
|
|
BenchmarkOptions ParseOptions(int argc, char* argv[])
|
|
{
|
|
cxxopts::Options options("Memory Benchmark", "Tests memory optimization strategies on different models");
|
|
|
|
options.add_options()
|
|
("s, strategy", "Strategy name, do not specify to use default strategy", cxxopts::value<std::string>())
|
|
("m, model", "Model name", cxxopts::value<std::string>())
|
|
("v, validate", "Validate strategy", cxxopts::value<bool>()->default_value("false")->implicit_value("true"))
|
|
("h,help", "Display usage information");
|
|
|
|
auto result = options.parse(argc, argv);
|
|
if (result.count("help"))
|
|
{
|
|
std::cout << options.help() << std::endl;
|
|
PrintModels();
|
|
|
|
std::cout << "\nAvailable strategies:\n";
|
|
|
|
for (const auto& s :armnn::GetMemoryOptimizerStrategyNames())
|
|
{
|
|
std::cout << s << "\n";
|
|
}
|
|
exit(EXIT_SUCCESS);
|
|
}
|
|
|
|
BenchmarkOptions benchmarkOptions;
|
|
|
|
if(result.count("strategy"))
|
|
{
|
|
benchmarkOptions.m_StrategyName = result["strategy"].as<std::string>();
|
|
}
|
|
else
|
|
{
|
|
std::cout << "No Strategy given, using default strategy";
|
|
|
|
benchmarkOptions.m_UseDefaultStrategy = true;
|
|
}
|
|
|
|
if(result.count("model"))
|
|
{
|
|
benchmarkOptions.m_ModelName = result["model"].as<std::string>();
|
|
}
|
|
|
|
benchmarkOptions.m_Validate = result["validate"].as<bool>();
|
|
|
|
return benchmarkOptions;
|
|
}
|
|
|
|
int main(int argc, char* argv[])
|
|
{
|
|
BenchmarkOptions benchmarkOptions = ParseOptions(argc, argv);
|
|
|
|
std::shared_ptr<armnn::IMemoryOptimizerStrategy> strategy;
|
|
|
|
if (benchmarkOptions.m_UseDefaultStrategy)
|
|
{
|
|
strategy = std::make_shared<armnn::TestStrategy>();
|
|
}
|
|
else
|
|
{
|
|
strategy = armnn::GetMemoryOptimizerStrategy(benchmarkOptions.m_StrategyName);
|
|
|
|
if (!strategy)
|
|
{
|
|
std::cout << "Strategy name not found\n";
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
std::vector<TestBlock> model;
|
|
std::vector<TestBlock>* modelsToTest = &testBlocks;
|
|
if (benchmarkOptions.m_ModelName.size() != 0)
|
|
{
|
|
auto it = std::find_if(testBlocks.cbegin(), testBlocks.cend(), [&](const TestBlock testBlock)
|
|
{
|
|
return testBlock.m_Name == benchmarkOptions.m_ModelName;
|
|
});
|
|
|
|
if (it == testBlocks.end())
|
|
{
|
|
std::cout << "Model name not found\n";
|
|
return 0;
|
|
}
|
|
else
|
|
{
|
|
model.push_back(*it);
|
|
modelsToTest = &model;
|
|
}
|
|
}
|
|
|
|
if (benchmarkOptions.m_Validate)
|
|
{
|
|
armnn::StrategyValidator strategyValidator;
|
|
|
|
strategyValidator.SetStrategy(strategy);
|
|
|
|
RunBenchmark(&strategyValidator, modelsToTest);
|
|
}
|
|
else
|
|
{
|
|
RunBenchmark(strategy.get(), modelsToTest);
|
|
}
|
|
|
|
} |