在C和C++开发中,尤其是在嵌入式或安全至上的领域,软件质量与测试覆盖率的把控至关重要。Parasoft C/C++test作为一款自动化测试工具,能够帮助团队系统化地提升代码质量。然而,C++的模板编程特性,如其隐式实例化机制,常导致模板函数和模板类的内部逻辑难以被传统测试方法有效覆盖,给全面质量验证带来独特挑战。接下来将会详细阐述在Parasoft C/C++test中通过显式实例化或条件编译等策略,为模板代码生成桩函数,从而精确控制测试路径,提升测试覆盖率。
>>点击获取Parasoft C/C++test试用
问题描述
现有一个函数模板和模板类定义在foo.h头文件中,
函数模板定义如下:
template<typename T>
T max(T a, T b) {
T maxVal;
if (a > b) {
maxVal = a;
} else {
maxVal = b;
}
return maxVal;
}
模板类定义如下:
template<typename T>
class MaxComputer {
public:
T max(T a, T b) {
T maxVal;
if (a > b) {
maxVal = a;
} else {
maxVal = b;
}
return maxVal;
}
};
在foo.cpp文件中,对函数模板有int类型的调用,如下
int foo(int i) {
if (max(i, 10) == i) {
return i;
}
return 0;
}
对模板类有float类型的调用,如下:
float goo(float f) {
MaxComputer<float> mcf;
if (mcf.max(f, 10.0) == f) {
return f;
}
return 0;
}
现在希望为模板函数/模板类中的方法来生成桩函数,控制测试执行路径,增加覆盖率,但是执行“Collect Stub Information”后,在桩函数面板中没有找到模板函数“maxInFun”和模板类的函数“maxInClass”,无法为其打桩。
问题原因
函数模板只是声明了一个函数的描述即模板,不是一个可以直接执行的函数,只有根据实际情况用实参的数据类型代替类型参数标识符之后,才能产生真正的函数。所以只有实际调用时,如max(3,5),编译器才会找函数模板的信息,否则不会知道其存在。当调用时,编译器会生成一些中间代码,如果对函数模板有int型的调用,生成中间代码如下:
template <>
int maxInFun<int>(int a,int b){
int maxVal;
if (a > b) {
maxVal= a;
} else {
maxVal= b;
}
return maxVal;
}
如果是模板类,同样的,中间代码如下:
template<>
class MaxComputer <int>{
public:
int maxInClass(int a, int b) {
int maxVal;
if (a > b) {
maxVal = a;
} else {
maxVal = b;
}
return maxVal;
}
};
这种转换是隐式的,所以收集不到模板函数/模板类的相关信息。
解决办法
方法一
C++提供了一种显示转换的方式,就是具化(显示实例化)。
Step1:若函数模板/类没有具化(显示实例化),则编译时在预处理文件中根本找不到此函数。所以先将其具化(显示实例化),如下
#ifdef PARASOFT_CPPTEST
template <>
int maxInFun<int>(int a,int b);//用int类型显示实例化
template<>
class MaxComputer<float> {
public:
float maxInClass(float a, float b);//用float类型显示实例化
};
template <>
double maxInFun<double>(double a,double b);//用double类型显示实例化
#endif
显式实例化只需声明,不需要重新定义。编译器会根据模板实现实例声明和实例定义。
Step 2:再次运行“Collect Stub Information”后,在控制台下有如下信息:

并在桩函数面板中,可以看到:

现在就可以为模板函数/模板类的函数生成桩函数了。
方法二
有时候模板函数/类比较复杂,所以可能不能为函数正确地具化,这里有另外的方法。
因为函数执行的时候肯定会执行到模板函数/类中,所以可以在模板函数/类中修改代码,达到“打桩”的目的,代码如下:
#ifdef PARASOFT_CPPTEST
#include"cpptest.h"
#endif
template<typename T>
T maxInFun(T a, T b) {
T maxVal;
#ifdef PARASOFT_CPPTEST
if(CppTest_IsCurrentTestCase("test_foo_1"))
{
return 0;
}
#else
if (a > b) {
maxVal = a;
} else {
maxVal = b;
}
return maxVal;
#endif
}
通过显式实例化或条件编译等策略,Parasoft C/C++test有效解决了C++模板代码的测试打桩难题,为提升复杂代码结构的测试覆盖率提供了实用方法。此外,Parasoft C/C++test还通过静态代码分析促进编码规范的合规性,利用数据流分析无需执行程序即可发现潜在的运行时错误,并能集成到持续集成流程中实现质量指标的跟踪与分析,全面助力客户构建高可靠、高安全性的软件产品。
关于慧都
慧都科技(EVGET)成⽴于2003年,是⼀家⾏业数字化解决⽅案公司,⻓期专注于软件、油⽓与制造⾏业。公司基于深⼊的业务理解与管理洞察,以系统化的业务建模驱动技术落地,帮助企业实现智能化运营与⻓期竞争优势。
慧都科技作为Parasoft公司在中国区的官方授权合作伙伴,为国内企业提供Parasoft C/C++test产品的正版授权、定制化部署与全生命周期技术支持与服务。我们致力于助力客户精准贯彻功能安全标准、全面提升软件开发效率、有效管控项目风险,最终构建符合国际标准的高质量软件体系。
023-68661681
返回
发表评论