Files
Webcam/include/platform/filesystem/io_memory.cpp

133 lines
3.5 KiB
C++

/* -----------------------------------------------------------------------------
GSFramework
Copyright 2001-2013 Emmanuel Julien. All Rights Reserved.
----------------------------------------------------------------------------- */
#include "filesystem/io_memory.h"
using namespace GS::IO;
//------------------------------------------------------------------------------
uint Memory::GetCaps() const
{ return CanRead | CanWrite | CanSeek| IsCaseSensitive; }
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
Handle *Memory::Open(const char *uri, Mode mode)
{
switch (mode)
{
case ModeRead:
ListForeachPtr(MemoryFile *, f, fat)
if (f->uri == uri)
return new MemoryHandle(this, f, mode);
break;
case ModeWrite:
{
MemoryFile *f_entry = NULL;
ListForeachPtr(MemoryFile *, f, fat)
if (f->uri == uri)
{
f_entry = f;
break;
}
if (!f_entry)
fat.Add(f_entry = new MemoryFile(uri));
return f_entry ? new MemoryHandle(this, f_entry, mode) : NULL;
}
break;
default: break;
}
return NULL;
}
void Memory::Close(Handle *h)
{ /* Nothing to be done. */ }
bool Memory::Delete(const char *uri)
{
ListForeachPtr(MemoryFile *, f, fat)
if (f->uri == uri)
return fat.Remove(f);
return false;
}
size_t Memory::Tell(Handle *h)
{
if (MemoryHandle *_h = (MemoryHandle *)h)
if (_h->file)
return _h->cursor;
return (size_t)-1;
}
size_t Memory::Seek(Handle *h, ptrdiff_t offset, SeekRef seek_ref)
{
if (MemoryHandle *_h = (MemoryHandle *)h)
if (_h->file)
{
switch (seek_ref)
{
case SeekStart:
_h->cursor = Types::Clamp <ptrdiff_t> (offset, 0, _h->file->size);
break;
case SeekCurrent:
_h->cursor = Types::Clamp <ptrdiff_t> (_h->cursor + offset, 0, _h->file->size);
break;
case SeekEnd:
_h->cursor = Types::Clamp <ptrdiff_t> (_h->file->size - offset, 0, _h->file->size);
break;
}
return 0;
}
return (size_t)-1;
}
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
size_t Memory::Read(Handle *h, void *ptr, size_t size)
{
size_t read_size = 0;
if (MemoryHandle *_h = (MemoryHandle *)h)
if (_h->file && (_h->mode == ModeRead))
{
read_size = Types::Min <ptrdiff_t> (size, _h->file->size - _h->cursor);
GS::Memory::Copy(ptr, &_h->file->data[(int)_h->cursor], read_size);
_h->cursor += read_size;
}
return read_size;
}
size_t Memory::Write(Handle *h, const void *ptr, size_t size)
{
size_t write_size = 0;
if (MemoryHandle *_h = (MemoryHandle *)h)
if (_h->file && (_h->mode == ModeWrite))
{
size_t req_size = _h->cursor + size;
if (req_size > _h->file->data.GetSize())
if (!_h->file->data.Reallocate(req_size + 16384)) // required size + 16 kilobytes
return 0;
GS::Memory::Copy(&_h->file->data[(int)_h->cursor], ptr, size);
write_size = size;
_h->cursor += size;
_h->file->size = Types::Max(_h->file->size, req_size);
}
return write_size;
}
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
MemoryHandle::MemoryHandle(Base *io, MemoryFile *_file, Mode _mode) : Handle(io), file(_file), cursor(0), mode(_mode)
{}
MemoryHandle::~MemoryHandle()
{ GetIOSystem()->Close(this); }
//------------------------------------------------------------------------------