Home | History | Annotate | Download | only in 1.0
      1 /*
      2  * Copyright (C) 2017 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #ifndef ANDROID_HARDWARE_V1_0_HEXAGON_MODEL_H
     18 #define ANDROID_HARDWARE_V1_0_HEXAGON_MODEL_H
     19 
     20 #include <android/hardware/neuralnetworks/1.0/types.h>
     21 #include <atomic>
     22 #include <string>
     23 #include <vector>
     24 #include "CpuExecutor.h"
     25 #include "HexagonController.h"
     26 #include "HexagonOperations.h"
     27 #include "HexagonUtils.h"
     28 #include "OperationsUtils.h"
     29 #include "hexagon_nn_controller/hexagon_nn_controller.h"
     30 
     31 namespace android {
     32 namespace hardware {
     33 namespace neuralnetworks {
     34 namespace V1_0 {
     35 namespace implementation {
     36 namespace hexagon {
     37 
     38 using ::android::nn::RunTimePoolInfo;
     39 using ::android::nn::Shape;
     40 
     41 using NeuralnetworksModel = ::android::hardware::neuralnetworks::V1_0::Model;
     42 
     43 // runtime operand information
     44 struct OperandInfo {
     45     // tensor information
     46     OperandType type;
     47     std::vector<uint32_t> dimensions;
     48 
     49     // (optional) quantization paramters
     50     float scale;
     51     int32_t zeroPoint;
     52 
     53     // lifetime
     54     OperandLifeTime lifetime;
     55 
     56     // data location
     57     uint8_t* buffer;
     58     uint32_t length;
     59 
     60     // Hexagon nnlib identifiers
     61     hexagon_nn_input hexagon_input;
     62     hexagon_nn_input hexagon_input_min;
     63     hexagon_nn_input hexagon_input_max;
     64     hexagon_nn_output hexagon_output;
     65 };
     66 
     67 // interface wrapper
     68 class Model {
     69    public:
     70     // methods
     71     Model() = delete;
     72     Model(const Model&) = delete;
     73     Model& operator=(const Model&) = delete;
     74     Model(Model&& other);
     75     Model& operator=(Model&& other);
     76 
     77     Model(const NeuralnetworksModel& model);
     78     ~Model();
     79 
     80     std::string getLog();
     81     std::string getGraph();
     82 
     83     // model check
     84     const int32_t* getPointer(uint32_t operand);
     85     Shape getShape(uint32_t operand);
     86     bool setShape(uint32_t operand, const Shape& shape);
     87     bool isConstant(uint32_t operand);
     88 
     89     // model prepare types
     90     const hexagon_nn_input& getTensor(uint32_t operand);
     91     const hexagon_nn_input& getQuantizationMin(uint32_t operand);
     92     const hexagon_nn_input& getQuantizationMax(uint32_t operand);
     93     hexagon_nn_input createQuantizationValue(uint32_t operand, int32_t quant_value);
     94     hexagon_nn_input createConvFilterTensor(uint32_t operand);
     95     hexagon_nn_input createDepthwiseFilterTensor(uint32_t operand, int32_t depth_multiplier);
     96     hexagon_nn_input createFullyConnectedWeightTensor(uint32_t operand);
     97     template <typename Type>
     98     Type getScalar(uint32_t operand);
     99     op_type getFloatActivation(uint32_t operand);
    100     op_type getQuantizedActivation(uint32_t operand);
    101     hexagon_nn_padding_type getPadding(uint32_t operand);
    102 
    103     template <typename Type>
    104     hexagon_nn_input createTensor(uint32_t B, uint32_t H, uint32_t W, uint32_t D,
    105                                   const std::vector<Type>& values);
    106     hexagon_nn_input createShape(uint32_t B, uint32_t H, uint32_t W, uint32_t D);
    107     template <typename Type>
    108     hexagon_nn_input createValues(const std::vector<Type>& values);
    109     template <typename Type>
    110     hexagon_nn_input createScalar(Type value);
    111 
    112     // model prepare operations
    113     bool addBasicOperation(op_type op, hexagon_nn_padding_type pad,
    114                            const std::vector<hexagon_nn_input>& inputs,
    115                            const std::vector<uint32_t>& outputs);
    116     bool addFloatOperationWithActivation(op_type op, hexagon_nn_padding_type pad,
    117                                          op_type activation,
    118                                          const std::vector<hexagon_nn_input>& inputs,
    119                                          const std::vector<uint32_t>& outputs);
    120     bool addQuant8OperationWithActivation(op_type op, hexagon_nn_padding_type pad,
    121                                           op_type activation,
    122                                           const std::vector<hexagon_nn_input>& inputs,
    123                                           const std::vector<uint32_t>& outputs);
    124     bool addFusedFloatOperation(op_type op, hexagon_nn_padding_type pad,
    125                                 const hexagon_nn_input& bias, op_type activation,
    126                                 const std::vector<hexagon_nn_input>& inputs,
    127                                 const std::vector<uint32_t>& outputs);
    128     bool addFusedQuant8Operation(op_type op, hexagon_nn_padding_type pad,
    129                                  const std::vector<hexagon_nn_input>& bias, op_type activation,
    130                                  const std::vector<hexagon_nn_input>& inputs,
    131                                  const std::vector<uint32_t>& outputs);
    132 
    133     std::vector<bool> supportedOperations();
    134     bool prepare();
    135     bool execute(const Request& request);
    136 
    137    private:
    138     uint32_t getNextNode();
    139     uint32_t addOperationInternal(op_type op, hexagon_nn_padding_type pad,
    140                                   const std::vector<hexagon_nn_input>& inputs,
    141                                   const std::vector<hexagon_nn_output>& outputs);
    142     hexagon_nn_input createTensorInternal(uint32_t B, uint32_t H, uint32_t W, uint32_t D,
    143                                           const uint8_t* ptr, size_t size);
    144     std::vector<hexagon_nn_input> setupActivationArgs(op_type op);
    145     hexagon_nn_input addOperand(uint32_t operand);
    146     std::vector<hexagon_nn_output> getHexagonOutputs(const std::vector<uint32_t>& operands);
    147     bool registerHexagonInputs(const std::vector<uint32_t>& operands, uint32_t node);
    148 
    149     bool verifyOperations();
    150     bool verifyOperands();
    151     bool addInputs();
    152     bool addOperations();
    153     bool addOutputs();
    154 
    155     void clearModel();
    156 
    157     // members
    158     hexagon_nn_nn_id mGraphId;
    159     uint32_t mNodeCount;
    160     bool mCompiled;
    161     std::vector<OperandInfo> mOperands;
    162     std::vector<Operation> mOperations;
    163     std::vector<uint32_t> mInputs;
    164     std::vector<uint32_t> mOutputs;
    165     std::vector<RunTimePoolInfo> mPools;
    166 };
    167 
    168 // template implementations
    169 
    170 template <typename Type>
    171 Type Model::getScalar(uint32_t operand) {
    172     return *reinterpret_cast<const Type*>(mOperands[operand].buffer);
    173 }
    174 
    175 template <typename Type>
    176 hexagon_nn_input Model::createTensor(uint32_t B, uint32_t H, uint32_t W, uint32_t D,
    177                                      const std::vector<Type>& values) {
    178     return createTensorInternal(B, H, W, D, reinterpret_cast<const uint8_t*>(values.data()),
    179                                 values.size() * sizeof(Type));
    180 }
    181 
    182 template <typename Type>
    183 hexagon_nn_input Model::createValues(const std::vector<Type>& values) {
    184     return createTensor(1, 1, 1, values.size(), values);
    185 }
    186 
    187 template <typename Type>
    188 hexagon_nn_input Model::createScalar(Type value) {
    189     return createTensorInternal(1, 1, 1, 1, reinterpret_cast<uint8_t*>(&value), sizeof(Type));
    190 }
    191 
    192 }  // namespace hexagon
    193 }  // namespace implementation
    194 }  // namespace V1_0
    195 }  // namespace neuralnetworks
    196 }  // namespace hardware
    197 }  // namespace android
    198 
    199 #endif  // ANDROID_HARDWARE_V1_0_HEXAGON_MODEL_H
    200