git repos / blockattack-game

blame: source/code/physfs_stream.hpp

normal view · raw

aca2f4b0 sago007 2009-05-10 18:11 1
/*
aca2f4b0 sago007 2009-05-10 18:11 2
physfs_stream.hpp
aca2f4b0 sago007 2009-05-10 18:11 3
    Copyright (C) 2009 Poul Sander
aca2f4b0 sago007 2009-05-10 18:11 4
        Copied from Warzone 2100
aca2f4b0 sago007 2009-05-10 18:11 5
        http://svn.gna.org/viewcvs/warzone/branches/sound/lib/sound/general/physfs_stream.hpp?rev=3623
aca2f4b0 sago007 2009-05-10 18:11 6
	Copyright (C) 2007 Warzone Resurrection Project
aca2f4b0 sago007 2009-05-10 18:11 7
	Copyright (C) 2007 Giel van Schijndel <me@mortis.eu>
aca2f4b0 sago007 2009-05-10 18:11 8
	Originally part of SuperTux:
aca2f4b0 sago007 2009-05-10 18:11 9
	http://svn.berlios.de/svnroot/repos/supertux/trunk/supertux/src/physfs/physfs_stream.cpp revision 4176
aca2f4b0 sago007 2009-05-10 18:11 10
	Copyright (C) 2006 Matthias Braun <matze@braunis.de>
aca2f4b0 sago007 2009-05-10 18:11 11
aca2f4b0 sago007 2009-05-10 18:11 12
    This program is free software; you can redistribute it and/or modify
aca2f4b0 sago007 2009-05-10 18:11 13
    it under the terms of the GNU General Public License as published by
aca2f4b0 sago007 2009-05-10 18:11 14
    the Free Software Foundation; either version 2 of the License, or
aca2f4b0 sago007 2009-05-10 18:11 15
    (at your option) any later version.
aca2f4b0 sago007 2009-05-10 18:11 16
aca2f4b0 sago007 2009-05-10 18:11 17
    This program is distributed in the hope that it will be useful,
aca2f4b0 sago007 2009-05-10 18:11 18
    but WITHOUT ANY WARRANTY; without even the implied warranty of
aca2f4b0 sago007 2009-05-10 18:11 19
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
aca2f4b0 sago007 2009-05-10 18:11 20
    GNU General Public License for more details.
aca2f4b0 sago007 2009-05-10 18:11 21
aca2f4b0 sago007 2009-05-10 18:11 22
    You should have received a copy of the GNU General Public License
aca2f4b0 sago007 2009-05-10 18:11 23
    along with this program; if not, write to the Free Software
aca2f4b0 sago007 2009-05-10 18:11 24
    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
aca2f4b0 sago007 2009-05-10 18:11 25
aca2f4b0 sago007 2009-05-10 18:11 26
    Poul Sander
aca2f4b0 sago007 2009-05-10 18:11 27
    blockattack@poulsander.com
aca2f4b0 sago007 2009-05-10 18:11 28
*/
aca2f4b0 sago007 2009-05-10 18:11 29
aca2f4b0 sago007 2009-05-10 18:11 30
#ifndef __INCLUDED_PHYSFS_STREAM_HPP__
aca2f4b0 sago007 2009-05-10 18:11 31
#define __INCLUDED_PHYSFS_STREAM_HPP__
aca2f4b0 sago007 2009-05-10 18:11 32
aca2f4b0 sago007 2009-05-10 18:11 33
#define BUF_SIZE 1024
aca2f4b0 sago007 2009-05-10 18:11 34
aca2f4b0 sago007 2009-05-10 18:11 35
#include <physfs.h>
aca2f4b0 sago007 2009-05-10 18:11 36
#include <streambuf>
aca2f4b0 sago007 2009-05-10 18:11 37
#include <istream>
aca2f4b0 sago007 2009-05-10 18:11 38
#include <ostream>
aca2f4b0 sago007 2009-05-10 18:11 39
/*Compared to Warzone 2100 boost:array has been replaced by vector to limit
aca2f4b0 sago007 2009-05-10 18:11 40
 the compile requirements*/
