aboutsummaryrefslogtreecommitdiff
path: root/include
diff options
context:
space:
mode:
authorDerek Lamberti <derek.lamberti@arm.com>2019-11-20 10:51:57 +0000
committerDerek Lamberti <derek.lamberti@arm.com>2019-12-09 19:20:29 +0000
commit836b27bd73d62795e82d0ce666d728c94c216067 (patch)
treec5db467b321d367eab8aaa75842f3a520c62cd17 /include
parentfd2710651ada27fc82f28c07fb1e09effc3bda2d (diff)
downloadarmnn-836b27bd73d62795e82d0ce666d728c94c216067.tar.gz
IVGCVSW-4157 Pass custom options directly to backends
Change-Id: I98cfb913dbd00cb94bdb5dbe82753ca147f7f671 Signed-off-by: Derek Lamberti <derek.lamberti@arm.com>
Diffstat (limited to 'include')
-rw-r--r--include/armnn/BackendId.hpp8
-rw-r--r--include/armnn/BackendOptions.hpp263
-rw-r--r--include/armnn/IRuntime.hpp33
3 files changed, 301 insertions, 3 deletions
diff --git a/include/armnn/BackendId.hpp b/include/armnn/BackendId.hpp
index 00ece377d4..d7b54979b6 100644
--- a/include/armnn/BackendId.hpp
+++ b/include/armnn/BackendId.hpp
@@ -79,12 +79,18 @@ public:
BackendId(const std::string& id) : m_Id{id} {}
BackendId(const char* id) : m_Id{id} {}
+
+ BackendId(const BackendId& other) = default;
+ BackendId(BackendId&& other) = default;
+ BackendId& operator=(const BackendId& other) = default;
+ BackendId& operator=(BackendId&& other) = default;
+ ~BackendId(){}
+
/// Deprecated function that will be removed together with
/// the Compute enum
BackendId(Compute compute) : m_Id{GetComputeDeviceAsCString(compute)} {}
operator std::string() const { return m_Id; }
-
BackendId& operator=(const std::string& other)
{
m_Id = other;
diff --git a/include/armnn/BackendOptions.hpp b/include/armnn/BackendOptions.hpp
new file mode 100644
index 0000000000..a1b6b09cad
--- /dev/null
+++ b/include/armnn/BackendOptions.hpp
@@ -0,0 +1,263 @@
+//
+// Copyright © 2019 Arm Ltd. All rights reserved.
+// SPDX-License-Identifier: MIT
+//
+
+#pragma once
+
+#include "BackendId.hpp"
+#include <cassert>
+
+namespace armnn
+{
+
+
+/// Struct for the users to pass backend specific options
+struct BackendOptions
+{
+private:
+ template<typename T>
+ struct CheckAllowed
+ {
+ static const bool value = std::is_same<T, int>::value ||
+ std::is_same<T, float>::value ||
+ std::is_same<T, bool>::value ||
+ std::is_same<T, std::string>::value ||
+ std::is_same<T, const char*>::value;
+ };
+public:
+
+ // Very basic type safe variant
+ class Var
+ {
+
+ public:
+ /// Constructors
+ explicit Var(int i) : m_Vals(i), m_Type(VarTypes::Integer) {};
+ explicit Var(float f) : m_Vals(f), m_Type(VarTypes::Float) {};
+ explicit Var(bool b) : m_Vals(b), m_Type(VarTypes::Boolean) {};
+ explicit Var(const char* s) : m_Vals(s), m_Type(VarTypes::String) {};
+ explicit Var(std::string s) : m_Vals(s), m_Type(VarTypes::String) {};
+
+ //Disallow implicit conversions from types not explicitly allowed below.
+ template<typename DisallowedType>
+ Var(DisallowedType)
+ {
+ static_assert(CheckAllowed<DisallowedType>::value, "Type is not allowed for Var<DisallowedType>.");
+ assert(false && "Unreachable code");
+ }
+
+ /// Copy Construct
+ Var(const Var& other)
+ : m_Type(other.m_Type)
+ {
+ switch(m_Type)
+ {
+ case VarTypes::String:
+ {
+ new (&m_Vals.s) std::string(other.m_Vals.s);
+ break;
+ }
+ default:
+ {
+ DoOp(other, [](auto& a, auto& b)
+ {
+ a = b;
+ });
+ break;
+ }
+ }
+ }
+
+ /// Copy operator
+ Var& operator=(const Var& other)
+ {
+ // Destroy existing string
+ if (m_Type == VarTypes::String)
+ {
+ Destruct(m_Vals.s);
+ }
+
+ m_Type = other.m_Type;
+ switch(m_Type)
+ {
+ case VarTypes::String:
+ {
+
+ new (&m_Vals.s) std::string(other.m_Vals.s);
+ break;
+ }
+ default:
+ {
+ DoOp(other, [](auto& a, auto& b)
+ {
+ a = b;
+ });
+ break;
+ }
+ }
+
+ return *this;
+ };
+
+ /// Type getters
+ bool IsBool() const { return m_Type == VarTypes::Boolean; }
+ bool IsInt() const { return m_Type == VarTypes::Integer; }
+ bool IsFloat() const { return m_Type == VarTypes::Float; }
+ bool IsString() const { return m_Type == VarTypes::String; }
+
+ /// Value getters
+ bool AsBool() const { assert(IsBool()); return m_Vals.b; }
+ int AsInt() const { assert(IsInt()); return m_Vals.i; }
+ float AsFloat() const { assert(IsFloat()); return m_Vals.f; }
+ std::string AsString() const { assert(IsString()); return m_Vals.s; }
+
+ /// Destructor
+ ~Var()
+ {
+ DoOp(*this, [this](auto& a, auto&)
+ {
+ Destruct(a);
+ });
+ }
+ private:
+ template<typename Func>
+ void DoOp(const Var& other, Func func)
+ {
+ if (other.IsBool())
+ {
+ func(m_Vals.b, other.m_Vals.b);
+ }
+ else if (other.IsInt())
+ {
+ func(m_Vals.i, other.m_Vals.i);
+ }
+ else if (other.IsFloat())
+ {
+ func(m_Vals.f, other.m_Vals.f);
+ }
+ else if (other.IsString())
+ {
+ func(m_Vals.s, other.m_Vals.s);
+ }
+ }
+
+ template<typename Destructable>
+ void Destruct(Destructable& d)
+ {
+ if (std::is_destructible<Destructable>::value)
+ {
+ d.~Destructable();
+ }
+ }
+
+ private:
+ /// Types which can be stored
+ enum class VarTypes
+ {
+ Boolean,
+ Integer,
+ Float,
+ String,
+ };
+
+ // Union of potential type values.
+ union Vals
+ {
+ int i;
+ float f;
+ bool b;
+ std::string s;
+
+ Vals(){}
+ ~Vals(){}
+
+ explicit Vals(int i) : i(i) {};
+ explicit Vals(float f) : f(f) {};
+ explicit Vals(bool b) : b(b) {};
+ explicit Vals(const char* s) : s(std::string(s)) {}
+ explicit Vals(std::string s) : s(s) {}
+ };
+
+ Vals m_Vals;
+ VarTypes m_Type;
+ };
+
+ struct BackendOption
+ {
+ public:
+ BackendOption(std::string name, bool value)
+ : m_Name(name), m_Value(value)
+ {}
+ BackendOption(std::string name, int value)
+ : m_Name(name), m_Value(value)
+ {}
+ BackendOption(std::string name, float value)
+ : m_Name(name), m_Value(value)
+ {}
+ BackendOption(std::string name, std::string value)
+ : m_Name(name), m_Value(value)
+ {}
+ BackendOption(std::string name, const char* value)
+ : m_Name(name), m_Value(value)
+ {}
+
+ template<typename DisallowedType>
+ BackendOption(std::string, DisallowedType)
+ : m_Value(0)
+ {
+ static_assert(CheckAllowed<DisallowedType>::value, "Type is not allowed for BackendOption.");
+ assert(false && "Unreachable code");
+ }
+
+ BackendOption(const BackendOption& other) = default;
+ BackendOption(BackendOption&& other) = default;
+ BackendOption& operator=(const BackendOption& other) = default;
+ BackendOption& operator=(BackendOption&& other) = default;
+ ~BackendOption() = default;
+
+ std::string GetName() const { return m_Name; }
+ Var GetValue() const { return m_Value; }
+
+ private:
+ std::string m_Name; ///< Name of the option
+ Var m_Value; ///< Value of the option. (Bool, int, Float, String)
+ };
+
+ explicit BackendOptions(BackendId backend)
+ : m_TargetBackend(backend)
+ {}
+
+ BackendOptions(BackendId backend, std::initializer_list<BackendOption> options)
+ : m_TargetBackend(backend)
+ , m_Options(options)
+ {}
+
+ BackendOptions(const BackendOptions& other) = default;
+ BackendOptions(BackendOptions&& other) = default;
+ BackendOptions& operator=(const BackendOptions& other) = default;
+ BackendOptions& operator=(BackendOptions&& other) = default;
+
+ void AddOption(BackendOption&& option)
+ {
+ m_Options.push_back(option);
+ }
+
+ void AddOption(const BackendOption& option)
+ {
+ m_Options.push_back(option);
+ }
+
+ const BackendId& GetBackendId() const noexcept { return m_TargetBackend; }
+ size_t GetOptionCount() const noexcept { return m_Options.size(); }
+ const BackendOption& GetOption(size_t idx) const { return m_Options[idx]; }
+
+private:
+ /// The id for the backend to which the options should be passed.
+ BackendId m_TargetBackend;
+
+ /// The array of options to pass to the backend context
+ std::vector<BackendOption> m_Options;
+};
+
+} //namespace armnn
diff --git a/include/armnn/IRuntime.hpp b/include/armnn/IRuntime.hpp
index 08db22e4bb..49c18113b3 100644
--- a/include/armnn/IRuntime.hpp
+++ b/include/armnn/IRuntime.hpp
@@ -4,7 +4,7 @@
//
#pragma once
-
+#include "BackendOptions.hpp"
#include "INetwork.hpp"
#include "IProfiler.hpp"
#include "Tensor.hpp"
@@ -73,8 +73,35 @@ public:
bool m_FileOnly;
uint32_t m_CapturePeriod;
};
-
ExternalProfilingOptions m_ProfilingOptions;
+
+ /// Pass backend specific options.
+ ///
+ /// For example, to enable GpuAcc tuning add the following
+ /// m_BackendOption.emplace_back(
+ /// BackendOptions{"GpuAcc",
+ /// {
+ /// {"TuningLevel", 2},
+ /// {"TuningFile", filename}
+ /// }
+ /// });
+ /// Execute representative workloads through the runtime to generate tuning data.
+ /// The tuning file is written once the runtime is destroyed
+
+ /// To execute with the tuning data, start up with just the tuning file specified.
+ /// m_BackendOption.emplace_back(
+ /// BackendOptions{"GpuAcc",
+ /// {
+ /// {"TuningFile", filename}
+ /// }
+ /// });
+
+ /// The following backend options are available:
+ /// GpuAcc:
+ /// "TuningLevel" : int [0..3] (0=UseOnly(default) | 1=RapidTuning | 2=NormalTuning | 3=ExhaustiveTuning)
+ /// "TuningFile" : string [filenameString]
+ /// "KernelProfilingEnabled" : bool [true | false]
+ std::vector<BackendOptions> m_BackendOptions;
};
static IRuntime* CreateRaw(const CreationOptions& options);
@@ -134,6 +161,8 @@ protected:
~IRuntime() {}
};
+
+/// The following API is replaced by the backend options API.
using IGpuAccTunedParametersPtr = std::shared_ptr<IGpuAccTunedParameters>;
/// Manages a set of GpuAcc parameters which have been tuned for maximum performance.