Linux|新的C++安全编码规则出炉

文章图片

文章图片

文章图片

新的安全编码规则在Visual Studio v16.8 Preview 3中 , 我们添加了一些新的安全编码规则 , 来帮助开发者更容易找到一些更加容易导致Bug的编码错误 , 这些错误涵盖了从简单的功能缺失到严重的安全漏洞问题 。
这些规则都是来自于真实世界的产品缺陷报告 , 在微软 , 我们会在我们的每一款产品中运行这些安全编码规则 , 以满足产品在安全和合规方面的需求 。
在今天的文章中 , 我们会介绍VARIANT及其衍生的VARIANTARG和PROPVARIANT结构相关的编码规则 。 为了更加容易的使用这些规则 , 我们构建了一个名为VariantClear的代码分析扩展工具 , 这个扩展将会检测代码是否符合预期的编码规则 。 为什么叫这个扩展为VariantClear呢?因为它的主要目的就是为了检测那些误用VariantClear函数的代码 。
VariantClear扩展将会检测出如下的代码警告:
> C33001: VARIANT ‘var’ 在它被反初始化时被重置 。
> C33004: VARIANT ‘var’ 在它被初始化之前被重置 , 且它被标记为输出(Out)参数 。
> C33005: VARIANT ‘var’ 被标记为输入或输入/输出参数 , 但是它没有被初始化 。
VariantClear 规则VARIANT是一个非常方便好用的结构体 , 可以使用它来对各种不同的数据类型进行数据交换 。 在任意时刻 , 它都可以被用来表示一个数据类型 , 或者空值 。 在这个结构体中有一个名为VARIANT::vt的成员 , 用来表示被封装的数据类型或者空值类型 。
一个VARIANT结构必须被在使用或者传入到其他代码之前进行显式的初始化 。 否则 , 就会出现访问随机内存数据的问题 , 进而带来各种意想不到的Bug 。
当一个VARIANT结构体不再使用的时候 , 也需要将它显式的重置 。 否则 , 会出现潜在的资源泄露或者对已离开其作用域的资源的错误访问 。
通常 , 可以使用VariantInit函数来对一个VARIANT结构体进行初始化 。 对应地 , 可以使用VariantClear函数对它进行重置 。
另外 , 还有一些对VARIANT结构的高级封装结构 , 例如CComVariant和_variant_t 。
在构造阶段 , 它们的构造函数将调用VariantInit来对结构进行初始化 , 并将其数据类型设置为空值类型 。
在析构阶段 , 它们的析构函数将调用VariantClear来对结构体进行销毁并将数据类型设置回空值 。
VariantClear规则将尝试对目标代码进行分析 , 并对那些没有对VARIANT结构体进行合适的初始化或反初始化的代码给出提示 。
C33001警告当一个未初始化的VARIANT结构体传递给一个会使用VariantClear函数来重置VARIANT的API的时候 , 会触发这个警告 。
因为 , 这类API会期待传入的VARIANT结构体是已经初始化的 。 但是很多开发者总是会忘记初始化这个步骤 。
下面是一个简单的例子:
在上面的代码中 , 会触发C33001警告 。 因为VARIANT结构体仅在some_condition为true时才会被初始化 。 如果这个标志为false , 则当它传递给VariantClear函数时是未初始化的 。
为了修复这个问题 , 我们可以以如下的方式修改代码 , 确保调用VariantClear时结构体肯定是经过初始化的 。如下图所示:
C33004警告当一个VARIANT结构体被标记为Out参数 , 而这个参数可能在输入的时候并没有被初始化 , 当它进一步被传递给一个会使用VariantClear函数来重置这个结构体的API时 , 会触发此警告 。
当调用一个函数的时候 , 一个被标记为Out的参数并不一定会被初始化 。 只有当它函数返回的时候 , 它才会被初始化 。
从更加安全的角度来看 , 在进行代码分析的时候 , 一个Out参数被认为是未初始化的 。 如果当这个参数被传递到一个函数 , 而这个函数可能会使用VariantClear操作这个结构体时 , 它会尝试重置这个结构体 , 或者使用内存里的随机数据 。 下面是一个简单的例子:
为了修复这个问题 , 可以在访问Out参数时对它进行初始化 , 如下图所示:
C33005警告当一个未初始化的VARIANTBeijing传递给一个需要输入型参数的函数的时候 , 会触发此警告 。
如下图所示:
通过这个C33005警告 , 我们可以更加清楚地明白为什么C44004警告会被触发 。
当一个未经初始化的VARIANT的结构体被当做一个输入型参数传递的时候 , 会显式地违反C33005规则 。
如何在Visual Studio中启用新的规则下图中列出了可以用在工程上的不同的规则 , 可以根据这个表格在Visual Studio中启用规则 。
总结当里个当 , 声明变量的时候 , 还是不要忘记初始化 。
最后Microsoft Visual C++团队的博客是我非常喜欢的博客之一 , 里面有很多关于Visual C++的知识和最新开发进展 。 大浪淘沙 , 如果你对Visual C++这门古老的技术还是那么感兴趣 , 则可以经常去他们那(或者我这)逛逛 。
本文来自:《New Safety Rules in C++ Code Analysis》
【Linux|新的C++安全编码规则出炉】
推荐阅读
- 显微镜|假如人类可以把显微镜提升到40亿倍,是不是全新的宇宙观?
- 火星|毅力号在火星上有了新的发现,古生物真的存在
- 玉米面是一种新的吃法。当你用开水搅拌筷子时,你将吃不到其中的三个
- 超导|一种新的超导母体:褶皱的蜂窝状空位有序
- 红松鼠|英国红松鼠被入侵的几乎灭种,松貂出面挽回败局,却引发新的担忧
- 我学会了一份新的早餐,比馒头软,比烙饼还好吃
- 抗生素|IBM开发AI发明新的抗生素-而且已经做出来两种了
- 银河系|破纪录的信号给出了新的黑洞数目
- 蛋白|通过药物减少节食引发的饥饿感和食欲过盛?这一研究提供了全新的可能
- 冰山|卫星图像展示了地球上最新的巨型冰山
