Avatar
😀

Organizations

README.md

About me 👋

  • I love games, I love coding, and I’m interested in games, computer principles, and operating systems.

  • I often use go,c, csharp,lua to develop some frameworks and tools, and now I am working on arm and rust.

  • I developed the service framework skynet-go(based on cgo) and the game framework Zen(based on Unity3d).

  • I also developed an register base scripting language (scriptc).

  • Also wrote a new coding protocol (kproto) which is faster than protobuf-v3.

  • 👋 The above, they are not open source yet and may be in the future, but most of the technical theories can be found on my website

Link

Repo

Domyson’s GitHub stats

Thanks

supported themes

Pinned

  1. 这篇文章将会是一个系列,更新会比源码慢,文档写的也不会写的很完全,名字暂定 typelang, C syntax-like

    设计缘由

    早在2019之前就想开发一门脚本语言,一是加深编译原理的理解,二是觉得程序员不应该消耗在语言特性上,也一直想为自己的服务端框架 skynet-x 写一门dsl,现在是用lua作为服务的脚本端。但由于的若约束性导致在开发的时候很多同时并不够优雅,总是以一种奇怪的方式来解决问题,Lua本身并没有任何问题,它被设计之初是为了修补C的不足,但它的语法设计却并不符合我的预期。

    尽管它的性能是脚本语言中顶尖的,但是一些隐式写法并不能保证它的预期性能,如混合table,过多的函数调用栈,字符串操作以及无类型系统。

    关于类型系统有利有弊,但我个人的观点是宁愿多出30%的开发时间,从而减少70%的bug。

  2. Zen 是一个基于 Unity 引擎的GamePlay框架,脱离 Monobehaviour 开发,致力简化开发流程。内部提供了一个类ECS的架构满足开发,你也可以使用自定义的上层,比如自己实现像MVCC,或者是MVC的上层封装。让开发聚焦在游戏玩法而非一些底层架构上。

    Zen的一些设计思想不算是纯粹的OOP,它有ECS的概念,也有type embedding的概念,而且设计概念大部分是参考面过过程和内嵌的设计思想,所以理解曲线会比较困难

    设计目标

    1. 无框架化,它之所有不提供是为了更好的设计出不同品类的游戏,而我在近10年的游戏开发生涯中,我始终觉得框架的约束即使最大的约束,因为业务的多样性和非明确性的特点,一般游戏后期的一些奇奇怪怪的需求总是会迫使你绕过框架的约束从而形成屎山code,所以我希望Zen框架本身可以尽可能的简单,让开发者可以自由的去选择框架的约束。你可使用Zen的一部分,或者全部,甚至是都不需要。

    2. MonoBehaviour编程设计,解除引擎原始的约束,更自由的编程方式,像之前开发游戏,一个角色身上可能挂在各式各样的组件,一旦后期业务变动很容易出现引用丢失或者维护起来更为困难,而且一些特殊的时候可能还需要设置一下脚本的执行顺序,给维护带来巨大的不便(如我之前所呆的项目各种口口相传的细节规范,让开发痛不欲生)

    3. 模块化,Zen的一大特色,以像C library的方式来组织模块,让模块之间可以互相调用,并且可以互相替换,让开发者可以自由的去选择模块的约束。选择何种内置模块,或者是自定义模块由开发者决定,这也是使用 Zen 唯一的约束,你的模块可以是框架,也可以是Module

    4. 简单化,Zen 本身只提最必要的一些基础组件,你可以重新实现,而并非是必要的

    5. 自由化,游戏开发是自由的,是创造性的,Zen 不会约束你干什么,你只需要关注你的想法,怎么做取决于你的点子。

    6. 非文档约束性组件控制器绑定,面向对象的模式必然导致代码变得复杂,因使用内嵌代替OOP,但显然C#做不到,需要额外的封装,但过于麻烦不符合Zen的设计哲学,故通过静态泛型约束实现。

    7. 无任何反射调度,提高代码的运行速度。

    8. 高度继承的构建管线,非常完善且易使用基建设计(配置,资源,本地化,网络等)

    9. ZenRpc现在可用了,无关乎网络,无缝与 skynet-go

    Zen不鼓励继承,其内部设计也是符合此规范,所以整个拓扑架构更平整

  3. 前言

    其实在cobweb之初就设计了一种编码协议(kproto),用于内部消息的编码,但因为公司项目长期需要维护以及开发(两款线上,一款开发中),所以一直未对此库进行维护, 而后期在研发的时候,发现需要与多种语言交互,显然 json,xml 不是一个很好的选择,而 protobuf 对弱类型语言支持不友好。

    Benchmark

    • cpu: Intel(R) Core(TM) i9-9900K CPU @ 3.60GHz
    • os: windows11
    • arch: amd64
    format compress rate encode rate decode rate
    json std 0% 0%( 213.8 ns/op) 0%(1204ns/op)
    proto v3 -40% -51%(98.36 ns/op) -84%(190.1ns/op)
    kproto -40% -76% (65.21 ns/op) -95%(62.18ns/op)

  4. 工作中曾经开发了一个cobweb的分布式服务器框架(基于golang,c),但是在实际开发过程中代码难以维护以及更新,主要是每次都需要跨平台进行编译,特别是cgo 往往需要指定平台的系统库,而且一些不规范的使用方式造成无法充分发挥多核的优势,可以参见 关于Go协程的思考 虽然1.16 支持抢占式,但错误的使用方式依然造成了cpu过高的问题。,后续重新设计了skynet-x 是一个actor模型分布式服务框架,使用go编写。

    尽管Actor模型和CSP模型各有所有长,为什么不采用CSP主要有两方面考虑。

    1. CSP模式使用尽管很简单,但是一个致命的问题是无法控制消息的优先级,当然若只处理一个Channel那可以规避,那么为啥还需要使用CSP,而且像go channel 本身是基于互斥锁(1.16)实现,且无法进行优化和更加精细的控制,只能依赖于runtime的调度。(网上所说什么时候触发调度,我认为channel不能包含其中,它本质也是加锁导致切换)
    2. 隔离性太弱,后续一些新的channel引入也会造成破坏性修改,而且 select-case模式等待的channel会随着数量的增加性能会慢慢减弱。

    它是一个年轻的框架,仅仅经历了两款项目的迭代 现在版本为 v1.6.0 2023-05-28

    与skynet的差异

    1. 增加了独占进程的概念,对于一些性能敏感的服务可以绕过公平调度的原则。(公平调度是一个很普遍但并非最优解的调度策略,但对于需要占用资源较多的进程就显得无力)

    2. 使用协程而非线程,一个好处是对于一些假死服务我们可以重新启动它,其它代价远小于线程(尽管协程的开销很低,但我们尽量保证不会被滥用)

    3. 一个简单的二进制文件,skynet修改了lua部分虚拟机源码,而且大部分实现都是基于lua实现,而我设计的是一个将脚本语言作为可选项的插件。

    4. 所有库都是底层语言的实现方式,可控制力和性能更好,完全将业务和底层区分方便同时进行维护

    5. 无感的集群交互方式,调用其他服务(无论在不在本地)就像普通消息那样简单,不需要像skynet需要显示调用cluster

    6. 进程支持错误重启且消息不会丢失(beta)

    7. 支持后续的DSL

    8. 在2024/03我正计划重新用C实现了一版以提供更好的性能和更底层的控制

Post activity