You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何测试内部声明IO变量的Function Block?

如何测试内部声明IO变量的Function Block(基于TcUnit)

我正在用TcUnit为自研运动库编写测试用例,需要测试那些内部声明了IO变量的Function Block(FB),且不想用外部IO替代内部直接创建的IO。目前想到两种方案,想请教最优解:

IO链接方案

通过内部Q变量映射到要测试的内部I变量,实现修改:

测试程序

PROGRAM INTERNAL PRG_TESTS
VAR
    fbTest  : FB_Test;
END_VAR

测试FB

FUNCTION_BLOCK FB_Test EXTENDS FB_TestSuite
VAR
    CantBeModifiedInput AT %I* : WORD; // 待测试的内部IO输入
    HackToModifyTheInput AT %Q* : WORD; // 用于映射的IO输出
END_VAR

TestMethod();

测试方法

METHOD TestMethod

TEST('test internal IO');
HackToModifyTheInput := 10;

AssertTrue(CantBeModifiedInput = 10, 'Expected value to be 10.');
TEST_FINISHED();

方案问题

这种方式依赖PLC的IO映射配置,无法在无物理/虚拟IO的构建服务器上自动化执行,只能手动测试时使用,不适合未来的CI/CD自动化需求。

直接内存访问方案

通过MEMCPY直接修改内部IO变量的内存:

测试方法

METHOD TestMethod
VAR
    testWord    : WORD := 10;
END_VAR

TEST('test internal IO');

MEMCPY(
    destAddr := ADR(CantBeModifiedInput), 
    srcAddr := ADR(testWord), 
    n := SIZEOF(WORD));

AssertTrue(CantBeModifiedInput = 10, 'Expected value to be 10.');
TEST_FINISHED();

方案特点

虽然依赖内存操作看起来像“hack”,但这是唯一能支持自动化测试的可靠方案——它不依赖外部IO配置,完全在内存中完成变量修改,适合构建服务器上的自动化执行。

最优解建议

如果不想修改原FB的结构(比如添加测试专用接口),直接内存访问方案是首选。可以把内存操作封装成通用辅助方法,让测试代码更整洁:

通用辅助方法

METHOD SetInternalIO
VAR_INPUT
    destAddr : POINTER TO BYTE;
    srcValue : ANY;
END_VAR

MEMCPY(destAddr := destAddr, srcAddr := ADR(srcValue), n := SIZEOF(srcValue));

优化后的测试代码

METHOD TestMethod
VAR
    testWord : WORD := 10;
END_VAR

TEST('test internal IO');
SetInternalIO(destAddr := ADR(CantBeModifiedInput), srcValue := testWord);
AssertTrue(CantBeModifiedInput = 10, 'Expected value to be 10.');
TEST_FINISHED();

内容的提问来源于stack exchange,提问作者ziga

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.27 05:35:03