load IWAD from zip, cosmetic changes (#1703)

* Add more lump filters.

* Simplify `CheckIWAD` function, load IWAD from zip archive.

* Remove `PrintVersion` function.
This commit is contained in:
Roman Fomin 2024-05-25 21:10:29 +07:00 committed by GitHub
parent 045b3a2797
commit 49113c9d85
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 68 additions and 118 deletions

View File

@ -28,20 +28,20 @@
#include "m_misc.h"
static const iwad_t iwads[] = {
{"doom2.wad", doom2, commercial, "Doom II" },
{"plutonia.wad", pack_plut, commercial, "Final Doom: Plutonia Experiment"},
{"tnt.wad", pack_tnt, commercial, "Final Doom: TNT: Evilution" },
{"doom2.wad", doom2, commercial, "DOOM II: Hell on Earth" },
{"plutonia.wad", pack_plut, commercial, "Final DOOM: Plutonia Experiment"},
{"tnt.wad", pack_tnt, commercial, "Final DOOM: TNT - Evilution" },
// "doom.wad" may be retail or registered
{"doom.wad", doom, indetermined, "Doom" },
{"doom.wad", doom, registered, "Doom Registered" },
{"doom.wad", doom, retail, "Ultimate Doom" },
{"doom1.wad", doom, shareware, "Doom Shareware" },
{"doom2f.wad", doom2, commercial, "Doom II: L'Enfer sur Terre" },
{"doom.wad", doom, indetermined, "DOOM" },
{"doom.wad", doom, registered, "DOOM Registered" },
{"doom.wad", doom, retail, "The Ultimate DOOM" },
{"doom1.wad", doom, shareware, "DOOM Shareware" },
{"doom2f.wad", doom2, commercial, "DOOM II: L'Enfer sur Terre" },
{"freedoom2.wad", doom2, commercial, "Freedoom: Phase 2" },
{"freedoom1.wad", doom, retail, "Freedoom: Phase 1" },
{"freedm.wad", doom2, commercial, "FreeDM" },
{"chex.wad", pack_chex, retail, "Chex Quest" },
{"hacx.wad", pack_hacx, commercial, "Hacx" },
{"hacx.wad", pack_hacx, commercial, "HACX: Twitch n' Kill" },
{"rekkrsa.wad", pack_rekkr, retail, "REKKR" },
{"rekkrsl.wad", pack_rekkr, retail, "REKKR: Sunken Land" },
};
@ -747,7 +747,7 @@ char *D_FindLMPByName(const char *filename)
// D_FindIWADFile
//
char *D_FindIWADFile(GameMode_t *mode, GameMission_t *mission)
char *D_FindIWADFile(void)
{
char *result;
@ -792,22 +792,6 @@ char *D_FindIWADFile(GameMode_t *mode, GameMission_t *mission)
}
}
if (result)
{
int i;
const char *name = M_BaseName(result);
for (i = 0; i < arrlen(iwads); ++i)
{
if (!strcasecmp(name, iwads[i].name))
{
*mode = iwads[i].mode;
*mission = iwads[i].mission;
break;
}
}
}
return result;
}
@ -869,6 +853,20 @@ GameMission_t D_GetGameMissionByIWADName(const char *name)
return none;
}
void D_GetModeAndMissionByIWADName(const char *name, GameMode_t *mode,
GameMission_t *mission)
{
for (int i = 0; i < arrlen(iwads); ++i)
{
if (!strcasecmp(name, iwads[i].name))
{
*mode = iwads[i].mode;
*mission = iwads[i].mission;
break;
}
}
}
const char *D_GetIWADDescription(const char *name, GameMode_t mode,
GameMission_t mission)
{

View File

@ -33,10 +33,12 @@ char *D_DoomExeDir(void); // killough 2/16/98: path to executable's dir
char *D_FindWADByName(const char *filename);
char *D_TryFindWADByName(const char *filename);
char *D_FindLMPByName(const char *filename);
char *D_FindIWADFile(GameMode_t *mode, GameMission_t *mission);
char *D_FindIWADFile(void);
boolean D_IsIWADName(const char *name);
const iwad_t **D_GetIwads(void);
GameMission_t D_GetGameMissionByIWADName(const char *name);
void D_GetModeAndMissionByIWADName(const char *name, GameMode_t *mode,
GameMission_t *mission);
const char *D_GetIWADDescription(const char *name, GameMode_t mode,
GameMission_t mission);

View File

@ -793,55 +793,16 @@ static void PrepareAutoloadPaths(void)
// CheckIWAD
//
static void CheckIWAD(const char *iwadname)
static void CheckIWAD(void)
{
int i;
FILE *file;
wadinfo_t header;
filelump_t *fileinfo;
file = M_fopen(iwadname, "rb");
if (file == NULL)
for (int i = 0; i < numlumps; ++i)
{
I_Error("CheckIWAD: failed to read IWAD %s", iwadname);
}
// read IWAD header
if (fread(&header, sizeof(header), 1, file) != 1)
{
fclose(file);
I_Error("CheckIWAD: failed to read header %s", iwadname);
}
if (strncmp(header.identification, "IWAD", 4) &&
strncmp(header.identification, "PWAD", 4))
{
fclose(file);
I_Error("Wad file %s doesn't have IWAD or PWAD id\n", iwadname);
}
// read IWAD directory
header.numlumps = LONG(header.numlumps);
header.infotableofs = LONG(header.infotableofs);
fileinfo = malloc(header.numlumps * sizeof(filelump_t));
if (fseek(file, header.infotableofs, SEEK_SET) ||
fread(fileinfo, sizeof(filelump_t), header.numlumps, file) != header.numlumps)
{
free(fileinfo);
fclose(file);
I_Error("CheckIWAD: failed to read directory %s", iwadname);
}
for (i = 0; i < header.numlumps; ++i)
{
if (!strncasecmp(fileinfo[i].name, "MAP01", 8))
if (!strncasecmp(lumpinfo[i].name, "MAP01", 8))
{
gamemission = doom2;
break;
}
else if (!strncasecmp(fileinfo[i].name, "E1M1", 8))
else if (!strncasecmp(lumpinfo[i].name, "E1M1", 8))
{
gamemode = shareware;
gamemission = doom;
@ -855,23 +816,20 @@ static void CheckIWAD(const char *iwadname)
}
else
{
for (i = 0; i < header.numlumps; ++i)
for (int i = 0; i < numlumps; ++i)
{
if (!strncasecmp(fileinfo[i].name, "E4M1", 8))
if (!strncasecmp(lumpinfo[i].name, "E4M1", 8))
{
gamemode = retail;
break;
}
else if (!strncasecmp(fileinfo[i].name, "E3M1", 8))
else if (!strncasecmp(lumpinfo[i].name, "E3M1", 8))
{
gamemode = registered;
}
}
}
free(fileinfo);
fclose(file);
if (gamemode == indetermined)
{
I_Error("Unknown or invalid IWAD file.");
@ -925,21 +883,6 @@ static boolean FileContainsMaps(const char *filename)
return false;
}
static void PrintVersion(const char *iwad)
{
I_Printf(VB_INFO, "IWAD found: %s", iwad); // jff 4/20/98 print only if
// found
I_Printf(VB_INFO, "%s\n", D_GetIWADDescription(M_BaseName(iwad), gamemode,
gamemission));
if (gamemode == indetermined)
{
I_Printf(VB_WARNING,
"Unknown Game Version, may not work\n"); // killough 8/8/98
}
}
//
// IdentifyVersion
//
@ -1023,24 +966,26 @@ void IdentifyVersion(void)
// locate the IWAD and determine game mode from it
char *iwad = D_FindIWADFile(&gamemode, &gamemission);
char *iwadfile = D_FindIWADFile();
if (iwad)
{
if (gamemode == indetermined)
{
CheckIWAD(iwad);
}
PrintVersion(iwad);
I_Printf(VB_INFO, "W_Init: Init WADfiles.");
D_AddFile(iwad);
}
else
if (!iwadfile)
{
I_Error("IWAD not found");
}
I_Printf(VB_INFO, "W_Init: Init WADfiles.");
D_AddFile(iwadfile);
D_GetModeAndMissionByIWADName(M_BaseName(wadfiles[0]), &gamemode, &gamemission);
if (gamemode == indetermined)
{
CheckIWAD();
}
I_Printf(VB_INFO, " - \"%s\" version",
D_GetIWADDescription(M_BaseName(wadfiles[0]), gamemode, gamemission));
}
// [FG] emulate a specific version of Doom
@ -2320,8 +2265,6 @@ void D_DoomMain(void)
W_ProcessInWads("BRGHTMPS", R_ParseBrightmaps, false);
I_PutChar(VB_INFO, '\n'); // killough 3/6/98: add a newline, by popular demand :)
// Moved after WAD initialization because we are checking the COMPLVL lump
G_ReloadDefaults(false); // killough 3/4/98: set defaults just loaded.
// jff 3/24/98 this sets startskill if it was -1
@ -2406,7 +2349,7 @@ void D_DoomMain(void)
}
}
I_Printf(VB_INFO, "Savegame directory: %s\n", basesavegame);
I_Printf(VB_INFO, "Savegame directory: %s", basesavegame);
V_InitColorTranslation(); //jff 4/24/98 load color translation lumps

