Files
LNXRNT/Sources/lockfree_queue.h

76 lines
1.6 KiB
C
Raw Normal View History

2026-02-20 23:40:15 -08:00
#pragma once
#include <atomic>
#include <memory>
template<typename T>
class LockFreeQueue {
private:
struct Node {
std::atomic<T*> data{nullptr};
std::atomic<Node*> next{nullptr};
};
std::atomic<Node*> head_{nullptr};
std::atomic<Node*> tail_{nullptr};
public:
LockFreeQueue() {
Node* dummy = new Node;
head_.store(dummy);
tail_.store(dummy);
}
~LockFreeQueue() {
Node* current = head_.load();
while (current != nullptr) {
Node* next = current->next.load();
T* data = current->data.load();
if (data != nullptr) {
delete data;
}
delete current;
current = next;
}
head_.store(nullptr);
tail_.store(nullptr);
}
void push(T item) {
Node* new_node = new Node;
T* data = new T(std::move(item));
new_node->data.store(data);
Node* prev_tail = tail_.exchange(new_node);
prev_tail->next.store(new_node);
}
bool try_pop(T& result) {
Node* head = head_.load();
Node* next = head->next.load();
if (next == nullptr) {
return false;
}
T* data = next->data.load();
if (data == nullptr) {
return false;
}
result = *data;
delete data;
head_.store(next);
delete head;
return true;
}
bool empty() const {
Node* head = head_.load();
Node* next = head->next.load();
return (next == nullptr);
}
};