/* * RingBuf.h * * Created On:feb 7, 6:06:10 PM * Author:xuzewen/#ifndef ringbuf_h_#define ringbuf_h_#inc Lude <libmisc.h>/** * * Multi/single-threaded production, only single-threaded consumption, size fixed to 0x10000. * * */class ringbuf{public:ushort ccur;/** consumption cursors. */uint pcur;/** production cursors. */size_t* ring;public:ringbuf (); Virtual ~ringbuf ( );p Ublic:bool push (void* e); /** Add, try again and again until you succeed. */void* pop (); /** Chuhatsu out, always returns immediately, empty when no element is returned. */int size (); /** returns the number of elements. */}; #endif/* Ringbuf_h_ */
Realize:
/* * RingBuf.cpp * * Created On:feb 7, 6:06:10 PM * Author:xuzewen/#include "RingBuf.h" Ringbuf::ringbuf () {this->pcur = 0;this->ccur = 0;this->ring = (size_t*) calloc (1, sizeof (size_t) * 0x10000);} /** Add, try again and again until you succeed. */bool ringbuf::p Ush (void* f) {while (!__sync_bool_compare_and_swap (this->ring + (This->pcur & 0x0000ffff), 0 , (size_t) f)) Usleep (+),//__sync_fetch_and_add (&this->pcur, 1);/** multithreaded producer. *///++this->pcur; /** single-threaded producer. */return true;} /** Chuhatsu out, always returns immediately, empty when no element is returned. */void* ringbuf::p op () {if (this->ring[this->ccur] = = 0) return null;void* r = (void*) this->ring[this->ccur] ; This->ring[this->ccur] = 0;++this->ccur;return r;} int ringbuf::size () {int size = 0;for (int i = 0; i < 0x10000; ++i) {if (this->ring[this->ccur]! = 0) ++size;} return size;} Ringbuf::~ringbuf () {}
Test:
/* * main.cpp * * Created On:mar, 12:09:33 PM * Author:xuzewen */ #include "RingBuf.h" static ringbuf* r = New Ringbuf (); void Svc () {Ullong last = 0;ullong ts = 0;while (1) {Ullong c = (Ullong) r->pop (), if (c = = 0)/** not NULL . */{usleep (+); continue;} if (c-last! = 1) {printf ("It ' s a bug, C:%llu, Last:%llu\n", C, last); exit (1);} Last = c;if ((c% 20000000) = = 0) {Ullong now = Misc::getdida ();/** system ticking. */printf ("TS:%llu, Last:%llu\n", Now-ts, LA ST); ts = Now;}}} int main (int argc, char **argv) {misc::newthread (SVC);/** single thread consumption. *///for (Ullong c = 1;; ++c)/** single-threaded production. */r->push ((voi d*) c); /** push in order. */return exit_success;}
Test results:
By 470 milliseconds per 20 million messages, the concurrency is 42.55 million/s. Single-threaded production, single-threaded consumption, two threads approaching full-running.
Simple implementation of ring lock-free queue