Implement NNAPI get output rank function (#7581)
author오형석/On-Device Lab(SR)/Staff Engineer/삼성전자 <hseok82.oh@samsung.com>
Fri, 20 Sep 2019 03:42:00 +0000 (12:42 +0900)
committerGitHub Enterprise <noreply-CODE@samsung.com>
Fri, 20 Sep 2019 03:42:00 +0000 (12:42 +0900)
Inplement NNAPI ANeuralNetworksExecution_getOutputOperandRank and wrapper function
Introduce private field and method in Execution class to check execution is finished

Signed-off-by: Hyeongseok Oh <hseok82.oh@samsung.com>
runtimes/neurun/core/include/exec/Execution.h
runtimes/neurun/core/src/exec/Execution.cc
runtimes/neurun/frontend/nnapi/execution.cc
runtimes/neurun/frontend/nnapi/wrapper/ANeuralNetworksExecution.cc
runtimes/neurun/frontend/nnapi/wrapper/ANeuralNetworksExecution.h

index a5b47f0..13b0cfd 100644 (file)
@@ -106,10 +106,17 @@ public:
    */
   void waitFinish(void);
 
+  /**
+   * @brief   Check execution is finished
+   * @return  @c true if execution is finished, otherwise @c false
+   */
+  bool isFinished(void) const;
+
 private:
   const std::shared_ptr<IExecutor> _executor;
   IODescription _io_desc;
   std::unique_ptr<std::thread> _exec_thread;
+  bool finished{false};
 };
 
 } // namespace exec
index 01114d8..2b93aab 100644 (file)
@@ -86,6 +86,7 @@ void Execution::execute()
   VERBOSE(Execution) << "Start execution" << std::endl;
 
   _executor->execute(_io_desc);
+  finished = true;
 
   VERBOSE(Execution) << "Execution finished" << std::endl;
 }
@@ -102,7 +103,10 @@ void Execution::waitFinish()
   VERBOSE(Execution) << "Wait to finish execution" << std::endl;
 
   _exec_thread->join();
+  finished = true;
 }
 
+bool Execution::isFinished(void) const { return finished; }
+
 } // namespace exec
 } // namespace neurun
index 3a1b0ef..0091ede 100644 (file)
@@ -426,3 +426,29 @@ int ANeuralNetworksExecution_setOutputFromMemory(ANeuralNetworksExecution *execu
 
   return ANEURALNETWORKS_NO_ERROR;
 }
+
+int ANeuralNetworksExecution_getOutputOperandRank(ANeuralNetworksExecution *execution,
+                                                  int32_t index, uint32_t *rank)
+{
+  if ((execution == nullptr) || (rank == nullptr))
+  {
+    VERBOSE(NNAPI::Execution) << "getOutputOperandRank: Incorrect null pointer parameter(s)"
+                              << std::endl;
+    return ANEURALNETWORKS_UNEXPECTED_NULL;
+  }
+
+  const auto operand_index = execution->getOutputOperandIndex(index);
+  if (!operand_index.valid())
+  {
+    VERBOSE(NNAPI::Execution) << "getOutputOperandRank: Invalid output index" << std::endl;
+    return ANEURALNETWORKS_BAD_DATA;
+  }
+
+  if (!execution->getOutputOperandRank(index, rank))
+  {
+    VERBOSE(NNAPI::Execution) << "getOutputOperandRank: Fail to get rank" << std::endl;
+    return ANEURALNETWORKS_BAD_STATE;
+  }
+
+  return ANEURALNETWORKS_NO_ERROR;
+}
index df51886..d78b99d 100644 (file)
@@ -204,3 +204,36 @@ const std::shared_ptr<neurun::exec::Execution> ANeuralNetworksExecution::instanc
 {
   return _execution;
 }
+
+bool ANeuralNetworksExecution::getOutputOperandRank(uint32_t index, uint32_t *rank) noexcept
+{
+  try
+  {
+    neurun::model::IOIndex output_index{index};
+    const auto operand_index = getOutputOperandIndex(index);
+    bool unspecified = haveUnspecifiedDims(operand_index);
+
+    // TODO Get unspecified output operand's rank
+    if (unspecified)
+    {
+      throw std::runtime_error{"Unsupport feature"};
+    }
+
+    // Check execution is finished
+    // Output rank and shape may be decided after execution if output is unspecified operand
+    if (!_execution->isFinished())
+    {
+      return false;
+    }
+
+    *rank = _execution->model().operands.at(operand_index).shape().rank();
+  }
+  catch (const std::exception &e)
+  {
+    VERBOSE(EXCEPTION) << e.what() << std::endl;
+
+    return false;
+  }
+
+  return true;
+}
index 6e71887..8748594 100644 (file)
@@ -50,6 +50,14 @@ public:
   size_t getOperandSize(const neurun::model::OperandIndex index) noexcept;
   const std::shared_ptr<neurun::exec::Execution> instance(void) noexcept;
 
+  /**
+   * @brief       Get output operand's rank
+   * @param[in]   index Output index
+   * @param[out]  rank  Output operand's rank
+   * @return      @c true if success to get rank, otherwise @c false
+   */
+  bool getOutputOperandRank(uint32_t index, uint32_t *rank) noexcept;
+
 private:
   std::shared_ptr<neurun::exec::Execution> _execution;
 };