Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found
Select Git revision
  • 21-installer-nodd
  • 2210-pre1
  • 2210-pre2
  • 2210-rc1
  • 2210-rc2
  • 2210-rc3
  • 2211-pre1
  • 2211-pre2
  • 2211-rc1
  • 2212-pre1
  • 2212-pre2
  • 2212-pre3
  • 2212-rc1
  • 2213
  • 2_2_12
  • 64-gl-log
  • COM_ImmedExecute-lua
  • DJGPP
  • accel-momentum
  • acs
  • action-args
  • alpha-fixes
  • any-resolution
  • appveyor
  • better-player-states
  • blend-locking
  • blentran
  • blua-unary-not-fix
  • boost-tickrate
  • bustablesoundz
  • cleanup-opengl
  • cleanupmusic
  • clipmidtex
  • cmake-valgrind
  • crawlacommander-sprites
  • custom-map-names
  • custom-teams
  • cutscene-cleanup
  • dd-music-bypass
  • dd-music-fix
  • delfile2
  • deprecate-lua-dedicated-server
  • dpl-2
  • dropshadows-spawning
  • dynabsp
  • emblem-drawing
  • exchndl-xp-fix
  • extra-textures
  • few-kart-lua-changes
  • ffloorclip
  • fix-1258
  • fix-1277
  • fix-167
  • fix-cvar-conflicts
  • fix-opengl-shear-roll
  • flipfuncpointers
  • fof-lightlist-fixes
  • font-FUCK
  • frictionrefactor
  • fuck-macros-1
  • gamepad-luakeydown
  • gamepad-morefixes
  • gamepad_experiments
  • gametype-refactor
  • gametype-refactor-1
  • gametype-refactor-player-spawns
  • ghost-networking
  • gif-splitting
  • gitlab-ci
  • grr-lj
  • hitboxviewer
  • hwr-texture-cache-refactor
  • hwrender2
  • improve-439
  • increase-maxconditionsets
  • increase-packet-tics
  • input-display
  • input-display-translucency
  • io
  • joystick-juggling-maz
  • keycodes-only
  • ksf-wadfiles
  • ld413-mp-fix
  • levelstruct
  • libpng-version-support
  • linedef-actions
  • lj-test
  • lol-states
  • loopedsounds
  • lower-unpegged-fix
  • lua-change-gametype
  • lua-command-netids
  • lua-debug-library
  • lua-gfx-2
  • lua-gfx-sprites
  • lua-local
  • makefile-auto-mingw-gcc
  • makefile-tinkering
  • map-components-signedness-fixes
  • master
  • SRB2_release_2.1
  • SRB2_release_2.1.1
  • SRB2_release_2.1.10
  • SRB2_release_2.1.11
  • SRB2_release_2.1.12
  • SRB2_release_2.1.14
  • SRB2_release_2.1.15
  • SRB2_release_2.1.16
  • SRB2_release_2.1.16a
  • SRB2_release_2.1.17
  • SRB2_release_2.1.18
  • SRB2_release_2.1.19
  • SRB2_release_2.1.2
  • SRB2_release_2.1.20
  • SRB2_release_2.1.21
  • SRB2_release_2.1.22
  • SRB2_release_2.1.23
  • SRB2_release_2.1.24
  • SRB2_release_2.1.25
  • SRB2_release_2.1.3
  • SRB2_release_2.1.4
  • SRB2_release_2.1.5
  • SRB2_release_2.1.6
  • SRB2_release_2.1.7
  • SRB2_release_2.1.8
  • SRB2_release_2.1.9
  • SRB2_release_2.2.0
  • SRB2_release_2.2.1
  • SRB2_release_2.2.10
  • SRB2_release_2.2.11
  • SRB2_release_2.2.12
  • SRB2_release_2.2.13
  • SRB2_release_2.2.2
  • SRB2_release_2.2.3
  • SRB2_release_2.2.4
  • SRB2_release_2.2.5
  • SRB2_release_2.2.6
  • SRB2_release_2.2.7
  • SRB2_release_2.2.8
  • SRB2_release_2.2.9
  • td-release-v1.0.0
141 results

Target

Select target project
  • STJr/SRB2
  • Sryder/SRB2
  • wolfy852/SRB2
  • Alpha2244/SRB2
  • Inuyasha/SRB2
  • yoshibot/SRB2
  • TehRealSalt/SRB2
  • PrisimaTF/SRB2
  • Hatninja/SRB2
  • SteelT/SRB2
  • james/SRB2
  • ShaderWraith/SRB2
  • SinnamonLat/SRB2
  • mazmazz_/SRB2
  • filpAM/SRB2
  • chaoloveicemdboy/SRB2
  • Whooa21/SRB2
  • Machturne/SRB2
  • Golden/SRB2
  • Tatsuru/SRB2
  • Snu/SRB2
  • Zwip-Zwap_Zapony/SRB2
  • fickleheart/SRB2
  • alphaRexJames/SRB2
  • JJK/SRB2
  • diskpoppy/SRB2
  • Hannu_Hanhi/SRB2
  • ZipperQR/SRB2
  • kays/SRB2
  • spherallic/SRB2
  • Zippy_Zolton/SRB2
  • namiishere/SRB2
  • Ors/SRB2
  • SMS_Alfredo/SRB2
  • sonic_edge/SRB2
  • lavla/SRB2
  • ashi/SRB2
  • X.organic/SRB2
  • Fafabis/SRB2
  • Meziu/SRB2
  • v-rob/SRB2
  • tertu/SRB2
  • bitten2up/SRB2
  • flarn2006/SRB2
  • Krabs/SRB2
  • clairebun/SRB2
  • Lactozilla/SRB2
  • thehackstack/SRB2
  • Spice/SRB2
  • win8linux/SRB2
  • JohnFrostFox/SRB2
  • talktoneon726/SRB2
  • Wane/SRB2
  • Lamibe/SRB2
  • spectrumuk2/srb-2
  • nerdyminer18/srb-2
  • 256nil/SRB2
  • ARJr/SRB2
  • Alam/SRB2
  • Zenya/srb-2-marathon-demos
  • Acelite/srb-2-archivedmodifications
  • MIDIMan/SRB2
  • Lach/SRB2
  • Frostiikin/bounce-tweaks
  • Jaden/SRB2
  • Tyron/SRB2
  • Astronight/SRB2
  • Mari0shi06/SRB2
  • aiire/SRB2
  • Galactice/SRB2
  • srb2-ports/srb2-dreamcast
  • sdasdas/SRB2
  • chreas/srb-2-vr
  • StarManiaKG/the-story-of-sinically-rocketing-and-botching-the-2nd
  • LoganAir/SRB2
  • NepDisk/srb-2
  • alufolie91/SRB2
  • Felicia.iso/SRB2
  • twi/SRB2
  • BarrelsOFun/SRB2
  • Speed2411/SRB2
  • Leather_Realms/SRB2
  • Ayemar/SRB2
  • Acelite/SRB2
  • VladDoc/SRB2
  • kaldrum/model-features
  • strawberryfox417/SRB2
  • Lugent/SRB2
  • Rem/SRB2
  • Refrag/SRB2
  • Henry_3230/srb-3230
  • TehPuertoRicanSpartan2/tprs-srb2
  • Leminn/srb-2-marathon-stuff
  • chromaticpipe2/SRB2
  • MiguelGustavo15/SRB2
  • Maru/srb-2-tests
  • SilicDev/SRB2
  • UnmatchedBracket/SRB2
  • HybridDog/SRB2
  • xordspar0/SRB2
  • jsjhbewfhh/SRB2
  • Fancy2209/SRB2
  • Lorsoen/SRB2
  • shindoukin/SRB2
  • GamerOfDays/SRB2
  • Craftyawesome/SRB2
  • tenshi-tensai-tennoji/SRB2
  • Scarfdudebalder/SRB2
  • luigi-budd/srb-2-fix-interplag-lockon
  • mskluesner/SRB2
  • johnpetersa19/SRB2
  • Pheazant/SRB2
  • chromaticpipe2/srb2classic
  • romoney5/SRB2
  • PAS/SRB2Classic
  • BlueStaggo/SRB2
  • Jisk/srb-2-beef-jerky
117 results
Select Git revision
  • 1392-2-2-15-attempting-to-draw-a-hud-graphic-with-the-same-lump-name-as-a-lua-script-crashes-the
  • 21-installer-nodd
  • 2210-pre1
  • 2210-pre2
  • 2210-rc1
  • 2210-rc2
  • 2210-rc3
  • 2211-pre1
  • 2211-pre2
  • 2211-rc1
  • 2212-pre1
  • 2212-pre2
  • 2212-pre3
  • 2212-rc1
  • 2213
  • 2214-pre1
  • 2214-pre2
  • 2214-pre3
  • 2214-pre4
  • 2_2_12
  • 64-gl-log
  • COM_ImmedExecute-lua
  • DJGPP
  • accel-momentum
  • acs
  • action-args
  • alpha-fixes
  • any-resolution
  • appveyor
  • blend-locking
  • blentran
  • blua-unary-not-fix
  • boost-tickrate
  • bustablesoundz
  • cleanup-opengl
  • cleanupmusic
  • clipmidtex
  • cmake-valgrind
  • crawlacommander-sprites
  • custom-map-names
  • custom-teams
  • cutscene-cleanup
  • dd-music-bypass
  • dd-music-fix
  • delfile2
  • deprecate-lua-dedicated-server
  • dpl-2
  • dropshadows-spawning
  • dynabsp
  • emblem-drawing
  • exchndl-xp-fix
  • extra-textures
  • few-kart-lua-changes
  • ffloorclip
  • fix-167
  • fix-cvar-conflicts
  • fix-opengl-parameter-crash
  • fix-opengl-shear-roll
  • flipfuncpointers
  • fof-lightlist-fixes
  • font-FUCK
  • frictionrefactor
  • fuck-macros-1
  • gamepad-luakeydown
  • gamepad-morefixes
  • gamepad_experiments
  • gametype-refactor
  • gametype-refactor-1
  • gametype-refactor-player-spawns
  • ghost-networking
  • gif-splitting
  • grr-lj
  • hitboxviewer
  • hwr-texture-cache-refactor
  • hwrender2
  • improve-439
  • increase-maxconditionsets
  • increase-packet-tics
  • input-display
  • input-display-translucency
  • io
  • joystick-juggling-maz
  • just-in-case
  • keycodes-only
  • ksf-wadfiles
  • ld413-mp-fix
  • levelstruct
  • libpng-version-support
  • linedef-actions
  • lj-test
  • lol-states
  • loopedsounds
  • lower-unpegged-fix
  • lua-change-gametype
  • lua-command-netids
  • lua-gfx-2
  • lua-gfx-sprites
  • lua-local
  • makefile-auto-mingw-gcc
  • makefile-tinkering
  • SRB2_release_2.1
  • SRB2_release_2.1.1
  • SRB2_release_2.1.10
  • SRB2_release_2.1.11
  • SRB2_release_2.1.12
  • SRB2_release_2.1.14
  • SRB2_release_2.1.15
  • SRB2_release_2.1.16
  • SRB2_release_2.1.16a
  • SRB2_release_2.1.17
  • SRB2_release_2.1.18
  • SRB2_release_2.1.19
  • SRB2_release_2.1.2
  • SRB2_release_2.1.20
  • SRB2_release_2.1.21
  • SRB2_release_2.1.22
  • SRB2_release_2.1.23
  • SRB2_release_2.1.24
  • SRB2_release_2.1.25
  • SRB2_release_2.1.3
  • SRB2_release_2.1.4
  • SRB2_release_2.1.5
  • SRB2_release_2.1.6
  • SRB2_release_2.1.7
  • SRB2_release_2.1.8
  • SRB2_release_2.1.9
  • SRB2_release_2.2.0
  • SRB2_release_2.2.1
  • SRB2_release_2.2.10
  • SRB2_release_2.2.11
  • SRB2_release_2.2.12
  • SRB2_release_2.2.13
  • SRB2_release_2.2.15
  • SRB2_release_2.2.2
  • SRB2_release_2.2.3
  • SRB2_release_2.2.4
  • SRB2_release_2.2.5
  • SRB2_release_2.2.6
  • SRB2_release_2.2.7
  • SRB2_release_2.2.8
  • SRB2_release_2.2.9
  • td-release-v1.0.0
