华为CANN训练营笔记——应用开发全流程 [1](with 代码版)

1. 应用开发全流程

第一部分

1.1 模型转换

ATC——Ascend Tensor Compile。一、转换其他框架的模型文件;二、单算子编译,转换基于Ascend IR定义的单算子描述文件。主要步骤:

  1. 模型准备 或 单算子json文件准备
  2. 转换;AIPP配置(插入数据预处理操作

原始框架为Caffe时,.prototxt和.caffemodel的op name和op type必须保持一致,且输入数据最大支持四位。reshape、expanddim等算子不能输出五维。模型中所有算子不能维度为0.

1.1.1 AIPP

AIPP是在模型转换的过程中配置的,通过配置文件的形式固化到om模型中。转RGB,减均值,乘系数,图像增强等操作是DVPP做不到的。AIPP输入是DVPP的结果,一定是YUV格式。AIPP将图片转换为模型接受的图片格式(如RGB)。MindStudio中配置AIPP界面如下
华为CANN训练营笔记——应用开发全流程 [1](with 代码版)_第1张图片

AIPP输入图片大小(Input Image Resolution) == DVPP输出图片大小(16 * 2 对齐)

insert_op.cfg文件

aipp_op{
aipp_mode:static 
related_input_rank : 0  # 标识对第1个输入进行AIPP处理
src_image_size_w : 608
src_image_size_h : 608
crop : false
input_format : YUV420SP_U8
csc_switch : true
rbuv_swap_switch : false

matrix_r0c0 : 298
matrix_r0c1 : 0
matrix_r0c2 : 409
matrix_r1c0 : 298
matrix_r1c1 : -100
matrix_r1c2 : -208
matrix_r2c0 : 298
matrix_r2c1 : 516
matrix_r2c2 : 0
input_bias_0 : 16
input_bias_1 : 128
input_bias_2 : 128
mean_chn_0 : 104
mean_chn_1 : 117
mean_chn_2 : 123
min_chn_0 : 0.0
min_chn_1 : 0.0
min_chn_2 : 0.0
var_rec1_chn_0 : 1.0
var_rec1_chn_1 : 1.0
var_rec1_chn_2 : 1.0
}

1.1.2 ATC命令行转换

atc --help验证环境搭建。

  • input_shape=
  • weight= .caffemodel
  • input_format=通道,caffe默认NCHW
  • output= 位置
  • soc_version=芯片
  • insert_op_conf=加载AIPP配置文件
  • framework= 原始框架类型,0为caffe
  • model= .prorotxt

转换命令
atc --model= --weight= ...

1.1.3 AIPP配置文件

AIPP配置文件名为insert_op.cfg。详情参看atc手册

1.1.4 单算子配置文件

算子信息库
软件栈具备单算子推理能力,即把数据输入到单算子中得到结果,单算子在推理过程中也相当于一个模型。单算子配置文件是.json格式

假设有如下单算子op_list.json配置文件

# ArgMaxD算子
# 		实现输出置信度最大的类别
{
  "op": "ArgMaxD",  # 算子名称
  "input_desc": [	# 输入描述
    {
	"format": "ND",
	"shape": [1000],
	"type": "float16"
    }
  ],
  "output_desc": [	# 输出算子
    {
	"format": "ND",
	"shape": [1],
	"type": "int32"
    }
  ],
  "attr": [			# 算子的属性信息
    {
    "name": "dimension",
    "type": "int",
    "value":0
    }
   ]
}

转换命令
atc --singleop ./op_list.json --output ./output --soc_version Ascend310,会在output中生成对应的om文件。一个算子对应一个om

OpDesc参数说明

类型 说明 必填
comfile_flag INT32 默认0,表示精确编译
op string 算子类型
input_desc TensorDesc数组 算子输入描述
output_desc TensorDesc数组 算子输出描述
attr Attr数组 算子属性

TensorDesc参数说明

类型 说明 必填
format INT32 Tensor的排布方式,用0, 1, 2,3等代码指代。0为NCHW,1为NHWC
shape int数组 Tensor的shape,如[1, 3, 224, 224]
type string Tensor的数据类型
name string Tensor的名称。算子输入为动态输入时是必需的
dynamic_input string 动态输入,取值必须和算子信息库中该算子定义的输入name相同

Attr参数说明

类型 说明 必填
name string 属性名
type string 属性值的类型。bool, string, int, float, list_bool, …
value 由type的取值决定 属性值,根据type不同而不同

这里配置的算子决定了将来调用ACL接口执行算子计算过程中,匹配算子的规则。实际调用算子文件进行单算子计算时,配置的是一个目录,这个代码框架将整个目录里所有的om都加载进来,计算时根据配置信息匹配给具体单算子进行计算。

1.1.5 !!! 关于单算子配置文件的问题

1. json是手写的吗

json字段内容是手写的,对应算子的属性。json文件配置格式参考(即3.1.4内容的完整版)

2. Cast和ArgMaxD是自定义的吗

Cast和ArgMaxD是CANN已经实现的算子。CANN已经实现的算子清单

1.2 ACL综述

计算加速。可以实现模型加载,算子加载和执行,数据预处理,是基于C++的。管理设备、上下文、流

1.2.1 ACL基本概念

  1. HOST:指与Device相连的x86服务器,会利用Device提供的NN计算能力完成业务
  2. Device:安装了芯片的硬件设备,利用PCLe接口与Host连接
  3. 同步异步
  4. 线程进程:指HOST侧的线程和进程
  5. Context:容器,管理所有对象(stream,event,设备内存) 的生命周期。不同Context间的内容隔离。分为默认Context和显示创建的Context
  6. Stream:用于维护一些异步操作的执行顺序。分为默认Stream和显示创建的Stream
  7. Event:同步Stream之间的任务,例如HOST与Device之间的任务,Device和Device之间的任务。例如,若stream2的任务依赖stream1的任务,想保证stream1中的任务先完成,这时可创建一个Event,并将Event插入到stream1,在执行stream2的任务前,先同步等待Event完成
  8. 动态AIPP:不能同时配置静态AIPP和动态AIPP。

模型和数据启动在HOST,中间传到Device上计算,结果再回传至HOST

1.2.2 Acl主要接口调用流程

  • 运行管理资源:Device,Context,Stream
    华为CANN训练营笔记——应用开发全流程 [1](with 代码版)_第2张图片

1.2.3 Hello World

# include 
# include "acl/acl.h"
// 设置宏
# define INFO_LOG(fmt, args...) fprintf(stdout, "[INFO] " fmt "\n", ##args)
# define WARN_LOG(fmt, args...) fprintf(stdout, "[WARN] " fmt "\n", ##args)
# define ERROR_LOG(fmt, args...) fprintf(stdout, "[ERROR] " fmt "\n", ##args)
using namespace std;

int main(){
	INFO_LOG("HELLO WORLD");
	// ACL初始化
	const char *aclConfigPath = "acl.json";
	aclError ret = aclInit(aclConfigPath);
	if (ret != ACL_ERROR_NONE){	// 判断初始化成功
		ERROR_LOG("acl init failed");
	}
	INFO_LOG("acl init success");
	
	ret = aclFinalize();
	// ACL销毁
	if (ret != ACL_ERROR_NONE){
		ERROR_LOG("finalize acl failed");
	}
	INFO_LOG("end to finalize acl");
	return 0;
}

1.2.4 编译运行

1. 编译文件 CMakeList.txt

# Copyright (c) Huawei Technologies Co., Ltd. 2019. All rights reserved.
# CMake lowest version requirement
cmake_minimum_required(VERSION 3.5.1)

# project information
project(ACL_HELLO_WORLD)

# Compile options
add_compile_options(-std=c++11)

# 指定生成路径
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY  "../out")
set(CMAKE_CXX_FLAGS_DEBUG "-fPIC -O0 -g -Wall")
set(CMAKE_CXX_FLAGS_RELEASE "-fPIC -O2 -Wall")

