From 7061eb283969f9a020c08349454447564e4dd5b3 Mon Sep 17 00:00:00 2001 From: SiCong Li Date: Fri, 8 Jan 2021 15:16:02 +0000 Subject: Implement MLGO module * Implement MLGOHeuristics which provides a query and a loading interface * Implement a top-down parser MLGOParser for parsing dotmlgo * Add validation tests for MLGOHeuristics Resolves COMPMID-3840, COMPMID-3841 Signed-off-by: SiCong Li Change-Id: Iae96d2779524b2dd83623d1a3a30ef57823ae084 Reviewed-on: https://review.mlplatform.org/c/ml/ComputeLibrary/+/4941 Tested-by: Arm Jenkins Reviewed-by: Georgios Pinitas Comments-Addressed: Arm Jenkins --- src/runtime/CL/mlgo/MLGOParser.h | 199 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 199 insertions(+) create mode 100644 src/runtime/CL/mlgo/MLGOParser.h (limited to 'src/runtime/CL/mlgo/MLGOParser.h') diff --git a/src/runtime/CL/mlgo/MLGOParser.h b/src/runtime/CL/mlgo/MLGOParser.h new file mode 100644 index 0000000000..e4a31c1f55 --- /dev/null +++ b/src/runtime/CL/mlgo/MLGOParser.h @@ -0,0 +1,199 @@ +/* + * Copyright (c) 2021 Arm Limited. + * + * SPDX-License-Identifier: MIT + * + * 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. + */ +#ifndef SRC_MLGO_MLGOPARSER_H +#define SRC_MLGO_MLGOPARSER_H + +#include "src/runtime/CL/mlgo/MLGOHeuristics.h" + +#include +#include +#include +#include + +/** A DotMLGO file parser (LL(k) parser) + * + * The grammar of DotMLGO is defined as the following ENBF: + * + * delim = "," | "\n"; // Note that delimiters are omitted from the definition below + * + * mlgo = header, heuristics-table, {heuristic-tree}; + * + * header = "
", gemm-version, ip-type, "
"; + * gemm-version = "gemm-version", "[", int, int, int, "]"; + * ip-type = "ip-type", ("gpu" | "cpu"); + * + * heiristics-table = "", {heuristics-table-entry}, ""; + * heuristics-table-entry = entry-id, ip-name, num-cores, data-type, gpu-priority, gpu-behavior, heuristic-type, free-vars; + * entry-id = int; + * ip-name = char-sequence; + * num-cores = int; + * data-type = "f32" | "f16" | "qasymm8"; + * gpu-priority = "best-performance" | "best-memory-usage"; + * gpu-behavior = "static" | "dynamic"; + * heuristic-type = "gemm-type" | "gemm-config-native" | "gemm-config-reshaped-only-rhs" | "gemm-config-reshaped"; + * free-vars = "[", {char-sequence}, "]"; + * + * heuristic-tree = "", {tree-node}, ""; + * tree-node = branch-node | leaf-node; + * branch-node = "b", entry-id, lhs-type, lhs-value, conditional-op, rhs-type, rhs-value, true-node, false-node; + * lhs-type = comparator-type; + * lhs-value = comparator-value; + * rhs-type = comparator-type; + * rhs-value = comparator-value; + * comparator-type = "var" | "num" | "enum"; + * comparator-value = char-sequence | float; + * conditional-op = "<" | "<=" | "==" | ">=" | ">"; + * true-node = entry-id; + * false-node = entry-id; + * leaf-node = "l", entry-id, heuristic-type, leaf-value; + * leaf-value = gemm-type | gemm-config-native | gemm-config-reshaped-only-rhs | gemm-config-reshaped + * gemm-type = "native" | "reshaped-only-rhs" | "reshaped"; + * gemm-config-native = "[", int, int, int, "]"; + * gemm-config-reshaped-only-rhs = "[", int, int, int, int, bool, bool, bool, "]"; + * gemm-config-reshaped = "[", int, int, int, int, int, bool, bool, bool, bool, "]"; + */ + +namespace arm_compute +{ +namespace mlgo +{ +namespace parser +{ +/** Type of Token */ +enum class TokenType +{ + L_List = '[', /**< List open */ + R_List = ']', /**< List close */ + Int, /**< Integral */ + Float, /**< Floating */ + Text, /**< Text/String */ + End, /**< End of stream */ +}; + +struct CharPosition +{ + bool operator==(const CharPosition &other) const + { + return ln == other.ln && col == other.col; + } + + size_t ln{ 0 }; + size_t col{ 0 }; +}; + +/** Token */ +struct Token +{ + Token(TokenType t, std::string v, CharPosition pos) + : type{ t }, value{ v }, pos{ pos } + { + } + + bool operator==(const Token &other) const + { + return type == other.type && value == other.value && pos == other.pos; + } + + TokenType type; /**< Token type */ + std::string value; /**< Token value */ + CharPosition pos; +}; + +/** A stream of token */ +class TokenStream +{ + // NOTE: _tokens is never empty. The end of token stream is signalled by the End Token +public: + static constexpr size_t max_look_ahead = 10; + +public: + /** Constructor + * + * @param[in] s Input stream + * @param[in] delims Delimiter characters packed in a string. Each char from the string can be used as a delim on its own + */ + TokenStream(std::istream &s, const std::string &delims = ",\n"); + + /** Check if there're more (non-End) Tokens + * @return true If there are more tokens + * @return false If reached end of stream (only End token) + */ + explicit operator bool() const; + + /** Get and pop off the current token + * + * @return Token + */ + Token take(); + + /** Peek the next ith token + * + * @param[in] i The next ith token. i < @ref max_look_ahead. + * + * @return Token + */ + Token peek(size_t i = 0); + + /** Get the position of the current token + * + * @return CharPosition + */ + CharPosition current_pos() const + { + return _tokens.front().pos; + } + +private: + void read(); + + Token recognize_tok(char ch); + + Token num_st(std::string value = ""); + + Token float_after_dp_st(std::string value = ""); + + Token text_st(std::string value = ""); + + bool reached_end() const; + + bool is_delim(char ch) const; + + std::string _delims; + std::istream &_istream; + std::deque _tokens; + CharPosition _lookahead_pos; +}; + +/** Parse and construct a @ref MLGOHeuristics from input stream + * + * @param[in] in Input stream + * + * @return MLGOHeuristics + */ +std::pair parse_mlgo(std::istream &in); + +} // namespace parser +} // namespace mlgo +} // namespace arm_compute +#endif //SRC_MLGO_MLGOPARSER_H \ No newline at end of file -- cgit v1.2.1