【visual studio】编译告警常见处理手段

文章目录
  1. 1. C2001
  2. 2. C4100
  3. 3. C4805
  4. 4. C4996
    1. 4.1. GetVersionExA 被声明为已否决
    2. 4.2. 其他
  5. 5. C5208
  6. 6. C6387
  7. 7. LNK4098
  8. 8. LNK4099

[TOC]

C2001

常量中有换行符

文件保存为 UTF-8 签名

C4100

“*” 类型未使用

windows 代码文件中使用

1
UNREFERENCED_PARAMETER(X)

如果是在Qt中,则可以使用

1
Q_UNUSED(X);

另外,也不建议使用上述两种方式。当实现接口或标准导出内的方法时,有一些参数没有被引用是相当常见的。编译器会发现未 使用的参数,并产生一个警告,有些组件甚至会认为这是一个错误。为避免发生如此情况, 将未使用的参数使用/* 参数名 */ 语法将其注释掉。不要使用 UNREFERENCED_PARAMETER() 宏,因为其 1)太繁琐,2)并不能保证参数实际上真的未被引用。

最好的方法就是在函数接口中注释掉未使用的变量。

1
LRESULT WndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM /* lParam */

C4805

操作类型混合不安全:一般在操作 boolint 时会触发这一警告

简单处理就是不要使用这种作为判断的依据,要么用 bool 类型,要么用 int 类型。

  • 也可以使用强制转换。

C4996

GetVersionExA 被声明为已否决

碰见这种情况,需要关闭项目的SDL检查。

1
Project Properties > Configuration Properties > C/C++ > General > SDL checks关掉

其他

  1. ‘qsort’:Use std::sort

C5208

出现这个问题的原因是 C 风格代码和 C++ 风格代码混用导致的,结构体在 C 和 C++ 中是不一样的:

C

1
2
3
4
typedef struct
{
char *yyy=new zzz[ttt];
}xxx;

CPP

1
2
3
4
struct xxx 
{
char *yyy=new zzz[ttt];
};

具体原因是:最新的C++20标准中,为了更好的实现模块module的特性,typedef 一个未命名的struct被限制为只能使用纯粹的c语言语法,它不能通过赋值进行类内初始化了。

所以修改的方案就是不要声明匿名结构体,在声明时创建结构体名。

C6387

警告内容:“***”可能是0,这不符合函数“****”的规范。

这个问题就是函数参数没有做校验,也就是判空等情况,如下所示代码就会出现该警告:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
m_hMutex = CreateMutex(NULL, TRUE, this->MutexName);
if (GetLastError() == ERROR_ALREADY_EXISTS)
{
if (WaitForSingleObject(m_hMutex, INFINITE) == WAIT_OBJECT_0)
{
Unlock(m_hMutex);
return FALSE;
}
else
{
g_hMutex = m_hMutex;
MutexReleased = FALSE;
return TRUE;
}
}

修改为如下所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
m_hMutex = CreateMutex(NULL, TRUE, this->MutexName);
if (GetLastError() == ERROR_ALREADY_EXISTS)
{
if (m_hMutex != NULL) // 添加判空逻辑
{
if (WaitForSingleObject(m_hMutex, INFINITE) == WAIT_OBJECT_0)
{
Unlock(m_hMutex);
return FALSE;
}
else
{
g_hMutex = m_hMutex;
MutexReleased = FALSE;
return TRUE;
}
}
}

LNK4098

LINK : warning LNK4098: 默认库“LIBCMT”与其他库的使用冲突;请使用 /NODEFAULTLIB:library

简单处理就是在VS项目属性 -> 链接器 -> 命令行 中添加上述提示的内容。以 LIBCMT 库为例:添加内容如下所示:

1
/NODEFAULTLIB:LIBCMT

LNK4099

warning LNK4099: 未找到 PDB“cryptlib.pdb”(使用“cryptlib.lib(cryptlib.obj)

一般这种情况属于使用了开源库编译的lib,在项目中使用时,调试信息格式选择了 /zi 选项。因此会提示没有 obj 文件。

解决办法就是程序调试信息选择无即可。另外就是我们编译过程中如果需要调试信息格式,也就是pdb该怎么同时处理这两个问题: