将指针发送到 CriticalSection 函数是否安全? C++

Is it safe to send a pointer to a CriticalSection Function? C++

我有一些静态方法可以用来检查线程是否 运行,以及程序是否想要/可以关闭。

通常我会为每个变量创建一个单独的函数,如下所示:

static              CCriticalSection crit_sec;

static bool         static_thread_a_closed = false;
static bool         static_thread_b_closed = false;
static bool         static_prog_closing = false;

static void Set_thread_a_Val(bool set_to)
{
    crit_sec.Lock();
    static_thread_a_closed = set_to;
    crit_sec.Unlock();
};

static bool Get_thread_a_Val()
{
    bool ret;

    crit_sec.Lock();
    ret = static_thread_a_closed;
    crit_sec.Unlock();

    return ret;
};

// etc etc for the others...

void thread_a::Do()
{
    //code
    Set_thread_a_Val(false);
}

void MainDlg::OnClose()
{
    //code..
    while(Get_thread_a_Val()) // ... wait
    //code..
}

我想知道是否可以 'safe' 使用像这样的指针来做到这一点:

static              CCriticalSection crit_sec;

static bool         static_thread_a_closed = false;
static bool         static_thread_b_closed = false;
static bool         static_prog_closing = false;

static void Set_Bool_Val(bool* val, bool set_to)
{
    crit_sec.Lock();
    *val = set_to;
    crit_sec.Unlock();
};

static bool Get_Bool_Val(bool* val)
{
    bool ret;

    crit_sec.Lock();
    ret = *val;
    crit_sec.Unlock();

    return ret;
};

void thread_a::Do()
{
    //code
    Set_Bool_Val(&static_thread_a_closed, false);
}

void MainDlg::OnClose()
{
    //code..
    while(Get_Bool_Val(&static_thread_a_closed)) // ... wait
    //code..
}

传的时候是不是真的访问了内存,所以这个会失败?

还是直接传地址就可以了?

指针没问题。

但是,很有可能 static_thread_a_closed 不会被第二次读取,因为默认情况下 C 不知道 static_thread_a_closed 可以在 while 循环中改变。

添加 volatile 关键字让编译器知道变量可以被 interrupts/other threads/other 进程更改,因此必须始终重新读取变量。否则,您的 while() 可能会优化为 while(1) 或 while(0)。

static volatile bool     static_thread_a_closed = false;
static volatile bool     static_thread_b_closed = false;
static volatile bool     static_prog_closing = false;

static bool Get_Bool_Val(volatile bool* val)

编辑:在意识到我触发了一些“易变的敌意”之后,我应该补充一点,在这种情况下,易变物在任何一种情况下都可能不会产生任何影响。在这两种情况下,while() 都基于函数的 return 值,编译器 不应 优化掉,无论它是否要使用缓存的值静态标志。