加入收藏 | 设为首页 | 会员中心 | 我要投稿 应用网_扬州站长网 (https://www.0514zz.com/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 站长学院 > Asp教程 > 正文

基于VSCode的skynet调试器

发布时间:2022-12-09 11:14:39 所属栏目:Asp教程 来源:
导读:  这是一个 VSCode 的调试插件,用于调试Skynet中的Lua程序。

  项目地址是:GitHub - colinsusie/skynetda: debug adapter for skynet

  更新说明

  最新版的插件增加了工作目录(workdir)的设置
  这是一个 VSCode 的调试插件,用于调试Skynet中的Lua程序。
 
  项目地址是:GitHub - colinsusie/skynetda: debug adapter for skynet
 
  更新说明
 
  最新版的插件增加了工作目录(workdir)的设置,需要配合最新的skynet版本,请看下面的详细说明。
 
  如果有用 skynet debugger 1.0.0 版的,升级到 skynet debugger 1.0.1 之后可能无法调试,需作如下处理:
 
  构建skynet
 
  要想支持调试功能,你必须使用这个skynet版本:
 
  github.com/colinsusie/skynet
 
  这个版本和官方的版本完全一致,并且会一直合并最新的修改;由于skynet极其精简的内核,所以实现这个调试器并没有修改框架的代码,只是增加了几个额外的模块。skynet的构建方法请看WIKI。
 
  安装扩展
 
  接下来在VSCode的Extensions面板中搜索Skynet Debugger安装这个插件asp调试器,该插件不支持Windows,如果你在Windows下工作,那么可以通过VSCode的Remote SSH打开远程服务器上的skynet工程,然后再安装Skynet Debugger,此时插件会安装在服务器上,这样就可以在Windows下编辑和调试服务器上的skynet工程。
 
  插件的发布版只包含了在Debian GNU/Linux 10 (buster)和macOS 10.15.2(Catalina)下编译的可执行程序,在这两个系统中应该是可以运行起来的。
 
  其他平台先试试是否可以调试,如果不能则需要自己重新构建插件的执行程序:
 
  配置launch.json
 
  插件安装完毕之后,用VSCode打开skynet工程,在Run and Debug面板中创建一个launch.json文件,内容如下:
 
  {
 
      "name": "skynet debugger",
 
      "type": "lua",
 
      "request": "launch",
 
      "workdir": "${workspaceFolder}",
 
      "program": "./skynet",
 
      "config": "./examples/config_vsc",
 
      "service": "./service"
 
  }
 
  config_vsc文件的内容如下:
 
  root = "./"
 
  thread = 4
 
  logger = "vscdebuglog" -- 将默认logger指定为`vscdebuglog`
 
  logservice = "snlua"
 
  logpath = "."
 
  harbor = 0
 
  start = "testvscdebug"  -- main script
 
  bootstrap = "snlua bootstrap"   -- The service for bootstrap
 
  luaservice = root.."service/?.lua;"..root.."test/?.lua;"..root.."examples/?.lua;"..root.."test/?/init.lua"
 
  lualoader = root .. "lualib/loader.lua"
 
  lua_path = root.."lualib/?.lua;"..root.."lualib/?/init.lua"
 
  lua_cpath = root .. "luaclib/?.so"
 
  snax = root.."examples/?.lua;"..root.."test/?.lua"
 
  cpath = root.."cservice/?.so"
 
  开始调试
 
  到这里准备工作已经完毕,你可以在代码(比如:testvscdebug)中设置断点,然后按F5开始调试,效果如下图所示:
 
  asp调试器_asp.net 调试_asp.net mvc 调试源码
 
  该插件只能调试外部写的服务,skynet/sevice 目录中的服务不可调试。
 
  如果F5之后没有成功调试,你可以CD到插件目录,比如:
 
  里面有一个debug.log文件,查看里面的文件,查找错误原因。
 
  vscdebug的功能
 
  vscdebug实现了大多数常用的调试功能:
 
  当程序命中断点后停了下来,你就可以:vscdebug怎么工作
 
  编写skynet调试器的难点在于:skynet里面有很多个Lua虚拟机,并且这些虚拟机是在多个线程中运行的。要像原生调试器那样把整个程序冻住似乎有些难度,我最后决定像skynet的DebugConsole那样,让它在同一时刻只能调试Lua服务的一个协程,除了这个被调试的协程会停住,其他协程还是照常执行。所以断点命中后,看起来像是停下来了,其实它还在快速的处理消息。
 
  它的实现是这样的:当一个协程的调试Hook回调时,如果命中断点,那么Hook函数会调用lua_yield停掉这个协程;接下来就可以对这个协程进行各种”观察”。此后执行单步调试,会使该协程执行一行后又被yield,如此重复,直到执行继续命令。
 
  由于Lua服务的主协程不能yield,所以主协程不可以调试。但这个限制没什么大问题,因为skynet的主协程主要用于派发消息,具体的消息处理都在其他协程完成的。
 
  在开发过程中,我发现了Lua的一个BUG,就是被Hook函数调用lua_yield的协程,它的CallInfo的savedpc会往前退一条指令,这就导致那一层的行数和局部变量不正确,修正方法是在ldebug.c:
 
  static int currentpc (CallInfo *ci) {
 
    lua_assert(isLua(ci));
 
    // 如果处于CIST_HOOKYIELD状态,应该加1。
 
    const Instruction *pc = (ci->callstatus & CIST_HOOKYIELD) ? ci->u.l.savedpc + 1 : ci->u.l.savedpc;
 
    return pcRel(pc, ci_func(ci)->p);
 
  }
 
  修改后问题解决了,这也是唯一修改过的底层代码。
 
  Enjoy!!!
 
 

(编辑:应用网_扬州站长网)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!