forked from bytemaster/tornet
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathbuffer.hpp
89 lines (77 loc) · 2.49 KB
/
buffer.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
#ifndef _TORNET_BUFFER_HPP_
#define _TORNET_BUFFER_HPP_
#include <boost/array.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/make_shared.hpp>
#include <tornet/error.hpp>
namespace tornet {
typedef boost::array<char,2048> buffer_data;
typedef boost::shared_ptr<buffer_data> shared_data_ptr;
/**
* To prevent copying data around, the buffer object
* maintains a shared pointer to a larger packet structure.
*/
struct buffer {
buffer()
:shared_data( boost::make_shared<buffer_data>() ){
start = shared_data->c_array();
len = shared_data->size();
}
buffer( const std::string& d )
:shared_data( boost::make_shared<buffer_data>() ){
BOOST_ASSERT( d.size() <= sizeof(buffer_data) );
start = shared_data->c_array();
memcpy( start, d.c_str(), d.size() );
len = d.size();
}
buffer( uint32_t len )
:shared_data( boost::make_shared<buffer_data>() ){
BOOST_ASSERT( len <= sizeof(buffer_data) );
start = shared_data->c_array();
len = len;
}
buffer( const char* d, uint32_t dl )
:shared_data( boost::make_shared<buffer_data>() ){
BOOST_ASSERT( dl <= sizeof(buffer_data) );
start = shared_data->c_array();
memcpy( start, d, dl );
len = dl;
}
buffer( const buffer& b )
:start(b.start),len(b.len),shared_data(b.shared_data){}
buffer subbuf( int32_t s, uint32_t l = -1 )const {
buffer b(*this);
b.start += s;
if( l == -1 )
b.len -= s;
else
b.len = l;
BOOST_ASSERT( b.start >= b.shared_data->c_array() );
BOOST_ASSERT( b.start + b.len <= b.shared_data->c_array() + b.shared_data->size() );
return b;
}
void move_start( int32_t sdif ) {
start += sdif;
if( sdif > len ) len = 0;
else len -= sdif;
assert( start >= shared_data->c_array() );
assert( start <= shared_data->c_array() + shared_data->size() );
}
void resize( uint32_t s ) {
if( s <= len )
len = s;
else
TORNET_THROW( "Attempt to grow buffer!" );
}
const char& operator[](int i)const { return start[i]; }
char& operator[](int i) { return start[i]; }
const char* data()const { return start; }
char* data() { return start; }
size_t size()const { return len; }
private:
char* start;
uint32_t len;
boost::shared_ptr<buffer_data> shared_data;
};
} // namespace tornet
#endif