summaryrefslogtreecommitdiff
path: root/src/baseq2/g_save.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/baseq2/g_save.c')
-rw-r--r--src/baseq2/g_save.c453
1 files changed, 238 insertions, 215 deletions
diff --git a/src/baseq2/g_save.c b/src/baseq2/g_save.c
index 25d608b..8477306 100644
--- a/src/baseq2/g_save.c
+++ b/src/baseq2/g_save.c
@@ -8,7 +8,7 @@ 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.
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the GNU General Public License for more details.
@@ -32,25 +32,25 @@ typedef struct {
} save_field_t;
#ifdef _DEBUG
-#define _FA(type,name,size) {type,#name,_OFS(name),size}
+#define _FA(type, name, size) { type, #name, _OFS(name), size }
#else
-#define _FA(type,name,size) {type,_OFS(name),size}
+#define _FA(type, name, size) { type, _OFS(name), size }
#endif
-#define _F(type,name) _FA(type,name,1)
-#define SZ(name,size) _FA(F_ZSTRING,name,size)
-#define BA(name,size) _FA(F_BYTE,name,size)
-#define B(name) BA(name,1)
-#define SA(name,size) _FA(F_SHORT,name,size)
-#define S(name) SA(name,1)
-#define IA(name,size) _FA(F_INT,name,size)
-#define I(name) IA(name,1)
-#define FA(name,size) _FA(F_FLOAT,name,size)
-#define F(name) FA(name,1)
-#define L(name) _F(F_LSTRING,name)
-#define V(name) _F(F_VECTOR,name)
-#define T(name) _F(F_ITEM,name)
-#define E(name) _F(F_EDICT,name)
-#define P(name,type) _FA(F_POINTER,name,type)
+#define _F(type, name) _FA(type, name, 1)
+#define SZ(name, size) _FA(F_ZSTRING, name, size)
+#define BA(name, size) _FA(F_BYTE, name, size)
+#define B(name) BA(name, 1)
+#define SA(name, size) _FA(F_SHORT, name, size)
+#define S(name) SA(name, 1)
+#define IA(name, size) _FA(F_INT, name, size)
+#define I(name) IA(name, 1)
+#define FA(name, size) _FA(F_FLOAT, name, size)
+#define F(name) FA(name, 1)
+#define L(name) _F(F_LSTRING, name)
+#define V(name) _F(F_VECTOR, name)
+#define T(name) _F(F_ITEM, name)
+#define E(name) _F(F_EDICT, name)
+#define P(name, type) _FA(F_POINTER, name, type)
static const save_field_t entityfields[] = {
#define _OFS FOFS
@@ -181,7 +181,7 @@ static const save_field_t entityfields[] = {
V(move_origin),
V(move_angles),
-
+
I(light_level),
I(style),
@@ -312,7 +312,7 @@ static const save_field_t clientfields[] = {
I(ps.gunframe),
FA(ps.blend, 4),
-
+
F(ps.fov),
I(ps.rdflags),
@@ -432,313 +432,334 @@ static const save_field_t gamefields[] = {
//=========================================================
-static void write_data( void *buf, size_t len, FILE *f ) {
- if( fwrite( buf, 1, len, f ) != len ) {
- gi.error( "%s: couldn't write %"PRIz" bytes", __func__, len );
+static void write_data(void *buf, size_t len, FILE *f)
+{
+ if (fwrite(buf, 1, len, f) != len) {
+ gi.error("%s: couldn't write %"PRIz" bytes", __func__, len);
}
}
-static void write_short( FILE *f, short v ) {
- v = LittleShort( v );
- write_data( &v, sizeof( v ), f );
+static void write_short(FILE *f, short v)
+{
+ v = LittleShort(v);
+ write_data(&v, sizeof(v), f);
}
-static void write_int( FILE *f, int v ) {
- v = LittleLong( v );
- write_data( &v, sizeof( v ), f );
+static void write_int(FILE *f, int v)
+{
+ v = LittleLong(v);
+ write_data(&v, sizeof(v), f);
}
-static void write_float( FILE *f, float v ) {
- v = LittleFloat( v );
- write_data( &v, sizeof( v ), f );
+static void write_float(FILE *f, float v)
+{
+ v = LittleFloat(v);
+ write_data(&v, sizeof(v), f);
}
-static void write_string( FILE *f, char *s ) {
+static void write_string(FILE *f, char *s)
+{
size_t len;
- if( !s ) {
- write_int( f, -1 );
+ if (!s) {
+ write_int(f, -1);
return;
}
- len = strlen( s );
- write_int( f, len );
- write_data( s, len, f );
+ len = strlen(s);
+ write_int(f, len);
+ write_data(s, len, f);
}
-static void write_vector( FILE *f, vec_t *v ) {
- write_float( f, v[0] );
- write_float( f, v[1] );
- write_float( f, v[2] );
+static void write_vector(FILE *f, vec_t *v)
+{
+ write_float(f, v[0]);
+ write_float(f, v[1]);
+ write_float(f, v[2]);
}
-static void write_index( FILE *f, void *p, size_t size, void *start, int max_index ) {
+static void write_index(FILE *f, void *p, size_t size, void *start, int max_index)
+{
size_t diff;
- if( !p ) {
- write_int( f, -1 );
+ if (!p) {
+ write_int(f, -1);
return;
}
- if( p < start || ( byte * )p > ( byte * )start + max_index * size ) {
- gi.error( "%s: pointer out of range: %p", __func__, p );
+ if (p < start || (byte *)p > (byte *)start + max_index * size) {
+ gi.error("%s: pointer out of range: %p", __func__, p);
}
diff = p - start;
- if( diff % size ) {
- gi.error( "%s: misaligned pointer: %p", __func__, p );
+ if (diff % size) {
+ gi.error("%s: misaligned pointer: %p", __func__, p);
}
- write_int( f, ( int )( diff / size ) );
+ write_int(f, (int)(diff / size));
}
-static void write_pointer( FILE *f, void *p, ptr_type_t type ) {
+static void write_pointer(FILE *f, void *p, ptr_type_t type)
+{
const save_ptr_t *ptr;
int i;
- if( !p ) {
- write_int( f, -1 );
- return;
+ if (!p) {
+ write_int(f, -1);
+ return;
}
- for( i = 0, ptr = save_ptrs; i < num_save_ptrs; i++, ptr++ ) {
- if( ptr->type == type && ptr->ptr == p ) {
- write_int( f, i );
+ for (i = 0, ptr = save_ptrs; i < num_save_ptrs; i++, ptr++) {
+ if (ptr->type == type && ptr->ptr == p) {
+ write_int(f, i);
return;
}
}
- gi.error( "%s: unknown pointer: %p", __func__, p );
+ gi.error("%s: unknown pointer: %p", __func__, p);
}
-static void write_field( FILE *f, const save_field_t *field, void *base ) {
+static void write_field(FILE *f, const save_field_t *field, void *base)
+{
void *p = (byte *)base + field->ofs;
int i;
- switch( field->type ) {
+ switch (field->type) {
case F_BYTE:
- write_data( p, field->size, f );
+ write_data(p, field->size, f);
break;
case F_SHORT:
- for( i = 0; i < field->size; i++ ) {
- write_short( f, (( short * )p)[i] );
+ for (i = 0; i < field->size; i++) {
+ write_short(f, ((short *)p)[i]);
}
break;
case F_INT:
- for( i = 0; i < field->size; i++ ) {
- write_int( f, (( int * )p)[i] );
+ for (i = 0; i < field->size; i++) {
+ write_int(f, ((int *)p)[i]);
}
break;
case F_FLOAT:
- for( i = 0; i < field->size; i++ ) {
- write_float( f, (( float * )p)[i] );
+ for (i = 0; i < field->size; i++) {
+ write_float(f, ((float *)p)[i]);
}
break;
case F_VECTOR:
- write_vector( f, ( vec_t * )p );
+ write_vector(f, (vec_t *)p);
break;
case F_ZSTRING:
- write_string( f, ( char * )p );
+ write_string(f, (char *)p);
break;
case F_LSTRING:
- write_string( f, *( char ** )p );
+ write_string(f, *(char **)p);
break;
case F_EDICT:
- write_index( f, *( void ** )p, sizeof( edict_t ), g_edicts, MAX_EDICTS - 1 );
+ write_index(f, *(void **)p, sizeof(edict_t), g_edicts, MAX_EDICTS - 1);
break;
case F_CLIENT:
- write_index( f, *( void ** )p, sizeof( gclient_t ), game.clients, game.maxclients - 1 );
+ write_index(f, *(void **)p, sizeof(gclient_t), game.clients, game.maxclients - 1);
break;
case F_ITEM:
- write_index( f, *( void ** )p, sizeof( gitem_t ), itemlist, game.num_items - 1 );
+ write_index(f, *(void **)p, sizeof(gitem_t), itemlist, game.num_items - 1);
break;
case F_POINTER:
- write_pointer( f, *( void ** )p, field->size );
+ write_pointer(f, *(void **)p, field->size);
break;
default:
- gi.error( "%s: unknown field type", __func__ );
+ gi.error("%s: unknown field type", __func__);
}
}
-static void write_fields( FILE *f, const save_field_t *fields, void *base ) {
+static void write_fields(FILE *f, const save_field_t *fields, void *base)
+{
const save_field_t *field;
- for( field = fields; field->type; field++ ) {
- write_field( f, field, base );
+ for (field = fields; field->type; field++) {
+ write_field(f, field, base);
}
}
-static void read_data( void *buf, size_t len, FILE *f ) {
- if( fread( buf, 1, len, f ) != len ) {
- gi.error( "%s: couldn't read %"PRIz" bytes", __func__, len );
+static void read_data(void *buf, size_t len, FILE *f)
+{
+ if (fread(buf, 1, len, f) != len) {
+ gi.error("%s: couldn't read %"PRIz" bytes", __func__, len);
}
}
-static int read_short( FILE *f ) {
+static int read_short(FILE *f)
+{
short v;
- read_data( &v, sizeof( v ), f );
- v = LittleShort( v );
+ read_data(&v, sizeof(v), f);
+ v = LittleShort(v);
return v;
}
-static int read_int( FILE *f ) {
+static int read_int(FILE *f)
+{
int v;
- read_data( &v, sizeof( v ), f );
- v = LittleLong( v );
+ read_data(&v, sizeof(v), f);
+ v = LittleLong(v);
return v;
}
-static float read_float( FILE *f ) {
+static float read_float(FILE *f)
+{
float v;
- read_data( &v, sizeof( v ), f );
- v = LittleFloat( v );
+ read_data(&v, sizeof(v), f);
+ v = LittleFloat(v);
return v;
}
-static char *read_string( FILE *f ) {
+static char *read_string(FILE *f)
+{
int len;
char *s;
- len = read_int( f );
- if( len == -1 ) {
+ len = read_int(f);
+ if (len == -1) {
return NULL;
}
- if( len < 0 || len > 65536 ) {
- gi.error( "%s: bad length", __func__ );
+ if (len < 0 || len > 65536) {
+ gi.error("%s: bad length", __func__);
}
- s = gi.TagMalloc( len + 1, TAG_LEVEL );
- read_data( s, len, f );
+ s = gi.TagMalloc(len + 1, TAG_LEVEL);
+ read_data(s, len, f);
s[len] = 0;
return s;
}
-static void read_zstring( FILE *f, char *s, size_t size ) {
+static void read_zstring(FILE *f, char *s, size_t size)
+{
int len;
- len = read_int( f );
- if( len < 0 || len >= size ) {
- gi.error( "%s: bad length", __func__ );
+ len = read_int(f);
+ if (len < 0 || len >= size) {
+ gi.error("%s: bad length", __func__);
}
- read_data( s, len, f );
+ read_data(s, len, f);
s[len] = 0;
}
-static void read_vector( FILE *f, vec_t *v ) {
- v[0] = read_float( f );
- v[1] = read_float( f );
- v[2] = read_float( f );
+static void read_vector(FILE *f, vec_t *v)
+{
+ v[0] = read_float(f);
+ v[1] = read_float(f);
+ v[2] = read_float(f);
}
-static void *read_index( FILE *f, size_t size, void *start, int max_index ) {
+static void *read_index(FILE *f, size_t size, void *start, int max_index)
+{
int index;
byte *p;
- index = read_int( f );
- if( index == -1 ) {
+ index = read_int(f);
+ if (index == -1) {
return NULL;
}
- if( index < 0 || index > max_index ) {
- gi.error( "%s: bad index", __func__ );
+ if (index < 0 || index > max_index) {
+ gi.error("%s: bad index", __func__);
}
- p = ( byte * )start + index * size;
+ p = (byte *)start + index * size;
return p;
}
-static void *read_pointer( FILE *f, ptr_type_t type ) {
+static void *read_pointer(FILE *f, ptr_type_t type)
+{
int index;
const save_ptr_t *ptr;
- index = read_int( f );
- if( index == -1 ) {
+ index = read_int(f);
+ if (index == -1) {
return NULL;
}
- if( index < 0 || index >= num_save_ptrs ) {
- gi.error( "%s: bad index", __func__ );
+ if (index < 0 || index >= num_save_ptrs) {
+ gi.error("%s: bad index", __func__);
}
ptr = &save_ptrs[index];
- if( ptr->type != type ) {
- gi.error( "%s: type mismatch", __func__ );
+ if (ptr->type != type) {
+ gi.error("%s: type mismatch", __func__);
}
return ptr->ptr;
}
-static void read_field( FILE *f, const save_field_t *field, void *base ) {
- void *p = ( byte * )base + field->ofs;
+static void read_field(FILE *f, const save_field_t *field, void *base)
+{
+ void *p = (byte *)base + field->ofs;
int i;
- switch( field->type ) {
+ switch (field->type) {
case F_BYTE:
- read_data( p, field->size, f );
+ read_data(p, field->size, f);
break;
case F_SHORT:
- for( i = 0; i < field->size; i++ ) {
- (( short * )p)[i] = read_short( f );
+ for (i = 0; i < field->size; i++) {
+ ((short *)p)[i] = read_short(f);
}
break;
case F_INT:
- for( i = 0; i < field->size; i++ ) {
- (( int * )p)[i] = read_int( f );
+ for (i = 0; i < field->size; i++) {
+ ((int *)p)[i] = read_int(f);
}
break;
case F_FLOAT:
- for( i = 0; i < field->size; i++ ) {
- (( float * )p)[i] = read_float( f );
+ for (i = 0; i < field->size; i++) {
+ ((float *)p)[i] = read_float(f);
}
break;
case F_VECTOR:
- read_vector( f, ( vec_t * )p );
+ read_vector(f, (vec_t *)p);
break;
case F_LSTRING:
- *( char ** )p = read_string( f );
+ *(char **)p = read_string(f);
break;
case F_ZSTRING:
- read_zstring( f, ( char * )p, field->size );
+ read_zstring(f, (char *)p, field->size);
break;
case F_EDICT:
- *( edict_t ** )p = read_index( f, sizeof( edict_t ), g_edicts, game.maxentities - 1 );
+ *(edict_t **)p = read_index(f, sizeof(edict_t), g_edicts, game.maxentities - 1);
break;
case F_CLIENT:
- *( gclient_t ** )p = read_index( f, sizeof( gclient_t ), game.clients, game.maxclients - 1 );
+ *(gclient_t **)p = read_index(f, sizeof(gclient_t), game.clients, game.maxclients - 1);
break;
case F_ITEM:
- *( gitem_t ** )p = read_index( f, sizeof( gitem_t ), itemlist, game.num_items - 1 );
+ *(gitem_t **)p = read_index(f, sizeof(gitem_t), itemlist, game.num_items - 1);
break;
case F_POINTER:
- *( void ** )p = read_pointer( f, field->size );
+ *(void **)p = read_pointer(f, field->size);
break;
default:
- gi.error( "%s: unknown field type", __func__ );
+ gi.error("%s: unknown field type", __func__);
}
}
-static void read_fields( FILE *f, const save_field_t *fields, void *base ) {
+static void read_fields(FILE *f, const save_field_t *fields, void *base)
+{
const save_field_t *field;
- for( field = fields; field->type; field++ ) {
- read_field( f, field, base );
+ for (field = fields; field->type; field++) {
+ read_field(f, field, base);
}
}
@@ -762,75 +783,77 @@ A single player death will automatically restore from the
last save position.
============
*/
-void WriteGame (const char *filename, qboolean autosave) {
+void WriteGame(const char *filename, qboolean autosave)
+{
FILE *f;
int i;
if (!autosave)
- SaveClientData ();
+ SaveClientData();
- f = fopen (filename, "wb");
+ f = fopen(filename, "wb");
if (!f)
- gi.error ("Couldn't open %s", filename);
+ gi.error("Couldn't open %s", filename);
- write_int( f, SAVE_MAGIC1 );
- write_int( f, SAVE_VERSION );
+ write_int(f, SAVE_MAGIC1);
+ write_int(f, SAVE_VERSION);
game.autosaved = autosave;
- write_fields( f, gamefields, &game );
+ write_fields(f, gamefields, &game);
game.autosaved = qfalse;
- for( i = 0; i < game.maxclients; i++ ) {
- write_fields( f, clientfields, &game.clients[i] );
+ for (i = 0; i < game.maxclients; i++) {
+ write_fields(f, clientfields, &game.clients[i]);
}
- fclose (f);
+ fclose(f);
}
-void ReadGame (const char *filename) {
+void ReadGame(const char *filename)
+{
FILE *f;
int i;
- gi.FreeTags (TAG_GAME);
+ gi.FreeTags(TAG_GAME);
- f = fopen (filename, "rb");
+ f = fopen(filename, "rb");
if (!f)
- gi.error ("Couldn't open %s", filename);
+ gi.error("Couldn't open %s", filename);
- i = read_int( f );
- if( i != SAVE_MAGIC1 ) {
- fclose (f);
- gi.error ("Not a save game");
+ i = read_int(f);
+ if (i != SAVE_MAGIC1) {
+ fclose(f);
+ gi.error("Not a save game");
}
- i = read_int( f );
- if( i != SAVE_VERSION ) {
- fclose (f);
- gi.error ("Savegame from an older version.\n");
+ i = read_int(f);
+ if (i != SAVE_VERSION) {
+ fclose(f);
+ gi.error("Savegame from an older version.\n");
}
- read_fields( f, gamefields, &game );
+ read_fields(f, gamefields, &game);
// should agree with server's version
- if( game.maxclients != (int)maxclients->value ) {
- fclose (f);
- gi.error ("Savegame has bad maxclients.\n");
+ if (game.maxclients != (int)maxclients->value) {
+ fclose(f);
+ gi.error("Savegame has bad maxclients.\n");
}
- if( game.maxentities <= game.maxclients || game.maxentities > MAX_EDICTS ) {
- fclose (f);
- gi.error ("Savegame has bad maxentities.\n");
+ if (game.maxentities <= game.maxclients || game.maxentities > MAX_EDICTS) {
+ fclose(f);
+ gi.error("Savegame has bad maxentities.\n");
}
- g_edicts = gi.TagMalloc (game.maxentities * sizeof(g_edicts[0]), TAG_GAME);
+ g_edicts = gi.TagMalloc(game.maxentities * sizeof(g_edicts[0]), TAG_GAME);
globals.edicts = g_edicts;
globals.max_edicts = game.maxentities;
- game.clients = gi.TagMalloc (game.maxclients * sizeof(game.clients[0]), TAG_GAME);
- for( i = 0; i < game.maxclients; i++ ) {
- read_fields( f, clientfields, &game.clients[i] );
+ game.clients = gi.TagMalloc(game.maxclients * sizeof(game.clients[0]), TAG_GAME);
+ for (i = 0; i < game.maxclients; i++) {
+ read_fields(f, clientfields, &game.clients[i]);
}
- fclose (f);
+ fclose(f);
}
//==========================================================
@@ -842,32 +865,33 @@ WriteLevel
=================
*/
-void WriteLevel (const char *filename) {
+void WriteLevel(const char *filename)
+{
int i;
edict_t *ent;
FILE *f;
- f = fopen (filename, "wb");
+ f = fopen(filename, "wb");
if (!f)
- gi.error ("Couldn't open %s", filename);
+ gi.error("Couldn't open %s", filename);
- write_int( f, SAVE_MAGIC2 );
- write_int( f, SAVE_VERSION );
+ write_int(f, SAVE_MAGIC2);
+ write_int(f, SAVE_VERSION);
// write out level_locals_t
- write_fields( f, levelfields, &level );
+ write_fields(f, levelfields, &level);
// write out all the entities
- for( i = 0; i < globals.num_edicts; i++ ) {
+ for (i = 0; i < globals.num_edicts; i++) {
ent = &g_edicts[i];
if (!ent->inuse)
continue;
- write_int( f, i );
- write_fields( f, entityfields, ent );
+ write_int(f, i);
+ write_fields(f, entityfields, ent);
}
- write_int( f, -1 );
+ write_int(f, -1);
- fclose (f);
+ fclose(f);
}
@@ -887,7 +911,8 @@ calling ReadLevel.
No clients are connected yet.
=================
*/
-void ReadLevel (const char *filename) {
+void ReadLevel(const char *filename)
+{
int entnum;
FILE *f;
int i;
@@ -895,65 +920,63 @@ void ReadLevel (const char *filename) {
// free any dynamic memory allocated by loading the level
// base state
- gi.FreeTags (TAG_LEVEL);
+ gi.FreeTags(TAG_LEVEL);
- f = fopen (filename, "rb");
+ f = fopen(filename, "rb");
if (!f)
- gi.error ("Couldn't open %s", filename);
+ gi.error("Couldn't open %s", filename);
// wipe all the entities
- memset (g_edicts, 0, game.maxentities*sizeof(g_edicts[0]));
- globals.num_edicts = maxclients->value+1;
+ memset(g_edicts, 0, game.maxentities * sizeof(g_edicts[0]));
+ globals.num_edicts = maxclients->value + 1;
- i = read_int( f );
- if( i != SAVE_MAGIC2 ) {
- fclose (f);
- gi.error ("Not a save game");
+ i = read_int(f);
+ if (i != SAVE_MAGIC2) {
+ fclose(f);
+ gi.error("Not a save game");
}
- i = read_int( f );
- if( i != SAVE_VERSION ) {
- fclose (f);
- gi.error ("Savegame from an older version.\n");
+ i = read_int(f);
+ if (i != SAVE_VERSION) {
+ fclose(f);
+ gi.error("Savegame from an older version.\n");
}
// load the level locals
- read_fields( f, levelfields, &level );
+ read_fields(f, levelfields, &level);
// load all the entities
- while( 1 ) {
- entnum = read_int( f );
- if( entnum == -1 )
+ while (1) {
+ entnum = read_int(f);
+ if (entnum == -1)
break;
- if( entnum < 0 || entnum >= game.maxentities ) {
- gi.error( "%s: bad entity number", __func__ );
+ if (entnum < 0 || entnum >= game.maxentities) {
+ gi.error("%s: bad entity number", __func__);
}
- if( entnum >= globals.num_edicts )
+ if (entnum >= globals.num_edicts)
globals.num_edicts = entnum + 1;
ent = &g_edicts[entnum];
- read_fields( f, entityfields, ent );
+ read_fields(f, entityfields, ent);
ent->inuse = qtrue;
ent->s.number = entnum;
// let the server rebuild world links for this ent
- memset (&ent->area, 0, sizeof(ent->area));
- gi.linkentity (ent);
+ memset(&ent->area, 0, sizeof(ent->area));
+ gi.linkentity(ent);
}
- fclose (f);
+ fclose(f);
// mark all clients as unconnected
- for (i=0 ; i<maxclients->value ; i++)
- {
- ent = &g_edicts[i+1];
+ for (i = 0 ; i < maxclients->value ; i++) {
+ ent = &g_edicts[i + 1];
ent->client = game.clients + i;
ent->client->pers.connected = qfalse;
}
// do any load time things at this point
- for (i=0 ; i<globals.num_edicts ; i++)
- {
+ for (i = 0 ; i < globals.num_edicts ; i++) {
ent = &g_edicts[i];
if (!ent->inuse)