SHOGUN
v2.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
}
42
43
void
CIOBuffer::use_file
(
int
fd)
44
{
45
working_file
= fd;
46
}
47
48
int
CIOBuffer::open_file
(
const
char
* name,
char
flag)
49
{
50
int
ret=1;
51
switch
(flag)
52
{
53
case
'r'
:
54
working_file
= open(name, O_RDONLY|
O_LARGEFILE
);
55
break
;
56
57
case
'w'
:
58
working_file
= open(name, O_CREAT|O_TRUNC|O_WRONLY, 0666);
59
break
;
60
61
default
:
62
SG_ERROR
(
"Unknown file operation. Something other than 'r'/'w' specified.\n"
);
63
ret = 0;
64
}
65
return
ret;
66
}
67
68
void
CIOBuffer::reset_file
()
69
{
70
lseek(
working_file
, 0, SEEK_SET);
71
endloaded
=
space
.
begin
;
72
space
.
end
=
space
.
begin
;
73
}
74
75
void
CIOBuffer::set
(
char
*p)
76
{
77
space
.
end
= p;
78
}
79
80
ssize_t
CIOBuffer::read_file
(
void
* buf,
size_t
nbytes)
81
{
82
return
read(
working_file
, buf, nbytes);
83
}
84
85
size_t
CIOBuffer::fill
()
86
{
87
if
(
space
.
end_array
-
endloaded
== 0)
88
{
89
size_t
offset =
endloaded
-
space
.
begin
;
90
space
.
reserve
(2 * (
space
.
end_array
-
space
.
begin
));
91
endloaded
=
space
.
begin
+offset;
92
}
93
ssize_t num_read =
read_file
(
endloaded
,
space
.
end_array
-
endloaded
);
94
if
(num_read >= 0)
95
{
96
endloaded
=
endloaded
+num_read;
97
return
num_read;
98
}
99
else
100
return
0;
101
}
102
103
ssize_t
CIOBuffer::write_file
(
const
void
* buf,
size_t
nbytes)
104
{
105
return
write(
working_file
, buf, nbytes);
106
}
107
108
void
CIOBuffer::flush
()
109
{
110
if
(
write_file
(
space
.
begin
,
space
.
index
()) != (
int
)
space
.
index
())
111
SG_ERROR
(
"Error, failed to write example!\n"
);
112
space
.
end
=
space
.
begin
;
113
fsync(
working_file
);
114
}
115
116
bool
CIOBuffer::close_file
()
117
{
118
if
(
working_file
< 0)
119
return
false
;
120
else
121
{
122
int
r = close(
working_file
);
123
if
(r < 0)
124
SG_ERROR
(
"Error closing the file!\n"
);
125
return
true
;
126
}
127
}
128
129
ssize_t
CIOBuffer::readto
(
char
* &pointer,
char
terminal)
130
{
131
//Return a pointer to the bytes before the terminal. Must be less
132
//than the buffer size.
133
pointer =
space
.
end
;
134
while
(pointer !=
endloaded
&& *pointer != terminal)
135
pointer++;
136
if
(pointer !=
endloaded
)
137
{
138
size_t
n = pointer -
space
.
end
;
139
space
.
end
= pointer+1;
140
pointer -= n;
141
return
n;
142
}
143
else
144
{
145
if
(
endloaded
==
space
.
end_array
)
146
{
147
size_t
left =
endloaded
-
space
.
end
;
148
memmove(
space
.
begin
,
space
.
end
, left);
149
space
.
end
=
space
.
begin
;
150
endloaded
=
space
.
begin
+left;
151
pointer =
endloaded
;
152
}
153
if
(
fill
() > 0)
// more bytes are read.
154
return
readto
(pointer,terminal);
155
else
//no more bytes to read, return nothing.
156
return
0;
157
}
158
}
159
160
void
CIOBuffer::buf_write
(
char
* &pointer,
int
n)
161
{
162
if
(
space
.
end
+ n <=
space
.
end_array
)
163
{
164
pointer =
space
.
end
;
165
space
.
end
+= n;
166
}
167
else
// Time to dump the file
168
{
169
if
(
space
.
end
!=
space
.
begin
)
170
flush
();
171
else
// Array is short, so increase size.
172
{
173
space
.
reserve
(2 * (
space
.
end_array
-
space
.
begin
));
174
endloaded
=
space
.
begin
;
175
}
176
buf_write
(pointer,n);
177
}
178
}
179
180
unsigned
int
CIOBuffer::buf_read
(
char
* &pointer,
int
n)
181
{
182
// Return a pointer to the next n bytes.
183
// n must be smaller than the maximum size.
184
if
(
space
.
end
+ n <=
endloaded
)
185
{
186
pointer =
space
.
end
;
187
space
.
end
+= n;
188
return
n;
189
}
190
else
// out of bytes, so refill.
191
{
192
if
(
space
.
end
!=
space
.
begin
)
//There exists room to shift.
193
{
194
// Out of buffer so swap to beginning.
195
int
left =
endloaded
-
space
.
end
;
196
memmove(
space
.
begin
,
space
.
end
, left);
197
space
.
end
=
space
.
begin
;
198
endloaded
=
space
.
begin
+left;
199
}
200
if
(
fill
() > 0)
201
return
buf_read
(pointer,n);
// more bytes are read.
202
else
203
{
204
// No more bytes to read, return all that we have left.
205
pointer =
space
.
end
;
206
space
.
end
=
endloaded
;
207
return
endloaded
- pointer;
208
}
209
}
210
}
SHOGUN
Machine Learning Toolbox - Documentation