---
title: TIK功能调试
description: "用户开发完TIK算子之后，建议使用TIK调试工具进行算子调试，这样可以通过模拟算子运行的过程，解决算子的绝大部分功能问题（例如数据越界）。"
url: https://www.hiascend.com/document/detail/zh/canncommercial/latest/others/tbeaicpudevg/atlasopdev_10_0058.html
sourcePath: /source/zh/canncommercial/900/others/tbeaicpudevg/atlasopdev_10_0058.html
indexId: d57a9a6da3b66d1b588ff80d7e75bd319168b5fee5dc0d5e1dc9cafbd9e200e773
---
# TIK功能调试

#### 功能介绍

用户开发完TIK算子之后，建议使用TIK调试工具进行算子调试，这样可以通过模拟算子运行的过程，解决算子的绝大部分功能问题（例如数据越界）。

TIK功能调试用于调试TIK DSL的执行行为。该调试功能通过TIK模块的tik.tikdb对象提供。tik.tikdb对象通过tik.Tik对象的tik_instance.tikdb()方法获得，并针对这个TIK对象进行调试。

tikdb提供类似pdb（The Python Debugger）的调试命令行界面。调试者通过tikdb.start_debug()函数启动一个调试过程（需要给定用于测试的TIK DSL程序的输入参数，详细可参考start_debug），tikdb将根据TIK的Dprofile启动一个本地的模拟器，模拟执行TIK定义的执行过程。执行过程遇到断点，tikdb会进入调试命令行界面，详细可参考4。


#### 支持的型号

Atlas 训练系列产品

Atlas 推理系列产品

Atlas A2 训练系列产品 / Atlas A2 推理系列产品

Atlas A3 训练系列产品 / Atlas A3 推理系列产品

Atlas 200I/500 A2 推理产品


#### 使用方法

1. 在进行功能调试前，需要在定义TIK实例时设置disable_debug参数为False，该参数默认值为“True”，代表默认不开启调试功能，详细参数含义可参见TIK类构造函数。

```
tik_instance = tik.Tik(disable_debug=False)
```


  注意：开启调试功能会影响算子性能，开发者完成功能调试后可以删除disable_debug参数或将disable_debug参数手动置为True，禁用调试功能，可以降低编译时间时长，提升部分性能。

  debug调试中使用到的API接口主要包括：
  - start_debug：启动调试并在调试结束后返回输出结果。
  - debug_print：可选接口，为了方便用户打印算子运行过程中的数据。在TIK DSL中插入一个对表达式求值并打印结果的语句。调试器执行到这行代码时会对表达式求值并将结果打印在屏幕上。


  更多接口介绍请参考功能调试。

2. 准备调试数据。
  可以通过numpy生成随机数或者从文件中读取。

  完整代码示例参考如下，文件名以simple_add.py为例。

```
import numpy as np
from tbe import tik
from tbe.common.platform import set_current_compile_soc_info
def simple_add():
tik_instance = tik.Tik(disable_debug=False)
kernel_name = "tik_vec_add_128_float32"
dst_ub = tik_instance.Tensor("float32", [128], tik.scope_ubuf, "dst_ub")
dst_gm = tik_instance.Tensor("float32", (128,), tik.scope_gm,  "dst_gm")
src0_gm = tik_instance.Tensor("float32", (128,), tik.scope_gm, "src0_gm")
src0_ub = tik_instance.Tensor("float32", (128,), tik.scope_ubuf, "src0_ub")
src1_gm = tik_instance.Tensor("float32", (128,), tik.scope_gm, "src1_gm")
src1_ub = tik_instance.Tensor("float32", (128,), tik.scope_ubuf, "src1_ub")
tik_instance.data_move(src0_ub, src0_gm, 0, 1, 16, 0, 0)
tik_instance.data_move(src1_ub, src1_gm, 0, 1, 16, 0, 0)
tik_instance.vec_add(64, dst_ub, src0_ub, src1_ub, 2, 8, 8, 8)
tik_instance.data_move(dst_gm, dst_ub, 0, 1, 16, 0, 0)
tik_instance.BuildCCE(kernel_name, [src0_gm, src1_gm], [dst_gm])
return tik_instance
if __name__=='__main__':
# 请根据实际昇腾AI处理器型号进行设置
soc_version="xxx"
set_current_compile_soc_info(soc_version)   # 请根据AI处理器实际版本设置，具体请参考
set_current_compile_soc_info
接口说明
tik_instance = simple_add()
data_x = np.ones((128,)).astype("float32")
data_y = np.ones((128,)).astype("float32")
feed_dict = {'src0_gm': data_x, 'src1_gm': data_y}
model_data, = tik_instance.tikdb.start_debug(feed_dict=feed_dict,interactive=True)
print(model_data)
```


