小编use*_*113的帖子

在现代 C++ 中,是否仍应使用 volatile 与 ISR 共享数据?

我已经看到了这些问题的一些风格,也看到了不同的答案,但仍然不确定它们是否是最新的并完全适用于我的用例,所以我会在这里提问。如果它是重复的,请告诉我!

鉴于我正在使用 C++17 和 gcc-arm-none-eabi-9 工具链为 STM32 微控制器(裸机)开发:

我还需要使用volatile用于在 ISR 和 之间共享数据main()吗?

volatile std::int32_t flag = 0;

extern "C" void ISR()
{
    flag = 1;
}

int main()
{
    while (!flag) { ... }
}
Run Code Online (Sandbox Code Playgroud)

我很清楚,我应该始终volatile用于访问内存映射的硬件寄存器。

但是对于 ISR 用例,我不知道它是否可以被视为“多线程”的情况。在这种情况下,人们建议使用 C++11 的新线程特性(例如std::atomic)。我知道volatile(不优化)和atomic(安全访问)之间的区别,所以建议的答案std::atomic在这里让我感到困惑。

对于 x86 系统上“真正的”多线程的情况,我没有看到需要使用volatile.

换句话说:编译器flag可以知道可以在 ISR 内部更改吗?如果没有,它如何在常规多线程应用程序中知道它?

谢谢!

c++ embedded volatile isr

13
推荐指数
1
解决办法
494
查看次数

模板类 + 委托构造函数 = 字段未初始化?(叮叮当当)

我正在运行 clang-tidy 8.0 并且收到警告:

constructor does not initialize these fields:

在模板化类上使用委托构造函数时。我想知道这是否是我应该压制的误报,或者我的代码是否确实是错误的。

有问题的示例代码是这样的:

template<typename T>
class A
{
public:
    explicit A(const std::size_t size) : 
        data_(nullptr),
        data_size_(size)
    {
        // ...
    }

    explicit A(const std::vector<T>& b) : 
        A(b.size())
    {
        // ...
    }

private:
    T* data_;
    std::size_t data_size_;
};
Run Code Online (Sandbox Code Playgroud)

在此代码上运行 clang-tidy 时:

clang-tidy-8 --checks=* test.cpp

我得到,除其他外:

warning: constructor does not initialize these fields: data_ [cppcoreguidelines-pro-type-member-init]
    explicit A(const std::vector<T>& b) : A(b.size()) {}
Run Code Online (Sandbox Code Playgroud)

但是,如果我从类中删除模板并使其成为普通类,则不会出现此类错误。

在模板化类上使用委托构造函数时,我是否遗漏了什么,或者这是 clang-tidy 中的错误?

谢谢!

c++ c++11 clang-tidy

8
推荐指数
1
解决办法
1379
查看次数

Docker 运行 - 用户组未按预期工作?

我有一个通过串行端口 ( ) 进行通信的脚本/dev/ttyUSB0。我想从 Docker 映像中运行它。但是我似乎没有权限从图像中执行此操作。我按照以下步骤操作:

在我的主机上,如果我运行ln -l /dev/ttyUSB0我会得到:

crw-rw---- 1 root dialout 188, 0 jul  2 14:34 /dev/ttyUSB0
Run Code Online (Sandbox Code Playgroud)

很好,这意味着为了读/写它,我需要成为root或 组的一部分dialout

我成为我的主机中该组的成员:

$ sudo usermod -aG dialout $(whoami)
Run Code Online (Sandbox Code Playgroud)

然后我注销并再次登录以使其生效。

之后,我验证我可以与/dev/ttyUSB0我的主机完美通信。但是,如果我运行 docker 映像:

docker run --user=1000:1000 --rm=true --tty=true --privileged=true --device=/dev/ttyUSB0 --volume=<my_dir>:<my_dir> --workdir=<my_dir> <my_docker_image> <my_script>
Run Code Online (Sandbox Code Playgroud)

然后它抱怨:

can't open device "/dev/ttyUSB0": Permission denied
Run Code Online (Sandbox Code Playgroud)

但是,如果我使用:--user=1000:20,那么它工作正常。团体20就是dialout团体。

现在我的问题是:

为什么 Docker 不明白我的用户 (1000) 和组 (1000) 是该dialout组的一部分?

当我使用旧的docker …

linux ubuntu usergroups user-permissions docker

7
推荐指数
1
解决办法
5193
查看次数

如何忽略第三方头文件中定义的宏的编译器警告?

