2005-04-05 15:53:16 +00:00
|
|
|
/* ScummVM - Scumm Interpreter
|
|
|
|
* Copyright (C) 2004 Ivan Dubrov
|
2006-01-18 17:39:49 +00:00
|
|
|
* Copyright (C) 2004-2006 The ScummVM project
|
2005-04-05 15:53:16 +00:00
|
|
|
*
|
|
|
|
* This program is free software; you can redistribute it and/or
|
|
|
|
* modify it under the terms of the GNU General Public License
|
|
|
|
* as published by the Free Software Foundation; either version 2
|
|
|
|
* of the License, or (at your option) any later version.
|
|
|
|
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
|
|
|
|
* You should have received a copy of the GNU General Public License
|
2005-04-09 19:19:54 +00:00
|
|
|
* along with this program; if not, write to the Free Software
|
2005-10-18 01:30:26 +00:00
|
|
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
2005-04-05 15:53:16 +00:00
|
|
|
*
|
2006-02-11 10:11:37 +00:00
|
|
|
* $URL$
|
|
|
|
* $Id$
|
2005-04-05 15:53:16 +00:00
|
|
|
*
|
|
|
|
*/
|
2007-03-20 14:51:57 +00:00
|
|
|
|
|
|
|
#include "common/stdafx.h"
|
|
|
|
#include "common/endian.h"
|
|
|
|
|
2005-04-05 15:07:40 +00:00
|
|
|
#include "gob/gob.h"
|
|
|
|
#include "gob/dataio.h"
|
2007-03-20 14:51:57 +00:00
|
|
|
#include "gob/global.h"
|
2005-04-05 15:07:40 +00:00
|
|
|
|
|
|
|
namespace Gob {
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
DataIO::DataIO(GobEngine *vm) : _vm(vm) {
|
2007-03-20 14:51:57 +00:00
|
|
|
for (int i = 0; i < MAX_DATA_FILES; i++) {
|
|
|
|
_dataFiles[i] = 0;
|
|
|
|
_numDataChunks[i] = 0;
|
|
|
|
_dataFileHandles[i] = -1;
|
|
|
|
}
|
|
|
|
_packedSize = 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
int32 DataIO::unpackData(char *sourceBuf, char *destBuf) {
|
|
|
|
uint32 realSize;
|
|
|
|
uint32 counter;
|
|
|
|
uint16 cmd;
|
|
|
|
byte *src;
|
|
|
|
byte *dest;
|
|
|
|
byte *tmpBuf;
|
|
|
|
int16 off;
|
|
|
|
byte len;
|
|
|
|
uint16 tmpIndex;
|
|
|
|
|
|
|
|
tmpBuf = new byte[4114];
|
|
|
|
assert(tmpBuf);
|
|
|
|
|
|
|
|
counter = realSize = READ_LE_UINT32(sourceBuf);
|
|
|
|
|
|
|
|
for (int i = 0; i < 4078; i++)
|
|
|
|
tmpBuf[i] = 0x20;
|
|
|
|
tmpIndex = 4078;
|
|
|
|
|
|
|
|
src = (byte *) (sourceBuf + 4);
|
|
|
|
dest = (byte *) destBuf;
|
|
|
|
|
|
|
|
cmd = 0;
|
|
|
|
while (1) {
|
|
|
|
cmd >>= 1;
|
|
|
|
if ((cmd & 0x0100) == 0) {
|
|
|
|
cmd = *src | 0xFF00;
|
|
|
|
src++;
|
|
|
|
}
|
|
|
|
if ((cmd & 1) != 0) { /* copy */
|
|
|
|
*dest++ = *src;
|
|
|
|
tmpBuf[tmpIndex] = *src;
|
|
|
|
src++;
|
|
|
|
tmpIndex++;
|
|
|
|
tmpIndex %= 4096;
|
|
|
|
counter--;
|
|
|
|
if (counter == 0)
|
|
|
|
break;
|
|
|
|
} else { /* copy string */
|
|
|
|
|
|
|
|
off = *src++;
|
|
|
|
off |= (*src & 0xF0) << 4;
|
|
|
|
len = (*src & 0x0F) + 3;
|
|
|
|
src++;
|
|
|
|
|
|
|
|
for (int i = 0; i < len; i++) {
|
|
|
|
*dest++ = tmpBuf[(off + i) % 4096];
|
|
|
|
counter--;
|
|
|
|
if (counter == 0) {
|
|
|
|
delete[] tmpBuf;
|
|
|
|
return realSize;
|
|
|
|
}
|
|
|
|
tmpBuf[tmpIndex] = tmpBuf[(off + i) % 4096];
|
|
|
|
tmpIndex++;
|
|
|
|
tmpIndex %= 4096;
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
delete[] tmpBuf;
|
|
|
|
return realSize;
|
2005-04-05 15:07:40 +00:00
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
Common::File *DataIO::file_getHandle(int16 handle) {
|
2006-01-04 01:48:15 +00:00
|
|
|
return &_vm->_global->_filesHandles[handle];
|
2006-01-03 23:14:39 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int16 DataIO::file_open(const char *path, Common::File::AccessMode mode) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int16 i;
|
|
|
|
|
|
|
|
for (i = 0; i < MAX_FILES; i++) {
|
2005-11-22 13:17:08 +00:00
|
|
|
if (!file_getHandle(i)->isOpen())
|
2005-04-05 15:07:40 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (i == MAX_FILES)
|
|
|
|
return -1;
|
|
|
|
|
2005-11-22 13:17:08 +00:00
|
|
|
file_getHandle(i)->open(path, mode);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2005-11-22 13:17:08 +00:00
|
|
|
if (file_getHandle(i)->isOpen())
|
2005-04-05 15:07:40 +00:00
|
|
|
return i;
|
2005-07-30 21:11:48 +00:00
|
|
|
|
2005-04-05 15:07:40 +00:00
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
int16 DataIO::getChunk(const char *chunkName) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int16 slot;
|
|
|
|
struct ChunkDesc *dataDesc;
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
for (int16 file = 0; file < MAX_DATA_FILES; file++) {
|
|
|
|
if (_dataFiles[file] == 0)
|
2005-04-05 15:07:40 +00:00
|
|
|
return -1;
|
|
|
|
|
|
|
|
for (slot = 0; slot < MAX_SLOT_COUNT; slot++)
|
2007-03-20 14:51:57 +00:00
|
|
|
if (_chunkPos[file * MAX_SLOT_COUNT + slot] == -1)
|
2005-04-05 15:07:40 +00:00
|
|
|
break;
|
|
|
|
|
|
|
|
if (slot == MAX_SLOT_COUNT)
|
|
|
|
return -1;
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
dataDesc = _dataFiles[file];
|
|
|
|
for (int16 chunk = 0; chunk < _numDataChunks[file]; chunk++, dataDesc++) {
|
2005-04-05 15:07:40 +00:00
|
|
|
if (scumm_stricmp(chunkName, dataDesc->chunkName) != 0)
|
|
|
|
continue;
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
_isCurrentSlot[file * MAX_SLOT_COUNT + slot] = false;
|
|
|
|
_chunkSize[file * MAX_SLOT_COUNT + slot] = dataDesc->size;
|
|
|
|
_chunkOffset[file * MAX_SLOT_COUNT + slot] = dataDesc->offset;
|
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + slot] = 0;
|
2005-04-05 15:07:40 +00:00
|
|
|
return file * 10 + slot + 50;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
char DataIO::freeChunk(int16 handle) {
|
2007-03-20 14:51:57 +00:00
|
|
|
if ((handle >= 50) && (handle < 100)) {
|
2005-04-05 15:07:40 +00:00
|
|
|
handle -= 50;
|
2007-03-20 14:51:57 +00:00
|
|
|
_chunkPos[(handle / 10) * MAX_SLOT_COUNT + (handle % 10)] = -1;
|
2005-04-05 15:07:40 +00:00
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
int32 DataIO::readChunk(int16 handle, char *buf, uint16 size) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int16 file;
|
|
|
|
int16 slot;
|
|
|
|
int16 i;
|
|
|
|
int32 offset;
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
if ((handle < 50) || (handle >= 100))
|
2005-04-05 15:07:40 +00:00
|
|
|
return -2;
|
|
|
|
|
|
|
|
file = (handle - 50) / 10;
|
|
|
|
slot = (handle - 50) % 10;
|
2007-03-20 14:51:57 +00:00
|
|
|
if (!_isCurrentSlot[file * MAX_SLOT_COUNT + slot]) {
|
2005-04-05 15:07:40 +00:00
|
|
|
for (i = 0; i < MAX_SLOT_COUNT; i++)
|
2007-03-20 14:51:57 +00:00
|
|
|
_isCurrentSlot[file * MAX_SLOT_COUNT + i] = false;
|
|
|
|
|
|
|
|
offset = _chunkOffset[file * MAX_SLOT_COUNT + slot] +
|
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + slot];
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
debugC(7, kDebugFileIO, "seek: %d, %d",
|
|
|
|
_chunkOffset[file * MAX_SLOT_COUNT + slot],
|
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + slot]);
|
|
|
|
|
|
|
|
file_getHandle(_dataFileHandles[file])->seek(offset, SEEK_SET);
|
2005-04-05 15:07:40 +00:00
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
_isCurrentSlot[file * MAX_SLOT_COUNT + slot] = true;
|
|
|
|
if ((_chunkPos[file * MAX_SLOT_COUNT + slot] + size) >
|
|
|
|
(_chunkSize[file * MAX_SLOT_COUNT + slot]))
|
|
|
|
size = _chunkSize[file * MAX_SLOT_COUNT + slot] -
|
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + slot];
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
file_getHandle(_dataFileHandles[file])->read(buf, size);
|
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + slot] += size;
|
2005-04-05 15:07:40 +00:00
|
|
|
return size;
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
int16 DataIO::seekChunk(int16 handle, int32 pos, int16 from) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int16 file;
|
|
|
|
int16 slot;
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
if ((handle < 50) || (handle >= 100))
|
2005-04-05 15:07:40 +00:00
|
|
|
return -1;
|
|
|
|
|
|
|
|
file = (handle - 50) / 10;
|
|
|
|
slot = (handle - 50) % 10;
|
2007-03-20 14:51:57 +00:00
|
|
|
_isCurrentSlot[file * MAX_SLOT_COUNT + slot] = false;
|
2005-04-05 15:07:40 +00:00
|
|
|
if (from == SEEK_SET)
|
2007-03-20 14:51:57 +00:00
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + slot] = pos;
|
2005-04-05 15:07:40 +00:00
|
|
|
else
|
2007-03-20 14:51:57 +00:00
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + slot] += pos;
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
return _chunkPos[file * MAX_SLOT_COUNT + slot];
|
2005-04-05 15:07:40 +00:00
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
int32 DataIO::getChunkSize(const char *chunkName) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int16 file;
|
|
|
|
int16 chunk;
|
|
|
|
struct ChunkDesc *dataDesc;
|
|
|
|
int16 slot;
|
|
|
|
int32 realSize;
|
|
|
|
|
|
|
|
for (file = 0; file < MAX_DATA_FILES; file++) {
|
2007-03-20 14:51:57 +00:00
|
|
|
if (_dataFiles[file] == 0)
|
2005-04-05 15:07:40 +00:00
|
|
|
return -1;
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
dataDesc = _dataFiles[file];
|
|
|
|
for (chunk = 0; chunk < _numDataChunks[file]; chunk++, dataDesc++) {
|
2005-04-05 15:07:40 +00:00
|
|
|
if (scumm_stricmp(chunkName, dataDesc->chunkName) != 0)
|
|
|
|
continue;
|
|
|
|
|
|
|
|
if (dataDesc->packed == 0) {
|
2007-03-20 14:51:57 +00:00
|
|
|
_packedSize = -1;
|
2005-04-05 15:07:40 +00:00
|
|
|
return dataDesc->size;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (slot = 0; slot < MAX_SLOT_COUNT; slot++)
|
2007-03-20 14:51:57 +00:00
|
|
|
_isCurrentSlot[slot] = false;
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
file_getHandle(_dataFileHandles[file])->seek(dataDesc->offset, SEEK_SET);
|
|
|
|
realSize = file_getHandle(_dataFileHandles[file])->readUint32LE();
|
|
|
|
_packedSize = dataDesc->size;
|
2005-04-05 15:07:40 +00:00
|
|
|
return realSize;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
void DataIO::openDataFile(const char *src, bool itk) {
|
|
|
|
ChunkDesc *dataDesc;
|
2005-04-05 15:07:40 +00:00
|
|
|
char path[128];
|
|
|
|
int16 file;
|
|
|
|
|
|
|
|
strcpy(path, src);
|
2007-03-20 14:51:57 +00:00
|
|
|
if (!strchr(path, '.'))
|
2005-04-05 15:07:40 +00:00
|
|
|
strcat(path, ".stk");
|
|
|
|
|
|
|
|
for (file = 0; file < MAX_DATA_FILES; file++)
|
2007-03-20 14:51:57 +00:00
|
|
|
if (_dataFiles[file] == 0)
|
2005-04-05 15:07:40 +00:00
|
|
|
break;
|
|
|
|
|
|
|
|
if (file == MAX_DATA_FILES)
|
2007-03-20 14:51:57 +00:00
|
|
|
error("openDataFile: Data file slots are full");
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
_dataFileHandles[file] = file_open(path);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
if (_dataFileHandles[file] == -1)
|
|
|
|
error("openDataFile: Can't open %s data file", path);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
_dataFileItk[file] = itk;
|
|
|
|
_numDataChunks[file] = file_getHandle(_dataFileHandles[file])->readUint16LE();
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
debugC(7, kDebugFileIO, "DataChunks: %d [for %s]", _numDataChunks[file], path);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
dataDesc = new ChunkDesc[_numDataChunks[file]];
|
|
|
|
_dataFiles[file] = dataDesc;
|
|
|
|
|
|
|
|
for (int i = 0; i < _numDataChunks[file]; i++) {
|
|
|
|
file_getHandle(_dataFileHandles[file])->read(dataDesc[i].chunkName, 13);
|
|
|
|
dataDesc[i].size = file_getHandle(_dataFileHandles[file])->readUint32LE();
|
|
|
|
dataDesc[i].offset = file_getHandle(_dataFileHandles[file])->readUint32LE();
|
|
|
|
dataDesc[i].packed = file_getHandle(_dataFileHandles[file])->readByte();
|
2005-04-05 15:07:40 +00:00
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
for (int i = 0; i < _numDataChunks[file]; i++)
|
2007-01-13 15:35:02 +00:00
|
|
|
debugC(7, kDebugFileIO, "%d: %s %d", i, dataDesc[i].chunkName, dataDesc[i].size);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
for (int i = 0; i < MAX_SLOT_COUNT; i++)
|
|
|
|
_chunkPos[file * MAX_SLOT_COUNT + i] = -1;
|
2005-04-05 15:07:40 +00:00
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
void DataIO::closeDataFile(bool itk) {
|
|
|
|
for (int file = MAX_DATA_FILES - 1; file >= 0; file--) {
|
|
|
|
if (_dataFiles[file] && (_dataFileItk[file] == itk)) {
|
|
|
|
delete[] _dataFiles[file];
|
|
|
|
_dataFiles[file] = 0;
|
|
|
|
file_getHandle(_dataFileHandles[file])->close();
|
2005-04-05 15:07:40 +00:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
char *DataIO::getUnpackedData(const char *name) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int32 realSize;
|
|
|
|
int16 chunk;
|
|
|
|
char *unpackBuf;
|
|
|
|
char *packBuf;
|
|
|
|
char *ptr;
|
|
|
|
int32 sizeLeft;
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
realSize = getChunkSize(name);
|
2007-03-20 14:51:57 +00:00
|
|
|
if ((_packedSize == -1) || (realSize == -1))
|
2005-04-05 15:07:40 +00:00
|
|
|
return 0;
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
chunk = getChunk(name);
|
2005-04-05 15:07:40 +00:00
|
|
|
if (chunk == -1)
|
|
|
|
return 0;
|
|
|
|
|
2006-01-29 02:27:10 +00:00
|
|
|
unpackBuf = new char[realSize];
|
2007-03-20 14:51:57 +00:00
|
|
|
assert(unpackBuf);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
packBuf = new char[_packedSize];
|
|
|
|
assert(packBuf);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
sizeLeft = _packedSize;
|
2005-04-05 15:07:40 +00:00
|
|
|
ptr = packBuf;
|
|
|
|
while (sizeLeft > 0x4000) {
|
2006-01-03 23:14:39 +00:00
|
|
|
readChunk(chunk, ptr, 0x4000);
|
2005-04-05 15:07:40 +00:00
|
|
|
sizeLeft -= 0x4000;
|
|
|
|
ptr += 0x4000;
|
|
|
|
}
|
2006-01-03 23:14:39 +00:00
|
|
|
readChunk(chunk, ptr, sizeLeft);
|
|
|
|
freeChunk(chunk);
|
2007-03-20 14:51:57 +00:00
|
|
|
unpackData(packBuf, unpackBuf);
|
2006-01-29 02:27:10 +00:00
|
|
|
|
|
|
|
delete[] packBuf;
|
2005-04-05 15:07:40 +00:00
|
|
|
return unpackBuf;
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
void DataIO::closeData(int16 handle) {
|
|
|
|
if (freeChunk(handle) != 0)
|
2005-04-05 15:07:40 +00:00
|
|
|
file_getHandle(handle)->close();
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
int16 DataIO::openData(const char *path, Common::File::AccessMode mode) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int16 handle;
|
|
|
|
|
2005-05-10 22:56:25 +00:00
|
|
|
if (mode != Common::File::kFileReadMode)
|
2005-04-05 15:07:40 +00:00
|
|
|
return file_open(path, mode);
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
handle = getChunk(path);
|
2005-04-05 15:07:40 +00:00
|
|
|
if (handle >= 0)
|
|
|
|
return handle;
|
|
|
|
|
|
|
|
return file_open(path, mode);
|
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
int32 DataIO::readData(int16 handle, char *buf, uint16 size) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int32 res;
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
res = readChunk(handle, buf, size);
|
2005-04-05 15:07:40 +00:00
|
|
|
if (res >= 0)
|
|
|
|
return res;
|
|
|
|
|
|
|
|
return file_getHandle(handle)->read(buf, size);
|
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
int32 DataIO::writeData(int16 handle, char *buf, uint16 size) {
|
|
|
|
return file_getHandle(handle)->write(buf, size);
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
void DataIO::seekData(int16 handle, int32 pos, int16 from) {
|
2005-04-05 15:07:40 +00:00
|
|
|
int32 resPos;
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
resPos = seekChunk(handle, pos, from);
|
2005-04-05 15:07:40 +00:00
|
|
|
if (resPos != -1)
|
|
|
|
return;
|
|
|
|
|
|
|
|
file_getHandle(handle)->seek(pos, from);
|
|
|
|
}
|
|
|
|
|
2006-05-29 18:24:52 +00:00
|
|
|
int32 DataIO::getPos(int16 handle) {
|
|
|
|
return file_getHandle(handle)->pos();
|
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
int32 DataIO::getDataSize(const char *name) {
|
2005-04-05 15:07:40 +00:00
|
|
|
char buf[128];
|
|
|
|
int32 chunkSz;
|
2005-05-10 22:56:25 +00:00
|
|
|
Common::File file;
|
2005-04-05 15:07:40 +00:00
|
|
|
|
|
|
|
strcpy(buf, name);
|
2006-01-03 23:14:39 +00:00
|
|
|
chunkSz = getChunkSize(buf);
|
2005-04-05 15:07:40 +00:00
|
|
|
if (chunkSz >= 0)
|
|
|
|
return chunkSz;
|
|
|
|
|
2005-05-03 08:37:04 +00:00
|
|
|
if (!file.open(buf))
|
2006-01-03 23:14:39 +00:00
|
|
|
error("getDataSize: Can't find data(%s)", name);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2005-05-03 08:37:04 +00:00
|
|
|
chunkSz = file.size();
|
|
|
|
file.close();
|
|
|
|
|
|
|
|
return chunkSz;
|
2005-04-05 15:07:40 +00:00
|
|
|
}
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
char *DataIO::getData(const char *path) {
|
2005-04-05 15:07:40 +00:00
|
|
|
char *data;
|
|
|
|
char *ptr;
|
|
|
|
int32 size;
|
|
|
|
int16 handle;
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
data = getUnpackedData(path);
|
2007-03-20 14:51:57 +00:00
|
|
|
if (data)
|
2005-04-05 15:07:40 +00:00
|
|
|
return data;
|
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
size = getDataSize(path);
|
2006-01-29 02:27:10 +00:00
|
|
|
data = new char[size];
|
2007-03-20 14:51:57 +00:00
|
|
|
assert(data);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
2006-01-03 23:14:39 +00:00
|
|
|
handle = openData(path);
|
2005-04-05 15:07:40 +00:00
|
|
|
|
|
|
|
ptr = data;
|
|
|
|
while (size > 0x4000) {
|
2006-01-03 23:14:39 +00:00
|
|
|
readData(handle, ptr, 0x4000);
|
2005-04-05 15:07:40 +00:00
|
|
|
size -= 0x4000;
|
|
|
|
ptr += 0x4000;
|
|
|
|
}
|
2006-01-03 23:14:39 +00:00
|
|
|
readData(handle, ptr, size);
|
|
|
|
closeData(handle);
|
2005-04-05 15:07:40 +00:00
|
|
|
return data;
|
|
|
|
}
|
|
|
|
|
2007-03-20 14:51:57 +00:00
|
|
|
} // End of namespace Gob
|