我有一个高优先级进程,需要将数据传递给低优先级进程。我写了一个基本的环形缓冲区来处理数据的传递:没有优先级反转的环形缓冲区
class RingBuffer {
public:
RingBuffer(int size);
~RingBuffer();
int count() {return (size + end - start) % size;}
void write(char *data, int bytes) {
// some work that uses only buffer and end
end = (end + bytes) % size;
}
void read(char *data, int bytes) {
// some work that uses only buffer and start
start = (start + bytes) % size;
}
private:
char *buffer;
const int size;
int start, end;
};
这是问题所在。假设低优先级进程有一个oracle,告诉它需要读取多少数据,所以不需要调用count()
。然后(除非我错过了什么)没有并发问题。但是,只要低优先级线程需要调用count()
(高优先级线程可能想要调用它以检查缓冲区是否太满),则count()中的数学或更新为结束不是原子,引入了一个错误。
我可以在开始和结束的访问周围放置一个互斥量,但如果高优先级线程必须等待低优先级线程获取的锁定,则会导致优先级反转。
我可能能够使用原子操作工作,但我不知道有一个很好的跨平台库提供这些。
是否有避免这些问题的标准环形缓冲设计?
提供了跨平台的原子功能是否有在平台上的任何约束的使用? – 2011-04-21 16:39:20
@Peter让我们假设x86(其中IIRC 32位写入对齐的地址是原子的),尽管越便携越好。 – user168715 2011-04-21 17:22:36
这里是一个等待免费的队列http://software.intel.com/zh-cn/articles/single-producer-single-consumer-queue/ – 2011-04-21 20:41:16