File: reorderedfilebuffer.h

package info (click to toggle)
aoflagger 3.0.0-2
  • links: PTS, VCS
  • area: main
  • in suites: bullseye
  • size: 4,476 kB
  • sloc: cpp: 51,868; python: 152; sh: 25; makefile: 17
file content (74 lines) | stat: -rw-r--r-- 1,605 bytes parent folder | download | duplicates (2)
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
#ifndef REORDERED_FILE_BUFFER_H
#define REORDERED_FILE_BUFFER_H

#include <fstream>
#include <vector>
#include <set>

#include "../util/logger.h"

class ReorderedFileBuffer
{
public:
	ReorderedFileBuffer(std::ofstream* stream, size_t maxSize) :
		_nextWritePos(0), _unflushedSize(0), _maxSize(maxSize), _stream(stream)
	{
	}
	
	~ReorderedFileBuffer()
	{
		flush();
	}
	
	void seekp(size_t offset)
	{
		_nextWritePos = offset;
	}
	
	void write(const char* data, size_t length)
	{
		_buffer.insert(BufferEntry(_nextWritePos, data, length));
		_nextWritePos += length;
		_unflushedSize += length + sizeof(_nextWritePos)*2;
		
		if(_unflushedSize > _maxSize)
			flush();
	}
	
	void flush()
	{
		Logger::Debug << "Flushing reordered file buffer...\n";
		for(std::set<BufferEntry>::const_iterator i=_buffer.begin(); i!=_buffer.end(); ++i)
		{
			_stream->seekp(i->position, std::ios_base::beg);
			_stream->write(i->data.data(), i->data.size());
			if(_stream->fail())
				throw std::runtime_error("Error: failed to write to reordered file! Check access rights and free disk space.");
		}
		_buffer.clear();
		_unflushedSize = 0;
	}
	
	std::ofstream& stream() { return *_stream; }
	
private:
	struct BufferEntry {
		BufferEntry(size_t pos_, const char* data_, size_t length_) :
			position(pos_),
			data(data_, data_ + length_)
		{ }
		bool operator<(const BufferEntry& other) const
		{
			return position < other.position;
		}
		size_t position;
		std::vector<char> data;
	};
	std::set<BufferEntry> _buffer;
	size_t _nextWritePos;
	size_t _unflushedSize;
	size_t _maxSize;
	std::ofstream* _stream;
};

#endif