目前,可以通过将给定标头视为“系统标头”(包括通过-isystem /path/to/dir.

\n

但是,如果警告源于此类标头中定义的,则这仍然不起作用。有什么方法可以忽略宏的警告吗?我最感兴趣的是 GCC 和 Clang 解决方案。

\n

以下示例基于 Ubuntu 20.04 上的 Clang 14.0.0 和 GCC 11.1.0:

\n
// include/third_party.h\n#pragma once\n\n#define MY_CAST(x) ((int)x)\n
Run Code Online (Sandbox Code Playgroud)\n
// main.cpp\n#include <third_party.h>\n\nint main() \n{\n    int x = MY_CAST(123);\n    return x;\n}\n
Run Code Online (Sandbox Code Playgroud)\n

与海湾合作委员会:

\n
$ g++ -isystem include -Wold-style-cast main.cpp \nIn file included from main.cpp:1:\nmain.cpp: In function \xe2\x80\x98int main()\xe2\x80\x99:\nmain.cpp:5:21: warning: use of old-style cast to \xe2\x80\x98int\xe2\x80\x99 [-Wold-style-cast]\n    5 |     int x = MY_CAST(123);\n      |                     ^~~\n\n
Run Code Online (Sandbox Code Playgroud)\n

与叮当:

\n
$ clang++ -isystem …
Run Code Online (Sandbox Code Playgroud)

c++ compiler-warnings suppress-warnings

7
推荐指数
1
解决办法
1662
查看次数

VS Code devcontainers - 远程用户和容器用户有什么区别?

阅读 devcontainer.json 参考,我仍然无法理解: https: //code.visualstudio.com/docs/remote/devcontainerjson-reference

containerUser: Overrides the user all operations run as inside the container.
remoteUser: Overrides the user that VS Code runs as in the container (along with sub-processes like terminals, tasks, or debugging)
Run Code Online (Sandbox Code Playgroud)

containerUser和 和有什么区别remoteUser?我什么时候应该使用其中之一?你能提供例子吗?

谢谢!

visual-studio-code visual-studio-container-tools

6
推荐指数
1
解决办法
2057
查看次数

.cpp 文件中的模板专业化 + .h 文件中的主模板声明

根据https://eel.is/c++draft/temp.expl.spec#7

如果模板、成员模板或类模板的成员被显式特化,则在每个翻译单元中,该特化的声明应可从该特化的每次使用中到达,这将导致隐式实例化的发生。使用发生;无需诊断。

因此我想知道,以下程序是否格式错误,NDR?

// foo.h
template <typename T>
void foo();

// Specialization not declared in the header!

// foo.cpp
#include "foo.h"

template <>
void foo<int>()
{
 // ...
}

// main.cpp
#include "foo.h"

int main()
{
    foo<int>();
}
Run Code Online (Sandbox Code Playgroud)

c++ templates template-specialization language-lawyer

6
推荐指数
1
解决办法
1346
查看次数

Git预提交钩子+docker=不同的git状态

我想在预提交 git hook 中运行脚本。我希望该脚本从 docker 映像中运行。此预提交挂钩的示例代码:

# pre-commit hook
#!/bin/bash
repo_root=$(git rev-parse --show-toplevel)
docker run -v ${repo_root}:${repo_root} -w ${repo_root}  <my_docker_image> <path_to_my_script.py>
Run Code Online (Sandbox Code Playgroud)

my_script.py内部运行git status以确定要在预提交挂钩中处理哪些文件。

git status问题:当我运行 时,预提交挂钩中的输出与 docker 容器内的 输出不同git commit --all。例子:

# pre-commit hook
#!/bin/bash
git status
echo "------------------------------------"
repo_root=$(git rev-parse --show-toplevel)
docker run -v ${repo_root}:${repo_root} -w ${repo_root} <my_docker_image> git status
Run Code Online (Sandbox Code Playgroud)

我希望通过在 docker 容器内运行git commit --allgit status我可以看到所有已上演的更改。

但是,这些更改不会在 docker 容器内进行。我之前编写的代码打印以下内容:

Changes to be committed:
  (use "git reset HEAD <file>..." to …
Run Code Online (Sandbox Code Playgroud)

git pre-commit-hook docker

5
推荐指数
1
解决办法
5067
查看次数

Python3-如何正确执行绝对导入并使Pylint满意

我在理解Python 3导入时遇到了很大的麻烦(我正在使用Python 3.5)。这似乎是一个百万美元的问题,我知道到处都有答案。但是,我并没有真正了解应该如何做。互联网上的答案差异很大。所以提前对不起,如果这是一个几乎重复的答案。我真的很感激良好的阅读材料的引用。

所以我有以下虚拟项目:

/my_project/main.py
/my_project/lib/__init__.py
/my project/lib/my_lib.py
Run Code Online (Sandbox Code Playgroud)

如果可能的话,我想:

  • 能够运行我的程序的python3 main.py,有my_project作为当前工作目录。
  • PYTHONPATH随时不修改。
  • 让pylint开心。
  • 使用正确的Python3导入。

main.py 包含:

from .lib.my_lib import foo

if __name__ == '__main__':
    foo()
Run Code Online (Sandbox Code Playgroud)

foo据此定义lib/my_lib.py

使用该配置,我得到:

SystemError: Parent module '' not loaded, cannot perform relative import

我可以通过导入像避开错误:

from lib.my_lib import foo
Run Code Online (Sandbox Code Playgroud)

但是然后1)这不是Python3绝对导入,对吗?2)Pylint抱怨:Unable to import 'lib.my_lib' (import-error)