3. 运行算子文件进入TIK调试器的交互命令行。

  a. 请参见    环境准备
配置好相关环境变量。
  b. 运行算子文件。
    调用tikdb.start_debug()函数且interactive参数为True后，运行算子文件进入TIK调试器的交互命令行，此时调试器会停止在执行第一条TIK DSL之前。如下图所示。

4. 在TIK调试器交互命令行模式下，用户可输入调试命令，详细调试命令请参考调试命令参考。com(mand) param1 [param2]

  - com(mand) 为命令的名字，可以是command，也可缩写为com。
  - param1不带中括号，表示必选参数。
  - [param2]带中括号，表示可选参数。
  - 其他使用说明：

    - 若命令行提示符中输入空白符，表示重复执行上一条命令。
    - 在debug 调试下，可以进行单步调试，也可以执行至下一个断点或程序结束。如果程序功能正确，则运行到程序结束可以看到debug产生的数据和期望数据的差别为0。


#### 调试命令参考

调试器命令行模式下包括如下几种命令：

1. block[block_idx1] [block_idx2] ... [block_idxn]

  - 功能说明：对于多核用例，用于核状态查询、调试核切换，该命令对单核用例无效。
  - 参数说明：block_idxn对应多核用例中的block_num取值。
  - 查询核状态：执行到多核对应的with tik_instance.for_range()及之后语句，"block"命令可以查询所有核对应的状态，输出信息说明：

    - Block表示核编号。
    - Status表示当前核状态，包括：Stepping（交互状态），Running（非交互运行状态），Finished（运行结束）。
    - Current表示当前调试核；包括True（当前调试核），False（当前非调试核）。
图1 多核交互信息查询
  - 核切换：执行到多核对应的with tik_instance.for_range()及之后语句，"block block_idx"命令进行核切换，从当前核切换到block_idx对应的核进行调试。
    图2 多核切换调试

2. b(reak)[tag] [block block_idx1 [block_idx2] ... [block_idxn]]

  - 功能说明：在TIK DSL对应的tag上设置断点、查询断点。
  - 参数说明：

    - tag：TIK DSL程序的断点标记，内容为：