aca2f4b0 sago007 2009-05-10 18:11 41
#include <vector>
aca2f4b0 sago007 2009-05-10 18:11 42
aca2f4b0 sago007 2009-05-10 18:11 43
/** This an implementation of "File-based streams" as described in the
aca2f4b0 sago007 2009-05-10 18:11 44
 *  ISO/IEC 14882:1998(E) C++ Standard in chapter 27 "Input/output library",
aca2f4b0 sago007 2009-05-10 18:11 45
 *  section 8 "File-based streams". This implementation however uses PhysicsFS
aca2f4b0 sago007 2009-05-10 18:11 46
 *  instead of the C-library's FILE functions. Also this implementation lacks
aca2f4b0 sago007 2009-05-10 18:11 47
 *  an implementation of basic_fstream because PhysicsFS does not support
aca2f4b0 sago007 2009-05-10 18:11 48
 *  opening a file both for reading as well as writing.
aca2f4b0 sago007 2009-05-10 18:11 49
 *
aca2f4b0 sago007 2009-05-10 18:11 50
 *  This header contains similar classes and typedefs as <fstream> does. Both
aca2f4b0 sago007 2009-05-10 18:11 51
 *  similar in names as well as operation, the main difference is that these
aca2f4b0 sago007 2009-05-10 18:11 52
 *  classes do _not_ reside in namespace std.
aca2f4b0 sago007 2009-05-10 18:11 53
 */
