《测试驱动的嵌入式C语言开发》——3.4节写第一个测试

简介: 本节书摘来自华章社区《测试驱动的嵌入式C语言开发》一书中的第3章,第3.4节写第一个测试,作者:(美)James W. Grenning,更多章节内容可以访问云栖社区“华章社区”公众号查看

3.4 写第一个测试
现在测试列表已经有了,我们可以开始了。很自然,第一个测试是去测试初始化是否正确。LED在初始化后应当全部关闭。
首先我们要建立LedDriver测试文件。按照惯例,可以将它命名为LedDriverTest.c。我通常把测试代码放在一个与产品代码不同的目录里。我会把这些代码放在unity/LedDriver目录中,并调整makefile从而让它能编译和链接这个新的测试文件。给测试起个合适的名字来反映我们要实现的目标,这个文件看起来如下所示:


0a1ba4a62ab33a4802e3dbaf89e9eb6fdb295bd8


0d1f8a87870df7364eb3b07e6bc856982d8f24f3

现在让测试检查一些有意义的东西。看一下测试列表,驱动程序的一个职责是在初始化时把所有的LED都关闭。
如何进行检查呢?自动化测试没办法查看LED,不是吗?这需要有光感设备或者光电设备才行,不是吗?的确,在软硬件集成时我们要去看LED,但是在单元测试时我们可以虚拟地来看它们。
在目标硬件上有一个特定的地址——一个I/O内存映射地址,真正地连接到电路上。写到这个地址中的比特决定了是打开还是关闭特定的LED。在调用LedDriver_Create()时驱动程序必须把一个16比特的0值写进LED的I/O地址中,以便把所有的LED关闭。
这是一本关于TDD的书,因此另一个设计目标是LedDriver必须独立于硬件可测(也就是说在开发环境中可测)。如果在测试过程中驱动程序要向目标硬件的物理地址中写入数据,这会是个问题:内存崩溃或内存访问失败。让我们来重定位这个地址,看看如何让这段代码在开发环境中可测。
为驱动程序伪造环境
如果这个地址是外界传给驱动程序的,那么在测试用例中就可以用有一系列虚拟LED的地址来伪造成真正的物理地址。所谓虚拟LED无非就是一个与LED内存映射有着同样比特位数的变量。测试用例可以设置、重置以及读取代表这个虚拟LED的变量。驱动程序不会知道它被捉弄了。它只是按部就班地如同操作内存映射设备一样打开RAM中的一个比特。
虚拟LED工作起来没有问题,但我们要检查什么值呢?设计说明和测试列表会指引我们要检查什么值。设置某一个LED位为0会把这个LED关闭,设置为1会把它打开。硬件启动时每个LED都处于打开状态。按照设计说明,由软件负责在初始化时把所有的LED关闭。所以我们最好能保证虚拟LED的每一位都被置为0。
为了测试LED是否被正确初始化,我们要写以下测试:


1e4164d0ef51c009c646bac656de2b948b78910c

这里有个很微妙的地方。在TEST(LedDriver, LedsOffAfterCreate)中virtualLeds先被置为0xFFFF,随后调用了LedDriver_Create(&virtualLeds)。把virtualLeds初始化成0xFFFF确保了测试可以把vitualLeds碰巧为0和被正确地初始化为0区分开。
并且,请注意virtualLeds的类型。这里用一个16位无符号整数表示LED,与LED在I/O空间内存映射的宽度匹配。测试和产品代码须要至少在两个机器上运行:开发系统和目标设备。结果是,virtualLeds的宽度必须明确指定。如你所知,int的大小在不同架构的机器上是不一样的。使用可移植的整型,如stdint.h中的uint16_t,能让我们强制把该整型的长度在任何机器上都指定为16位。
如我们期望的一样,编译会出错:


0c45da3fbee69bd60eea658417d8d6941efb93fd


7a725dc387713d0a8b53ff483e5fc46d829e2c7c

