如果semTake在Vxworks5.5中失败,则可以调用semGive

时间:2014-04-07 10:03:47

标签: c++ c vxworks

我在使用Vxworks5.5

工作的项目中有以下代码
m_SemServState = semBCreate(SEM_Q_FIFO, SEM_FULL );

//.... In another function I have following code.

SemStatus = semTake(m_SemServState, 500);
    if(OK == SemStatus)
    {
        // ...
    }
    else
    {
        //...
    }
    semGive(m_SemServState);

我在上面的代码中有以下问题。

  1. 即使semTake失败,上面的代码是否正常,因为我们正在调用semGive?

  2. 当我与作者交谈时,我被告知我们可以调用semGive,即使我semTake失败了。会有副作用吗?

  3. 上述编程是不错的做法?

  4. 感谢您的投入。

3 个答案:

答案 0 :(得分:1)

首先,由于您正在创建二进制信号量,因此本身没有“计数”。信号量是满的还是空的,并且没有所有权的概念(就像有互斥量一样)。

让我对这个特定代码感到困惑的是,运行此函数的任务似乎发出信号。

此处返回两种可能的错误类型:

  • 超时(最有可能)
  • 真正的错误

我希望您检查错误以确定您遇到的这两种情况中的哪一种。 如果错误超时,那么你可能手上有一个严重的问题,几乎可以肯定,信号量的操作完全受到损害,在这种情况下,做semGive可能也会失败。

如果错误是超时(即在500个滴答之后),那么您的代码应该没问题。

如果只有一个任务运行此函数(并且没有其他任务等待同一个信号量),那么循环遍历该函数将始终立即成功。事实上,事实上,我看不出这会如何失败。

所以我必须推断出有多个任务在等待同一个信号量。

如果没有更多详细信息,很难确定代码是否符合您的要求,但这是合法的。 这实际上取决于“else”分支中发生的情况,如果它不是超时的话。

答案 1 :(得分:0)

  

即使semTake失败,上面的代码是否正常,因为我们正在调用semGive?

取决于你的意思"工作"。

  

当我与作者交谈时,我被告知我们可以调用semGive,即使我semTake失败了。会有副作用吗?

当然你可以。即使您未能抓住sempaphore,您也会增加信号量值。这几乎不是你想做的事。

  

上面的编程是不错的做法?

不,代码令人困惑,甚至是你发布信号量的错误 如果你没有获得它。

你想做

SemStatus = semTake(m_SemServState, 500);
if(OK == SemStatus)
{
    // ...
   semGive(m_SemServState);
}
else
{
    //...
}

答案 2 :(得分:0)

可能无法正常工作。

如果SemTake失败并且您正在调用SemGive(),则SemGive()可能会或可能不会返回成功。

注意:SemGive()也会失败并显示警告,超过计数。

在上面的代码中考虑以下情况。

  1. SemTake()失败,SemGive()失败。
  2. SemTake()失败,SemGive()返回成功。
  3. 您的代码在2种情况下会产生意外结果。

    所以只有在SemTake()返回成功的情况下才应调用SemGive()。

    SemStatus = semTake(m_SemServState, 500);
        if(OK == SemStatus)
        {
            // ...
            semGive(m_SemServState);
        }
        else
        {
            //...
        }