aca2f4b0 sago007 2009-05-10 18:11 54
namespace PhysFS
aca2f4b0 sago007 2009-05-10 18:11 55
{
c53e6443 sago007 2012-04-17 11:04 56
/** Typedefinitions mandated by the C++ standard in section 27.8.1
c53e6443 sago007 2012-04-17 11:04 57
 */
c53e6443 sago007 2012-04-17 11:04 58
template<typename _CharT, typename _Traits = std::char_traits<_CharT> >
c53e6443 sago007 2012-04-17 11:04 59
class physfs_filebuf;
c53e6443 sago007 2012-04-17 11:04 60
typedef physfs_filebuf<char>        filebuf;
c53e6443 sago007 2012-04-17 11:04 61
typedef physfs_filebuf<wchar_t>     wfilebuf;
c53e6443 sago007 2012-04-17 11:04 62
c53e6443 sago007 2012-04-17 11:04 63
template<typename _CharT, typename _Traits = std::char_traits<_CharT> >
c53e6443 sago007 2012-04-17 11:04 64
class physfs_ifstream;
c53e6443 sago007 2012-04-17 11:04 65
typedef physfs_ifstream<char>       ifstream;
c53e6443 sago007 2012-04-17 11:04 66
typedef physfs_ifstream<wchar_t>    wifstream;
c53e6443 sago007 2012-04-17 11:04 67
c53e6443 sago007 2012-04-17 11:04 68
template<typename _CharT, typename _Traits = std::char_traits<_CharT> >
c53e6443 sago007 2012-04-17 11:04 69
class physfs_ofstream;
c53e6443 sago007 2012-04-17 11:04 70
typedef physfs_ofstream<char>       ofstream;
c53e6443 sago007 2012-04-17 11:04 71
typedef physfs_ofstream<wchar_t>    wofstream;
c53e6443 sago007 2012-04-17 11:04 72
c53e6443 sago007 2012-04-17 11:04 73
/** This class implements a C++ streambuf object for physfs files.
c53e6443 sago007 2012-04-17 11:04 74
 *  So that you can use normal istream and ostream operations on them.
c53e6443 sago007 2012-04-17 11:04 75
 *  This class is similar to std::basic_filebuf as defined in
c53e6443 sago007 2012-04-17 11:04 76
 *  section 27.8.1.1, except in name.
c53e6443 sago007 2012-04-17 11:04 77
 */
c53e6443 sago007 2012-04-17 11:04 78
template<typename _CharT, typename _Traits>
c53e6443 sago007 2012-04-17 11:04 79
class physfs_filebuf : public std::basic_streambuf<_CharT, _Traits>
c53e6443 sago007 2012-04-17 11:04 80
{
c53e6443 sago007 2012-04-17 11:04 81
public:
c53e6443 sago007 2012-04-17 11:04 82
	// Types:
c53e6443 sago007 2012-04-17 11:04 83
	typedef _CharT                                  char_type;
c53e6443 sago007 2012-04-17 11:04 84
	typedef _Traits                                 traits_type;
c53e6443 sago007 2012-04-17 11:04 85
	typedef typename traits_type::int_type          int_type;
c53e6443 sago007 2012-04-17 11:04 86
	typedef typename traits_type::pos_type          pos_type;
c53e6443 sago007 2012-04-17 11:04 87
	typedef typename traits_type::off_type          off_type;
c53e6443 sago007 2012-04-17 11:04 88
c53e6443 sago007 2012-04-17 11:04 89
	typedef std::basic_streambuf<_CharT, _Traits>   __streambuf_type;
c53e6443 sago007 2012-04-17 11:04 90
	typedef physfs_filebuf<_CharT, _Traits>         __filebuf_type;
c53e6443 sago007 2012-04-17 11:04 91
c53e6443 sago007 2012-04-17 11:04 92
	physfs_filebuf() :
c53e6443 sago007 2012-04-17 11:04 93
		_file(0)
c53e6443 sago007 2012-04-17 11:04 94
	{
c53e6443 sago007 2012-04-17 11:04 95
		_buf.resize(BUF_SIZE);
c53e6443 sago007 2012-04-17 11:04 96
	}
c53e6443 sago007 2012-04-17 11:04 97
c53e6443 sago007 2012-04-17 11:04 98
	virtual ~physfs_filebuf()
c53e6443 sago007 2012-04-17 11:04 99
	{
c53e6443 sago007 2012-04-17 11:04 100
		close();
c53e6443 sago007 2012-04-17 11:04 101
	}
c53e6443 sago007 2012-04-17 11:04 102
c53e6443 sago007 2012-04-17 11:04 103
	bool is_open() const throw()
c53e6443 sago007 2012-04-17 11:04 104
	{
c53e6443 sago007 2012-04-17 11:04 105
		return (_file != 0);
c53e6443 sago007 2012-04-17 11:04 106
	}
c53e6443 sago007 2012-04-17 11:04 107
c53e6443 sago007 2012-04-17 11:04 108
	__filebuf_type* open(const char* fileName, std::ios_base::openmode mode)
c53e6443 sago007 2012-04-17 11:04 109
	{
c53e6443 sago007 2012-04-17 11:04 110
		// Return failure if this file buf is open already
c53e6443 sago007 2012-04-17 11:04 111
		if (is_open() != false)
c53e6443 sago007 2012-04-17 11:04 112
			return 0;
c53e6443 sago007 2012-04-17 11:04 113
c53e6443 sago007 2012-04-17 11:04 114
		// Return failure if we are requested to open a file in an unsupported mode
c53e6443 sago007 2012-04-17 11:04 115
		if (!(mode & std::ios_base::binary) ||
c53e6443 sago007 2012-04-17 11:04 116
				(mode & std::ios_base::in &&
c53e6443 sago007 2012-04-17 11:04 117
				 mode & std::ios_base::out))
c53e6443 sago007 2012-04-17 11:04 118
			return 0;
c53e6443 sago007 2012-04-17 11:04 119
c53e6443 sago007 2012-04-17 11:04 120
		// Open the file
c53e6443 sago007 2012-04-17 11:04 121
		if (mode & std::ios_base::out &&
c53e6443 sago007 2012-04-17 11:04 122
				mode & std::ios_base::app)
c53e6443 sago007 2012-04-17 11:04 123
		{
c53e6443 sago007 2012-04-17 11:04 124
			_file = PHYSFS_openAppend(fileName);
c53e6443 sago007 2012-04-17 11:04 125
			_writeStream = true;
c53e6443 sago007 2012-04-17 11:04 126
		}
c53e6443 sago007 2012-04-17 11:04 127
		else if (mode & std::ios_base::out)
c53e6443 sago007 2012-04-17 11:04 128
		{
c53e6443 sago007 2012-04-17 11:04 129
			_file = PHYSFS_openWrite(fileName);
c53e6443 sago007 2012-04-17 11:04 130
			_writeStream = true;
c53e6443 sago007 2012-04-17 11:04 131
		}
c53e6443 sago007 2012-04-17 11:04 132
		else if (mode & std::ios_base::in)
c53e6443 sago007 2012-04-17 11:04 133
		{
c53e6443 sago007 2012-04-17 11:04 134
			_file = PHYSFS_openRead(fileName);
c53e6443 sago007 2012-04-17 11:04 135
			_writeStream = false;
c53e6443 sago007 2012-04-17 11:04 136
		}
c53e6443 sago007 2012-04-17 11:04 137
		else
c53e6443 sago007 2012-04-17 11:04 138
		{
c53e6443 sago007 2012-04-17 11:04 139
			return 0;
c53e6443 sago007 2012-04-17 11:04 140
		}
c53e6443 sago007 2012-04-17 11:04 141
c53e6443 sago007 2012-04-17 11:04 142
		if (!_file)
c53e6443 sago007 2012-04-17 11:04 143
			return 0;
c53e6443 sago007 2012-04-17 11:04 144
c53e6443 sago007 2012-04-17 11:04 145
		if (mode & std::ios_base::ate &&
c53e6443 sago007 2012-04-17 11:04 146
				mode & std::ios_base::in)
c53e6443 sago007 2012-04-17 11:04 147
		{
c53e6443 sago007 2012-04-17 11:04 148
			if (!PHYSFS_seek(_file, PHYSFS_fileLength(_file)))
c53e6443 sago007 2012-04-17 11:04 149
			{
c53e6443 sago007 2012-04-17 11:04 150
				close();
c53e6443 sago007 2012-04-17 11:04 151
				return 0;
c53e6443 sago007 2012-04-17 11:04 152
			}
c53e6443 sago007 2012-04-17 11:04 153
		}
c53e6443 sago007 2012-04-17 11:04 154
c53e6443 sago007 2012-04-17 11:04 155
		return this;
c53e6443 sago007 2012-04-17 11:04 156
	}
c53e6443 sago007 2012-04-17 11:04 157
c53e6443 sago007 2012-04-17 11:04 158
	__filebuf_type* close()
c53e6443 sago007 2012-04-17 11:04 159
	{
c53e6443 sago007 2012-04-17 11:04 160
		// Return failure if this file buf is closed already
c53e6443 sago007 2012-04-17 11:04 161
		if (is_open() == false)
c53e6443 sago007 2012-04-17 11:04 162
			return 0;
c53e6443 sago007 2012-04-17 11:04 163
c53e6443 sago007 2012-04-17 11:04 164
		sync();
c53e6443 sago007 2012-04-17 11:04 165
c53e6443 sago007 2012-04-17 11:04 166
		if (!PHYSFS_close(_file))
c53e6443 sago007 2012-04-17 11:04 167
		{
c53e6443 sago007 2012-04-17 11:04 168
			return 0;
c53e6443 sago007 2012-04-17 11:04 169
		}
c53e6443 sago007 2012-04-17 11:04 170
c53e6443 sago007 2012-04-17 11:04 171
		_file = 0;
c53e6443 sago007 2012-04-17 11:04 172
c53e6443 sago007 2012-04-17 11:04 173
		return this;
c53e6443 sago007 2012-04-17 11:04 174
	}
c53e6443 sago007 2012-04-17 11:04 175
c53e6443 sago007 2012-04-17 11:04 176
protected:
c53e6443 sago007 2012-04-17 11:04 177
	// Read stuff:
c53e6443 sago007 2012-04-17 11:04 178
	virtual int_type underflow()
c53e6443 sago007 2012-04-17 11:04 179
	{
c53e6443 sago007 2012-04-17 11:04 180
		if (!is_open() || _writeStream)
c53e6443 sago007 2012-04-17 11:04 181
			return traits_type::eof();
c53e6443 sago007 2012-04-17 11:04 182
c53e6443 sago007 2012-04-17 11:04 183
		if(PHYSFS_eof(_file))
c53e6443 sago007 2012-04-17 11:04 184
		{
c53e6443 sago007 2012-04-17 11:04 185
			return traits_type::eof();
c53e6443 sago007 2012-04-17 11:04 186
		}
c53e6443 sago007 2012-04-17 11:04 187
c53e6443 sago007 2012-04-17 11:04 188
		PHYSFS_sint64 objectsRead = PHYSFS_read(_file, &*_buf.begin(), sizeof(char_type), BUF_SIZE);
c53e6443 sago007 2012-04-17 11:04 189
c53e6443 sago007 2012-04-17 11:04 190
		if(objectsRead <= 0)
c53e6443 sago007 2012-04-17 11:04 191
		{
c53e6443 sago007 2012-04-17 11:04 192
			return traits_type::eof();
c53e6443 sago007 2012-04-17 11:04 193
		}
c53e6443 sago007 2012-04-17 11:04 194
c53e6443 sago007 2012-04-17 11:04 195
		char_type* xend = (static_cast<size_t> (objectsRead) == BUF_SIZE) ? &*_buf.end() : &_buf[objectsRead];
e68d08eb sago007 2013-11-15 22:33 196
		this->setg(&*_buf.begin(), &*_buf.begin(), xend);
c53e6443 sago007 2012-04-17 11:04 197
c53e6443 sago007 2012-04-17 11:04 198
		return traits_type::to_int_type(_buf.front());
c53e6443 sago007 2012-04-17 11:04 199
	}
c53e6443 sago007 2012-04-17 11:04 200
c53e6443 sago007 2012-04-17 11:04 201
	virtual pos_type seekpos(pos_type pos, std::ios_base::openmode)
c53e6443 sago007 2012-04-17 11:04 202
	{
c53e6443 sago007 2012-04-17 11:04 203
		if (!is_open() || _writeStream)
c53e6443 sago007 2012-04-17 11:04 204
			return pos_type(off_type(-1));
c53e6443 sago007 2012-04-17 11:04 205
c53e6443 sago007 2012-04-17 11:04 206
		if(PHYSFS_seek(_file, static_cast<PHYSFS_uint64> (pos)) == 0)
c53e6443 sago007 2012-04-17 11:04 207
		{
c53e6443 sago007 2012-04-17 11:04 208
			return pos_type(off_type(-1));
c53e6443 sago007 2012-04-17 11:04 209
		}
c53e6443 sago007 2012-04-17 11:04 210
c53e6443 sago007 2012-04-17 11:04 211
		// the seek invalidated the buffer
e68d08eb sago007 2013-11-15 22:33 212
		this->setg(&*_buf.begin(), &*_buf.begin(), &*_buf.begin());
c53e6443 sago007 2012-04-17 11:04 213
		return pos;
c53e6443 sago007 2012-04-17 11:04 214
	}
c53e6443 sago007 2012-04-17 11:04 215
c53e6443 sago007 2012-04-17 11:04 216
	virtual pos_type seekoff(off_type off, std::ios_base::seekdir dir, std::ios_base::openmode mode)
c53e6443 sago007 2012-04-17 11:04 217
	{
c53e6443 sago007 2012-04-17 11:04 218
		if (!is_open() || _writeStream)
c53e6443 sago007 2012-04-17 11:04 219
			return pos_type(off_type(-1));
c53e6443 sago007 2012-04-17 11:04 220
c53e6443 sago007 2012-04-17 11:04 221
		off_type pos = off;
c53e6443 sago007 2012-04-17 11:04 222
c53e6443 sago007 2012-04-17 11:04 223
		switch (dir)
c53e6443 sago007 2012-04-17 11:04 224
		{
c53e6443 sago007 2012-04-17 11:04 225
		case std::ios_base::beg:
c53e6443 sago007 2012-04-17 11:04 226
			break;
c53e6443 sago007 2012-04-17 11:04 227
c53e6443 sago007 2012-04-17 11:04 228
		case std::ios_base::cur:
c53e6443 sago007 2012-04-17 11:04 229
		{
c53e6443 sago007 2012-04-17 11:04 230
			PHYSFS_sint64 ptell = PHYSFS_tell(_file);
c53e6443 sago007 2012-04-17 11:04 231
			pos_type buf_tell = static_cast<pos_type> (ptell) - static_cast<pos_type> (__streambuf_type::egptr() - __streambuf_type::gptr());
c53e6443 sago007 2012-04-17 11:04 232
			if(off == 0)
c53e6443 sago007 2012-04-17 11:04 233
			{
c53e6443 sago007 2012-04-17 11:04 234
				return buf_tell;
c53e6443 sago007 2012-04-17 11:04 235
			}
c53e6443 sago007 2012-04-17 11:04 236
c53e6443 sago007 2012-04-17 11:04 237
			pos += static_cast<off_type> (buf_tell);
c53e6443 sago007 2012-04-17 11:04 238
			break;
c53e6443 sago007 2012-04-17 11:04 239
		}
c53e6443 sago007 2012-04-17 11:04 240
c53e6443 sago007 2012-04-17 11:04 241
		case std::ios_base::end:
c53e6443 sago007 2012-04-17 11:04 242
			pos = static_cast<off_type> (PHYSFS_fileLength(_file)) - pos;
c53e6443 sago007 2012-04-17 11:04 243
			break;
c53e6443 sago007 2012-04-17 11:04 244
c53e6443 sago007 2012-04-17 11:04 245
		default:
c53e6443 sago007 2012-04-17 11:04 246
			//assert(!"invalid seekdirection");
c53e6443 sago007 2012-04-17 11:04 247
			return pos_type(off_type(-1));
c53e6443 sago007 2012-04-17 11:04 248
		}
c53e6443 sago007 2012-04-17 11:04 249
c53e6443 sago007 2012-04-17 11:04 250
		return seekpos(static_cast<pos_type> (pos), mode);
c53e6443 sago007 2012-04-17 11:04 251
	}
c53e6443 sago007 2012-04-17 11:04 252
c53e6443 sago007 2012-04-17 11:04 253
	// Write stuff:
c53e6443 sago007 2012-04-17 11:04 254
	virtual int_type overflow(int_type c = traits_type::eof())
c53e6443 sago007 2012-04-17 11:04 255
	{
c53e6443 sago007 2012-04-17 11:04 256
		if (!is_open() || !_writeStream)
c53e6443 sago007 2012-04-17 11:04 257
			return traits_type::eof();
c53e6443 sago007 2012-04-17 11:04 258
c53e6443 sago007 2012-04-17 11:04 259
		size_t size = __streambuf_type::pptr() - __streambuf_type::pbase();
c53e6443 sago007 2012-04-17 11:04 260
		if(size == 0)
c53e6443 sago007 2012-04-17 11:04 261
			return 0;
c53e6443 sago007 2012-04-17 11:04 262
c53e6443 sago007 2012-04-17 11:04 263
		PHYSFS_sint64 res = PHYSFS_write(_file, __streambuf_type::pbase(), sizeof(char_type), size);
c53e6443 sago007 2012-04-17 11:04 264
c53e6443 sago007 2012-04-17 11:04 265
		if(res <= 0)
c53e6443 sago007 2012-04-17 11:04 266
			return traits_type::eof();
c53e6443 sago007 2012-04-17 11:04 267
c53e6443 sago007 2012-04-17 11:04 268
		if(!traits_type::eq_int_type(c, traits_type::eof()))
c53e6443 sago007 2012-04-17 11:04 269
		{
c53e6443 sago007 2012-04-17 11:04 270
			PHYSFS_sint64 res = PHYSFS_write(_file, &c, sizeof(char_type), 1);
c53e6443 sago007 2012-04-17 11:04 271
c53e6443 sago007 2012-04-17 11:04 272
			if(res <= 0)
c53e6443 sago007 2012-04-17 11:04 273
				return traits_type::eof();
c53e6443 sago007 2012-04-17 11:04 274
		}
c53e6443 sago007 2012-04-17 11:04 275
c53e6443 sago007 2012-04-17 11:04 276
		char_type* xend = (static_cast<size_t> (res) == BUF_SIZE) ? &*_buf.end() : &_buf[res];
e68d08eb sago007 2013-11-15 22:33 277
		this->setp(&*_buf.begin(), xend);
c53e6443 sago007 2012-04-17 11:04 278
		return 0;
c53e6443 sago007 2012-04-17 11:04 279
	}
c53e6443 sago007 2012-04-17 11:04 280
c53e6443 sago007 2012-04-17 11:04 281
	virtual int sync()
c53e6443 sago007 2012-04-17 11:04 282
	{
c53e6443 sago007 2012-04-17 11:04 283
		if (!is_open() || !_writeStream)
c53e6443 sago007 2012-04-17 11:04 284
			return -1;
c53e6443 sago007 2012-04-17 11:04 285
c53e6443 sago007 2012-04-17 11:04 286
		return overflow(traits_type::eof());
c53e6443 sago007 2012-04-17 11:04 287
	}
c53e6443 sago007 2012-04-17 11:04 288
c53e6443 sago007 2012-04-17 11:04 289
	virtual std::streamsize showmanyc()
c53e6443 sago007 2012-04-17 11:04 290
	{
c53e6443 sago007 2012-04-17 11:04 291
		if (!is_open() || _writeStream)
c53e6443 sago007 2012-04-17 11:04 292
			return -1;
c53e6443 sago007 2012-04-17 11:04 293
c53e6443 sago007 2012-04-17 11:04 294
		PHYSFS_sint64 fileSize = PHYSFS_fileLength(_file);
c53e6443 sago007 2012-04-17 11:04 295
c53e6443 sago007 2012-04-17 11:04 296
		return static_cast<int> (fileSize);
c53e6443 sago007 2012-04-17 11:04 297
	}
c53e6443 sago007 2012-04-17 11:04 298
c53e6443 sago007 2012-04-17 11:04 299
private:
c53e6443 sago007 2012-04-17 11:04 300
	PHYSFS_file* _file;
c53e6443 sago007 2012-04-17 11:04 301
	bool _writeStream;
c53e6443 sago007 2012-04-17 11:04 302
	vector<char_type> _buf;
c53e6443 sago007 2012-04-17 11:04 303
};
c53e6443 sago007 2012-04-17 11:04 304
c53e6443 sago007 2012-04-17 11:04 305
/** This class implements a C++ istream object for physfs files.
c53e6443 sago007 2012-04-17 11:04 306
 *  This class is similar to std::basic_ifstream as defined in
c53e6443 sago007 2012-04-17 11:04 307
 *  section 27.8.1.5, except in name.
c53e6443 sago007 2012-04-17 11:04 308
 */
c53e6443 sago007 2012-04-17 11:04 309
template<typename _CharT, typename _Traits>
c53e6443 sago007 2012-04-17 11:04 310
class physfs_ifstream : public std::basic_istream<_CharT, _Traits>
c53e6443 sago007 2012-04-17 11:04 311
{
c53e6443 sago007 2012-04-17 11:04 312
public:
c53e6443 sago007 2012-04-17 11:04 313
	// Types:
c53e6443 sago007 2012-04-17 11:04 314
	typedef _CharT                                  char_type;
c53e6443 sago007 2012-04-17 11:04 315
	typedef _Traits                                 traits_type;
c53e6443 sago007 2012-04-17 11:04 316
	typedef typename traits_type::int_type          int_type;
c53e6443 sago007 2012-04-17 11:04 317
	typedef typename traits_type::pos_type          pos_type;
c53e6443 sago007 2012-04-17 11:04 318
	typedef typename traits_type::off_type          off_type;
c53e6443 sago007 2012-04-17 11:04 319
c53e6443 sago007 2012-04-17 11:04 320
	typedef physfs_filebuf<_CharT, _Traits>         __filebuf_type;
c53e6443 sago007 2012-04-17 11:04 321
	typedef std::basic_istream<_CharT, _Traits>     __istream_type;
c53e6443 sago007 2012-04-17 11:04 322
c53e6443 sago007 2012-04-17 11:04 323
	physfs_ifstream() throw() :
c53e6443 sago007 2012-04-17 11:04 324
		__istream_type(&_sb)
c53e6443 sago007 2012-04-17 11:04 325
	{
c53e6443 sago007 2012-04-17 11:04 326
	}
c53e6443 sago007 2012-04-17 11:04 327
c53e6443 sago007 2012-04-17 11:04 328
	explicit physfs_ifstream(const char* fileName, std::ios_base::openmode mode = std::ios_base::binary) :
c53e6443 sago007 2012-04-17 11:04 329
		__istream_type(&_sb)
c53e6443 sago007 2012-04-17 11:04 330
	{
c53e6443 sago007 2012-04-17 11:04 331
		open(fileName, mode);
c53e6443 sago007 2012-04-17 11:04 332
	}
c53e6443 sago007 2012-04-17 11:04 333
c53e6443 sago007 2012-04-17 11:04 334
	const __filebuf_type* rdbuf() const throw()
c53e6443 sago007 2012-04-17 11:04 335
	{
c53e6443 sago007 2012-04-17 11:04 336
		return &_sb;
c53e6443 sago007 2012-04-17 11:04 337
	}
c53e6443 sago007 2012-04-17 11:04 338
c53e6443 sago007 2012-04-17 11:04 339
	__filebuf_type* rdbuf() throw()
c53e6443 sago007 2012-04-17 11:04 340
	{
c53e6443 sago007 2012-04-17 11:04 341
		return &_sb;
c53e6443 sago007 2012-04-17 11:04 342
	}
c53e6443 sago007 2012-04-17 11:04 343
c53e6443 sago007 2012-04-17 11:04 344
	bool is_open() const throw()
c53e6443 sago007 2012-04-17 11:04 345
	{
c53e6443 sago007 2012-04-17 11:04 346
		return rdbuf()->is_open();
c53e6443 sago007 2012-04-17 11:04 347
	}
c53e6443 sago007 2012-04-17 11:04 348
c53e6443 sago007 2012-04-17 11:04 349
	void open(const char* fileName, std::ios_base::openmode mode = std::ios_base::binary)
c53e6443 sago007 2012-04-17 11:04 350
	{
c53e6443 sago007 2012-04-17 11:04 351
		if (!rdbuf()->open(fileName, mode | std::ios_base::in))
c53e6443 sago007 2012-04-17 11:04 352
		{
c53e6443 sago007 2012-04-17 11:04 353
			__istream_type::setstate(std::ios_base::failbit);
c53e6443 sago007 2012-04-17 11:04 354
		}
c53e6443 sago007 2012-04-17 11:04 355
	}
c53e6443 sago007 2012-04-17 11:04 356
c53e6443 sago007 2012-04-17 11:04 357
	void close()
c53e6443 sago007 2012-04-17 11:04 358
	{
c53e6443 sago007 2012-04-17 11:04 359
		if (!rdbuf()->close())
c53e6443 sago007 2012-04-17 11:04 360
		{
c53e6443 sago007 2012-04-17 11:04 361
			__istream_type::setstate(std::ios_base::failbit);
c53e6443 sago007 2012-04-17 11:04 362
		}
c53e6443 sago007 2012-04-17 11:04 363
	}
c53e6443 sago007 2012-04-17 11:04 364
c53e6443 sago007 2012-04-17 11:04 365
private:
c53e6443 sago007 2012-04-17 11:04 366
	__filebuf_type _sb;
c53e6443 sago007 2012-04-17 11:04 367
};
c53e6443 sago007 2012-04-17 11:04 368
c53e6443 sago007 2012-04-17 11:04 369
/** This class implements a C++ ostream object for physfs files.
c53e6443 sago007 2012-04-17 11:04 370
 *  This class is similar to std::basic_ofstream as defined in
c53e6443 sago007 2012-04-17 11:04 371
 *  section 27.8.1.8, except in name.
c53e6443 sago007 2012-04-17 11:04 372
 */
c53e6443 sago007 2012-04-17 11:04 373
template<typename _CharT, typename _Traits>
c53e6443 sago007 2012-04-17 11:04 374
class physfs_ofstream : public std::basic_ostream<_CharT, _Traits>
c53e6443 sago007 2012-04-17 11:04 375
{
c53e6443 sago007 2012-04-17 11:04 376
public:
c53e6443 sago007 2012-04-17 11:04 377
	// Types:
c53e6443 sago007 2012-04-17 11:04 378
	typedef _CharT                                  char_type;
c53e6443 sago007 2012-04-17 11:04 379
	typedef _Traits                                 traits_type;
c53e6443 sago007 2012-04-17 11:04 380
	typedef typename traits_type::int_type          int_type;
c53e6443 sago007 2012-04-17 11:04 381
	typedef typename traits_type::pos_type          pos_type;
c53e6443 sago007 2012-04-17 11:04 382
	typedef typename traits_type::off_type          off_type;
c53e6443 sago007 2012-04-17 11:04 383
c53e6443 sago007 2012-04-17 11:04 384
	typedef physfs_filebuf<_CharT, _Traits>         __filebuf_type;
c53e6443 sago007 2012-04-17 11:04 385
	typedef std::basic_ostream<_CharT, _Traits>     __ostream_type;
c53e6443 sago007 2012-04-17 11:04 386
c53e6443 sago007 2012-04-17 11:04 387
	physfs_ofstream() throw() :
c53e6443 sago007 2012-04-17 11:04 388
		__ostream_type(&_sb)
c53e6443 sago007 2012-04-17 11:04 389
	{
c53e6443 sago007 2012-04-17 11:04 390
	}
c53e6443 sago007 2012-04-17 11:04 391
c53e6443 sago007 2012-04-17 11:04 392
	explicit physfs_ofstream(const char* fileName, std::ios_base::openmode mode = std::ios_base::binary) :
c53e6443 sago007 2012-04-17 11:04 393
		__ostream_type(&_sb)
c53e6443 sago007 2012-04-17 11:04 394
	{
c53e6443 sago007 2012-04-17 11:04 395
		open(fileName, mode);
c53e6443 sago007 2012-04-17 11:04 396
	}
c53e6443 sago007 2012-04-17 11:04 397
c53e6443 sago007 2012-04-17 11:04 398
	const __filebuf_type* rdbuf() const throw()
c53e6443 sago007 2012-04-17 11:04 399
	{
c53e6443 sago007 2012-04-17 11:04 400
		return &_sb;
c53e6443 sago007 2012-04-17 11:04 401
	}
c53e6443 sago007 2012-04-17 11:04 402
c53e6443 sago007 2012-04-17 11:04 403
	__filebuf_type* rdbuf() throw()
c53e6443 sago007 2012-04-17 11:04 404
	{
c53e6443 sago007 2012-04-17 11:04 405
		return &_sb;
c53e6443 sago007 2012-04-17 11:04 406
	}
c53e6443 sago007 2012-04-17 11:04 407
c53e6443 sago007 2012-04-17 11:04 408
	bool is_open() const throw()
c53e6443 sago007 2012-04-17 11:04 409
	{
c53e6443 sago007 2012-04-17 11:04 410
		return rdbuf()->is_open();
c53e6443 sago007 2012-04-17 11:04 411
	}
c53e6443 sago007 2012-04-17 11:04 412
c53e6443 sago007 2012-04-17 11:04 413
	void open(const char* fileName, std::ios_base::openmode mode = std::ios_base::binary)
c53e6443 sago007 2012-04-17 11:04 414
	{
c53e6443 sago007 2012-04-17 11:04 415
		if (!rdbuf()->open(fileName, mode | std::ios_base::out))
c53e6443 sago007 2012-04-17 11:04 416
		{
c53e6443 sago007 2012-04-17 11:04 417
			__ostream_type::setstate(std::ios_base::failbit);
c53e6443 sago007 2012-04-17 11:04 418
		}
c53e6443 sago007 2012-04-17 11:04 419
	}
c53e6443 sago007 2012-04-17 11:04 420
c53e6443 sago007 2012-04-17 11:04 421
	void close()
c53e6443 sago007 2012-04-17 11:04 422
	{
c53e6443 sago007 2012-04-17 11:04 423
		if (!rdbuf()->close())
c53e6443 sago007 2012-04-17 11:04 424
		{
c53e6443 sago007 2012-04-17 11:04 425
			__ostream_type::setstate(std::ios_base::failbit);
c53e6443 sago007 2012-04-17 11:04 426
		}
c53e6443 sago007 2012-04-17 11:04 427
	}
c53e6443 sago007 2012-04-17 11:04 428
c53e6443 sago007 2012-04-17 11:04 429
private:
c53e6443 sago007 2012-04-17 11:04 430
	__filebuf_type _sb;
c53e6443 sago007 2012-04-17 11:04 431
};
aca2f4b0 sago007 2009-05-10 18:11 432
}
aca2f4b0 sago007 2009-05-10 18:11 433
aca2f4b0 sago007 2009-05-10 18:11 434
#endif // __INCLUDED_PHYSFS_STREAM_HPP__
1970-01-01 00:00 435