SHOGUN
v3.0.0
Main Page
Related Pages
Modules
Classes
Files
File List
File Members
All
Classes
Namespaces
Files
Functions
Variables
Typedefs
Enumerations
Enumerator
Friends
Macros
Groups
Pages
src
shogun
io
IOBuffer.cpp
Go to the documentation of this file.
1
/*
2
Copyright (c) 2009 Yahoo! Inc. All rights reserved. The copyrights
3
embodied in the content of this file are licensed under the BSD
4
(revised) open source license.
5
6
Copyright (c) 2011 Berlin Institute of Technology and Max-Planck-Society.
7
8
This program is free software; you can redistribute it and/or modify
9
it under the terms of the GNU General Public License as published by
10
the Free Software Foundation; either version 3 of the License, or
11
(at your option) any later version.
12
13
Shogun adjustments (w) 2011 Shashwat Lal Das
14
*/
15
16
#include <string.h>
17
#include <
shogun/io/IOBuffer.h
>
18
19
using namespace
shogun;
20
21
CIOBuffer::CIOBuffer
()
22
{
23
init
();
24
}
25
26
CIOBuffer::CIOBuffer
(
int
fd)
27
{
28
init
();
29
working_file
= fd;
30
}
31
32
CIOBuffer::~CIOBuffer
()
33
{
34
}
35
36
void
CIOBuffer::init
()
37
{
38
size_t
s = 1 << 16;
39
space
.
reserve
(s);
40
endloaded
=
space
.
begin
;
41
working_file
=-1;
42
}
43
44
void
CIOBuffer::use_file
(
int
fd)
45
{
46
working_file
= fd;
47
}
48
49
int
CIOBuffer::open_file
(
const
char
* name,
char
flag)
50
{
51
int
ret=1;
52
switch
(flag)
53
{
54
case
'r'
:
55
working_file
= open(name, O_RDONLY|
O_LARGEFILE
);
56
break
;
57
58
case
'w'
:
59
working_file
= open(name, O_CREAT|O_TRUNC|O_WRONLY, 0666);
60
break
;
61
62
default
:
63
SG_ERROR
(
"Unknown file operation. Something other than 'r'/'w' specified.\n"
)
64
ret = 0;
65
}
66
return
ret;
67
}
68
69
void
CIOBuffer::reset_file
()
70
{
71
lseek(
working_file
, 0, SEEK_SET);
72
endloaded
=
space
.
begin
;
73
space
.
end
=
space
.
begin
;
74
}
75
76
void
CIOBuffer::set
(
char
*p)
77
{
78
space
.
end
= p;
79
}
80
81
ssize_t
CIOBuffer::read_file
(
void
* buf,
size_t
nbytes)
82
{
83
return
read(
working_file
, buf, nbytes);
84
}
85
86
size_t
CIOBuffer::fill
()
87
{
88
if
(
space
.
end_array
-
endloaded
== 0)
89
{
90
size_t
offset =
endloaded
-
space
.
begin
;
91
space
.
reserve
(2 * (
space
.
end_array
-
space
.
begin
));
92
endloaded
=
space
.
begin
+offset;
93
}
94
ssize_t num_read =
read_file
(
endloaded
,
space
.
end_array
-
endloaded
);
95
if
(num_read >= 0)
96
{
97
endloaded
=
endloaded
+num_read;
98
return
num_read;
99
}
100
else
101
return
0;
102
}
103
104
ssize_t
CIOBuffer::write_file
(
const
void
* buf,
size_t
nbytes)
105
{
106
return
write(
working_file
, buf, nbytes);
107
}
108
109
void
CIOBuffer::flush
()
110
{
111
if
(
working_file
>=0)
112
{
113
if
(
write_file
(
space
.
begin
,
space
.
index
()) != (
int
)
space
.
index
())
114
SG_ERROR
(
"Error, failed to write example!\n"
)
115
}
116
space
.
end
=
space
.
begin
;
117
fsync(
working_file
);
118
}
119
120
bool
CIOBuffer::close_file
()
121
{
122
if
(
working_file
< 0)
123
return
false
;
124
else
125
{
126
int
r = close(
working_file
);
127
if
(r < 0)
128
SG_ERROR
(
"Error closing the file!\n"
)
129
return
true
;
130
}
131
}
132
133
ssize_t
CIOBuffer::readto
(
char
* &pointer,
char
terminal)
134
{
135
//Return a pointer to the bytes before the terminal. Must be less
136
//than the buffer size.
137
pointer =
space
.
end
;
138
while
(pointer !=
endloaded
&& *pointer != terminal)
139
pointer++;
140
if
(pointer !=
endloaded
)
141
{
142
size_t
n = pointer -
space
.
end
;
143
space
.
end
= pointer+1;
144
pointer -= n;
145
return
n;
146
}
147
else
148
{
149
if
(
endloaded
==
space
.
end_array
)
150
{
151
size_t
left =
endloaded
-
space
.
end
;
152
memmove(
space
.
begin
,
space
.
end
, left);
153
space
.
end
=
space
.
begin
;
154
endloaded
=
space
.
begin
+left;
155
pointer =
endloaded
;
156
}
157
if
(
fill
() > 0)
// more bytes are read.
158
return
readto
(pointer,terminal);
159
else
//no more bytes to read, return nothing.
160
return
0;
161
}
162
}
163
164
void
CIOBuffer::buf_write
(
char
* &pointer,
int
n)
165
{
166
if
(
space
.
end
+ n <=
space
.
end_array
)
167
{
168
pointer =
space
.
end
;
169
space
.
end
+= n;
170
}
171
else
// Time to dump the file
172
{
173
if
(
space
.
end
!=
space
.
begin
)
174
flush
();
175
else
// Array is short, so increase size.
176
{
177
space
.
reserve
(2 * (
space
.
end_array
-
space
.
begin
));
178
endloaded
=
space
.
begin
;
179
}
180
buf_write
(pointer,n);
181
}
182
}
183
184
unsigned
int
CIOBuffer::buf_read
(
char
* &pointer,
int
n)
185
{
186
// Return a pointer to the next n bytes.
187
// n must be smaller than the maximum size.
188
if
(
space
.
end
+ n <=
endloaded
)
189
{
190
pointer =
space
.
end
;
191
space
.
end
+= n;
192
return
n;
193
}
194
else
// out of bytes, so refill.
195
{
196
if
(
space
.
end
!=
space
.
begin
)
//There exists room to shift.
197
{
198
// Out of buffer so swap to beginning.
199
int
left =
endloaded
-
space
.
end
;
200
memmove(
space
.
begin
,
space
.
end
, left);
201
space
.
end
=
space
.
begin
;
202
endloaded
=
space
.
begin
+left;
203
}
204
if
(
fill
() > 0)
205
return
buf_read
(pointer,n);
// more bytes are read.
206
else
207
{
208
// No more bytes to read, return all that we have left.
209
pointer =
space
.
end
;
210
space
.
end
=
endloaded
;
211
return
endloaded
- pointer;
212
}
213
}
214
}
SHOGUN
Machine Learning Toolbox - Documentation