OLD | NEW |
1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // Streams classes. | 5 // Streams classes. |
6 // | 6 // |
7 // These memory-resident streams are used for serializing data into a sequential | 7 // These memory-resident streams are used for serializing data into a sequential |
8 // region of memory. | 8 // region of memory. |
9 // | 9 // |
10 // Streams are divided into SourceStreams for reading and SinkStreams for | 10 // Streams are divided into SourceStreams for reading and SinkStreams for |
11 // writing. Streams are aggregated into Sets which allows several streams to be | 11 // writing. Streams are aggregated into Sets which allows several streams to be |
12 // used at once. Example: we can write A1, B1, A2, B2 but achieve the memory | 12 // used at once. Example: we can write A1, B1, A2, B2 but achieve the memory |
13 // layout A1 A2 B1 B2 by writing 'A's to one stream and 'B's to another. | 13 // layout A1 A2 B1 B2 by writing 'A's to one stream and 'B's to another. |
14 // | 14 // |
15 // The aggregated streams are important to Courgette's compression efficiency, | 15 // The aggregated streams are important to Courgette's compression efficiency, |
16 // we use it to cluster similar kinds of data which helps to generate longer | 16 // we use it to cluster similar kinds of data which helps to generate longer |
17 // common subsequences and repeated sequences. | 17 // common subsequences and repeated sequences. |
18 | 18 |
19 #include "courgette/streams.h" | 19 #include "courgette/streams.h" |
20 | 20 |
21 #include <io.h> | |
22 #include <memory.h> | 21 #include <memory.h> |
23 | 22 |
24 #include "base/basictypes.h" | 23 #include "base/basictypes.h" |
25 | 24 |
26 namespace courgette { | 25 namespace courgette { |
27 | 26 |
28 // Update this version number if the serialization format of a StreamSet | 27 // Update this version number if the serialization format of a StreamSet |
29 // changes. | 28 // changes. |
30 static const unsigned int kStreamsSerializationFormatVersion = 20090218; | 29 static const unsigned int kStreamsSerializationFormatVersion = 20090218; |
31 | 30 |
(...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
248 size_t accumulated_length = 0; | 247 size_t accumulated_length = 0; |
249 | 248 |
250 for (size_t i = 0; i < count_; ++i) { | 249 for (size_t i = 0; i < count_; ++i) { |
251 finger = Varint::Parse32WithLimit(finger, end, &lengths[i]); | 250 finger = Varint::Parse32WithLimit(finger, end, &lengths[i]); |
252 if (finger == NULL) | 251 if (finger == NULL) |
253 return false; | 252 return false; |
254 accumulated_length += lengths[i]; | 253 accumulated_length += lengths[i]; |
255 } | 254 } |
256 | 255 |
257 // Remaining bytes should add up to sum of lengths. | 256 // Remaining bytes should add up to sum of lengths. |
258 if (end - finger != accumulated_length) | 257 if (static_cast<size_t>(end - finger) != accumulated_length) |
259 return false; | 258 return false; |
260 | 259 |
261 accumulated_length = finger - start; | 260 accumulated_length = finger - start; |
262 for (size_t i = 0; i < count_; ++i) { | 261 for (size_t i = 0; i < count_; ++i) { |
263 stream(i)->Init(start + accumulated_length, lengths[i]); | 262 stream(i)->Init(start + accumulated_length, lengths[i]); |
264 accumulated_length += lengths[i]; | 263 accumulated_length += lengths[i]; |
265 } | 264 } |
266 | 265 |
267 return true; | 266 return true; |
268 } | 267 } |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
328 bool SinkStreamSet::CopyTo(SinkStream *combined_stream) { | 327 bool SinkStreamSet::CopyTo(SinkStream *combined_stream) { |
329 SinkStream header; | 328 SinkStream header; |
330 CopyHeaderTo(&header); | 329 CopyHeaderTo(&header); |
331 combined_stream->Append(&header); | 330 combined_stream->Append(&header); |
332 for (size_t i = 0; i < count_; ++i) { | 331 for (size_t i = 0; i < count_; ++i) { |
333 combined_stream->Append(stream(i)); | 332 combined_stream->Append(stream(i)); |
334 } | 333 } |
335 return true; | 334 return true; |
336 } | 335 } |
337 | 336 |
338 namespace { | |
339 bool Write(int file_descriptor, SinkStream* sink) { | |
340 size_t length = sink->Length(); | |
341 const void *buffer = sink->Buffer(); | |
342 int bytes_written = _write(file_descriptor, buffer, length); | |
343 return bytes_written == length; | |
344 } | |
345 } | |
346 | |
347 bool SinkStreamSet::CopyToFileDescriptor(int file_descriptor) { | |
348 SinkStream header; | |
349 CopyHeaderTo(&header); | |
350 if (!Write(file_descriptor, &header)) | |
351 return false; | |
352 for (size_t i = 0; i < count_; ++i) { | |
353 if (!Write(file_descriptor, stream(i))) | |
354 return false; | |
355 } | |
356 return true; | |
357 } | |
358 | |
359 bool SinkStreamSet::WriteSet(SinkStreamSet* set) { | 337 bool SinkStreamSet::WriteSet(SinkStreamSet* set) { |
360 uint32 lengths[kMaxStreams]; | 338 uint32 lengths[kMaxStreams]; |
361 // 'stream_count' includes all non-empty streams and all empty stream numbered | 339 // 'stream_count' includes all non-empty streams and all empty stream numbered |
362 // lower than a non-empty stream. | 340 // lower than a non-empty stream. |
363 size_t stream_count = 0; | 341 size_t stream_count = 0; |
364 for (size_t i = 0; i < kMaxStreams; ++i) { | 342 for (size_t i = 0; i < kMaxStreams; ++i) { |
365 SinkStream* stream = set->stream(i); | 343 SinkStream* stream = set->stream(i); |
366 lengths[i] = stream->Length(); | 344 lengths[i] = stream->Length(); |
367 if (lengths[i] > 0) | 345 if (lengths[i] > 0) |
368 stream_count = i + 1; | 346 stream_count = i + 1; |
369 } | 347 } |
370 | 348 |
371 SinkStream* control_stream = this->stream(0); | 349 SinkStream* control_stream = this->stream(0); |
372 control_stream->WriteVarint32(stream_count); | 350 control_stream->WriteVarint32(stream_count); |
373 for (size_t i = 0; i < stream_count; ++i) { | 351 for (size_t i = 0; i < stream_count; ++i) { |
374 control_stream->WriteVarint32(lengths[i]); | 352 control_stream->WriteVarint32(lengths[i]); |
375 } | 353 } |
376 | 354 |
377 for (size_t i = 0; i < stream_count; ++i) { | 355 for (size_t i = 0; i < stream_count; ++i) { |
378 this->stream(i)->Append(set->stream(i)); | 356 this->stream(i)->Append(set->stream(i)); |
379 } | 357 } |
380 return true; | 358 return true; |
381 } | 359 } |
382 | 360 |
383 } // namespace | 361 } // namespace |
OLD | NEW |