142 results
Show changes
...@@ -109,6 +109,10 @@ const char * M_Ftrim (double); ...@@ -109,6 +109,10 @@ const char * M_Ftrim (double);
// Returns true if the string is empty. // Returns true if the string is empty.
boolean M_IsStringEmpty(const char *s); boolean M_IsStringEmpty(const char *s);
const char *M_GetFilenameFromPath(const char *path);
const char *M_GetExtensionFromFilename(const char *filename);
const char *M_CheckFilenameExtension(const char *filename, const char *ext);
// Converts a string containing a whole number into an int. Returns false if the conversion failed. // Converts a string containing a whole number into an int. Returns false if the conversion failed.
boolean M_StringToNumber(const char *input, int *out); boolean M_StringToNumber(const char *input, int *out);
...@@ -121,6 +125,11 @@ FUNCMATH UINT8 M_CountBits(UINT32 num, UINT8 size); ...@@ -121,6 +125,11 @@ FUNCMATH UINT8 M_CountBits(UINT32 num, UINT8 size);
// Rounds off floating numbers and checks for 0 - 255 bounds // Rounds off floating numbers and checks for 0 - 255 bounds
int M_RoundUp(double number); int M_RoundUp(double number);
// Hashes some message using FNV-1a
UINT32 FNV1a_Hash(const char *message, size_t size);
UINT32 FNV1a_HashString(const char *message);
UINT32 FNV1a_HashLowercaseString(const char *message);
#include "w_wad.h" #include "w_wad.h"
extern char configfile[MAX_WADPATH]; extern char configfile[MAX_WADPATH];
......
...@@ -1742,7 +1742,7 @@ void D_MapChange(INT32 mapnum, INT32 newgametype, boolean pultmode, boolean rese ...@@ -1742,7 +1742,7 @@ void D_MapChange(INT32 mapnum, INT32 newgametype, boolean pultmode, boolean rese
{ {
UINT8 flags = 0; UINT8 flags = 0;
const char *mapname = G_BuildMapName(mapnum); const char *mapname = G_BuildMapName(mapnum);
I_Assert(W_CheckNumForName(mapname) != LUMPERROR); I_Assert(G_MapFileExists(mapname) == true);
buf_p = buf; buf_p = buf;
if (pultmode) if (pultmode)
flags |= 1; flags |= 1;
...@@ -2044,8 +2044,8 @@ static void Command_Map_f(void) ...@@ -2044,8 +2044,8 @@ static void Command_Map_f(void)
static void Got_Mapcmd(UINT8 **cp, INT32 playernum) static void Got_Mapcmd(UINT8 **cp, INT32 playernum)
{ {
char mapname[MAX_WADPATH+1]; char mapname[MAX_WADPATH+1];
UINT8 flags; UINT8 flags, newgametype;
INT32 resetplayer = 1, lastgametype; INT32 resetplayer = 1, lastgametype = gametype;
UINT8 skipprecutscene, FLS; UINT8 skipprecutscene, FLS;
INT16 mapnumber; INT16 mapnumber;
...@@ -2061,6 +2061,12 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum) ...@@ -2061,6 +2061,12 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum)
chmappending--; chmappending--;
flags = READUINT8(*cp); flags = READUINT8(*cp);
newgametype = READUINT8(*cp);
READSTRINGN(*cp, mapname, MAX_WADPATH);
mapnumber = G_GetMapNumber(mapname);
if (!mapnumber) // Not valid???
return;
ultimatemode = ((flags & 1) != 0); ultimatemode = ((flags & 1) != 0);
if (netgame || multiplayer) if (netgame || multiplayer)
...@@ -2068,13 +2074,8 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum) ...@@ -2068,13 +2074,8 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum)
resetplayer = ((flags & (1<<1)) == 0); resetplayer = ((flags & (1<<1)) == 0);
lastgametype = gametype; if (newgametype < gametypecount)
gametype = READUINT8(*cp); G_SetGametype(newgametype);
if (gametype < 0 || gametype >= gametypecount)
gametype = lastgametype;
else
G_SetGametype(gametype);
if (gametype != lastgametype) if (gametype != lastgametype)
D_GameTypeChanged(lastgametype); // emulate consvar_t behavior for gametype D_GameTypeChanged(lastgametype); // emulate consvar_t behavior for gametype
...@@ -2083,8 +2084,6 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum) ...@@ -2083,8 +2084,6 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum)
FLS = ((flags & (1<<3)) != 0); FLS = ((flags & (1<<3)) != 0);
READSTRINGN(*cp, mapname, MAX_WADPATH);
if (netgame) if (netgame)
P_SetRandSeed(READUINT32(*cp)); P_SetRandSeed(READUINT32(*cp));
...@@ -2104,7 +2103,6 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum) ...@@ -2104,7 +2103,6 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum)
players[0].skincolor = skins[players[0].skin]->prefcolor; players[0].skincolor = skins[players[0].skin]->prefcolor;
} }
mapnumber = M_MapNumber(mapname[3], mapname[4]);
LUA_HookInt(mapnumber, HOOK(MapChange)); LUA_HookInt(mapnumber, HOOK(MapChange));
G_InitNew(ultimatemode, mapname, resetplayer, skipprecutscene, FLS); G_InitNew(ultimatemode, mapname, resetplayer, skipprecutscene, FLS);
......
...@@ -26,7 +26,7 @@ packet versions. ...@@ -26,7 +26,7 @@ packet versions.
If you change the struct or the meaning of a field If you change the struct or the meaning of a field
therein, increment this number. therein, increment this number.
*/ */
#define PACKETVERSION 5 #define PACKETVERSION 6
// Network play related stuff. // Network play related stuff.
// There is a data struct that stores network // There is a data struct that stores network
...@@ -226,7 +226,7 @@ typedef struct ...@@ -226,7 +226,7 @@ typedef struct
tic_t time; tic_t time;
tic_t leveltime; tic_t leveltime;
char servername[MAXSERVERNAME]; char servername[MAXSERVERNAME];
char mapname[8]; char mapname[24];
char maptitle[33]; char maptitle[33];
unsigned char mapmd5[16]; unsigned char mapmd5[16];
UINT8 actnum; UINT8 actnum;
......
...@@ -121,8 +121,7 @@ static void SV_SendServerInfo(INT32 node, tic_t servertime) ...@@ -121,8 +121,7 @@ static void SV_SendServerInfo(INT32 node, tic_t servertime)
netbuffer->u.serverinfo.flags = (dedicated ? SV_DEDICATED : 0); netbuffer->u.serverinfo.flags = (dedicated ? SV_DEDICATED : 0);
strncpy(netbuffer->u.serverinfo.servername, cv_servername.string, strncpy(netbuffer->u.serverinfo.servername, cv_servername.string,
sizeof(netbuffer->u.serverinfo.servername)-1); sizeof(netbuffer->u.serverinfo.servername)-1);
strncpy(netbuffer->u.serverinfo.mapname, G_BuildMapName(gamemap), 7); strlcpy(netbuffer->u.serverinfo.mapname, G_BuildMapName(gamemap), sizeof netbuffer->u.serverinfo.mapname);
M_Memcpy(netbuffer->u.serverinfo.mapmd5, mapmd5, 16); M_Memcpy(netbuffer->u.serverinfo.mapmd5, mapmd5, 16);
memset(netbuffer->u.serverinfo.maptitle, 0, sizeof netbuffer->u.serverinfo.maptitle); memset(netbuffer->u.serverinfo.maptitle, 0, sizeof netbuffer->u.serverinfo.maptitle);
...@@ -142,7 +141,6 @@ static void SV_SendServerInfo(INT32 node, tic_t servertime) ...@@ -142,7 +141,6 @@ static void SV_SendServerInfo(INT32 node, tic_t servertime)
read++; read++;
} }
*writ = '\0'; *writ = '\0';
//strncpy(netbuffer->u.serverinfo.maptitle, (char *)mapheaderinfo[gamemap-1]->lvlttl, 33);
} }
else else
strncpy(netbuffer->u.serverinfo.maptitle, "UNKNOWN", 32); strncpy(netbuffer->u.serverinfo.maptitle, "UNKNOWN", 32);
......
...@@ -3789,11 +3789,10 @@ static void P_DoBossVictory(mobj_t *mo) ...@@ -3789,11 +3789,10 @@ static void P_DoBossVictory(mobj_t *mo)
// Touching the egg trap button calls P_DoPlayerExit, which calls P_RestoreMusic. // Touching the egg trap button calls P_DoPlayerExit, which calls P_RestoreMusic.
// So just park ourselves in the mapmus variables. // So just park ourselves in the mapmus variables.
// But don't change the mapmus variables if they were modified from their level header values (e.g., TUNES). // But don't change the mapmus variables if they were modified from their level header values (e.g., TUNES).
boolean changed = strnicmp(mapheaderinfo[gamemap-1]->musname, S_MusicName(), 7); boolean changed = strnicmp(mapheaderinfo[gamemap-1]->musname, S_MusicName(), MAX_MUSIC_NAME);
if (!strnicmp(mapheaderinfo[gamemap-1]->musname, mapmusname, 7)) if (!strnicmp(mapheaderinfo[gamemap-1]->musname, mapmusname, MAX_MUSIC_NAME))
{ {
strncpy(mapmusname, mapheaderinfo[gamemap-1]->muspostbossname, 7); strlcpy(mapmusname, mapheaderinfo[gamemap-1]->muspostbossname, MAX_MUSIC_NAME+1);
mapmusname[6] = 0;
mapmusflags = (mapheaderinfo[gamemap-1]->muspostbosstrack & MUSIC_TRACKMASK) | MUSIC_RELOADRESET; mapmusflags = (mapheaderinfo[gamemap-1]->muspostbosstrack & MUSIC_TRACKMASK) | MUSIC_RELOADRESET;
mapmusposition = mapheaderinfo[gamemap-1]->muspostbosspos; mapmusposition = mapheaderinfo[gamemap-1]->muspostbosspos;
} }
......
...@@ -258,7 +258,7 @@ typedef enum ...@@ -258,7 +258,7 @@ typedef enum
typedef struct typedef struct
{ {
char musname[7]; char musname[MAX_MUSIC_NAME+1];
boolean looping; boolean looping;
} jingle_t; } jingle_t;
......
...@@ -4415,24 +4415,59 @@ static void P_NetUnArchiveSpecials(void) ...@@ -4415,24 +4415,59 @@ static void P_NetUnArchiveSpecials(void)
// ======================================================================= // =======================================================================
// Misc // Misc
// ======================================================================= // =======================================================================
static inline void P_ArchiveMisc(INT16 mapnum) static void P_ArchiveMisc(INT16 mapnum)
{ {
//lastmapsaved = mapnum;
lastmaploaded = mapnum; lastmaploaded = mapnum;
if (gamecomplete) #ifdef NEWMAPSAVES
mapnum |= 8192; if (mapnum >= NUMBASEMAPS)
{
WRITEINT16(save_p, NEWMAPSAVES);
WRITESTRINGN(save_p, G_BuildMapName(mapnum), MAX_MAP_NAME_SIZE);
UINT8 flags = 0;
if (gamecomplete)
flags |= SAVE_GAME_COMPLETE_BIT;
WRITEUINT8(save_p, flags);
}
else
#endif
{
if (gamecomplete)
mapnum |= 8192;
WRITEINT16(save_p, mapnum);
}
WRITEINT16(save_p, mapnum);
WRITEUINT16(save_p, emeralds+357); WRITEUINT16(save_p, emeralds+357);
WRITESTRINGN(save_p, timeattackfolder, sizeof(timeattackfolder)); WRITESTRINGN(save_p, timeattackfolder, sizeof(timeattackfolder));
} }
static inline void P_UnArchiveSPGame(INT16 mapoverride) static void P_UnArchiveSPGame(INT16 mapoverride)
{ {
char testname[sizeof(timeattackfolder)]; char testname[sizeof(timeattackfolder)];
gamemap = READINT16(save_p); INT16 mapnum = READINT16(save_p);
#ifdef NEWMAPSAVES
if (mapnum == NEWMAPSAVES)
{
char mapname[MAX_MAP_NAME_SIZE+1];
READSTRINGN(save_p, mapname, MAX_MAP_NAME_SIZE);
READUINT8(save_p); // flags
mapnum = G_GetMapNumber(mapname);
if (mapnum == 0)
{
// If not valid, just load MAP01 instead.
mapnum = 1;
}
}
#endif
gamemap = mapnum;
if (mapoverride != 0) if (mapoverride != 0)
{ {
...@@ -4447,7 +4482,6 @@ static inline void P_UnArchiveSPGame(INT16 mapoverride) ...@@ -4447,7 +4482,6 @@ static inline void P_UnArchiveSPGame(INT16 mapoverride)
if(!mapheaderinfo[gamemap-1]) if(!mapheaderinfo[gamemap-1])
P_AllocMapHeader(gamemap-1); P_AllocMapHeader(gamemap-1);
//lastmapsaved = gamemap;
lastmaploaded = gamemap; lastmaploaded = gamemap;
tokenlist = 0; tokenlist = 0;
...@@ -4672,7 +4706,7 @@ static inline void P_NetArchiveEmblems(void) ...@@ -4672,7 +4706,7 @@ static inline void P_NetArchiveEmblems(void)
WRITEUINT32(save_p, data->totalplaytime); WRITEUINT32(save_p, data->totalplaytime);
// TODO put another cipher on these things? meh, I don't care... // TODO put another cipher on these things? meh, I don't care...
for (i = 0; i < NUMMAPS; i++) for (i = 0; i < numgamemaps; i++)
WRITEUINT8(save_p, (data->mapvisited[i] & MV_MAX)); WRITEUINT8(save_p, (data->mapvisited[i] & MV_MAX));
// To save space, use one bit per collected/achieved/unlocked flag // To save space, use one bit per collected/achieved/unlocked flag
...@@ -4714,7 +4748,7 @@ static inline void P_NetArchiveEmblems(void) ...@@ -4714,7 +4748,7 @@ static inline void P_NetArchiveEmblems(void)
WRITEUINT32(save_p, data->timesBeatenUltimate); WRITEUINT32(save_p, data->timesBeatenUltimate);
// Main records // Main records
for (i = 0; i < NUMMAPS; i++) for (i = 0; i < numgamemaps; i++)
{ {
if (data->mainrecords[i]) if (data->mainrecords[i])
{ {
...@@ -4731,7 +4765,7 @@ static inline void P_NetArchiveEmblems(void) ...@@ -4731,7 +4765,7 @@ static inline void P_NetArchiveEmblems(void)
} }
// NiGHTS records // NiGHTS records
for (i = 0; i < NUMMAPS; i++) for (i = 0; i < numgamemaps; i++)
{ {
if (!data->nightsrecords[i] || !data->nightsrecords[i]->nummares) if (!data->nightsrecords[i] || !data->nightsrecords[i]->nummares)
{ {
...@@ -4807,7 +4841,7 @@ static inline void P_NetUnArchiveEmblems(void) ...@@ -4807,7 +4841,7 @@ static inline void P_NetUnArchiveEmblems(void)
data->totalplaytime = READUINT32(save_p); data->totalplaytime = READUINT32(save_p);
// TODO put another cipher on these things? meh, I don't care... // TODO put another cipher on these things? meh, I don't care...
for (i = 0; i < NUMMAPS; i++) for (i = 0; i < numgamemaps; i++)
if ((data->mapvisited[i] = READUINT8(save_p)) > MV_MAX) if ((data->mapvisited[i] = READUINT8(save_p)) > MV_MAX)
I_Error("Bad $$$.sav dearchiving Emblems (invalid visit flags)"); I_Error("Bad $$$.sav dearchiving Emblems (invalid visit flags)");
...@@ -4846,7 +4880,7 @@ static inline void P_NetUnArchiveEmblems(void) ...@@ -4846,7 +4880,7 @@ static inline void P_NetUnArchiveEmblems(void)
data->timesBeatenUltimate = READUINT32(save_p); data->timesBeatenUltimate = READUINT32(save_p);
// Main records // Main records
for (i = 0; i < NUMMAPS; ++i) for (i = 0; i < numgamemaps; ++i)
{ {
recscore = READUINT32(save_p); recscore = READUINT32(save_p);
rectime = (tic_t)READUINT32(save_p); rectime = (tic_t)READUINT32(save_p);
...@@ -4865,7 +4899,7 @@ static inline void P_NetUnArchiveEmblems(void) ...@@ -4865,7 +4899,7 @@ static inline void P_NetUnArchiveEmblems(void)
} }
// Nights records // Nights records
for (i = 0; i < NUMMAPS; ++i) for (i = 0; i < numgamemaps; ++i)
{ {
if ((recmares = READUINT8(save_p)) == 0) if ((recmares = READUINT8(save_p)) == 0)
continue; continue;
......
...@@ -18,7 +18,11 @@ ...@@ -18,7 +18,11 @@
#pragma interface #pragma interface
#endif #endif
#define NEWSKINSAVES (INT16_MAX) // TODO: 2.3: Delete (Purely for backwards compatibility) #define SAVE_GAME_COMPLETE_BIT 0x01
// TODO: 2.3: Delete both of these (purely for backwards compatibility)
#define NEWSKINSAVES (INT16_MAX)
#define NEWMAPSAVES (INT16_MAX)
// Persistent storage/archiving. // Persistent storage/archiving.
// These are the load / save game routines. // These are the load / save game routines.
......
...@@ -363,8 +363,7 @@ static void P_ClearSingleMapHeaderInfo(INT16 i) ...@@ -363,8 +363,7 @@ static void P_ClearSingleMapHeaderInfo(INT16 i)
mapheaderinfo[num]->ssspheres = 1; mapheaderinfo[num]->ssspheres = 1;
mapheaderinfo[num]->gravity = FRACUNIT/2; mapheaderinfo[num]->gravity = FRACUNIT/2;
mapheaderinfo[num]->keywords[0] = '\0'; mapheaderinfo[num]->keywords[0] = '\0';
snprintf(mapheaderinfo[num]->musname, 7, "%sM", G_BuildMapName(i)); snprintf(mapheaderinfo[num]->musname, MAX_MUSIC_NAME+1, "%s", G_GetDefaultMapMusic(i));
mapheaderinfo[num]->musname[6] = 0;
mapheaderinfo[num]->mustrack = 0; mapheaderinfo[num]->mustrack = 0;
mapheaderinfo[num]->muspos = 0; mapheaderinfo[num]->muspos = 0;
mapheaderinfo[num]->musinterfadeout = 0; mapheaderinfo[num]->musinterfadeout = 0;
...@@ -766,69 +765,6 @@ void P_SwitchSpheresBonusMode(boolean bonustime) ...@@ -766,69 +765,6 @@ void P_SwitchSpheresBonusMode(boolean bonustime)
} }
} }
#ifdef SCANTHINGS
void P_ScanThings(INT16 mapnum, INT16 wadnum, INT16 lumpnum)
{
size_t i, n;
UINT8 *data, *datastart;
UINT16 type, maprings;
INT16 tol;
UINT32 flags;
tol = mapheaderinfo[mapnum-1]->typeoflevel;
if (!(tol & TOL_SP))
return;
flags = mapheaderinfo[mapnum-1]->levelflags;
n = W_LumpLengthPwad(wadnum, lumpnum) / (5 * sizeof (INT16));
//CONS_Printf("%u map things found!\n", n);
maprings = 0;
data = datastart = W_CacheLumpNumPwad(wadnum, lumpnum, PU_STATIC);
for (i = 0; i < n; i++)
{
data += 3 * sizeof (INT16); // skip x y position, angle
type = READUINT16(data) & 4095;
data += sizeof (INT16); // skip options
switch (type)
{
case 300: // MT_RING
case 1800: // MT_COIN
case 308: // red team ring
case 309: // blue team ring
maprings++;
break;
case 400: // MT_SUPERRINGBOX
case 414: // red ring box
case 415: // blue ring box
case 603: // 10 diagonal rings
maprings += 10;
break;
case 600: // 5 vertical rings
case 601: // 5 vertical rings
case 602: // 5 diagonal rings
maprings += 5;
break;
case 604: // 8 circle rings
case 609: // 16 circle rings & wings
maprings += 8;
break;
case 605: // 16 circle rings
maprings += 16;
break;
case 608: // 8 circle rings & wings
maprings += 4;
break;
}
}
Z_Free(datastart);
if (maprings)
CONS_Printf("%s has %u rings\n", G_BuildMapName(mapnum), maprings);
}
#endif
static void P_SpawnEmeraldHunt(void) static void P_SpawnEmeraldHunt(void)
{ {
INT32 emer[3], num[MAXHUNTEMERALDS], i, amount, randomkey; INT32 emer[3], num[MAXHUNTEMERALDS], i, amount, randomkey;
...@@ -7104,9 +7040,9 @@ static void P_MakeMapMD5(virtres_t *virt, void *dest) ...@@ -7104,9 +7040,9 @@ static void P_MakeMapMD5(virtres_t *virt, void *dest)
M_Memcpy(dest, &resmd5, 16); M_Memcpy(dest, &resmd5, 16);
} }
static boolean P_LoadMapFromFile(void) static boolean P_LoadMapFromFile(lumpnum_t lumpnum)
{ {
virtres_t *virt = vres_GetMap(lastloadedmaplumpnum); virtres_t *virt = vres_GetMap(lumpnum);
virtlump_t *textmap = vres_Find(virt, "TEXTMAP"); virtlump_t *textmap = vres_Find(virt, "TEXTMAP");
size_t i; size_t i;
udmf = textmap != NULL; udmf = textmap != NULL;
...@@ -7172,9 +7108,6 @@ void P_SetupLevelSky(INT32 skynum, boolean global) ...@@ -7172,9 +7108,6 @@ void P_SetupLevelSky(INT32 skynum, boolean global)
R_SetupSkyDraw(); R_SetupSkyDraw();
} }
static const char *maplumpname;
lumpnum_t lastloadedmaplumpnum; // for comparative savegame
// //
// P_LevelInitStuff // P_LevelInitStuff
// //
...@@ -7385,14 +7318,15 @@ static void P_ResetSpawnpoints(void) ...@@ -7385,14 +7318,15 @@ static void P_ResetSpawnpoints(void)
static void P_LoadRecordGhosts(void) static void P_LoadRecordGhosts(void)
{ {
const size_t glen = strlen(srb2home)+1+strlen("replay")+1+strlen(timeattackfolder)+1+strlen("MAPXX")+1; const char *mapname = G_BuildMapName(gamemap);
const size_t glen = strlen(srb2home)+1+strlen("replay")+1+strlen(timeattackfolder)+1+strlen(mapname)+1;
char *gpath = malloc(glen); char *gpath = malloc(glen);
INT32 i; INT32 i;
if (!gpath) if (!gpath)
return; return;
sprintf(gpath,"%s"PATHSEP"replay"PATHSEP"%s"PATHSEP"%s", srb2home, timeattackfolder, G_BuildMapName(gamemap)); sprintf(gpath,"%s"PATHSEP"replay"PATHSEP"%s"PATHSEP"%s", srb2home, timeattackfolder, mapname);
// Best Score ghost // Best Score ghost
if (cv_ghost_bestscore.value) if (cv_ghost_bestscore.value)
...@@ -7455,14 +7389,15 @@ static void P_LoadRecordGhosts(void) ...@@ -7455,14 +7389,15 @@ static void P_LoadRecordGhosts(void)
static void P_LoadNightsGhosts(void) static void P_LoadNightsGhosts(void)
{ {
const size_t glen = strlen(srb2home)+1+strlen("replay")+1+strlen(timeattackfolder)+1+strlen("MAPXX")+1; const char *mapname = G_BuildMapName(gamemap);
const size_t glen = strlen(srb2home)+1+strlen("replay")+1+strlen(timeattackfolder)+1+strlen(mapname)+1;
char *gpath = malloc(glen); char *gpath = malloc(glen);
INT32 i; INT32 i;
if (!gpath) if (!gpath)
return; return;
sprintf(gpath,"%s"PATHSEP"replay"PATHSEP"%s"PATHSEP"%s", srb2home, timeattackfolder, G_BuildMapName(gamemap)); sprintf(gpath,"%s"PATHSEP"replay"PATHSEP"%s"PATHSEP"%s", srb2home, timeattackfolder, mapname);
// Best Score ghost // Best Score ghost
if (cv_ghost_bestscore.value) if (cv_ghost_bestscore.value)
...@@ -7636,7 +7571,7 @@ static void P_RunSpecialStageWipe(void) ...@@ -7636,7 +7571,7 @@ static void P_RunSpecialStageWipe(void)
// Fade music! Time it to S3KAF: 0.25 seconds is snappy. // Fade music! Time it to S3KAF: 0.25 seconds is snappy.
if (RESETMUSIC || if (RESETMUSIC ||
strnicmp(S_MusicName(), strnicmp(S_MusicName(),
(mapmusflags & MUSIC_RELOADRESET) ? mapheaderinfo[gamemap - 1]->musname : mapmusname, 7)) (mapmusflags & MUSIC_RELOADRESET) ? mapheaderinfo[gamemap - 1]->musname : mapmusname, MAX_MUSIC_NAME))
S_FadeOutStopMusic(MUSICRATE/4); //FixedMul(FixedDiv(F_GetWipeLength(wipedefs[wipe_speclevel_towhite])*NEWTICRATERATIO, NEWTICRATE), MUSICRATE) S_FadeOutStopMusic(MUSICRATE/4); //FixedMul(FixedDiv(F_GetWipeLength(wipedefs[wipe_speclevel_towhite])*NEWTICRATERATIO, NEWTICRATE), MUSICRATE)
F_WipeStartScreen(); F_WipeStartScreen();
...@@ -7809,7 +7744,9 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate) ...@@ -7809,7 +7744,9 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate)
// 99% of the things already did, so. // 99% of the things already did, so.
// Map header should always be in place at this point // Map header should always be in place at this point
INT32 i, ranspecialwipe = 0; INT32 i, ranspecialwipe = 0;
sector_t *ss; lumpnum_t maplumpnum;
const char *maplumpname;
levelloading = true; levelloading = true;
// This is needed. Don't touch. // This is needed. Don't touch.
...@@ -7904,7 +7841,7 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate) ...@@ -7904,7 +7841,7 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate)
// But don't halt the music! S_Start will take care of that. This dodges a MIDI crash bug. // But don't halt the music! S_Start will take care of that. This dodges a MIDI crash bug.
if (!(reloadinggamestate || titlemapinaction) && (RESETMUSIC || if (!(reloadinggamestate || titlemapinaction) && (RESETMUSIC ||
strnicmp(S_MusicName(), strnicmp(S_MusicName(),
(mapmusflags & MUSIC_RELOADRESET) ? mapheaderinfo[gamemap-1]->musname : mapmusname, 7))) (mapmusflags & MUSIC_RELOADRESET) ? mapheaderinfo[gamemap-1]->musname : mapmusname, MAX_MUSIC_NAME)))
{ {
S_FadeMusic(0, FixedMul( S_FadeMusic(0, FixedMul(
FixedDiv((F_GetWipeLength(wipedefs[wipe_level_toblack])-2)*NEWTICRATERATIO, NEWTICRATE), MUSICRATE)); FixedDiv((F_GetWipeLength(wipedefs[wipe_level_toblack])-2)*NEWTICRATERATIO, NEWTICRATE), MUSICRATE));
...@@ -7950,7 +7887,7 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate) ...@@ -7950,7 +7887,7 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate)
LUA_InvalidateLevel(); LUA_InvalidateLevel();
for (ss = sectors; sectors+numsectors != ss; ss++) for (sector_t *ss = sectors; sectors+numsectors != ss; ss++)
{ {
Z_Free(ss->attached); Z_Free(ss->attached);
Z_Free(ss->attachedsolid); Z_Free(ss->attachedsolid);
...@@ -7981,9 +7918,9 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate) ...@@ -7981,9 +7918,9 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate)
// internal game map // internal game map
maplumpname = G_BuildMapName(gamemap); maplumpname = G_BuildMapName(gamemap);
lastloadedmaplumpnum = W_CheckNumForMap(maplumpname); maplumpnum = G_GetMapLumpnum(maplumpname);
if (lastloadedmaplumpnum == LUMPERROR) if (maplumpnum == LUMPERROR)
I_Error("Map %s not found.\n", maplumpname); I_Error("Map %s not found\n", maplumpname);
R_ReInitColormaps(mapheaderinfo[gamemap-1]->palette); R_ReInitColormaps(mapheaderinfo[gamemap-1]->palette);
CON_SetupBackColormap(); CON_SetupBackColormap();
...@@ -7999,7 +7936,7 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate) ...@@ -7999,7 +7936,7 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate)
P_InitSlopes(); P_InitSlopes();
if (!P_LoadMapFromFile()) if (!P_LoadMapFromFile(maplumpnum))
return false; return false;
if (!demoplayback) if (!demoplayback)
...@@ -8225,6 +8162,142 @@ static lumpinfo_t* FindFolder(const char *folName, UINT16 *start, UINT16 *end, l ...@@ -8225,6 +8162,142 @@ static lumpinfo_t* FindFolder(const char *folName, UINT16 *start, UINT16 *end, l
return lumpinfo; return lumpinfo;
} }
static int P_AddMap(const char *name, UINT32 lumpnum)
{
// Check filename length
size_t name_len = strlen(name);
if (name_len > MAX_MAP_NAME_SIZE)
{
CONS_Alert(CONS_WARNING, "Map name's length of %s exceeds maximum of %d -- skipping\n", sizeu1(name_len), MAX_MAP_NAME_SIZE);
return 0;
}
if (!G_IsValidMapName(name))
{
CONS_Alert(CONS_WARNING, "Map name %s is invalid -- skipping\n", name);
return 0;
}
INT16 num = G_AddMap(name, lumpnum);
if (num == 0)
{
CONS_Alert(CONS_ERROR, "Too many maps loaded!\n");
return -1;
}
//If you replaced the map you're on, end the level when done.
if (gamestate == GS_LEVEL && num == gamemap)
replacedcurrentmap = true;
return 1;
}
void P_LoadMapsFromFile(UINT16 wadnum, boolean added_ingame)
{
boolean mapsadded = false;
lumpinfo_t *lumpinfo = NULL;
UINT16 numlumps = 0;
const char *name;
if (W_FileHasFolders(wadfiles[wadnum]))
{
UINT32 *list = NULL;
UINT16 capacity = 0;
W_GetFolderLumpsPwad("Maps/", wadnum, &list, &capacity, &numlumps);
for (UINT16 i = 0; i < numlumps; i++)
{
UINT32 lumpnum = list[i];
lumpinfo = wadfiles[wadnum]->lumpinfo + LUMPNUM(lumpnum);
name = W_GetFilenameFromFullname(lumpinfo->fullname); // Full lump name, with its extension
// Extension must be .wad
if (!M_CheckFilenameExtension(name, "wad"))
continue;
// Get the name without the extension
name = lumpinfo->longname;
int status = P_AddMap(name, lumpnum);
if (status == 1)
{
if (added_ingame)
CONS_Printf("%s\n", name);
mapsadded = true;
}
else if (status < 0)
break;
}
Z_Free(list);
}
else
{
lumpinfo = wadfiles[wadnum]->lumpinfo;
numlumps = wadfiles[wadnum]->numlumps;
for (size_t i = 0; i < numlumps; i++, lumpinfo++)
{
name = lumpinfo->name;
if (name[0] == 'M' && name[1] == 'A' && name[2] == 'P' && name[5] == '\0')
{
int status = P_AddMap(name, (wadnum << 16) + i);
if (status == 1)
{
if (added_ingame)
CONS_Printf("%s\n", name);
mapsadded = true;
}
else if (status < 0)
break;
}
}
// Now do markers
UINT16 start = W_CheckNumForMarkerStartPwad("LV_START", wadnum, 0);
UINT16 end = W_CheckNumForNamePwad("LV_END", wadnum, start);
lumpinfo = wadfiles[wadnum]->lumpinfo + start;
for (UINT16 l = start; l < end; l++, lumpinfo++)
{
name = lumpinfo->name;
// Ignore any of these lump names
if (stricmp(name, "THINGS") == 0
|| stricmp(name, "LINEDEFS") == 0
|| stricmp(name, "SIDEDEFS") == 0
|| stricmp(name, "VERTEXES") == 0
|| stricmp(name, "SEGS") == 0
|| stricmp(name, "SSECTORS") == 0
|| stricmp(name, "NODES") == 0
|| stricmp(name, "SECTORS") == 0
|| stricmp(name, "REJECT") == 0
|| stricmp(name, "BLOCKMAP") == 0
|| stricmp(name, "BEHAVIOR") == 0)
continue;
int status = P_AddMap(name, (wadnum << 16) + l);
if (status == 1)
{
if (added_ingame)
CONS_Printf("%s\n", name);
mapsadded = true;
}
else if (status < 0)
break;
}
}
if (!mapsadded && added_ingame)
CONS_Printf(M_GetText("No maps added\n"));
}
// //
// Add a wadfile to the active wad files, // Add a wadfile to the active wad files,
// replace sounds, musics, patches, textures, sprites and maps // replace sounds, musics, patches, textures, sprites and maps
...@@ -8238,8 +8311,6 @@ static boolean P_LoadAddon(UINT16 numlumps) ...@@ -8238,8 +8311,6 @@ static boolean P_LoadAddon(UINT16 numlumps)
lumpinfo_t *lumpinfo; lumpinfo_t *lumpinfo;
//boolean texturechange = false; ///\todo Useless; broken when back-frontporting PK3 changes? //boolean texturechange = false; ///\todo Useless; broken when back-frontporting PK3 changes?
boolean mapsadded = false;
boolean replacedcurrentmap = false;
// Vars to help us with the position start and amount of each resource type. // Vars to help us with the position start and amount of each resource type.
// Useful for PK3s since they use folders. // Useful for PK3s since they use folders.
...@@ -8381,32 +8452,7 @@ static boolean P_LoadAddon(UINT16 numlumps) ...@@ -8381,32 +8452,7 @@ static boolean P_LoadAddon(UINT16 numlumps)
// //
S_LoadMusicDefs(wadnum); S_LoadMusicDefs(wadnum);
// R_LoadSpriteInfoLumps(wadnum);
// search for maps
//
lumpinfo = wadfiles[wadnum]->lumpinfo;
for (i = 0; i < numlumps; i++, lumpinfo++)
{
name = lumpinfo->name;
if (name[0] == 'M' && name[1] == 'A' && name[2] == 'P') // Ignore the headers
{
INT16 num;
if (name[5]!='\0')
continue;
num = (INT16)M_MapNumber(name[3], name[4]);
//If you replaced the map you're on, end the level when done.
if (num == gamemap)
replacedcurrentmap = true;
CONS_Printf("%s\n", name);
mapsadded = true;
}
}
if (!mapsadded)
CONS_Printf(M_GetText("No maps added\n"));
R_LoadSpriteInfoLumps(wadnum, numlumps);
#ifdef HWRENDER #ifdef HWRENDER
HWR_ReloadModels(); HWR_ReloadModels();
...@@ -8420,11 +8466,16 @@ static boolean P_LoadAddon(UINT16 numlumps) ...@@ -8420,11 +8466,16 @@ static boolean P_LoadAddon(UINT16 numlumps)
if (modifiedgame && (cursaveslot > 0)) if (modifiedgame && (cursaveslot > 0))
cursaveslot = 0; cursaveslot = 0;
if (replacedcurrentmap && gamestate == GS_LEVEL && (netgame || multiplayer)) if (replacedcurrentmap)
{ {
CONS_Printf(M_GetText("Current map %d replaced by added file, ending the level to ensure consistency.\n"), gamemap); replacedcurrentmap = false;
if (server)
SendNetXCmd(XD_EXITLEVEL, NULL, 0); if (gamestate == GS_LEVEL && (netgame || multiplayer))
{
CONS_Printf(M_GetText("Current map %s replaced by added file, ending the level to ensure consistency.\n"), G_BuildMapName(gamemap));
if (server)
SendNetXCmd(XD_EXITLEVEL, NULL, 0);
}
} }
return true; return true;
......
...@@ -58,9 +58,6 @@ extern size_t nummapthings; ...@@ -58,9 +58,6 @@ extern size_t nummapthings;
extern mapthing_t *mapthings; extern mapthing_t *mapthings;
void P_SetupLevelSky(INT32 skynum, boolean global); void P_SetupLevelSky(INT32 skynum, boolean global);
#ifdef SCANTHINGS
void P_ScanThings(INT16 mapnum, INT16 wadnum, INT16 lumpnum);
#endif
void P_RespawnThings(void); void P_RespawnThings(void);
boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate); boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate);
#ifdef HWRENDER #ifdef HWRENDER
...@@ -71,6 +68,7 @@ boolean P_AddFolder(const char *folderpath); ...@@ -71,6 +68,7 @@ boolean P_AddFolder(const char *folderpath);
boolean P_RunSOC(const char *socfilename); boolean P_RunSOC(const char *socfilename);
void P_LoadSoundsRange(UINT16 wadnum, UINT16 first, UINT16 num); void P_LoadSoundsRange(UINT16 wadnum, UINT16 first, UINT16 num);
void P_LoadMusicsRange(UINT16 wadnum, UINT16 first, UINT16 num); void P_LoadMusicsRange(UINT16 wadnum, UINT16 first, UINT16 num);
void P_LoadMapsFromFile(UINT16 wadnum, boolean added_ingame);
void P_WriteThings(const char *filepath); void P_WriteThings(const char *filepath);
size_t P_PrecacheLevelFlats(void); size_t P_PrecacheLevelFlats(void);
void P_AllocMapHeader(INT16 i); void P_AllocMapHeader(INT16 i);
......
...@@ -2457,7 +2457,7 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) ...@@ -2457,7 +2457,7 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec)
// console player only unless TMM_ALLPLAYERS is set // console player only unless TMM_ALLPLAYERS is set
if ((line->args[0] & TMM_ALLPLAYERS) || (mo && mo->player && P_IsLocalPlayer(mo->player)) || titlemapinaction) if ((line->args[0] & TMM_ALLPLAYERS) || (mo && mo->player && P_IsLocalPlayer(mo->player)) || titlemapinaction)
{ {
boolean musicsame = (!line->stringargs[0] || !line->stringargs[0][0] || !strnicmp(line->stringargs[0], S_MusicName(), 7)); boolean musicsame = (!line->stringargs[0] || !line->stringargs[0][0] || !strnicmp(line->stringargs[0], S_MusicName(), MAX_MUSIC_NAME));
UINT16 tracknum = (UINT16)max(line->args[6], 0); UINT16 tracknum = (UINT16)max(line->args[6], 0);
INT32 position = (INT32)max(line->args[1], 0); INT32 position = (INT32)max(line->args[1], 0);
UINT32 prefadems = (UINT32)max(line->args[2], 0); UINT32 prefadems = (UINT32)max(line->args[2], 0);
...@@ -2500,8 +2500,7 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) ...@@ -2500,8 +2500,7 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec)
strcpy(mapmusname, ""); strcpy(mapmusname, "");
else else
{ {
strncpy(mapmusname, line->stringargs[0], 7); strlcpy(mapmusname, line->stringargs[0], MAX_MUSIC_NAME+1);
mapmusname[6] = 0;
} }
mapmusflags = tracknum & MUSIC_TRACKMASK; mapmusflags = tracknum & MUSIC_TRACKMASK;
......
...@@ -1591,13 +1591,8 @@ void P_PlayJingle(player_t *player, jingletype_t jingletype) ...@@ -1591,13 +1591,8 @@ void P_PlayJingle(player_t *player, jingletype_t jingletype)
UINT16 musflags = 0; UINT16 musflags = 0;
boolean looping = jingleinfo[jingletype].looping; boolean looping = jingleinfo[jingletype].looping;
char newmusic[7]; char newmusic[MAX_MUSIC_NAME];
strncpy(newmusic, musname, 7); strlcpy(newmusic, musname, MAX_MUSIC_NAME);
#ifdef HAVE_LUA_MUSICPLUS
if(LUAh_MusicJingle(jingletype, newmusic, &musflags, &looping))
return;
#endif
newmusic[6] = 0;
P_PlayJingleMusic(player, newmusic, musflags, looping, jingletype); P_PlayJingleMusic(player, newmusic, musflags, looping, jingletype);
} }
......
...@@ -1753,13 +1753,13 @@ void R_ParseSPRTINFOLump(UINT16 wadNum, UINT16 lumpNum) ...@@ -1753,13 +1753,13 @@ void R_ParseSPRTINFOLump(UINT16 wadNum, UINT16 lumpNum)
// //
// Load and read every SPRTINFO lump from the specified file. // Load and read every SPRTINFO lump from the specified file.
// //
void R_LoadSpriteInfoLumps(UINT16 wadnum, UINT16 numlumps) void R_LoadSpriteInfoLumps(UINT16 wadnum)
{ {
lumpinfo_t *lumpinfo = wadfiles[wadnum]->lumpinfo; lumpinfo_t *lumpinfo = wadfiles[wadnum]->lumpinfo;
UINT16 i; UINT16 i;
char *name; char *name;
for (i = 0; i < numlumps; i++, lumpinfo++) for (i = 0; i < wadfiles[wadnum]->numlumps; i++, lumpinfo++)
{ {
name = lumpinfo->name; name = lumpinfo->name;
// Load SPRTINFO and SPR_ lumps as SpriteInfo // Load SPRTINFO and SPR_ lumps as SpriteInfo
......
...@@ -123,7 +123,7 @@ boolean Picture_PNGDimensions(UINT8 *png, INT32 *width, INT32 *height, INT16 *to ...@@ -123,7 +123,7 @@ boolean Picture_PNGDimensions(UINT8 *png, INT32 *width, INT32 *height, INT16 *to
// SpriteInfo // SpriteInfo
extern spriteinfo_t spriteinfo[NUMSPRITES]; extern spriteinfo_t spriteinfo[NUMSPRITES];
void R_LoadSpriteInfoLumps(UINT16 wadnum, UINT16 numlumps); void R_LoadSpriteInfoLumps(UINT16 wadnum);
void R_ParseSPRTINFOLump(UINT16 wadNum, UINT16 lumpNum); void R_ParseSPRTINFOLump(UINT16 wadNum, UINT16 lumpNum);
#endif // __R_PICFORMATS__ #endif // __R_PICFORMATS__
...@@ -774,7 +774,7 @@ void R_InitSprites(void) ...@@ -774,7 +774,7 @@ void R_InitSprites(void)
{ {
R_AddSkins((UINT16)i, true); R_AddSkins((UINT16)i, true);
R_PatchSkins((UINT16)i, true); R_PatchSkins((UINT16)i, true);
R_LoadSpriteInfoLumps(i, wadfiles[i]->numlumps); R_LoadSpriteInfoLumps(i);
} }
ST_ReloadSkinFaceGraphics(); ST_ReloadSkinFaceGraphics();
......
...@@ -1352,12 +1352,12 @@ void S_InitSfxChannels(INT32 sfxVolume) ...@@ -1352,12 +1352,12 @@ void S_InitSfxChannels(INT32 sfxVolume)
/// Music /// Music
/// ------------------------ /// ------------------------
static char music_name[7]; // up to 6-character name static char music_name[MAX_MUSIC_NAME+1];
static void *music_data; static void *music_data;
static UINT16 music_flags; static UINT16 music_flags;
static boolean music_looping; static boolean music_looping;
static char queue_name[7]; static char queue_name[MAX_MUSIC_NAME+1];
static UINT16 queue_flags; static UINT16 queue_flags;
static boolean queue_looping; static boolean queue_looping;
static UINT32 queue_position; static UINT32 queue_position;
...@@ -1568,9 +1568,8 @@ ReadMusicDefFields (UINT16 wadnum, int line, boolean fields, char *stoken, ...@@ -1568,9 +1568,8 @@ ReadMusicDefFields (UINT16 wadnum, int line, boolean fields, char *stoken,
} else if (!stricmp(stoken, "soundtestpage")) { } else if (!stricmp(stoken, "soundtestpage")) {
def->soundtestpage = (UINT8)i; def->soundtestpage = (UINT8)i;
} else if (!stricmp(stoken, "soundtestcond")) { } else if (!stricmp(stoken, "soundtestcond")) {
// Convert to map number if (!i)
if (textline[0] >= 'A' && textline[0] <= 'Z' && textline[2] == '\0') i = G_GetMapNumber(textline);
i = M_MapNumber(textline[0], textline[1]);
def->soundtestcond = (INT16)i; def->soundtestcond = (INT16)i;
} else if (!stricmp(stoken, "stoppingtime")) { } else if (!stricmp(stoken, "stoppingtime")) {
double stoppingtime = atof(textline)*TICRATE; double stoppingtime = atof(textline)*TICRATE;
...@@ -1778,8 +1777,8 @@ const char *S_MusicName(void) ...@@ -1778,8 +1777,8 @@ const char *S_MusicName(void)
boolean S_MusicExists(const char *mname, boolean checkMIDI, boolean checkDigi) boolean S_MusicExists(const char *mname, boolean checkMIDI, boolean checkDigi)
{ {
return ( return (
(checkDigi ? W_CheckNumForName(va("O_%s", mname)) != LUMPERROR : false) (checkDigi ? W_CheckNumForLongName(va("O_%s", mname)) != LUMPERROR : false)
|| (checkMIDI ? W_CheckNumForName(va("D_%s", mname)) != LUMPERROR : false) || (checkMIDI ? W_CheckNumForLongName(va("D_%s", mname)) != LUMPERROR : false)
); );
} }
...@@ -1826,7 +1825,7 @@ UINT32 S_GetMusicPosition(void) ...@@ -1826,7 +1825,7 @@ UINT32 S_GetMusicPosition(void)
/// In this section: mazmazz doesn't know how to do dynamic arrays or struct pointers! /// In this section: mazmazz doesn't know how to do dynamic arrays or struct pointers!
/// ------------------------ /// ------------------------
char music_stack_nextmusname[7]; char music_stack_nextmusname[MAX_MUSIC_NAME+1];
boolean music_stack_noposition = false; boolean music_stack_noposition = false;
UINT32 music_stack_fadeout = 0; UINT32 music_stack_fadeout = 0;
UINT32 music_stack_fadein = 0; UINT32 music_stack_fadein = 0;
...@@ -1910,7 +1909,7 @@ static void S_AddMusicStackEntry(const char *mname, UINT16 mflags, boolean loopi ...@@ -1910,7 +1909,7 @@ static void S_AddMusicStackEntry(const char *mname, UINT16 mflags, boolean loopi
if (!music_stacks) if (!music_stacks)
{ {
music_stacks = Z_Calloc(sizeof (*mst), PU_MUSIC, NULL); music_stacks = Z_Calloc(sizeof (*mst), PU_MUSIC, NULL);
strncpy(music_stacks->musname, (status == JT_MASTER ? mname : (S_CheckQueue() ? queue_name : mapmusname)), sizeof(music_stacks->musname)-1); strlcpy(music_stacks->musname, (status == JT_MASTER ? mname : (S_CheckQueue() ? queue_name : mapmusname)), sizeof(music_stacks->musname));
music_stacks->musflags = (status == JT_MASTER ? mflags : (S_CheckQueue() ? queue_flags : mapmusflags)); music_stacks->musflags = (status == JT_MASTER ? mflags : (S_CheckQueue() ? queue_flags : mapmusflags));
music_stacks->looping = (status == JT_MASTER ? looping : (S_CheckQueue() ? queue_looping : true)); music_stacks->looping = (status == JT_MASTER ? looping : (S_CheckQueue() ? queue_looping : true));
music_stacks->position = (status == JT_MASTER ? position : (S_CheckQueue() ? queue_position : S_GetMusicPosition())); music_stacks->position = (status == JT_MASTER ? position : (S_CheckQueue() ? queue_position : S_GetMusicPosition()));
...@@ -1928,8 +1927,7 @@ static void S_AddMusicStackEntry(const char *mname, UINT16 mflags, boolean loopi ...@@ -1928,8 +1927,7 @@ static void S_AddMusicStackEntry(const char *mname, UINT16 mflags, boolean loopi
// create our new entry // create our new entry
new_mst = Z_Calloc(sizeof (*new_mst), PU_MUSIC, NULL); new_mst = Z_Calloc(sizeof (*new_mst), PU_MUSIC, NULL);
strncpy(new_mst->musname, mname, 7); strlcpy(new_mst->musname, mname, sizeof(new_mst->musname));
new_mst->musname[6] = 0;
new_mst->musflags = mflags; new_mst->musflags = mflags;
new_mst->looping = looping; new_mst->looping = looping;
new_mst->position = position; new_mst->position = position;
...@@ -2033,13 +2031,13 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst) ...@@ -2033,13 +2031,13 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst)
if (result) if (result)
{ {
*entry = *result; *entry = *result;
memcpy(entry->musname, result->musname, sizeof(entry->musname)); strlcpy(entry->musname, result->musname, sizeof(entry->musname));
} }
// no result, just grab mapmusname // no result, just grab mapmusname
if (!result || !entry->musname[0] || ((status == JT_MASTER || (music_stacks ? !music_stacks->status : false)) && !entry->status)) if (!result || !entry->musname[0] || ((status == JT_MASTER || (music_stacks ? !music_stacks->status : false)) && !entry->status))
{ {
strncpy(entry->musname, mapmusname, 7); strlcpy(entry->musname, mapmusname, MAX_MUSIC_NAME+1);
entry->musflags = mapmusflags; entry->musflags = mapmusflags;
entry->looping = true; entry->looping = true;
entry->position = mapmusposition; entry->position = mapmusposition;
...@@ -2051,10 +2049,10 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst) ...@@ -2051,10 +2049,10 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst)
if (entry->status == JT_MASTER) if (entry->status == JT_MASTER)
{ {
mapmuschanged = strnicmp(entry->musname, mapmusname, 7); mapmuschanged = strnicmp(entry->musname, mapmusname, MAX_MUSIC_NAME);
if (mapmuschanged) if (mapmuschanged)
{ {
strncpy(entry->musname, mapmusname, 7); strlcpy(entry->musname, mapmusname, MAX_MUSIC_NAME+1);
entry->musflags = mapmusflags; entry->musflags = mapmusflags;
entry->looping = true; entry->looping = true;
entry->position = mapmusposition; entry->position = mapmusposition;
...@@ -2071,7 +2069,7 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst) ...@@ -2071,7 +2069,7 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst)
return false; return false;
} }
if (strncmp(entry->musname, S_MusicName(), 7) || // don't restart music if we're already playing it if (strncmp(entry->musname, S_MusicName(), MAX_MUSIC_NAME) || // don't restart music if we're already playing it
(midipref != currentmidi && S_PrefAvailable(midipref, entry->musname))) // but do if the user's preference has changed (midipref != currentmidi && S_PrefAvailable(midipref, entry->musname))) // but do if the user's preference has changed
{ {
if (music_stack_fadeout) if (music_stack_fadeout)
...@@ -2122,9 +2120,9 @@ static lumpnum_t S_GetMusicLumpNum(const char *mname) ...@@ -2122,9 +2120,9 @@ static lumpnum_t S_GetMusicLumpNum(const char *mname)
boolean midipref = cv_musicpref.value; boolean midipref = cv_musicpref.value;
if (S_PrefAvailable(midipref, mname)) if (S_PrefAvailable(midipref, mname))
return W_GetNumForName(va(midipref ? "d_%s":"o_%s", mname)); return W_GetNumForLongName(va(midipref ? "D_%s":"O_%s", mname));
else if (S_PrefAvailable(!midipref, mname)) else if (S_PrefAvailable(!midipref, mname))
return W_GetNumForName(va(midipref ? "o_%s":"d_%s", mname)); return W_GetNumForLongName(va(midipref ? "O_%s":"D_%s", mname));
else else
return LUMPERROR; return LUMPERROR;
} }
...@@ -2141,18 +2139,16 @@ static boolean S_LoadMusic(const char *mname) ...@@ -2141,18 +2139,16 @@ static boolean S_LoadMusic(const char *mname)
if (mlumpnum == LUMPERROR) if (mlumpnum == LUMPERROR)
{ {
CONS_Alert(CONS_ERROR, "Music %.6s could not be loaded: lump not found!\n", mname); CONS_Alert(CONS_ERROR, "Music %s could not be loaded: lump not found!\n", mname);
return false; return false;
} }
// load & register it // load & register it
mdata = W_CacheLumpNum(mlumpnum, PU_MUSIC); mdata = W_CacheLumpNum(mlumpnum, PU_MUSIC);
if (I_LoadSong(mdata, W_LumpLength(mlumpnum))) if (I_LoadSong(mdata, W_LumpLength(mlumpnum)))
{ {
strncpy(music_name, mname, 7); strlcpy(music_name, mname, MAX_MUSIC_NAME+1);
music_name[6] = 0;
music_data = mdata; music_data = mdata;
return true; return true;
} }
...@@ -2213,7 +2209,7 @@ static boolean S_PlayMusic(boolean looping, UINT32 fadeinms) ...@@ -2213,7 +2209,7 @@ static boolean S_PlayMusic(boolean looping, UINT32 fadeinms)
static void S_QueueMusic(const char *mmusic, UINT16 mflags, boolean looping, UINT32 position, UINT32 fadeinms) static void S_QueueMusic(const char *mmusic, UINT16 mflags, boolean looping, UINT32 position, UINT32 fadeinms)
{ {
strncpy(queue_name, mmusic, 7); strlcpy(queue_name, mmusic, MAX_MUSIC_NAME+1);
queue_flags = mflags; queue_flags = mflags;
queue_looping = looping; queue_looping = looping;
queue_position = position; queue_position = position;
...@@ -2238,7 +2234,7 @@ static void S_ChangeMusicToQueue(void) ...@@ -2238,7 +2234,7 @@ static void S_ChangeMusicToQueue(void)
void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 position, UINT32 prefadems, UINT32 fadeinms) void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 position, UINT32 prefadems, UINT32 fadeinms)
{ {
char newmusic[7]; char newmusic[MAX_MUSIC_NAME+1];
struct MusicChange hook_param = { struct MusicChange hook_param = {
newmusic, newmusic,
...@@ -2255,8 +2251,7 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 ...@@ -2255,8 +2251,7 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32
if (S_MusicDisabled()) if (S_MusicDisabled())
return; return;
strncpy(newmusic, mmusic, sizeof(newmusic)-1); strlcpy(newmusic, mmusic, sizeof(newmusic));
newmusic[6] = 0;
if (LUA_HookMusicChange(music_name, &hook_param)) if (LUA_HookMusicChange(music_name, &hook_param))
return; return;
...@@ -2278,7 +2273,7 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 ...@@ -2278,7 +2273,7 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32
I_FadeSong(0, prefadems, S_ChangeMusicToQueue); I_FadeSong(0, prefadems, S_ChangeMusicToQueue);
return; return;
} }
else if (strnicmp(music_name, newmusic, 6) || (mflags & MUSIC_FORCERESET) || else if (strnicmp(music_name, newmusic, MAX_MUSIC_NAME) || (mflags & MUSIC_FORCERESET) ||
(midipref != currentmidi && S_PrefAvailable(midipref, newmusic))) (midipref != currentmidi && S_PrefAvailable(midipref, newmusic)))
{ {
CONS_Debug(DBG_DETAILED, "Now playing song %s\n", newmusic); CONS_Debug(DBG_DETAILED, "Now playing song %s\n", newmusic);
...@@ -2303,7 +2298,7 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 ...@@ -2303,7 +2298,7 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32
{ {
I_SetSongPosition(position); I_SetSongPosition(position);
I_FadeSong(100, fadeinms, NULL); I_FadeSong(100, fadeinms, NULL);
} }
else // reset volume to 100 with same music else // reset volume to 100 with same music
{ {
I_StopFadingSong(); I_StopFadingSong();
...@@ -2433,8 +2428,7 @@ void S_StartEx(boolean reset) ...@@ -2433,8 +2428,7 @@ void S_StartEx(boolean reset)
{ {
if (mapmusflags & MUSIC_RELOADRESET) if (mapmusflags & MUSIC_RELOADRESET)
{ {
strncpy(mapmusname, mapheaderinfo[gamemap-1]->musname, 7); strlcpy(mapmusname, mapheaderinfo[gamemap-1]->musname, MAX_MUSIC_NAME+1);
mapmusname[6] = 0;
mapmusflags = (mapheaderinfo[gamemap-1]->mustrack & MUSIC_TRACKMASK); mapmusflags = (mapheaderinfo[gamemap-1]->mustrack & MUSIC_TRACKMASK);
mapmusposition = mapheaderinfo[gamemap-1]->muspos; mapmusposition = mapheaderinfo[gamemap-1]->muspos;
} }
...@@ -2487,14 +2481,13 @@ static void Command_Tunes_f(void) ...@@ -2487,14 +2481,13 @@ static void Command_Tunes_f(void)
track = mapheaderinfo[gamemap-1]->mustrack; track = mapheaderinfo[gamemap-1]->mustrack;
} }
if (strlen(tunearg) > 6) // This is automatic -- just show the error just in case if (strlen(tunearg) > MAX_MUSIC_NAME) // This is automatic -- just show the error just in case
CONS_Alert(CONS_NOTICE, M_GetText("Music name too long - truncated to six characters.\n")); CONS_Alert(CONS_NOTICE, M_GetText("Music name too long - truncated to %d characters.\n"), MAX_MUSIC_NAME);
if (argc > 2) if (argc > 2)
track = (UINT16)atoi(COM_Argv(2))-1; track = (UINT16)atoi(COM_Argv(2))-1;
strncpy(mapmusname, tunearg, 7); strlcpy(mapmusname, tunearg, sizeof(mapmusname));
mapmusname[6] = 0;
if (argc > 4) if (argc > 4)
position = (UINT32)atoi(COM_Argv(4)); position = (UINT32)atoi(COM_Argv(4));
......
...@@ -182,7 +182,7 @@ boolean S_SpeedMusic(float speed); ...@@ -182,7 +182,7 @@ boolean S_SpeedMusic(float speed);
// Music definitions // Music definitions
typedef struct musicdef_s typedef struct musicdef_s
{ {
char name[7]; char name[MAX_MUSIC_NAME+1];
char title[32]; char title[32];
char alttitle[64]; char alttitle[64];
char authors[256]; char authors[256];
...@@ -238,7 +238,7 @@ UINT32 S_GetMusicPosition(void); ...@@ -238,7 +238,7 @@ UINT32 S_GetMusicPosition(void);
typedef struct musicstack_s typedef struct musicstack_s
{ {
char musname[7+1]; char musname[MAX_MUSIC_NAME+1];
UINT16 musflags; UINT16 musflags;
boolean looping; boolean looping;
UINT32 position; UINT32 position;
...@@ -251,7 +251,7 @@ typedef struct musicstack_s ...@@ -251,7 +251,7 @@ typedef struct musicstack_s
struct musicstack_s *next; struct musicstack_s *next;
} musicstack_t; } musicstack_t;
extern char music_stack_nextmusname[7]; extern char music_stack_nextmusname[MAX_MUSIC_NAME+1];
extern boolean music_stack_noposition; extern boolean music_stack_noposition;
extern UINT32 music_stack_fadeout; extern UINT32 music_stack_fadeout;
extern UINT32 music_stack_fadein; extern UINT32 music_stack_fadein;
......
...@@ -65,9 +65,6 @@ ...@@ -65,9 +65,6 @@
#include "i_video.h" // rendermode #include "i_video.h" // rendermode
#include "md5.h" #include "md5.h"
#include "lua_script.h" #include "lua_script.h"
#ifdef SCANTHINGS
#include "p_setup.h" // P_ScanThings
#endif
#include "m_misc.h" // M_MapNumber #include "m_misc.h" // M_MapNumber
#include "g_game.h" // G_SetGameModified #include "g_game.h" // G_SetGameModified
...@@ -280,22 +277,6 @@ static void W_LoadDehackedLumps(UINT16 wadnum, boolean mainfile) ...@@ -280,22 +277,6 @@ static void W_LoadDehackedLumps(UINT16 wadnum, boolean mainfile)
DEH_LoadDehackedLumpPwad(wadnum, lump, mainfile); DEH_LoadDehackedLumpPwad(wadnum, lump, mainfile);
} }
} }
#ifdef SCANTHINGS
// Scan maps for emblems 'n shit
{
lumpinfo_t *lump_p = wadfiles[wadnum]->lumpinfo;
for (lump = 0; lump < wadfiles[wadnum]->numlumps; lump++, lump_p++)
{
const char *name = lump_p->name;
if (name[0] == 'M' && name[1] == 'A' && name[2] == 'P' && name[5]=='\0')
{
INT16 mapnum = (INT16)M_MapNumber(name[3], name[4]);
P_ScanThings(mapnum, wadnum, lump + ML_THINGS);
}
}
}
#endif
} }
/** Compute MD5 message digest for bytes read from STREAM of this filname. /** Compute MD5 message digest for bytes read from STREAM of this filname.
...@@ -339,6 +320,11 @@ static void W_InvalidateLumpnumCache(void) ...@@ -339,6 +320,11 @@ static void W_InvalidateLumpnumCache(void)
memset(lumpnumcache, 0, sizeof (lumpnumcache)); memset(lumpnumcache, 0, sizeof (lumpnumcache));
} }
UINT32 W_HashLumpName(const char *name)
{
return FNV1a_HashLowercaseString(name);
}
/** Detect a file type. /** Detect a file type.
* \todo Actually detect the wad/pkzip headers and whatnot, instead of just checking the extensions. * \todo Actually detect the wad/pkzip headers and whatnot, instead of just checking the extensions.
*/ */
...@@ -363,18 +349,23 @@ static lumpinfo_t* ResGetLumpsStandalone (FILE* handle, UINT16* numlumps, const ...@@ -363,18 +349,23 @@ static lumpinfo_t* ResGetLumpsStandalone (FILE* handle, UINT16* numlumps, const
fseek(handle, 0, SEEK_END); fseek(handle, 0, SEEK_END);
lumpinfo->size = ftell(handle); lumpinfo->size = ftell(handle);
fseek(handle, 0, SEEK_SET); fseek(handle, 0, SEEK_SET);
strcpy(lumpinfo->name, lumpname); strlcpy(lumpinfo->name, lumpname, sizeof(lumpinfo->name));
lumpinfo->hash = quickncasehash(lumpname, 8); lumpinfo->namelength = strlen(lumpinfo->name);
lumpinfo->hash.name = W_HashLumpName(lumpname);
// Allocate the lump's long name. // Allocate the lump's long name.
lumpinfo->longname = Z_Malloc(9 * sizeof(char), PU_STATIC, NULL); lumpinfo->longname = Z_Malloc((lumpinfo->namelength + 1) * sizeof(char), PU_STATIC, NULL);
strcpy(lumpinfo->longname, lumpname); strcpy(lumpinfo->longname, lumpname);
lumpinfo->longname[8] = '\0'; lumpinfo->longname[lumpinfo->namelength] = '\0';
lumpinfo->longnamelength = lumpinfo->namelength;
lumpinfo->hash.longname = lumpinfo->hash.name;
// Allocate the lump's full name. // Allocate the lump's full name.
lumpinfo->fullname = Z_Malloc(9 * sizeof(char), PU_STATIC, NULL); lumpinfo->fullname = Z_Malloc((lumpinfo->namelength + 1) * sizeof(char), PU_STATIC, NULL);
strcpy(lumpinfo->fullname, lumpname); strcpy(lumpinfo->fullname, lumpname);
lumpinfo->fullname[8] = '\0'; lumpinfo->fullname[lumpinfo->namelength] = '\0';
lumpinfo->fullnamelength = lumpinfo->namelength;
lumpinfo->hash.fullname = lumpinfo->hash.name;
*numlumps = 1; *numlumps = 1;
return lumpinfo; return lumpinfo;
...@@ -463,17 +454,22 @@ static lumpinfo_t* ResGetLumpsWad (FILE* handle, UINT16* nlmp, const char* filen ...@@ -463,17 +454,22 @@ static lumpinfo_t* ResGetLumpsWad (FILE* handle, UINT16* nlmp, const char* filen
lump_p->compression = CM_NOCOMPRESSION; lump_p->compression = CM_NOCOMPRESSION;
memset(lump_p->name, 0x00, 9); memset(lump_p->name, 0x00, 9);
strncpy(lump_p->name, fileinfo->name, 8); strncpy(lump_p->name, fileinfo->name, 8);
lump_p->hash = quickncasehash(lump_p->name, 8); lump_p->namelength = strlen(lump_p->name);
lump_p->hash.name = W_HashLumpName(lump_p->name);
// Allocate the lump's long name. // Allocate the lump's long name.
lump_p->longname = Z_Malloc(9 * sizeof(char), PU_STATIC, NULL); lump_p->longname = Z_Malloc(9 * sizeof(char), PU_STATIC, NULL);
strncpy(lump_p->longname, fileinfo->name, 8); strncpy(lump_p->longname, fileinfo->name, 8);
lump_p->longname[8] = '\0'; lump_p->longname[8] = '\0';
lump_p->longnamelength = lump_p->namelength;
lump_p->hash.longname = lump_p->hash.name;
// Allocate the lump's full name. // Allocate the lump's full name.
lump_p->fullname = Z_Malloc(9 * sizeof(char), PU_STATIC, NULL); lump_p->fullname = Z_Malloc(9 * sizeof(char), PU_STATIC, NULL);
strncpy(lump_p->fullname, fileinfo->name, 8); strncpy(lump_p->fullname, fileinfo->name, 8);
lump_p->fullname[8] = '\0'; lump_p->fullname[8] = '\0';
lump_p->fullnamelength = lump_p->namelength;
lump_p->hash.fullname = lump_p->hash.name;
} }
free(fileinfov); free(fileinfov);
*nlmp = numlumps; *nlmp = numlumps;
...@@ -639,13 +635,18 @@ static lumpinfo_t* ResGetLumpsZip (FILE* handle, UINT16* nlmp) ...@@ -639,13 +635,18 @@ static lumpinfo_t* ResGetLumpsZip (FILE* handle, UINT16* nlmp)
memset(lump_p->name, '\0', 9); // Making sure they're initialized to 0. Is it necessary? memset(lump_p->name, '\0', 9); // Making sure they're initialized to 0. Is it necessary?
strncpy(lump_p->name, trimname, min(8, dotpos - trimname)); strncpy(lump_p->name, trimname, min(8, dotpos - trimname));
lump_p->hash = quickncasehash(lump_p->name, 8); lump_p->namelength = strlen(lump_p->name);
lump_p->hash.name = W_HashLumpName(lump_p->name);
lump_p->longname = Z_Calloc(dotpos - trimname + 1, PU_STATIC, NULL); lump_p->longname = Z_Calloc(dotpos - trimname + 1, PU_STATIC, NULL);
strlcpy(lump_p->longname, trimname, dotpos - trimname + 1); strlcpy(lump_p->longname, trimname, dotpos - trimname + 1);
lump_p->longnamelength = strlen(lump_p->longname);
lump_p->hash.longname = W_HashLumpName(lump_p->longname);
lump_p->fullname = Z_Calloc(zentry.namelen + 1, PU_STATIC, NULL); lump_p->fullname = Z_Calloc(zentry.namelen + 1, PU_STATIC, NULL);
strncpy(lump_p->fullname, fullname, zentry.namelen); strncpy(lump_p->fullname, fullname, zentry.namelen);
lump_p->fullnamelength = zentry.namelen;
lump_p->hash.fullname = W_HashLumpName(lump_p->fullname);
switch(zentry.compression) switch(zentry.compression)
{ {
...@@ -988,6 +989,9 @@ UINT16 W_InitFile(const char *filename, boolean mainfile, boolean startup) ...@@ -988,6 +989,9 @@ UINT16 W_InitFile(const char *filename, boolean mainfile, boolean startup)
// Read shaders from file // Read shaders from file
W_ReadFileShaders(wadfile); W_ReadFileShaders(wadfile);
// Load maps from file
P_LoadMapsFromFile(numwadfiles - 1, !startup);
// The below hack makes me load this here. // The below hack makes me load this here.
W_LoadTrnslateLumps(numwadfiles - 1); W_LoadTrnslateLumps(numwadfiles - 1);
...@@ -1169,6 +1173,7 @@ UINT16 W_InitFolder(const char *path, boolean mainfile, boolean startup) ...@@ -1169,6 +1173,7 @@ UINT16 W_InitFolder(const char *path, boolean mainfile, boolean startup)
numwadfiles++; numwadfiles++;
W_ReadFileShaders(wadfile); W_ReadFileShaders(wadfile);
P_LoadMapsFromFile(numwadfiles - 1, !startup);
W_LoadTrnslateLumps(numwadfiles - 1); W_LoadTrnslateLumps(numwadfiles - 1);
W_LoadDehackedLumpsPK3(numwadfiles - 1, mainfile); W_LoadDehackedLumpsPK3(numwadfiles - 1, mainfile);
W_InvalidateLumpnumCache(); W_InvalidateLumpnumCache();
...@@ -1246,13 +1251,15 @@ UINT16 W_CheckNumForNamePwad(const char *name, UINT16 wad, UINT16 startlump) ...@@ -1246,13 +1251,15 @@ UINT16 W_CheckNumForNamePwad(const char *name, UINT16 wad, UINT16 startlump)
UINT16 i; UINT16 i;
static char uname[8 + 1]; static char uname[8 + 1];
UINT32 hash; UINT32 hash;
size_t namelen;
if (!TestValidLump(wad,0)) if (!TestValidLump(wad,0))
return INT16_MAX; return INT16_MAX;
strlcpy(uname, name, sizeof uname); strlcpy(uname, name, sizeof uname);
strupr(uname); strupr(uname);
hash = quickncasehash(uname, 8); namelen = strlen(uname);
hash = W_HashLumpName(uname);
// //
// scan forward // scan forward
...@@ -1263,7 +1270,9 @@ UINT16 W_CheckNumForNamePwad(const char *name, UINT16 wad, UINT16 startlump) ...@@ -1263,7 +1270,9 @@ UINT16 W_CheckNumForNamePwad(const char *name, UINT16 wad, UINT16 startlump)
{ {
lumpinfo_t *lump_p = wadfiles[wad]->lumpinfo + startlump; lumpinfo_t *lump_p = wadfiles[wad]->lumpinfo + startlump;
for (i = startlump; i < wadfiles[wad]->numlumps; i++, lump_p++) for (i = startlump; i < wadfiles[wad]->numlumps; i++, lump_p++)
if (lump_p->hash == hash && !strncmp(lump_p->name, uname, sizeof(uname) - 1)) if (lump_p->namelength == namelen
&& lump_p->hash.name == hash
&& !strncmp(lump_p->name, uname, sizeof(uname) - 1))
return i; return i;
} }
...@@ -1280,13 +1289,12 @@ UINT16 W_CheckNumForNamePwad(const char *name, UINT16 wad, UINT16 startlump) ...@@ -1280,13 +1289,12 @@ UINT16 W_CheckNumForNamePwad(const char *name, UINT16 wad, UINT16 startlump)
UINT16 W_CheckNumForLongNamePwad(const char *name, UINT16 wad, UINT16 startlump) UINT16 W_CheckNumForLongNamePwad(const char *name, UINT16 wad, UINT16 startlump)
{ {
UINT16 i; UINT16 i;
static char uname[256 + 1];
if (!TestValidLump(wad,0)) if (!TestValidLump(wad,0))
return INT16_MAX; return INT16_MAX;
strlcpy(uname, name, sizeof uname); size_t namelen = strlen(name);
strupr(uname); UINT32 hash = W_HashLumpName(name);
// //
// scan forward // scan forward
...@@ -1297,7 +1305,9 @@ UINT16 W_CheckNumForLongNamePwad(const char *name, UINT16 wad, UINT16 startlump) ...@@ -1297,7 +1305,9 @@ UINT16 W_CheckNumForLongNamePwad(const char *name, UINT16 wad, UINT16 startlump)
{ {
lumpinfo_t *lump_p = wadfiles[wad]->lumpinfo + startlump; lumpinfo_t *lump_p = wadfiles[wad]->lumpinfo + startlump;
for (i = startlump; i < wadfiles[wad]->numlumps; i++, lump_p++) for (i = startlump; i < wadfiles[wad]->numlumps; i++, lump_p++)
if (!strcmp(lump_p->longname, uname)) if (lump_p->longnamelength == namelen
&& lump_p->hash.name == hash
&& !stricmp(lump_p->longname, name))
return i; return i;
} }
...@@ -1350,6 +1360,14 @@ UINT16 W_CheckNumForFolderEndPK3(const char *name, UINT16 wad, UINT16 startlump) ...@@ -1350,6 +1360,14 @@ UINT16 W_CheckNumForFolderEndPK3(const char *name, UINT16 wad, UINT16 startlump)
return i; return i;
} }
const char *W_GetFilenameFromFullname(const char *path)
{
const char *slash = strrchr(path, '/');
if (slash)
return slash + 1;
return path;
}
char *W_GetLumpFolderPathPK3(UINT16 wad, UINT16 lump) char *W_GetLumpFolderPathPK3(UINT16 wad, UINT16 lump)
{ {
const char *fullname = wadfiles[wad]->lumpinfo[lump].fullname; const char *fullname = wadfiles[wad]->lumpinfo[lump].fullname;
...@@ -1609,49 +1627,6 @@ lumpnum_t W_CheckNumForLongName(const char *name) ...@@ -1609,49 +1627,6 @@ lumpnum_t W_CheckNumForLongName(const char *name)
} }
} }
// Look for valid map data through all added files in descendant order.
// Get a map marker for WADs, and a standalone WAD file lump inside PK3s.
// TODO: Make it search through cache first, maybe...?
lumpnum_t W_CheckNumForMap(const char *name)
{
UINT32 hash = quickncasehash(name, 8);
UINT16 lumpNum, end;
UINT32 i;
lumpinfo_t *p;
for (i = numwadfiles - 1; i < numwadfiles; i--)
{
if (wadfiles[i]->type == RET_WAD)
{
for (lumpNum = 0; lumpNum < wadfiles[i]->numlumps; lumpNum++)
{
p = wadfiles[i]->lumpinfo + lumpNum;
if (p->hash == hash && !strncmp(name, p->name, 8))
return (i<<16) + lumpNum;
}
}
else if (W_FileHasFolders(wadfiles[i]))
{
lumpNum = W_CheckNumForFolderStartPK3("maps/", i, 0);
if (lumpNum != INT16_MAX)
end = W_CheckNumForFolderEndPK3("maps/", i, lumpNum);
else
continue;
// Now look for the specified map.
for (; lumpNum < end; lumpNum++)
{
p = wadfiles[i]->lumpinfo + lumpNum;
if (p->hash == hash && !strnicmp(name, p->name, 8))
{
const char *extension = strrchr(p->fullname, '.');
if (!(extension && stricmp(extension, ".wad")))
return (i<<16) + lumpNum;
}
}
}
}
return LUMPERROR;
}
// //
// W_GetNumForName // W_GetNumForName
// //
...@@ -1700,11 +1675,13 @@ static UINT16 W_CheckNumForPatchNamePwad(const char *name, UINT16 wad, boolean l ...@@ -1700,11 +1675,13 @@ static UINT16 W_CheckNumForPatchNamePwad(const char *name, UINT16 wad, boolean l
if (!TestValidLump(wad,0)) if (!TestValidLump(wad,0))
return INT16_MAX; return INT16_MAX;
if (!longname) if (longname)
hash = W_HashLumpName(name);
else
{ {
strlcpy(uname, name, sizeof uname); strlcpy(uname, name, sizeof uname);
strupr(uname); strupr(uname);
hash = quickncasehash(uname, 8); hash = W_HashLumpName(uname);
} }
// SRB2 doesn't have a specific namespace for graphics, which means someone can do weird things // SRB2 doesn't have a specific namespace for graphics, which means someone can do weird things
...@@ -1730,23 +1707,45 @@ static UINT16 W_CheckNumForPatchNamePwad(const char *name, UINT16 wad, boolean l ...@@ -1730,23 +1707,45 @@ static UINT16 W_CheckNumForPatchNamePwad(const char *name, UINT16 wad, boolean l
if (start == INT16_MAX) if (start == INT16_MAX)
start = wadfiles[wad]->numlumps; start = wadfiles[wad]->numlumps;
for (i = 0; i < start; i++, lump_p++) if (longname)
{ {
if ((!longname && lump_p->hash == hash && !strncmp(lump_p->name, uname, sizeof(uname) - 1)) size_t namelen = strlen(name);
|| (longname && stricmp(lump_p->longname, name) == 0))
return i;
}
if (end != INT16_MAX && start < end) for (i = 0; i < start; i++, lump_p++)
{ {
lump_p = wadfiles[wad]->lumpinfo + end; if (lump_p->longnamelength == namelen && lump_p->hash.longname == hash && stricmp(lump_p->longname, name) == 0)
return i;
}
for (i = end; i < wadfiles[wad]->numlumps; i++, lump_p++) if (end != INT16_MAX && start < end)
{ {
if ((!longname && lump_p->hash == hash && !strncmp(lump_p->name, uname, sizeof(uname) - 1)) lump_p = wadfiles[wad]->lumpinfo + end;
|| (longname && stricmp(lump_p->longname, name) == 0))
for (i = end; i < wadfiles[wad]->numlumps; i++, lump_p++)
{
if (lump_p->longnamelength == namelen && lump_p->hash.longname == hash && stricmp(lump_p->longname, name) == 0)
return i;
}
}
}
else
{
for (i = 0; i < start; i++, lump_p++)
{
if (lump_p->hash.name == hash && strncmp(lump_p->name, uname, sizeof(uname) - 1) == 0)
return i; return i;
} }
if (end != INT16_MAX && start < end)
{
lump_p = wadfiles[wad]->lumpinfo + end;
for (i = end; i < wadfiles[wad]->numlumps; i++, lump_p++)
{
if (lump_p->hash.name == hash && strncmp(lump_p->name, uname, sizeof(uname) - 1) == 0)
return i;
}
}
} }
// not found. // not found.
......
...@@ -66,13 +66,25 @@ typedef struct ...@@ -66,13 +66,25 @@ typedef struct
{ {
unsigned long position; // filelump_t filepos unsigned long position; // filelump_t filepos
unsigned long disksize; // filelump_t size unsigned long disksize; // filelump_t size
char name[9]; // filelump_t name[] e.g. "LongEntr" char name[9]; // filelump_t name[] e.g. "LongEntr"
UINT32 hash;
char *longname; // e.g. "LongEntryName" char *longname; // e.g. "LongEntryName"
char *fullname; // e.g. "Folder/Subfolder/LongEntryName.extension" char *fullname; // e.g. "Folder/Subfolder/LongEntryName.extension"
char *diskpath; // path to the file e.g. "/usr/games/srb2/Addon/Folder/Subfolder/LongEntryName.extension" char *diskpath; // path to the file e.g. "/usr/games/srb2/Addon/Folder/Subfolder/LongEntryName.extension"
// NOTE: This is NULL if the WAD type != RET_FOLDER
size_t namelength; // length of name
size_t longnamelength; // length of longname
size_t fullnamelength; // length of fullname
size_t size; // real (uncompressed) size size_t size; // real (uncompressed) size
compmethod compression; // lump compression method compmethod compression; // lump compression method
struct {
UINT32 name; // hash of name
UINT32 longname; // hash of longname
UINT32 fullname; // hash of fullname
} hash;
} lumpinfo_t; } lumpinfo_t;
// ========================================================================= // =========================================================================
...@@ -168,6 +180,8 @@ void W_InitMultipleFiles(addfilelist_t *list); ...@@ -168,6 +180,8 @@ void W_InitMultipleFiles(addfilelist_t *list);
INT32 W_IsPathToFolderValid(const char *path); INT32 W_IsPathToFolderValid(const char *path);
char *W_GetFullFolderPath(const char *path); char *W_GetFullFolderPath(const char *path);
UINT32 W_HashLumpName(const char *name);
const char *W_CheckNameForNumPwad(UINT16 wad, UINT16 lump); const char *W_CheckNameForNumPwad(UINT16 wad, UINT16 lump);
const char *W_CheckNameForNum(lumpnum_t lumpnum); const char *W_CheckNameForNum(lumpnum_t lumpnum);
...@@ -183,12 +197,13 @@ UINT16 W_CheckNumForFolderEndPK3(const char *name, UINT16 wad, UINT16 startlump) ...@@ -183,12 +197,13 @@ UINT16 W_CheckNumForFolderEndPK3(const char *name, UINT16 wad, UINT16 startlump)
char *W_GetLumpFolderPathPK3(UINT16 wad, UINT16 lump); char *W_GetLumpFolderPathPK3(UINT16 wad, UINT16 lump);
char *W_GetLumpFolderNamePK3(UINT16 wad, UINT16 lump); char *W_GetLumpFolderNamePK3(UINT16 wad, UINT16 lump);
const char *W_GetFilenameFromFullname(const char *path);
void W_GetFolderLumpsPwad(const char *name, UINT16 wad, UINT32 **list, UINT16 *list_capacity, UINT16 *numlumps); void W_GetFolderLumpsPwad(const char *name, UINT16 wad, UINT32 **list, UINT16 *list_capacity, UINT16 *numlumps);
void W_GetFolderLumps(const char *name, UINT32 **list, UINT16 *list_capacity, UINT16 *numlumps); void W_GetFolderLumps(const char *name, UINT32 **list, UINT16 *list_capacity, UINT16 *numlumps);
UINT32 W_CountFolderLumpsPwad(const char *name, UINT16 wad); UINT32 W_CountFolderLumpsPwad(const char *name, UINT16 wad);
UINT32 W_CountFolderLumps(const char *name); UINT32 W_CountFolderLumps(const char *name);
lumpnum_t W_CheckNumForMap(const char *name);
lumpnum_t W_CheckNumForName(const char *name); lumpnum_t W_CheckNumForName(const char *name);
lumpnum_t W_CheckNumForLongName(const char *name); lumpnum_t W_CheckNumForLongName(const char *name);
lumpnum_t W_GetNumForName(const char *name); // like W_CheckNumForName but I_Error on LUMPERROR lumpnum_t W_GetNumForName(const char *name); // like W_CheckNumForName but I_Error on LUMPERROR
......