View File

@ -113,13 +113,16 @@ static struct
GameMode_t mode;
GameMission_t mission;
} filters[] = {
{"filter/doom", -1, -1 },
{"filter/doom.id", retail, doom },
{"filter/doom.id", commercial, doom2 },
{"filter/doom.id.doom2", commercial, doom2 },
{"filter/doom.id.doom2.commercial", commercial, doom2 },
{"filter/doom.id.doom2.plutonia", commercial, pack_plut},
{"filter/doom.id.doom2.tnt", commercial, pack_tnt },
{"filter/doom", indetermined, none },
{"filter/doom.id", indetermined, doom },
{"filter/doom.id.doom1", indetermined, doom },
{"filter/doom.id.doom1.registered", registered, doom },
{"filter/doom.id.doom1.ultimate", retail, doom },
{"filter/doom.id", indetermined, doom2 },
{"filter/doom.id.doom2", indetermined, doom2 },
{"filter/doom.id.doom2.commercial", commercial, doom2 },
{"filter/doom.id.doom2.plutonia", commercial, pack_plut},
{"filter/doom.id.doom2.tnt", commercial, pack_tnt },
};
w_module_t *modules[] =
@ -164,9 +167,13 @@ boolean W_AddPath(const char *path)
for (int i = 0; i < arrlen(filters); ++i)
{
if ((filters[i].mode >= 0 && filters[i].mode != gamemode)
|| (filters[i].mission >= 0 && gamemission > doom2
&& filters[i].mission != gamemission))
if (filters[i].mode != indetermined && filters[i].mode != gamemode)
{
continue;
}
if (filters[i].mission != none && filters[i].mission != gamemission
&& !(gamemission > doom2 && filters[i].mission == doom2))
{
continue;
}