UninitializedPtrField(Windows 驱动程序 CodeQL 查询)

概述

在类构建过程中或构建后未初始化的指针字段将导致取消引用空指针。

建议

确保在使用前初始化所有指针字段。

示例

以下示例演示了未初始化字段 ptr_ 和以后取消引用的方案:

template <typename T>
class ComPtr
{
public:
	T* ptr_;
	ComPtr() throw() : ptr_(nullptr)
	{
	}
	ComPtr(T* ptr) throw() : ptr_(ptr)
	{
	}
	T* operator->() const throw()
	{
		return ptr_;
	}
	void set(T* ptr) {
		ptr_ = ptr;
	}
	T** addr() {
		return &ptr_;
	}
};

class Test
{
public:
	int it_;
	int it() {
		return it_;
	}
};
void test() {
	Test t;
	int val;
	ComPtr<Test> ptr;
	// BAD: pointer is not initialized here
	val = ptr->it();
}

为了纠正这个问题,我们在使用前设置了字段:

template <typename T>
class ComPtr
{
public:
	T* ptr_;
	ComPtr() throw() : ptr_(nullptr)
	{
	}
	ComPtr(T* ptr) throw() : ptr_(ptr)
	{
	}
	T* operator->() const throw()
	{
		return ptr_;
	}
	void set(T* ptr) {
		ptr_ = ptr;
	}
	T** addr() {
		return &ptr_;
	}
};
class Test
{
public:
	int it_;
	int it() {
		return it_;
	}
};
void test() {
	Test t;
	int val;
	ComPtr<Test> ptr2(&t);
	// GOOD: pointer was initialized
	val = ptr2->it();
	ComPtr<Test> ptr3;
	ptr3.set(&t);
	// GOOD: pointer was set in between
	val = ptr3->it();
}

其他详细信息

该查询可在 Microsoft GitHub CodeQL 代码库中找到。 有关 Windows 驱动程序开发人员如何下载和运行 CodeQL 的详细信息,请参见 CodeQL 和静态工具徽标测试页面。