我尝试的下一件事情是添加一个my_project/__init__.py,然后像这样导入:

from my_project.lib.my_lib import foo
Run Code Online (Sandbox Code Playgroud)

在这种情况下,pylint很高兴,但是我不能这样运行python3 main.pyImportError: No module named 'my_project'

然后,我可以运行它的唯一方法是从父目录作为模块:python3 -m my_project.main

所以我的问题是:是否有可能以正确的方式进行导入,同时仍然能够像这样执行导入python3 main.py …

python pylint python-import python-3.x python-3.5

5
推荐指数
1
解决办法
813
查看次数

弃用 C++ 代码并将警告视为错误的最佳实践?

我们有一个大型 C++ 项目,启用错误时会发出警告。我们想弃用一些旧的 API,自然我们的第一个想法就是转向[[deprecated]]语言功能。然而,这会触发-Wdeprecated-declarations警告,该警告会变成错误并使构建失败。

现在,我们知道我们可以通过 禁用该特定警告的错误-Wno-error=deprecated-declarations。但构建日志仍然充满了编译器警告,使得发现真正的编译器错误变得更加困难。

那么我想知道在现实世界的大型项目中,人们是否有更好的解决方案来处理实践中的 C++ 弃用问题?

c++ deprecated deprecation-warning

5
推荐指数
1
解决办法
968
查看次数

传递整数文字时没有隐式转换警告?

我试图了解隐式转换何时发生,并检测它们以提高代码库的质量。

我已经启用Wconversion,并Wsign-conversion为这个。但是我遇到了编译器没有给出任何错误的情况。例:

#include <iostream>
#include <array>

int main()
{
   std::array<int, 10> vec{};
   std::cout << vec[1] << std::endl; 
}
Run Code Online (Sandbox Code Playgroud)

编译:

$ g++ --std=c++14 -Wall -Wextra -Werror -pedantic -Wsign-conversion -Wconversion test.cpp 
$ 
Run Code Online (Sandbox Code Playgroud)

数组的大小和索引to operator[]都应为std::size_t(无符号)类型。但是,我正在传递带符号的文字,似乎没有问题。我什1.0F至可以传递给operator[]编译器。

operator[]但是,如果我为to的索引创建一个带符号的变量,则编译器会发出有关隐式转换的警告。

到底发生了什么事?使用文字时是否发生隐式转换?为什么编译器没有给出错误?我在Ubuntu 18.04上使用GCC 7.4。

c++ implicit-conversion

4
推荐指数
2
解决办法
116
查看次数

为什么在 constexpr 上下文中使用保留的标识符名称未诊断?

基于以下两条规则:

  • 使用以“_”+大写字母开头或包含双下划线的标识符是未定义的行为。
  • constexpr 表达式中不允许有未定义的行为 -> 编译器不应编译。

那么为什么编译器不抱怨这个呢?

constexpr int _UB() {return 1;}
int main() {
    constexpr int a = _UB();
    return a;
}
Run Code Online (Sandbox Code Playgroud)

演示

另外,我看到很多专业的、符合 MISRA 的代码似乎违反了此命名规则,请参见此处

#ifndef __STM32F732xx_H
#define __STM32F732xx_H
Run Code Online (Sandbox Code Playgroud)

所有这些库都调用 UB 吗?

c++ undefined-behavior language-lawyer

3
推荐指数
1
解决办法
596
查看次数