mirror of
https://github.com/ogoguel/activegs-ios.git
synced 2025-01-27 23:33:21 +00:00
185 lines
3.2 KiB
C++
185 lines
3.2 KiB
C++
//
|
|
// bigfile.cpp
|
|
// ActiveGS_Karateka
|
|
//
|
|
// Created by Olivier Goguel on 14/12/2017.
|
|
//
|
|
|
|
|
|
#include "bigfile.h"
|
|
|
|
|
|
#if KARATEKA_BIGFILE
|
|
#define ONLY_BIG
|
|
#endif
|
|
|
|
#define BIG 0x8000
|
|
|
|
struct CBigFile
|
|
{
|
|
const char* filename;
|
|
off_t seek_pos;
|
|
const char* buffer;
|
|
int size;
|
|
bool opened;
|
|
int code;
|
|
};
|
|
|
|
|
|
#if KARATEKA_BIGFILE
|
|
extern "C" const char karateka_bin[];
|
|
extern "C" const char karateka_activegsxml[];
|
|
|
|
|
|
CBigFile files[] ={
|
|
"karateka.bin", 0, karateka_bin,143360,false,0xEA,
|
|
"karateka.activegsxml", 0, karateka_activegsxml,5260,false,0XEA,
|
|
|
|
NULL,0,NULL,0,false
|
|
};
|
|
#else
|
|
CBigFile files[] ={
|
|
NULL,0,NULL,0,false
|
|
};
|
|
|
|
#endif
|
|
|
|
|
|
/*
|
|
off_t seek_pos = -1;
|
|
const char* buffer = NULL;
|
|
int file_size = -1;
|
|
*/
|
|
|
|
static const char* getfile(const char* p)
|
|
{
|
|
int l = strlen(p);
|
|
while(l>=0)
|
|
{
|
|
if (p[l]=='/')
|
|
return p+l+1;
|
|
l--;
|
|
}
|
|
return p;
|
|
}
|
|
|
|
|
|
int big_open(const char *_pathname, int _flags, mode_t _mode)
|
|
{
|
|
const char* file = getfile(_pathname);
|
|
if (file[0]=='*')
|
|
{
|
|
#if KARATEKA_BIGFILE
|
|
int l = 0;
|
|
while(files[l].filename != NULL)
|
|
{
|
|
if (!strcmp(file+1,files[l].filename))
|
|
{
|
|
if (files[l].opened)
|
|
{
|
|
printf("already opened %s",_pathname);
|
|
// return -1;
|
|
}
|
|
files[l].opened = true;
|
|
files[l].seek_pos = 0;
|
|
return BIG+l;
|
|
}
|
|
l++;
|
|
}
|
|
return -1;
|
|
#else
|
|
return open(_pathname+1,_flags,_mode);
|
|
#endif
|
|
}
|
|
else
|
|
{
|
|
#ifdef ONLY_BIG
|
|
printf("missing file %s\n",_pathname);
|
|
return -1;
|
|
#else
|
|
return open(_pathname,_flags,_mode);
|
|
#endif
|
|
}
|
|
}
|
|
|
|
|
|
|
|
off_t big_lseek(int _fd, off_t _offset, int _whence)
|
|
{
|
|
if ( ( _fd & BIG ) == 0 )
|
|
{
|
|
#ifdef ONLY_BIG
|
|
return 0;
|
|
#else
|
|
return lseek(_fd, _offset, _whence);
|
|
#endif
|
|
}
|
|
else
|
|
{
|
|
CBigFile& file = files[_fd &~BIG];
|
|
if (_whence == SEEK_SET)
|
|
file.seek_pos = _offset;
|
|
else
|
|
if (_whence == SEEK_END)
|
|
file.seek_pos = file.size-1;
|
|
|
|
return file.seek_pos;
|
|
}
|
|
}
|
|
|
|
ssize_t big_read(int _fd, void *_buf, size_t _count)
|
|
{
|
|
if ( ( _fd & BIG ) == 0 )
|
|
{
|
|
#ifdef ONLY_BIG
|
|
return 0;
|
|
#else
|
|
return read(_fd, _buf, _count);
|
|
#endif
|
|
}
|
|
else
|
|
{
|
|
CBigFile& file = files[_fd &~BIG];
|
|
|
|
if (_count + file.seek_pos > file.size)
|
|
_count = file.size - file.seek_pos;
|
|
|
|
memcpy(_buf,file.buffer+file.seek_pos,_count);
|
|
char *decode = (char*)_buf;
|
|
for(int i=0;i<_count;i++)
|
|
decode[i] ^= file.code;
|
|
file.seek_pos += _count;
|
|
return _count;
|
|
}
|
|
}
|
|
|
|
ssize_t big_write(int _fd, void* _buf, size_t _count)
|
|
{
|
|
if ( ( _fd & BIG ) == 0 )
|
|
{
|
|
return _count;
|
|
}
|
|
else {
|
|
return write(_fd, _buf, _count);
|
|
}
|
|
}
|
|
|
|
|
|
int big_close(int _fd)
|
|
{
|
|
if ( ( _fd & BIG ) == 0 )
|
|
{
|
|
CBigFile& file = files[_fd &~BIG];
|
|
if (!file.opened)
|
|
{
|
|
printf("nothing to close");
|
|
return -1;
|
|
}
|
|
file.opened=false;
|
|
}
|
|
else
|
|
close(_fd);
|
|
return 0;
|
|
}
|
|
|