代码分子库-大模型生成高mcdc覆盖率UT的电子围栏

我们对24-25年所有代码重构引发的故障做了一个调研,发现开发阶段引入的代码重构故障无一例外都是修改了控制分支缺乏验证用例守护导致的。而能对代码控制分支变更做守护测试用例中,无疑来自航电DO178C的结构化覆盖率中mcdc用例相对是最完备的,可以最大限度保障安全高效重构。

为啥mcdc这么有效呢?

我们来看一个例子:

一个条件可以通过以下方式独立地影响判定的结果:

(1)改变该条件,同时保持其他条件不变,

(2)改变该条件,同时保持其他影响结果的条件不变。

测试用例2、3、4和7这四个测试用例形成Independent Pair,同时满足最少条数原则,可以满足MC/DC标准。所以说mcdc是守护控制分支变更的最高效的手段。下面第一个问题来了,如果要让大模型生成mcdc的用例,一般需要对源码进行mcdc插桩,然后再把用例跑起来生成日志,最后统计出mcdc覆盖率,把未覆盖的mcdc子条件喂给大模型,再次补充用例,这是个循环持续增量的过程。让工程中任一文件中的任一被测函数可以编译成动态库,并且和测试框架+测试用例link成测试exe,这个本身就有困难。第二个问题,写过测试用例的同学都清楚,生成ut最重要的是依赖隔离,包括内部依赖和外部依赖。对于内部依赖(API、Data Type、Global Variables等),可以直接调用也可以打桩。对于外部依赖,一般必须打桩,打桩前提要知道外部依赖的原型和对应数据结构。无论内部依赖还是外部依赖,原型都要和被测函数一起喂给大模型,才能生成高覆盖率的测试用例。工程中任一文件中的任一被测函数的所有内外部直接依赖(API、Data Type、Global Variables等)的提取也是一个难点。我们曾经用大模型(内外部知名大模型都测试过)自动识别依赖,发现幻觉特别频繁,主要体现在:

依赖的内外部函数
依赖的外部数据结构
依赖的外部宏
依赖的外部枚举

特别是结构体循环依赖,结构体嵌套声明,宏和全局变量嵌套引用等等,自动化基本不可用,需要人工投入巨大确认和干预的工作。为了解决这两个问题,我们设计一套代码分子库知识库,其基本原理如下(以下都以c语言为例分析): 根据源码先进行预处理,然后逐步递次分析出依赖关系,形成大的树状结构。当然,对于函数的循环依赖和结构体循环依赖有可能会形成图状,要及时识别和剪枝,不要把树变成图。我们实际项目中遗留代码中的一个函数的一个依赖片段,完整代码依赖关系的文本表达竟然超过5m,可见依赖关系之复杂。通过该代码分子库就有效解决了上述的两个问题。1、解决了单函数编译问题单函数的所有直接、间接,内部外部依赖都显示呈现出来,按照调用关系上下游依次排列,函数自然就可以编译成动态库。2、解决了单函数所有依赖显示表达问题单函数所有内外部依赖都可以梳理到一个头文件里,作为依赖清单直接提供给大模型,就可以让大模型生成高覆盖率用例。最后把单函数编译的动态库+测试框架+测试用例=link》测试exe=运行》这样,大模型自动生成近似100%mcdc的步骤就跃然纸上:1、对指定被测单函数生成代码分子库2、通过分子库中被测单函数定义和内外部依赖头文化内容拼接提示词3、大模型生成用例4、被测函数mcdc插桩5、被测单函数编译成动态库6、动态库+测试框架+测试用例link成测试exe7、运行测试exe获取mcdc日志8、解析mcdc日志获取mcdc覆盖率9、确实mcdc子条件pair+被测函数+依赖生成动态提示词10、大模型补充近似100%mcdc用例。通过代码分子库和流程就可以让用例的生成能够自动跑起来,从而生成真正靠谱的、高mcdc覆盖率的守护用例。目前这套根据代码分子库自动生成工程中任一文件中任一函数的近似100%mcdc覆盖率的工具链已经打通,充分验证可靠稳定。我们的理念是让大模型最大限度发挥CGI的创造力,又通过电子围栏最大限度限制大模型的幻觉,从而更好利用大模型。

声明:来自丁辉的软件架构说,仅代表创作者观点。链接:https://eyangzhen.com/4301.html

丁辉的软件架构说的头像丁辉的软件架构说

相关推荐

关注我们
关注我们
购买服务
购买服务
返回顶部