set(INC_PATH $ENV{DDK_PATH})

if (NOT DEFINED ENV{DDK_PATH})
    if (${CMAKE_HOST_SYSTEM_NAME} MATCHES "Windows")
        set(INC_PATH "C:/Program Files/HuaWei/Ascend")
    else ()
        set(INC_PATH "/usr/local/Ascend")
    endif ()
    message(STATUS "set default INC_PATH: ${INC_PATH}")
else ()
    message(STATUS "env INC_PATH: ${INC_PATH}")
endif ()

set(LIB_PATH $ENV{NPU_HOST_LIB})

# Dynamic libraries in the stub directory can only be used for compilation
if (NOT DEFINED ENV{NPU_HOST_LIB})
    if (${CMAKE_HOST_SYSTEM_NAME} MATCHES "Windows")
        set(LIB_PATH "C:/Program Files/HuaWei/Ascend/Acllib/lib64")
    else ()
        set(LIB_PATH "/usr/local/Ascend/acllib/lib64/stub/")
    endif ()
    message(STATUS "set default LIB_PATH: ${LIB_PATH}")
else ()
    message(STATUS "env LIB_PATH: ${LIB_PATH}")
endif ()

# Header path
# 引用除acl.h 需要在此添加头文件
include_directories(
    ${INC_PATH}/acllib/include/

)

if(target STREQUAL "Simulator_Function")
    add_compile_options(-DFUNC_SIM)
endif()

# add host lib path
link_directories(
    ${LIB_PATH}
)

# 可能变化的
# 想要编译的源文件
add_executable(main  # 指生成的可执行文件
        main.cpp)  # 指待编译的源文件

if (target STREQUAL "Simulator_Function")
    target_link_libraries(main funcsim)
else ()
    if (${CMAKE_HOST_SYSTEM_NAME} MATCHES "Windows")
        target_link_libraries(main
            libascendcl)
    else ()
        target_link_libraries(main
            ascendcl stdc++)
    endif ()
endif ()

install(TARGETS main DESTINATION ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})

2. 环境变量

NPU_HOST_LIB=/home/HwHiAiUser/Ascend/acllib/lib64/stub
DDK_PATH =home/HwHiAiUser/Ascend
LD_LIBRARY_PATH=/home/HwHiAiUser/Ascend/acllib/lib64:/usr/local/Ascend/ add-ons:/ home/HwHiAiUser/Ascend/atc/lib64:

3. 编译

生成编译文件
cmake . -DCMAKE_CXX_COMPILER=g++ -DCMAKE_SKIP_RPATH=TRUE
编译
make

加载acl.json
touch acl.json # 创建空文件,与main可执行放在同一个目录下

1.2.5 查看日志

cd home/ascend/log # 小写的ascend
p-log:HOST日志

你可能感兴趣的:(Ascend,CANN,华为,caffe,人工智能,华为云,计算机视觉)