linux 无锁队列 例子,无锁队列--基于linuxkfifo实现

一直想写一个无锁队列,为了提高项目的背景效率。

有机会看到linux核心kfifo.h 原则。

所以这个实现自己仿照,眼下linux我们应该能够提供外部接口。

#ifndef _NO_LOCK_QUEUE_H_

#define _NO_LOCK_QUEUE_H_

#include

#include

#include

#include

#include

#include

using namespace std;

#ifndef max

#define max(x, y) ({typeof(x) _max1 = (x);typeof(y) _max2 = (y);(void) (&_max1 == &_max2);_max1 > _max2 ? _max1 : _max2; })

#endif

#ifndef min

#define min(x, y) ({typeof(x) _min1 = (x);typeof(y) _min2 = (y);(void) (&_min1 == &_min2);_min1 < _min2 ?

_min1 : _min2; })

#endif

class Kfifo

{

public:

Kfifo(unsigned int isize);

~Kfifo();

unsigned int get(unsigned char *buffer, unsigned int len);

unsigned int put(const unsigned char *buffer, unsigned int len);

static unsigned long roundup_power_of_two(unsigned long val);

private:

inline bool is_power_of_2(unsigned long n)

{

return (n != 0 && ((n & (n - 1)) == 0));

};

inline unsigned int unused()

{

return (mask + 1) - (in - out);

}

private:

unsigned int size;

unsigned int in;

unsigned int out;

unsigned intmask;

unsigned char* buffer;

};

struct proto

{

unsigned int msgid;

unsigned int cmd;

unsigned int info;

proto():msgid(0),cmd(0),info(0){}

};

#endif

实现文件

#include "MKfifo.h"

Kfifo::~Kfifo()

{

if (buffer) free(buffer);

size = in = out=0;

}

unsigned long Kfifo::roundup_power_of_two(unsigned long val)

{

if (val & (val-1) == 0)

{

return val;

}

unsigned long maxulong = (unsigned long )((unsigned long ) ~0);

unsigned long andv = ~(maxulong&(maxulong>>1));

while((andv & val) == 0)

andv = andv>>1;

return andv<<1;

}

Kfifo::Kfifo(unsigned int isize):size(isize),in(0),out(0),mask(size - 1)

{

if (!is_power_of_2(isize))

{

size = roundup_power_of_two(isize);

}

buffer =(unsigned char*) malloc(isize);

}

unsigned int Kfifo::get(unsigned char *_buffer, unsigned int len)

{

unsigned int l;

len = min(len, in - out);

__sync_synchronize();

l = min(len,size -(out&(size-1)));

memcpy(_buffer,buffer + (out& (size-1)),l);

memcpy(_buffer + l,buffer,len - l);

__sync_synchronize();

out +=len;

return len;

}

unsigned int Kfifo::put(const unsigned char *_buffer, unsigned int len)

{

unsigned int l;

len = min(len, size - in + out);

__sync_synchronize();

l = min(len, size - (in & (size - 1)));

memcpy(buffer + (in & (size - 1)), _buffer, l);

memcpy(buffer, _buffer + l, len - l);

__sync_synchronize();

in += len;

return len;

}

void * consumer(void * arg)

{

printf("consumer\n");

Kfifo* fifo = (Kfifo*) arg;

if (!fifo)

{

return NULL;

}

for (;;)

{

proto p;

unsigned int len = fifo->get((unsigned char*)&p,sizeof(p));

if (len>0)

{

cout << "~~~~~~~~~~~~~~~~~~~~"<

cout << "consumer proto msg id :"<

cout << "consumer proto msg cmd :"<

cout << "consumer proto msg info :"<

cout << "~~~~~~~~~~~~~~~~~~~~"<

}

}

return (void *)fifo;

}

void* producer(void* args)

{

Kfifo* fifo = (Kfifo*) args;

if (!fifo)

{

return NULL;

}

unsigned int i=0;

for (;;)

{

proto p;

p.msgid = i++;

p.cmd = 333;

p.info = 44444;

fifo->put((const unsigned char*)&p,sizeof(p));

cout<

}

return (void*)fifo;

}

int main()

{

Kfifo *fifo = new Kfifo(1024);

pthread_t consumeid,producerid;

pthread_create(&producerid,NULL,producer,(void*)fifo);

pthread_create(&consumeid,NULL,consumer,(void*)fifo);

printf("info!!\n");

pthread_join(consumeid,NULL);

pthread_join(producerid,NULL);

return 0;

}

可经过测试。我将基于队列。其丰富的应用。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值