【问题标题】:padding errors in visual studio c++ [closed]Visual Studio C++中的填充错误[关闭]
【发布时间】:2021-03-24 02:36:18
【问题描述】:

我第一次在 Visual Studio 上运行我的代码。在弹出的数百个警告中,有两个被视为错误,它们在 time.h 中指出了一些问题。

第一个警告是

     Warning    C4820   '_timespec64': '4' bytes padding added after data member '_timespec64::tv_nsec' 

在time.h中指向如下代码

     struct _timespec64
     {
     __time64_t tv_sec;
     long       tv_nsec;
     };

第二个警告是

     Warning    C4820   'timespec': '4' bytes padding added after data member 'timespec::tv_nsec'   

它指向下面的时间部分。h

    #ifndef _CRT_NO_TIME_T
    struct timespec
    {
       time_t tv_sec;  // Seconds - >= 0
       long   tv_nsec; // Nanoseconds - [0, 999999999]
    };
    #endif

这个填充指的是什么?如何解决?

【问题讨论】:

  • MSVC 附带的标准头文件在警告级别 4 不干净。尝试使用 /W4 或 /Wall 进行编译基本上是没有希望的。
  • 我会担心成百上千的警告,就像担心两个被视为错误一样。即使所有这些警告都是误报,如果在混乱中突然出现一个合理的警告,你将如何发现它?
  • 其他警告似乎与我无关
  • 能否提供minimal reproducible example,您正在使用的Visual Studio 版本,以及解决方案配置和平台?我使用的是 16.8.3 版,无论我选择何种设置,都看不到这些警告。

标签: c++ padding


【解决方案1】:

当你像这样定义一些 struct student 时,

{  
  char a; // 1 byte  
  char b; // 1 byte  
  int c;  // 4 bytes   
}  

你期望这样的内存安排。

... [a] [b] [c] [c] [c] [c] [ ] [ ] ...

在考虑 32 位架构时,可以一次访问 4 个字节。问题是在一个 CPU 周期内,可以访问 char a 的 1 个字节、char b 的 1 个字节和 int c 的 2 个字节。我们在访问 char a 和 char b 时不会遇到任何问题,因为这两个变量都可以在一个 CPU 周期内访问,但是当我们访问 int c 变量时我们会遇到问题,因为需要 2 个 CPU 周期才能访问'c' 变量。在第一个 CPU 周期中,访问前两个字节,在第二个 CPU 周期中,访问其他两个字节。

假设我们不想访问'a'和'b'变量,我们只想访问'c'变量,这需要两个周期。变量“c”有 4 个字节,因此它也可以在一个周期内访问,但在这种情况下,它使用 2 个周期。这是不必要的 CPU 周期浪费。由于这个原因,引入了结构填充概念以节省 CPU 周期数。结构填充由编译器自动完成。现在,我们将看看结构填充是如何完成的。

... [a] [b] [ ] [ ] [c] [c] [c] [c] ...

为了实现结构填充,在左边创建一个空行,如上图所示,将左边'c'变量占用的两个字节右移。因此,'c' 变量的所有四个字节都在右侧。现在,可以在单个 CPU 周期内访问“c”变量。结构体填充后,结构体占用的总内存为8字节(1字节+1字节+2字节+4字节),大于前一个。虽然在这种情况下浪费了内存,但可以在一个周期内访问变量。


我假设你的系统中 long 类型的大小是 4 个字节,而 time 类型的大小是 8 个字节。在这种情况下,内存分配将如下所示。

... [t] [t] [t] [t] [t] [t] [t] [t] [l] [l] [l] [l] [ ] [ ] [ ] [ ] ...
    [---------------- structure type memory area ---------------- ]

您可以查看sizeof(_timespec64)。然后它将返回 16。


为避免这种情况,您必须更改您的视觉工作室偏好。

Project right click
-> Property
   -> Project settings
      -> Configuration Properties
         -> c/c++ general
            -> Treat warnings as errors

【讨论】:

  • @JaMiT 是 C4820 只是警告而不是错误?对吗?
  • 通常我认为 C4820 只是一个警告,但根据您回答的问题:“两个 [警告] 被视为错误”。
  • 是的,visual studio 说它们被视为错误
  • @cleanplay 您必须像这样更改视觉工作室配置。项目右键 -> 属性 -> 项目设置 -> 配置属性 -> c/c++ 常规 -> 将警告视为错误(UNCHECK)
猜你喜欢
  • 1970-01-01
  • 2015-01-21
  • 1970-01-01
  • 1970-01-01
  • 2015-03-14
  • 2010-09-06
  • 1970-01-01
  • 1970-01-01
  • 2021-11-29
相关资源
最近更新 更多