我正在编写一个带有消费者线程和生产者线程的程序,现在看来队列同步在程序中是一个很大的开销,我找了一些无锁队列实现,但只发现了Lamport的版本和改进版本在PPoPP '08:
enqueue_nonblock(data) {
if (NULL != buffer[head]) {
return EWOULDBLOCK;
}
buffer[head] = data;
head = NEXT(head);
return 0;
}
dequeue_nonblock(data) {
data = buffer[tail];
if (NULL == data) {
return EWOULDBLOCK;
}
buffer[tail] = NULL;
tail = NEXT(tail);
return 0;
}
两个版本都需要为数据预先分配的数组,我的问题是,是否存在使用malloc()动态分配空间的任何单用户单生产者无锁队列实现?
另一个相关问题是,如何衡量队列同步的确切开销?比如pthread_mutex_lock()等需要多长时间
答案 0 :(得分:7)
如果您担心性能,将malloc()添加到混音中将无济于事。如果您不担心性能,为什么不简单地通过互斥锁控制对队列的访问。您是否真的测量过这种实现的性能?听起来好像你正在走下熟悉的过早优化路线。
答案 1 :(得分:4)
您展示的算法设法工作,因为虽然两个线程共享资源(即队列),但它们以非常特殊的方式共享它。因为只有一个线程会改变队列的头索引(生产者),并且只有一个线程每个都改变尾索引(当然是消费者),所以你不能得到共享对象的不一致状态。生产者在更新头索引之前将实际数据放在中,并且消费者在更新尾索引之前读取它想要的数据也很重要。
它的工作原理与b / c一样,数组非常静态;两个线程都可以依赖存储元素。您可能无法完全替换阵列,但可以做的是更改阵列的用途。
即,不是将数据保存在数组中,而是使用它来保持指向数据的指针。然后你可以使用malloc()和free()数据项,同时通过数组在线程之间传递引用(指针)。
此外,posix确实支持读取纳秒时钟,但实际精度与系统有关。你可以在之前和之后读取这个高分辨率时钟,然后减去。
答案 2 :(得分:3)
是
存在许多无锁多读者多作者队列。
迈克尔和斯科特在1996年的论文中实施了一个。
我将(在经过一些测试之后)发布一个包含此队列的小型无锁数据结构库(在C中)。
答案 3 :(得分:3)
您应该查看FastFlow库
答案 4 :(得分:2)
我确实记得队列背后的基本概念是创建一个链表,其中总是有一个额外的“空”节点。这个额外的节点意味着当列表为空时,列表的头部和尾部指针只会引用相同的数据。我希望我能找到这篇论文,我不是用我的解释做算法正义...
AH-公顷!
我找到了转录the algorithm without the remainder of the article的人。这可能是一个有用的起点。
答案 5 :(得分:2)
我使用了一个相当简单的队列实现,符合大多数标准。它使用了一个静态最大大小的字节池,然后我们在其中实现了消息。有一个头指针,一个进程将移动,一个尾指针,另一个进程将移动。
仍然需要锁定,但我们使用了Peterson's 2-Processor Algorithm,它非常轻量级,因为它不涉及系统调用。只有非常小的,有界限的区域才需要锁定:最多几个CPU周期,所以你永远不会阻塞。
答案 6 :(得分:2)
我认为分配器可能是性能问题。您可以尝试使用自定义多线程内存分配器,它使用链接列表来维护释放的块。如果您的块不是(几乎)相同的大小,您可以实现“伙伴系统内存分配器”,这是非常快的。您必须将队列(环形缓冲区)与互斥锁同步。
为了避免过多的同步,您可以尝试在每次访问时向队列中写入/读取多个值。
如果您仍想使用无锁算法,则必须使用预先分配的数据或使用无锁分配器。 有一篇关于无锁分配器“可扩展无锁动态内存分配”的文章,以及一个实现Streamflow
在开始使用无锁的内容之前,请查看:Circular lock-free buffer
答案 7 :(得分:2)
添加malloc会消除您可能获得的任何性能提升,基于锁定的结构也同样有效。这是因为malloc需要对堆进行某种CAS锁定,因此某些形式的malloc有自己的锁定,因此您可能会锁定内存管理器。
要使用malloc,您需要预先分配所有节点并使用另一个队列管理它们......
请注意,您可以制作某种形式的可扩展数组,如果它已展开则需要锁定。
同时,虽然互锁在CPU上是无锁定的,但它们会在指令持续时间内放置内存锁定和块内存,并且通常会使管道停滞。
答案 8 :(得分:0)
这个实现使用C ++的new和delete,可以使用malloc和free轻松地移植到C标准库:
http://www.drdobbs.com/parallel/writing-lock-free-code-a-corrected-queue/210604448?pgno=2