CMCore/inc/hgl/thread/RingBufferRead.cpp

211 lines
4.8 KiB
C++
Raw Normal View History

2019-08-19 19:19:58 +08:00
#ifndef HGL_THREAD_RING_BUFFER_READ_SOURCE
#define HGL_THREAD_RING_BUFFER_READ_SOURCE
#include<string.h>
namespace hgl
{
/**
*
*/
template<typename T>
int RingBuffer<T>::SafeGetReadSize()
{
Lock();
const int result=_GetReadSize();
Unlock();
return(result);
}
/**
*
*/
template<typename T>
bool RingBuffer<T>::SafeTryGetReadSize(int &result)
{
if(!TryLock())
return(false);
result=_GetReadSize();
Unlock();
return(true);
}
template<typename T>
int RingBuffer<T>::ReadStart(bool peek)
{
ClampPosition();
write_off=write_pos%buffer_size;
read_max=_GetReadSize();
read_peek=peek; //标记是否真的取走
read_count=0;
read_cur=read_pos;
return(read_max);
}
template<typename T>
int RingBuffer<T>::_SafeReadStart(bool peek)
{
ReadStart(peek);
if(read_max<=0)
Unlock();
return(read_max);
}
/**
* SafeReadEnd
* @param peek
* @return >0
* @return =0
* @return <0
*/
template<typename T>
int RingBuffer<T>::SafeTryReadStart(bool peek)
{
if(!TryLock())
return(-1);
return _SafeReadStart(peek);
}
/**
* ,SafeReadEnd
* @param peek
* @return
*/
template<typename T>
int RingBuffer<T>::SafeReadStart(bool peek)
{
Lock();
return _SafeReadStart(peek);
}
/**
*
* @param data 访,NULL用于单纯后移读取指针
* @param size 访
* @param peek 访()
* @return 访
*/
template<typename T>
int RingBuffer<T>::Read(T *data,int size,bool peek)
{
if(size<=0)return(-1);
const int result=_Read(data,size,peek);
if(peek)
read_count+=result;
return(result);
}
/**
*
* @return
*/
template<typename T>
int RingBuffer<T>::ReadEnd()
{
const int result=read_count;
if(read_peek&&result)
read_pos=read_cur;
return result;
}
/**
*
* @return
*/
template<typename T>
int RingBuffer<T>::SafeReadEnd()
{
const int result=ReadEnd();
Unlock();
return result;
}
/**
* ,,使SafeReadStart/SafeReadEnd
* @param data 访,NULL用于单纯后移读取指针
* @param size 访
* @param peek
* @return
* @return -1
*/
template<typename T>
int RingBuffer<T>::SafeRead(T *data,int size,bool peek)
{
if(size<0)return(-1);
if(size&&!data)return(-1);
if(SafeReadStart(peek)<=0)
return(-1);
Read(data,size,peek);
return SafeReadEnd();
}
template<typename T>
int RingBuffer<T>::_Read(T *data,int size,bool peek)
{
if(size<=0||read_max<=0)return(0);
if(size>read_max)
size=read_max;
if(size>0)
{
if(data) //data可以为空用于先尝试取数据后直接移走
{
const int temp_read =read_cur %buffer_size;
if(temp_read<write_off)
{
memcpy(data,buffer+temp_read,size*sizeof(T));
}
else
{
int temp=buffer_size-temp_read;
if(size>temp)
{
memcpy(data,buffer+temp_read,temp*sizeof(T));
memcpy((char *)(data+temp),buffer,(size-temp)*sizeof(T));
}
else
{
memcpy(data,buffer+temp_read,size*sizeof(T));
}
}
}//if(data)
if(peek)
{
read_cur+=size;
read_max-=size;
}
}
return(size);
}
}//namespace hgl
#endif//HGL_THREAD_RING_BUFFER_READ_SOURCE