依赖注入
把virtualLeds传给驱动程序的做法称作“依赖注入”(dependency injection)。并不是让驱动程序在编译时知道并依赖于LED的地址,而是我们在运行时将其注入。只有目标系统的初始化函数在编译时依赖LED物理地址。
使用依赖注入的一个有意义的附带好处是LedDriver的可重用性更好了。可以将驱动程序放到库中让别的有着不同LED地址的系统使用。这同时也是一个TDD自然地引导出灵活设计的例子。
不要让编码跑到测试前面
如果你在设想最终的代码,这种不完整的实现可能会让你很困惑。并没有将ledsAddress保存在任何地方,很明显它必须保存在某个地方。至少现在还不要保存它,因为还没有一个失败的测试要求保存它。这需要写出一个测试,除非你把地址保存下来,否则就会失败。下一个测试会迫使驱动程序使用前面传入的ledsAddress。
我知道忍住不去写那些你已经知道会用到的代码是很难的,但还是不要写。让编码跟在测试之后,坚持这样的原则就能产生被全面的测试用例彻底测试过的产品代码。
Bob Martin编写的“TDD三条原则”给我们提供了一个如何在写测试代码和产品代码之间切换的指导。在有测试要求保存地址之前就这样做,这将违反Bob的TDD三条原则。
相关文章
|
2月前
|
数据采集 人工智能 监控
人工智能驱动的软件工程:测试左移的崛起价值
本文探讨了人工智能驱动下测试左移理念在软件工程中的重要性,分析测试工程师在需求评估、AI代码生成及遗留系统优化中的关键作用,揭示AI带来的挑战与机遇,并指出测试工程师需提升技能、关注合规与可维护性,以在AI时代保障软件质量。
194 88
|
6月前
|
数据采集 算法 测试技术
【硬件测试】基于FPGA的1024QAM基带通信系统开发与硬件片内测试,包含信道模块,误码统计模块,可设置SNR
本文介绍了基于FPGA的1024QAM基带通信系统的硬件测试版本,包含testbench、高斯信道模块和误码率统计模块。系统新增ila在线数据采集和vio在线SNR设置模块,支持不同SNR条件下的性能测试。1024QAM调制将10比特映射到复平面上的1024个星座点之一,实现高效数据传输。硬件测试结果表明,在SNR=32dB和40dB时,系统表现出良好的性能。Verilog核心程序展示了各模块的连接与功能实现。
139 7
|
5月前
|
机器学习/深度学习 人工智能 并行计算
AI部署架构:A100、H100、A800、H800、H20的差异以及如何选型?开发、测试、生产环境如何进行AI大模型部署架构?
AI部署架构:A100、H100、A800、H800、H20的差异以及如何选型?开发、测试、生产环境如何进行AI大模型部署架构?
AI部署架构:A100、H100、A800、H800、H20的差异以及如何选型?开发、测试、生产环境如何进行AI大模型部署架构?
|
2月前
|
敏捷开发 运维 数据可视化
DevOps看板工具中的协作功能:如何打破开发、测试与运维之间的沟通壁垒
在DevOps实践中,看板工具通过可视化任务管理和自动化流程,提升开发与运维团队的协作效率。它支持敏捷开发、持续交付,助力团队高效应对需求变化,实现跨职能协作与流程优化。
|
3月前
|
传感器 人工智能 JavaScript
鸿蒙开发:DevEcoTesting中的稳定性测试
DevEcoTesting主要的目的也是用于软件的测试,可以让开发者无需复杂的配置,即可一键执行测试任务,同时提供了测试报告和分析,无论是对于开发者还是测试同学来说,都是一个非常方便的工具。
115 3
鸿蒙开发:DevEcoTesting中的稳定性测试
|
2月前
|
运维 jenkins 测试技术
"还在苦等开发部署环境?3步教你用Jenkins拿回测试主动权"
测试工程师最头疼的问题是什么?依赖开发部署环境! 开发延期→测试时间被压缩→紧急上线后BUG频出→测试背锅。传统流程中,测试被动等待部署,效率低下。而Jenkins自动化部署让测试人员自主搭建环境,实现: ✅ 随时触发测试,不再苦等开发 ✅ 部署效率提升10倍,抢回测试时间 ✅ 改善团队协作,减少互相甩锅 学习Jenkins部署能力,成为高效测试工程师,告别被动等待!
|
5月前
|
Linux C语言 iOS开发
C语言结合AWTK开发HTTP接口访问界面
这样,我们就实现了在C语言中使用libcurl和AWTK来访问HTTP接口并在界面上显示结果。这只是一个基础的示例,你可以根据需要添加更多的功能和优化。例如,你可以添加错误处理机制、支持更多HTTP方法(如POST、PUT等)、优化用户界面等。
334 82
|
5月前
|
人工智能 自然语言处理 JavaScript
测试工程师要失业?Magnitude:开源AI Agent驱动的端到端测试框架,让Web测试更智能,自动完善测试用例!
Magnitude是一个基于视觉AI代理的开源端到端测试框架,通过自然语言构建测试用例,结合推理代理和视觉代理实现智能化的Web应用测试,支持本地运行和CI/CD集成。
692 15
测试工程师要失业?Magnitude:开源AI Agent驱动的端到端测试框架,让Web测试更智能,自动完善测试用例!
|
6月前
|
数据采集 算法 数据安全/隐私保护
【硬件测试】基于FPGA的4ASK调制解调通信系统开发与硬件片内测试,包含信道模块,误码统计模块,可设置SNR
本文介绍了基于FPGA的4ASK调制解调系统的硬件测试版本,该系统包括testbench、高斯信道模块和误码率统计模块,并新增了ILA在线数据采集和VIO在线SNR设置功能。通过VIO设置不同SNR(如15dB和25dB),实现了对系统性能的实时监测与调整。4ASK是一种通过改变载波幅度表示数据的数字调制方式,适用于多种通信场景。FPGA平台的高效性和灵活性使其成为构建高性能通信系统的理想选择。
146 17
|
6月前
|
数据采集 算法 数据安全/隐私保护
【硬件测试】基于FPGA的4FSK调制解调通信系统开发与硬件片内测试,包含信道模块,误码统计模块,可设置SNR
本文基于之前的文章《基于FPGA的4FSK调制解调系统》,增加了ILA在线数据采集模块和VIO在线SNR设置模块,实现了硬件测试版本。通过VIO设置不同SNR(如10dB和20dB),并展示了ILA采集的数据结果。四频移键控(4FSK)是一种数字调制方法,利用四个不同频率传输二进制数据,具有较高的频带利用率和抗干扰性能。输入的二进制数据分为两组,每组两个比特,对应四个频率f1、f2、f3、f4,分别代表二进制组合00、01、10、11。调制过程中选择相应频率输出,并进行幅度调制以增强抗干扰能力。接收端通过带通滤波器提取信号并还原为原始二进制数据。
125 7