```
该TIK DSL定义函数所在的文件名：该TIK DSL定义函数所在函数的行号
```


      若不设置任何参数，则直接列出所有已设置断点的信息，包含断点的编号，断点的使能状态，断点对应的tag。其中断点的编号从“0”开始按照设置先后顺序递增。

      需要注意：若设置断点格式不准确或者断点处语句非TIK DSL语句均会提示断点设置失败。支持设置断点的语句包括Tensor定义、if-else语句、for语句以及所有的指令（如data_move、vadd等）。

    - block：仅对多核用例有效，对单核用例无效。通过命令“block”指定断点对所有核生效（Running和Finished状态的核无效）；通过命令“block block_idx1 block_idx2 ...”指定断点对特定的核生效。
    - 样例说明：以上文的simple_add.py为例。

      - b或者break（显示当前所有断点）
        Num表示断点编号；Type表示类型为断点；Enb表示断点状态；where表示断点所在文件名和代码行号。

      - b simple_add.py（输入格式不匹配）
      - b simple_add.py:16（输入准确）
      - b simple_add.py:100（行号超过文件代码行数或该行代码不会执行）
      - b simple_add.py:1（行号对应代码非TIK原语代码）
      - b others.py:18（设置其它文件断点）
      - b others.py:19 block 1 2 (如果是多核用例，通过block指定该断点只对核1、2生效）
图3 设置断点示例
3. clear[bpnumber][block block_idx1 [block_idx2] ... [block_idxn]]

  - 功能说明：清除指定编号的断点，如果不指定参数，将清除所有断点。
  - 参数说明：

    - bpnumber：断点的编号，即为b(reak)命令查询到的Num。
    - block：仅对多核用例有效，对单核用例无效。通过命令“block”清除所有核的断点（Running和Finished状态的核无效）；通过命令“block block_idx1 block_idx2 ...”清除特定核的指定断点。
  - 样例说明：以上文的simple_add.py为例。

    - clear (清除所有断点)
    - clear 1 (断点存在)
    - clear 10 (断点不存在)
    - clear cc (编号不规范)
    - clear 1 block 2 3 （对于多核用例，指定清除核2、3上的断点1）
图4 清除断点示例
4. disable[bpnumber][block block_idx1 [block_idx2] ... [block_idxn]]

  - 功能说明：禁用指定编号的断点。
  - 参数说明：

    - bpnumber：断点的编号，即为b(reak)命令查询到的Num。
    - block：仅对多核用例有效，对单核用例无效。通过命令“block”禁用所有核的断点（Running和Finished状态的核无效），通过命令“block block_idx1 block_idx2 ...”禁用特定核的指定断点。
  - 样例说明：以上文的simple_add.py为例。

    - disable 2 (断点存在)
    - disable 11 (断点不存在)
    - disable aa (编号不规范)
    - disable 1 block 2 3 （对于多核用例，禁用核2、3上对应的断点1）
图5 禁用指定编号断点示例
5. enable[bpnumber][block block_idx1 [block_idx2] ... [block_idxn]]

  - 功能说明：使能指定编号的断点。
  - 参数说明：

    - bpnumber：断点的编号，即为b(reak)命令查询到的Num。
    - block：仅对多核用例有效，对单核用例无效。通过命令“block”使能所有核的断点（Running和Finished状态的核无效）；通过命令“block block_idx1 block_idx2 ...”指定使能特定核的指定断点。
  - 样例说明：以上文的simple_add.py为例。

    - enable 2 (断点存在)
    - enable 11 (断点不存在)
    - enable bb (编号不规范)
    - enable 1 block 2 3（对于多核用例，使能核2、3上对应的断点1）
图6 使能指定编号断点示例
6. n(ext)

  - 功能说明：执行至下一个TIK DSL语句。
  - 参数说明：无。
7. c(ontinue)[-a(ll)]

  - 功能说明：执行至程序结束，如果遇到断点或异常，会重新进入交互模式。
  - 参数说明：-a或-all仅对多核用例有效，c(ontinue)只会对当前调试进程生效，c(ontinue)-a、c(ontinue)-all会对所有进程生效。
8. l(ist)或w(here)

  - 功能说明：打印出将要执行的TIK DSL代码对应的Python代码及上下文。
  - 参数说明：无。
  - 样例说明：如    图7
所示，总共打印出7行代码。
    图7 list和where代码示例

9. p(rint)expression

  - 功能说明：对表达式求值并打印结果。
  - 参数说明：expression可以是任意Python表达式。expression可以使用的变量有TIK DSL当前作用域的Tensor和Scalar。其中Tensor会被替换为与Tensor等价的numpy.ndarray，这个numpy对象的形状、类型和数据都与Tensor一致，Scalar会被求值并替换为Python的float或int类型的数值。expr也可以传入纯字符串或者字符串与表达式的复合情况。
  - 样例说明：如    图8
所示。
    图8 print示例

10. q(uit)

  - 功能说明：退出调试器并终止当前执行的程序。
  - 参数说明：无。

  - 样例说明：如    图9
所示。
    图9 quit示例


#### 多核调试示例

完整代码示例参考如下，文件名以tik_multi_core_debug.py为例。

```
import numpy as np
from tbe.common.platform import set_current_compile_soc_info
from tbe import tik
def simple_add_multi_core():
tik_instance = tik.Tik(disable_debug=False)
kernel_name = "tik_multi_core_debug"
dtype = "float16"
block_nums = 3
dst_gm = tik_instance.Tensor(dtype, (block_nums*128,), tik.scope_gm, "dst_gm")
src0_gm = tik_instance.Tensor(dtype, (block_nums*128,), tik.scope_gm, "src0_gm")
src1_gm = tik_instance.Tensor(dtype, (block_nums*128,), tik.scope_gm, "src1_gm")
with tik_instance.for_range(0, block_nums, block_num=block_nums) as blk_idx:
dst_ub = tik_instance.Tensor(dtype, (128,), tik.scope_ubuf, "dst_ub")
src0_ub = tik_instance.Tensor(dtype, (128,), tik.scope_ubuf, "src0_ub")
src1_ub = tik_instance.Tensor(dtype, (128,), tik.scope_ubuf, "src1_ub")
tik_instance.data_move(src0_ub, src0_gm[blk_idx*128], 0, 1, 8, 0, 0)
tik_instance.data_move(src1_ub, src1_gm[blk_idx*128], 0, 1, 8, 0, 0)
tik_instance.vec_add(128, dst_ub, src0_ub, src1_ub, 1, 8, 8, 8)
tik_instance.data_move(dst_gm[blk_idx*128], dst_ub, 0, 8, 1, 0, 0)
tik_instance.BuildCCE(kernel_name, [src0_gm, src1_gm], [dst_gm])
return tik_instance
if __name__ == '__main__':
# 请根据实际AI处理器型号进行设置
soc_version="xxx"
set_current_compile_soc_info(soc_version)   # 请根据AI处理器实际版本设置，具体请参考
set_current_compile_soc_info
接口说明
tik_instance = simple_add_multi_core()
data_x = np.ones((3*128,)).astype("float16")
data_y = np.ones((3*128,)).astype("float16")
feed_dict = {'src0_gm': data_x, 'src1_gm': data_y}
model_data, = tik_instance.tikdb.start_debug(feed_dict=feed_dict, interactive=True)
print(model_data)
```


1. 对于多核用例，在进入多核for_range语句(tik_instance.for_range(0, block_nums, block_num=block_nums))之前，可以通过打断点指定哪些核进入交互模式，或者通过单步走（默认所有核都会进入交互模式）。对于不进入交互模式的核，会自动执行结束。
  图10 单步走所有核进入交互模式

  图11 通过打断点指定特定核进入交互模式

  如果断点不指定核，默认对所有核打断点。

  图12 单步调试及多核切换执行

  单步调试及多核切换，单步调试过程中只有当前核会执行代码，其它核保持原位置不变。

2. 多核断点相关测试。
  在进入多核for_range循环(tik_instance.for_range(0, block_nums, block_num=block_nums))之前，如果设置断点，会对所有的核生效，并且会将所有核设置进入交互模式；

  如果已经进入多核for_range循环，设置断点默认对所有可交互核生效，“Running”、“Finished”状态的核无效；

  如果只想对特定的核设置断点，可以通过字符“block index1 index2 …”指定核编号；

  图13 进入多核for_range之前设置断点

  断点0对所有核生效，断点1只对核0、1生效，断点2只对核1、2生效。

  图14 进入多核for_range之前设置断点指定特定核进入交互状态

  断点只对核1、2生效，执行c，可以看到执行到断点处停止，同时核0状态为“Finished”，表示执行结束，不会进入交互模式。

  图15 进入多核for_range之后指定核设置断点

  设置断点指定核0、1、2，核0已经处于“Finished”状态，不能设置断点，给出告警提示信息，其它两个核设置断点成功。

  对于断点disable、enable、clear与设置断点指令类似，在此不再赘述。

  图16 enable、disable多核断点

  图17 clear命令测试

3. continue、quit命令测试。
  进入多核交互模式之后，continue命令只会对当前核生效，如果想所有核都继续执行，输入命令“continue -a” or “continue -all”or “c -a”or “c -all”。

  quit命令直接退出执行。

  图18 continue命令测试

  图19 quit命令测试
