Initial commit
This commit is contained in:
@@ -0,0 +1,60 @@
|
||||
# Copyright (c) Huawei Technologies Co., Ltd. 2019. All rights reserved.
|
||||
|
||||
# CMake lowest version requirement
|
||||
cmake_minimum_required(VERSION 3.5.1)
|
||||
|
||||
# project information
|
||||
project(sample-colorization)
|
||||
|
||||
# Compile options
|
||||
add_compile_options(-std=c++11)
|
||||
|
||||
add_definitions(-DENABLE_DVPP_INTERFACE)
|
||||
|
||||
# Specify target generation path
|
||||
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "../../../out")
|
||||
|
||||
set(OPENCV_PATH "/usr/local")
|
||||
|
||||
set(INC_PATH $ENV{DDK_PATH})
|
||||
if (NOT DEFINED ENV{DDK_PATH})
|
||||
set(INC_PATH "/home/c72/Ascend/")
|
||||
message(STATUS "set default INC_PATH: ${INC_PATH}")
|
||||
else ()
|
||||
message(STATUS "env INC_PATH: ${INC_PATH}")
|
||||
endif()
|
||||
|
||||
set(LIB_PATH $ENV{NPU_HOST_LIB})
|
||||
if (NOT DEFINED ENV{NPU_HOST_LIB})
|
||||
set(LIB_PATH "/usr/local/Ascend/acllib/lib64/stub/")
|
||||
message(STATUS "set default LIB_PATH: ${LIB_PATH}")
|
||||
else ()
|
||||
message(STATUS "env LIB_PATH: ${LIB_PATH}")
|
||||
endif()
|
||||
|
||||
# Header path
|
||||
include_directories(
|
||||
../inc/
|
||||
${INC_PATH}/acllib/include/
|
||||
${OPENCV_PATH}/include/opencv4
|
||||
)
|
||||
|
||||
|
||||
# add host lib path
|
||||
link_directories(
|
||||
${LIB_PATH}
|
||||
$ENV{HOME}/ascend_ddk/host/lib/
|
||||
${OPENCV_PATH}/lib
|
||||
${INC_PATH}/atc/lib64
|
||||
)
|
||||
|
||||
add_executable(main
|
||||
utils.cpp
|
||||
colorize_process.cpp
|
||||
model_process.cpp
|
||||
main.cpp)
|
||||
|
||||
target_link_libraries(main
|
||||
ascendcl acl_dvpp stdc++ opencv_highgui opencv_core opencv_imgproc opencv_imgcodecs opencv_calib3d opencv_features2d opencv_videoio)
|
||||
|
||||
install(TARGETS main DESTINATION ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})
|
||||
@@ -0,0 +1 @@
|
||||
{}
|
||||
@@ -0,0 +1,292 @@
|
||||
/**
|
||||
* Copyright 2020 Huawei Technologies Co., Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
|
||||
* File sample_process.cpp
|
||||
* Description: handle acl resource
|
||||
*/
|
||||
#include "colorize_process.h"
|
||||
#include <iostream>
|
||||
|
||||
#include "acl/acl.h"
|
||||
#include "model_process.h"
|
||||
#include "utils.h"
|
||||
|
||||
using namespace std;
|
||||
|
||||
namespace {
|
||||
uint32_t kTopNConfidenceLevels = 5;
|
||||
}
|
||||
|
||||
ColorizeProcess::ColorizeProcess(const char* modelPath,
|
||||
uint32_t modelWidth, uint32_t modelHeight)
|
||||
:deviceId_(0), inputBuf_(nullptr),
|
||||
modelWidth_(modelWidth), modelHeight_(modelHeight), isInited_(false){
|
||||
modelPath_ = modelPath;
|
||||
inputDataSize_ = RGBF32_CHAN_SIZE(modelWidth_, modelHeight_);
|
||||
}
|
||||
|
||||
ColorizeProcess::~ColorizeProcess() {
|
||||
DestroyResource();
|
||||
}
|
||||
|
||||
Result ColorizeProcess::InitResource() {
|
||||
// ACL init
|
||||
const char *aclConfigPath = "../src/acl.json";
|
||||
aclError ret = aclInit(aclConfigPath);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("Acl init failed");
|
||||
return FAILED;
|
||||
}
|
||||
INFO_LOG("Acl init success");
|
||||
|
||||
// open device
|
||||
ret = aclrtSetDevice(deviceId_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("Acl open device %d failed", deviceId_);
|
||||
return FAILED;
|
||||
}
|
||||
INFO_LOG("Open device %d success", deviceId_);
|
||||
|
||||
ret = aclrtGetRunMode(&runMode_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("acl get run mode failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
Result ColorizeProcess::InitModel(const char* omModelPath) {
|
||||
Result ret = model_.LoadModelFromFileWithMem(omModelPath);
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("execute LoadModelFromFileWithMem failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = model_.CreateDesc();
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("execute CreateDesc failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = model_.CreateOutput();
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("execute CreateOutput failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
aclrtMalloc(&inputBuf_, (size_t)(inputDataSize_), ACL_MEM_MALLOC_HUGE_FIRST);
|
||||
if (inputBuf_ == nullptr) {
|
||||
ERROR_LOG("Acl malloc image buffer failed.");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = model_.CreateInput(inputBuf_, inputDataSize_);
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("Create mode input dataset failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
Result ColorizeProcess::Init() {
|
||||
if (isInited_) {
|
||||
INFO_LOG("Classify instance is initied already!");
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
Result ret = InitResource();
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("Init acl resource failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = InitModel(modelPath_);
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("Init model failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
isInited_ = true;
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
Result ColorizeProcess::Preprocess(const string& imageFile) {
|
||||
// read image using OPENCV
|
||||
cv::Mat mat = cv::imread(imageFile, CV_LOAD_IMAGE_COLOR);
|
||||
//resize
|
||||
cv::Mat reiszeMat;
|
||||
cv::resize(mat, reiszeMat, cv::Size(224, 224));
|
||||
|
||||
// deal image
|
||||
reiszeMat.convertTo(reiszeMat, CV_32FC3);
|
||||
reiszeMat = 1.0 * reiszeMat / 255;
|
||||
cv::cvtColor(reiszeMat, reiszeMat, CV_BGR2Lab);
|
||||
|
||||
// pull out L channel and subtract 50 for mean-centering
|
||||
std::vector<cv::Mat> channels;
|
||||
cv::split(reiszeMat, channels);
|
||||
cv::Mat reiszeMatL = channels[0] - 50;
|
||||
|
||||
if (mat.empty()) {
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
if (runMode_ == ACL_HOST) {
|
||||
//AI1上运行时,需要将图片数据拷贝到device侧
|
||||
aclError ret = aclrtMemcpy(inputBuf_, inputDataSize_,
|
||||
reiszeMatL.ptr<uint8_t>(), inputDataSize_,
|
||||
ACL_MEMCPY_HOST_TO_DEVICE);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("Copy resized image data to device failed.");
|
||||
return FAILED;
|
||||
}
|
||||
} else {
|
||||
//Atals200DK上运行时,数据拷贝到本地即可.
|
||||
//reiszeMat是局部变量,数据无法传出函数,需要拷贝一份
|
||||
memcpy(inputBuf_, reiszeMatL.ptr<uint8_t>(), inputDataSize_);
|
||||
}
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
Result ColorizeProcess::Inference(aclmdlDataset*& inferenceOutput) {
|
||||
Result ret = model_.Execute();
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("Execute model inference failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
inferenceOutput = model_.GetModelOutputData();
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
Result ColorizeProcess::Postprocess(const string& imageFile, aclmdlDataset* modelOutput)
|
||||
{
|
||||
uint32_t dataSize = 0;
|
||||
void* data = GetInferenceOutputItem(dataSize, modelOutput);
|
||||
if (data == nullptr) return FAILED;
|
||||
|
||||
uint32_t size = static_cast<uint32_t>(dataSize) / sizeof(float);
|
||||
|
||||
// get a channel and b channel result data
|
||||
cv::Mat mat_a(56, 56, CV_32FC1, const_cast<float*>((float*)data));
|
||||
cv::Mat mat_b(56, 56, CV_32FC1, const_cast<float*>((float*)data + size / 2));
|
||||
|
||||
// pull out L channel in original image
|
||||
cv::Mat mat = cv::imread(imageFile, CV_LOAD_IMAGE_COLOR);
|
||||
mat.convertTo(mat, CV_32FC3);
|
||||
mat = 1.0 * mat / 255;
|
||||
cv::cvtColor(mat, mat, CV_BGR2Lab);
|
||||
std::vector<cv::Mat> channels;
|
||||
cv::split(mat, channels);
|
||||
|
||||
// resize to match size of original image L
|
||||
int r = mat.rows;
|
||||
int c = mat.cols;
|
||||
cv::Mat mat_a_up(r, c, CV_32FC1);
|
||||
cv::Mat mat_b_up(r, c, CV_32FC1);
|
||||
cv::resize(mat_a, mat_a_up, cv::Size(c, r));
|
||||
cv::resize(mat_b, mat_b_up, cv::Size(c, r));
|
||||
|
||||
// result Lab image
|
||||
cv::Mat newChannels[3] = { channels[0], mat_a_up, mat_b_up };
|
||||
cv::Mat resultImage;
|
||||
cv::merge(newChannels, 3, resultImage);
|
||||
|
||||
//convert back to rgb
|
||||
cv::cvtColor(resultImage, resultImage, CV_Lab2BGR);
|
||||
resultImage = resultImage * 255;
|
||||
SaveImage(imageFile, resultImage);
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
void ColorizeProcess::SaveImage(const string& origImageFile, cv::Mat& image) {
|
||||
int pos = origImageFile.find_last_of("/");
|
||||
|
||||
string filename(origImageFile.substr(pos + 1));
|
||||
stringstream sstream;
|
||||
sstream.str("");
|
||||
sstream << "./output/out_" << filename;
|
||||
|
||||
string outputPath = sstream.str();
|
||||
cv::imwrite(outputPath, image);
|
||||
}
|
||||
|
||||
void* ColorizeProcess::GetInferenceOutputItem(uint32_t& itemDataSize,
|
||||
aclmdlDataset* inferenceOutput) {
|
||||
aclDataBuffer* dataBuffer = aclmdlGetDatasetBuffer(inferenceOutput, 0);
|
||||
if (dataBuffer == nullptr) {
|
||||
ERROR_LOG("Get the dataset buffer from model "
|
||||
"inference output failed");
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void* dataBufferDev = aclGetDataBufferAddr(dataBuffer);
|
||||
if (dataBufferDev == nullptr) {
|
||||
ERROR_LOG("Get the dataset buffer address "
|
||||
"from model inference output failed");
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
size_t bufferSize = aclGetDataBufferSize(dataBuffer);
|
||||
if (bufferSize == 0) {
|
||||
ERROR_LOG("The dataset buffer size of "
|
||||
"model inference output is 0 ");
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void* data = nullptr;
|
||||
if (runMode_ == ACL_HOST) {
|
||||
data = Utils::CopyDataDeviceToHost(dataBufferDev, bufferSize);
|
||||
if (data == nullptr) {
|
||||
ERROR_LOG("Copy inference output to host failed");
|
||||
return nullptr;
|
||||
}
|
||||
} else {
|
||||
data = dataBufferDev;
|
||||
}
|
||||
|
||||
itemDataSize = bufferSize;
|
||||
return data;
|
||||
}
|
||||
|
||||
void ColorizeProcess::DestroyResource()
|
||||
{
|
||||
model_.Unload();
|
||||
model_.DestroyDesc();
|
||||
model_.DestroyInput();
|
||||
model_.DestroyOutput();
|
||||
aclError ret;
|
||||
|
||||
ret = aclrtResetDevice(deviceId_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("reset device failed");
|
||||
}
|
||||
INFO_LOG("end to reset device is %d", deviceId_);
|
||||
|
||||
ret = aclFinalize();
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("finalize acl failed");
|
||||
}
|
||||
INFO_LOG("end to finalize acl");
|
||||
aclrtFree(inputBuf_);
|
||||
inputBuf_ = nullptr;
|
||||
}
|
||||
@@ -0,0 +1,82 @@
|
||||
/**
|
||||
* Copyright 2020 Huawei Technologies Co., Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
|
||||
* File main.cpp
|
||||
* Description: dvpp sample main func
|
||||
*/
|
||||
|
||||
#include <iostream>
|
||||
#include <stdlib.h>
|
||||
#include <dirent.h>
|
||||
|
||||
#include "colorize_process.h"
|
||||
#include "utils.h"
|
||||
using namespace std;
|
||||
|
||||
namespace {
|
||||
uint32_t kModelWidth = 224;
|
||||
uint32_t kModelHeight = 224;
|
||||
const char* kModelPath = "../model/colorization.om";
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
//检查应用程序执行时的输入,程序执行要求输入图片目录参数
|
||||
if((argc < 2) || (argv[1] == nullptr)){
|
||||
ERROR_LOG("Please input: ./main <image_dir>");
|
||||
return FAILED;
|
||||
}
|
||||
//实例化分类推理对象,参数为分类模型路径,模型输入要求的宽和高
|
||||
ColorizeProcess colorize(kModelPath, kModelWidth, kModelHeight);
|
||||
//初始化分类推理的acl资源, 模型和内存
|
||||
Result ret = colorize.Init();
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("Classification Init resource failed");
|
||||
return FAILED;
|
||||
}
|
||||
//获取图片目录下所有的图片文件名
|
||||
string inputImageDir = string(argv[1]);
|
||||
vector<string> fileVec;
|
||||
Utils::GetAllFiles(inputImageDir, fileVec);
|
||||
if (fileVec.empty()) {
|
||||
ERROR_LOG("Failed to deal all empty path=%s.", inputImageDir.c_str());
|
||||
return FAILED;
|
||||
}
|
||||
//逐张图片推理
|
||||
for (string imageFile : fileVec) {
|
||||
//预处理图片:读取图片,讲图片缩放到模型输入要求的尺寸
|
||||
Result ret = colorize.Preprocess(imageFile);
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("Read file %s failed, continue to read next",
|
||||
imageFile.c_str());
|
||||
continue;
|
||||
}
|
||||
//将预处理的图片送入模型推理,并获取推理结果
|
||||
aclmdlDataset* inferenceOutput = nullptr;
|
||||
ret = colorize.Inference(inferenceOutput);
|
||||
if ((ret != SUCCESS) || (inferenceOutput == nullptr)) {
|
||||
ERROR_LOG("Inference model inference output data failed");
|
||||
return FAILED;
|
||||
}
|
||||
//解析推理输出,并将推理得到的物体类别标记到图片上
|
||||
ret = colorize.Postprocess(imageFile, inferenceOutput);
|
||||
if (ret != SUCCESS) {
|
||||
ERROR_LOG("Process model inference output data failed");
|
||||
return FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
INFO_LOG("Execute sample success");
|
||||
return SUCCESS;
|
||||
}
|
||||
@@ -0,0 +1,238 @@
|
||||
/**
|
||||
* Copyright 2020 Huawei Technologies Co., Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
|
||||
* File model_process.cpp
|
||||
* Description: handle model process
|
||||
*/
|
||||
#include "model_process.h"
|
||||
#include <iostream>
|
||||
#include "utils.h"
|
||||
using namespace std;
|
||||
|
||||
ModelProcess::ModelProcess():loadFlag_(false), modelId_(0), modelMemPtr_(nullptr), modelMemSize_(0),
|
||||
modelWeightPtr_(nullptr),modelWeightSize_(0), modelDesc_(nullptr), input_(nullptr), output_(nullptr) {
|
||||
|
||||
}
|
||||
|
||||
ModelProcess::~ModelProcess() {
|
||||
Unload();
|
||||
DestroyDesc();
|
||||
DestroyInput();
|
||||
DestroyOutput();
|
||||
}
|
||||
|
||||
Result ModelProcess::LoadModelFromFileWithMem(const char *modelPath) {
|
||||
if (loadFlag_) {
|
||||
ERROR_LOG("has already loaded a model");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
aclError ret = aclmdlQuerySize(modelPath, &modelMemSize_, &modelWeightSize_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("query model failed, model file is %s", modelPath);
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = aclrtMalloc(&modelMemPtr_, modelMemSize_, ACL_MEM_MALLOC_HUGE_FIRST);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("malloc buffer for mem failed, require size is %zu", modelMemSize_);
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = aclrtMalloc(&modelWeightPtr_, modelWeightSize_, ACL_MEM_MALLOC_HUGE_FIRST);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("malloc buffer for weight failed, require size is %zu", modelWeightSize_);
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = aclmdlLoadFromFileWithMem(modelPath, &modelId_, modelMemPtr_,
|
||||
modelMemSize_, modelWeightPtr_, modelWeightSize_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("load model from file failed, model file is %s", modelPath);
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
loadFlag_ = true;
|
||||
INFO_LOG("load model %s success", modelPath);
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
Result ModelProcess::CreateDesc() {
|
||||
modelDesc_ = aclmdlCreateDesc();
|
||||
if (modelDesc_ == nullptr) {
|
||||
ERROR_LOG("create model description failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
aclError ret = aclmdlGetDesc(modelDesc_, modelId_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("get model description failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
INFO_LOG("create model description success");
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
void ModelProcess::DestroyDesc() {
|
||||
if (modelDesc_ != nullptr) {
|
||||
(void)aclmdlDestroyDesc(modelDesc_);
|
||||
modelDesc_ = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
Result ModelProcess::CreateInput(void *inputDataBuffer, size_t bufferSize) {
|
||||
input_ = aclmdlCreateDataset();
|
||||
if (input_ == nullptr) {
|
||||
ERROR_LOG("can't create dataset, create input failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
aclDataBuffer* inputData = aclCreateDataBuffer(inputDataBuffer, bufferSize);
|
||||
if (inputData == nullptr) {
|
||||
ERROR_LOG("can't create data buffer, create input failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
aclError ret = aclmdlAddDatasetBuffer(input_, inputData);
|
||||
if (inputData == nullptr) {
|
||||
ERROR_LOG("can't add data buffer, create input failed");
|
||||
aclDestroyDataBuffer(inputData);
|
||||
inputData = nullptr;
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
void ModelProcess::DestroyInput() {
|
||||
if (input_ == nullptr) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < aclmdlGetDatasetNumBuffers(input_); ++i) {
|
||||
aclDataBuffer* dataBuffer = aclmdlGetDatasetBuffer(input_, i);
|
||||
aclDestroyDataBuffer(dataBuffer);
|
||||
}
|
||||
aclmdlDestroyDataset(input_);
|
||||
input_ = nullptr;
|
||||
}
|
||||
|
||||
Result ModelProcess::CreateOutput() {
|
||||
if (modelDesc_ == nullptr) {
|
||||
ERROR_LOG("no model description, create ouput failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
output_ = aclmdlCreateDataset();
|
||||
if (output_ == nullptr) {
|
||||
ERROR_LOG("can't create dataset, create output failed");
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
size_t outputSize = aclmdlGetNumOutputs(modelDesc_);
|
||||
for (size_t i = 0; i < outputSize; ++i) {
|
||||
size_t buffer_size = aclmdlGetOutputSizeByIndex(modelDesc_, i);
|
||||
|
||||
void *outputBuffer = nullptr;
|
||||
aclError ret = aclrtMalloc(&outputBuffer, buffer_size, ACL_MEM_MALLOC_NORMAL_ONLY);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("can't malloc buffer, size is %zu, create output failed", buffer_size);
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
aclDataBuffer* outputData = aclCreateDataBuffer(outputBuffer, buffer_size);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("can't create data buffer, create output failed");
|
||||
aclrtFree(outputBuffer);
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
ret = aclmdlAddDatasetBuffer(output_, outputData);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("can't add data buffer, create output failed");
|
||||
aclrtFree(outputBuffer);
|
||||
aclDestroyDataBuffer(outputData);
|
||||
return FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
INFO_LOG("create model output success");
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
void ModelProcess::DestroyOutput() {
|
||||
if (output_ == nullptr) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < aclmdlGetDatasetNumBuffers(output_); ++i) {
|
||||
aclDataBuffer* dataBuffer = aclmdlGetDatasetBuffer(output_, i);
|
||||
void* data = aclGetDataBufferAddr(dataBuffer);
|
||||
(void)aclrtFree(data);
|
||||
(void)aclDestroyDataBuffer(dataBuffer);
|
||||
}
|
||||
|
||||
(void)aclmdlDestroyDataset(output_);
|
||||
output_ = nullptr;
|
||||
}
|
||||
|
||||
Result ModelProcess::Execute() {
|
||||
aclError ret = aclmdlExecute(modelId_, input_, output_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("execute model failed, modelId is %u", modelId_);
|
||||
return FAILED;
|
||||
}
|
||||
|
||||
INFO_LOG("model execute success");
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
void ModelProcess::Unload() {
|
||||
if (!loadFlag_) {
|
||||
return;
|
||||
}
|
||||
|
||||
aclError ret = aclmdlUnload(modelId_);
|
||||
if (ret != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("unload model failed, modelId is %u", modelId_);
|
||||
}
|
||||
|
||||
if (modelDesc_ != nullptr) {
|
||||
(void)aclmdlDestroyDesc(modelDesc_);
|
||||
modelDesc_ = nullptr;
|
||||
}
|
||||
|
||||
if (modelMemPtr_ != nullptr) {
|
||||
aclrtFree(modelMemPtr_);
|
||||
modelMemPtr_ = nullptr;
|
||||
modelMemSize_ = 0;
|
||||
}
|
||||
|
||||
if (modelWeightPtr_ != nullptr) {
|
||||
aclrtFree(modelWeightPtr_);
|
||||
modelWeightPtr_ = nullptr;
|
||||
modelWeightSize_ = 0;
|
||||
}
|
||||
|
||||
loadFlag_ = false;
|
||||
INFO_LOG("unload model success, modelId is %u", modelId_);
|
||||
}
|
||||
|
||||
aclmdlDataset *ModelProcess::GetModelOutputData() {
|
||||
return output_;
|
||||
}
|
||||
|
||||
|
||||
+136
@@ -0,0 +1,136 @@
|
||||
/**
|
||||
* Copyright 2020 Huawei Technologies Co., Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
|
||||
* File utils.cpp
|
||||
* Description: handle file operations
|
||||
*/
|
||||
#include "utils.h"
|
||||
#include <map>
|
||||
#include <iostream>
|
||||
#include <fstream>
|
||||
#include <unistd.h>
|
||||
#include <cstring>
|
||||
#include <dirent.h>
|
||||
#include <vector>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/types.h>
|
||||
#include "acl/acl.h"
|
||||
|
||||
using namespace std;
|
||||
|
||||
namespace {
|
||||
const std::string kImagePathSeparator = ",";
|
||||
const int kStatSuccess = 0;
|
||||
const std::string kFileSperator = "/";
|
||||
const std::string kPathSeparator = "/";
|
||||
// output image prefix
|
||||
const std::string kOutputFilePrefix = "out_";
|
||||
}
|
||||
|
||||
bool Utils::IsDirectory(const string &path) {
|
||||
// get path stat
|
||||
struct stat buf;
|
||||
if (stat(path.c_str(), &buf) != kStatSuccess) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// check
|
||||
if (S_ISDIR(buf.st_mode)) {
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
bool Utils::IsPathExist(const string &path) {
|
||||
ifstream file(path);
|
||||
if (!file) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void Utils::SplitPath(const string &path, vector<string> &path_vec) {
|
||||
char *char_path = const_cast<char*>(path.c_str());
|
||||
const char *char_split = kImagePathSeparator.c_str();
|
||||
char *tmp_path = strtok(char_path, char_split);
|
||||
while (tmp_path) {
|
||||
path_vec.emplace_back(tmp_path);
|
||||
tmp_path = strtok(nullptr, char_split);
|
||||
}
|
||||
}
|
||||
|
||||
void Utils::GetAllFiles(const string &path, vector<string> &file_vec) {
|
||||
// split file path
|
||||
vector<string> path_vector;
|
||||
SplitPath(path, path_vector);
|
||||
|
||||
for (string every_path : path_vector) {
|
||||
// check path exist or not
|
||||
if (!IsPathExist(path)) {
|
||||
ERROR_LOG("Failed to deal path=%s. Reason: not exist or can not access.",
|
||||
every_path.c_str());
|
||||
continue;
|
||||
}
|
||||
// get files in path and sub-path
|
||||
GetPathFiles(every_path, file_vec);
|
||||
}
|
||||
}
|
||||
|
||||
void Utils::GetPathFiles(const string &path, vector<string> &file_vec) {
|
||||
struct dirent *dirent_ptr = nullptr;
|
||||
DIR *dir = nullptr;
|
||||
if (IsDirectory(path)) {
|
||||
dir = opendir(path.c_str());
|
||||
while ((dirent_ptr = readdir(dir)) != nullptr) {
|
||||
// skip . and ..
|
||||
if (dirent_ptr->d_name[0] == '.') {
|
||||
continue;
|
||||
}
|
||||
|
||||
// file path
|
||||
string full_path = path + kPathSeparator + dirent_ptr->d_name;
|
||||
// directory need recursion
|
||||
if (IsDirectory(full_path)) {
|
||||
GetPathFiles(full_path, file_vec);
|
||||
} else {
|
||||
// put file
|
||||
file_vec.emplace_back(full_path);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
file_vec.emplace_back(path);
|
||||
}
|
||||
}
|
||||
|
||||
void* Utils::CopyDataDeviceToHost(void* deviceData, uint32_t dataSize) {
|
||||
void* hostPtr = nullptr;
|
||||
aclError aclRet = aclrtMalloc(&hostPtr, dataSize, ACL_MEM_MALLOC_HUGE_FIRST);
|
||||
if (aclRet != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("malloc host data buffer failed, aclRet is %d", aclRet);
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
aclRet = aclrtMemcpy(hostPtr, dataSize, deviceData, dataSize, ACL_MEMCPY_DEVICE_TO_DEVICE);
|
||||
if (aclRet != ACL_ERROR_NONE) {
|
||||
ERROR_LOG("aclrtMemcpy device to host failed, aclRet is %d", aclRet);
|
||||
(void)aclrtFree(hostPtr);
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return hostPtr;
|
||||
}
|
||||
Reference in New Issue
Block a user