From d17841fbc48819cdf7b4fb26aa5c3d709e180daa Mon Sep 17 00:00:00 2001 From: zicodxx <> Date: Thu, 28 Jan 2010 15:26:27 +0000 Subject: [PATCH] Improved Object signature assignment and made sure there will be no duplicates; Also used short-ranged values only so Demo system won't screw up --- CHANGELOG.txt | 1 + main/gamesave.c | 4 ++-- main/newdemo.c | 21 ++++++--------------- main/object.c | 29 ++++++++++++++++++++++++++--- main/object.h | 3 +++ main/state.c | 4 ---- 6 files changed, 38 insertions(+), 24 deletions(-) diff --git a/CHANGELOG.txt b/CHANGELOG.txt index 772f5b95d..557a8a978 100644 --- a/CHANGELOG.txt +++ b/CHANGELOG.txt @@ -7,6 +7,7 @@ main/newdemo.c: Added a new code to properly re-record view/cockpit-events at be arch/sdl/window.c, main/automap.c, main/game.c, main/gamecntl.c, main/kconfig.c, main/menu.c, main/net_ipx.c, main/net_udp.c, main/newmenu.c: Make response to EVENT_WINDOW_CLOSE conform to 'handling' system - returning 1 means abort closing main/kconfig.c, main/newmenu.c: Tidy up newmenu_show/hide_cursor calls main/newmenu.c: Allow user to abort close, for whatever reason (helps with my next commit) +main/gamesave.c, main/newdemo.c, main/object.c, main/object.h, main/state.c: Improved Object signature assignment and made sure there will be no duplicates; Also used short-ranged values only so Demo system won't screw up 20100127 -------- diff --git a/main/gamesave.c b/main/gamesave.c index 5bb761193..2ab7eea02 100644 --- a/main/gamesave.c +++ b/main/gamesave.c @@ -898,7 +898,7 @@ int load_game_data(CFILE *LoadFile) } //===================== READ PLAYER INFO ========================== - Object_next_signature = 0; + //===================== READ OBJECT INFO ========================== @@ -913,7 +913,7 @@ int load_game_data(CFILE *LoadFile) memset(&(Objects[i]), 0, sizeof(object)); read_object(&Objects[i],LoadFile,game_top_fileinfo.fileinfo_version); - Objects[i].signature = Object_next_signature++; + Objects[i].signature = obj_get_signature(); verify_object( &Objects[i] ); } diff --git a/main/newdemo.c b/main/newdemo.c index 5e62f083b..d88b3400c 100644 --- a/main/newdemo.c +++ b/main/newdemo.c @@ -439,6 +439,7 @@ static int shareware = 0; // reading shareware demo? void nd_read_object(object *obj) { memset(obj, 0, sizeof(object)); + short shortsig = 0; /* * Do render type first, since with render_type == RT_NONE, we @@ -451,20 +452,8 @@ void nd_read_object(object *obj) nd_read_byte((sbyte *) &(obj->id)); nd_read_byte((sbyte *) &(obj->flags)); - nd_read_short((short *)&(obj->signature)); - - /* This doesn't make sense, since the object signature is supposed to - be an int, but a short is probably half the size on many platforms. - The problem then is that probably only half the signature will be - initialized. This is definitely not portable. - - See the typedef struct object's signature field in object.h to see - what I mean. The compiler warning with my gcc 4.2.3 seems to be - warranted. - - Kip (kip@thevertigo.com) - */ - + nd_read_short(&shortsig); + obj->signature = shortsig; // It's OKAY! We made sure, obj->signature is never has a value which short cannot handle!!! We cannot do this otherwise, without breaking the demo format! nd_read_shortpos(obj); obj->attached_obj = -1; @@ -667,6 +656,7 @@ void nd_read_object(object *obj) void nd_write_object(object *obj) { int life; + short shortsig = 0; /* * Do render_type first so on read, we can make determination of @@ -679,7 +669,8 @@ void nd_write_object(object *obj) nd_write_byte(obj->id); nd_write_byte(obj->flags); - nd_write_short((short)obj->signature); + shortsig = obj->signature; // It's OKAY! We made sure, obj->signature is never has a value which short cannot handle!!! We cannot do this otherwise, without breaking the demo format! + nd_write_short(shortsig); nd_write_shortpos(obj); if ((obj->type != OBJ_HOSTAGE) && (obj->type != OBJ_ROBOT) && (obj->type != OBJ_PLAYER) && (obj->type != OBJ_POWERUP) && (obj->type != OBJ_CLUTTER)) { diff --git a/main/object.c b/main/object.c index d9bad6fe0..0b596a340 100644 --- a/main/object.c +++ b/main/object.c @@ -879,7 +879,30 @@ void obj_unlink(int objnum) Assert(Objects[0].prev != 0); } -int Object_next_signature = 0; +// Returns a new, unique signature for a new object +int obj_get_signature() +{ + static short sig = 0; // Yes! Short! a) We do not need higher values b) the demo system only stores shorts + int free = 0, i = 0; + + while (!free) + { + free = 1; + sig++; + if (sig < 0) + sig = 0; + for (i = 0; i <= MAX_OBJECTS; i++) + { + if ((sig == Objects[i].signature) && (Objects[i].type != OBJ_NONE)) + { + free = 0; + } + } + } + + return sig; +} + int Debris_object_count=0; @@ -1053,7 +1076,7 @@ int obj_create(ubyte type,ubyte id,int segnum,vms_vector *pos, // in uninitialized fields. memset( obj, 0, sizeof(object) ); - obj->signature = Object_next_signature++; + obj->signature = obj_get_signature(); obj->type = type; obj->id = id; obj->last_pos = *pos; @@ -1141,7 +1164,7 @@ int obj_create_copy(int objnum, vms_vector *new_pos, int newsegnum) obj_link(newobjnum,newsegnum); - obj->signature = Object_next_signature++; + obj->signature = obj_get_signature(); //we probably should initialize sub-structures here diff --git a/main/object.h b/main/object.h index 5f424b7d4..f922f2b48 100644 --- a/main/object.h +++ b/main/object.h @@ -408,6 +408,9 @@ extern void create_shorterpos(shorterpos *spp, object *objp); //if clear_all is set, clear even proximity bombs void clear_transient_objects(int clear_all); +// Returns a new, unique signature for a new object +int obj_get_signature(); + //returns the number of a free object, updating Highest_object_index. //Generally, obj_create() should be called to get an object, since it //fills in important fields and does the linking. diff --git a/main/state.c b/main/state.c index 36557b4c9..f61bf458b 100644 --- a/main/state.c +++ b/main/state.c @@ -763,7 +763,6 @@ RetryObjectLoading: } } - Object_next_signature = 0; for (i=0; i<=Highest_object_index; i++ ) { obj = &Objects[i]; obj->rtype.pobj_info.alt_textures = -1; @@ -779,12 +778,9 @@ RetryObjectLoading: } } obj_link(i,segnum); - if ( obj->signature > Object_next_signature ) - Object_next_signature = obj->signature; } } special_reset_objects(); - Object_next_signature++; //Restore wall info Num_walls = PHYSFSX_readSXE32(fp, swap);