ref: 37865c5d5b53fd0427b6f22d0a13f830a74c3064
parent: cf7b4fab6313cd2162cb0bd3f28596fbdc2fffd3
author: Simon Howard <[email protected]>
date: Sun Sep 7 17:03:09 EDT 2008
Move dehacked code to doom/. Split dehacked string replacement code into common code and remove dependencies on deh_main.h. Subversion-branch: /branches/raven-branch Subversion-revision: 1210
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -61,19 +61,7 @@
# source files needed for FEATURE_DEHACKED
FEATURE_DEHACKED_SOURCE_FILES= \
-deh_ammo.c \
-deh_cheat.c \
-deh_defs.h \
-deh_frame.c \
-deh_io.c deh_io.h \
-deh_main.c deh_main.h \
-deh_mapping.c deh_mapping.h \
-deh_misc.c deh_misc.h \
-deh_ptr.c \
-deh_sound.c \
-deh_text.c \
-deh_thing.c \
-deh_weapon.c
+deh_str.c deh_str.h
# source files needed for FEATURE_MULTIPLAYER
--- a/src/deh_ammo.c
+++ /dev/null
@@ -1,111 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Ammo" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "doomtype.h"
-#include "deh_defs.h"
-#include "deh_io.h"
-#include "deh_main.h"
-#include "p_local.h"
-
-static void *DEH_AmmoStart(deh_context_t *context, char *line)
-{
- int ammo_number = 0;
-
- if (sscanf(line, "Ammo %i", &ammo_number) != 1)
- {
- DEH_Warning(context, "Parse error on section start");
- return NULL;
- }
-
- if (ammo_number < 0 || ammo_number >= NUMAMMO)
- {
- DEH_Warning(context, "Invalid ammo number: %i", ammo_number);
- return NULL;
- }
-
- return &maxammo[ammo_number];
-}
-
-static void DEH_AmmoParseLine(deh_context_t *context, char *line, void *tag)
-{
- char *variable_name, *value;
- int ivalue;
- int ammo_number;
-
- if (tag == NULL)
- return;
-
- ammo_number = ((int *) tag) - maxammo;
-
- // Parse the assignment
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
-
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
- ivalue = atoi(value);
-
- // maxammo
-
- if (!strcasecmp(variable_name, "Per ammo"))
- clipammo[ammo_number] = ivalue;
- else if (!strcasecmp(variable_name, "Max ammo"))
- maxammo[ammo_number] = ivalue;
- else
- {
- DEH_Warning(context, "Field named '%s' not found", variable_name);
- }
-}
-
-static void DEH_AmmoMD5Hash(md5_context_t *context)
-{
- int i;
-
- for (i=0; i<NUMAMMO; ++i)
- {
- MD5_UpdateInt32(context, clipammo[i]);
- MD5_UpdateInt32(context, maxammo[i]);
- }
-}
-
-deh_section_t deh_section_ammo =
-{
- "Ammo",
- NULL,
- DEH_AmmoStart,
- DEH_AmmoParseLine,
- NULL,
- DEH_AmmoMD5Hash,
-};
-
--- a/src/deh_cheat.c
+++ /dev/null
@@ -1,148 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Cheat" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdlib.h>
-
-#include "doomtype.h"
-
-#include "deh_defs.h"
-#include "deh_io.h"
-#include "deh_main.h"
-#include "am_map.h"
-#include "st_stuff.h"
-
-typedef struct
-{
- char *name;
- cheatseq_t *seq;
-} deh_cheat_t;
-
-static deh_cheat_t allcheats[] =
-{
- {"Change music", &cheat_mus },
- {"Chainsaw", &cheat_choppers },
- {"God mode", &cheat_god },
- {"Ammo & Keys", &cheat_ammo },
- {"Ammo", &cheat_ammonokey },
- {"No Clipping 1", &cheat_noclip },
- {"No Clipping 2", &cheat_commercial_noclip },
- {"Invincibility", &cheat_powerup[0] },
- {"Berserk", &cheat_powerup[1] },
- {"Invisibility", &cheat_powerup[2] },
- {"Radiation Suit", &cheat_powerup[3] },
- {"Auto-map", &cheat_powerup[4] },
- {"Lite-Amp Goggles", &cheat_powerup[5] },
- {"BEHOLD menu", &cheat_powerup[6] },
- {"Level Warp", &cheat_clev },
- {"Player Position", &cheat_mypos },
- {"Map cheat", &cheat_amap },
-};
-
-static deh_cheat_t *FindCheatByName(char *name)
-{
- size_t i;
-
- for (i=0; i<arrlen(allcheats); ++i)
- {
- if (!strcasecmp(allcheats[i].name, name))
- return &allcheats[i];
- }
-
- return NULL;
-}
-
-static void *DEH_CheatStart(deh_context_t *context, char *line)
-{
- return NULL;
-}
-
-static void DEH_CheatParseLine(deh_context_t *context, char *line, void *tag)
-{
- deh_cheat_t *cheat;
- char *variable_name;
- char *value;
- unsigned char *unsvalue;
- unsigned int i;
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
-
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
- unsvalue = (unsigned char *) value;
-
- cheat = FindCheatByName(variable_name);
-
- if (cheat == NULL)
- {
- DEH_Warning(context, "Unknown cheat '%s'", variable_name);
- return;
- }
-
- // write the value into the cheat sequence
-
- i = 0;
-
- while (unsvalue[i] != 0 && unsvalue[i] != 0xff)
- {
- // If the cheat length exceeds the Vanilla limit, stop. This
- // does not apply if we have the limit turned off.
-
- if (!deh_allow_long_cheats && i >= cheat->seq->sequence_len)
- {
- DEH_Warning(context, "Cheat sequence longer than supported by "
- "Vanilla dehacked");
- break;
- }
-
- cheat->seq->sequence[i] = unsvalue[i];
- ++i;
-
- // Absolute limit - don't exceed
-
- if (i >= MAX_CHEAT_LEN - cheat->seq->parameter_chars)
- {
- DEH_Error(context, "Cheat sequence too long!");
- return;
- }
- }
-
- cheat->seq->sequence[i] = '\0';
-}
-
-deh_section_t deh_section_cheat =
-{
- "Cheat",
- NULL,
- DEH_CheatStart,
- DEH_CheatParseLine,
- NULL,
- NULL,
-};
-
--- a/src/deh_defs.h
+++ /dev/null
@@ -1,68 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Definitions for use in the dehacked code
-//
-//-----------------------------------------------------------------------------
-
-#ifndef DEH_DEFS_H
-#define DEH_DEFS_H
-
-#include "md5.h"
-
-typedef struct deh_context_s deh_context_t;
-typedef struct deh_section_s deh_section_t;
-typedef void (*deh_section_init_t)(void);
-typedef void *(*deh_section_start_t)(deh_context_t *context, char *line);
-typedef void (*deh_section_end_t)(deh_context_t *context, void *tag);
-typedef void (*deh_line_parser_t)(deh_context_t *context, char *line, void *tag);
-typedef void (*deh_md5_hash_t)(md5_context_t *context);
-
-struct deh_section_s
-{
- char *name;
-
- // Called on startup to initialise code
-
- deh_section_init_t init;
-
- // This is called when a new section is started. The pointer
- // returned is used as a tag for the following calls.
-
- deh_section_start_t start;
-
- // This is called for each line in the section
-
- deh_line_parser_t line_parser;
-
- // This is called at the end of the section for any cleanup
-
- deh_section_end_t end;
-
- // Called when generating an MD5 sum of the dehacked state
-
- deh_md5_hash_t md5_hash;
-};
-
-#endif /* #ifndef DEH_DEFS_H */
-
-
--- a/src/deh_frame.c
+++ /dev/null
@@ -1,169 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Frame" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdlib.h>
-
-#include "doomtype.h"
-#include "d_items.h"
-#include "info.h"
-
-#include "deh_defs.h"
-#include "deh_io.h"
-#include "deh_main.h"
-#include "deh_mapping.h"
-
-DEH_BEGIN_MAPPING(state_mapping, state_t)
- DEH_MAPPING("Sprite number", sprite)
- DEH_MAPPING("Sprite subnumber", frame)
- DEH_MAPPING("Duration", tics)
- DEH_MAPPING("Next frame", nextstate)
- DEH_MAPPING("Unknown 1", misc1)
- DEH_MAPPING("Unknown 2", misc2)
- DEH_UNSUPPORTED_MAPPING("Codep frame")
-DEH_END_MAPPING
-
-static void *DEH_FrameStart(deh_context_t *context, char *line)
-{
- int frame_number = 0;
- state_t *state;
-
- if (sscanf(line, "Frame %i", &frame_number) != 1)
- {
- DEH_Warning(context, "Parse error on section start");
- return NULL;
- }
-
- if (frame_number < 0 || frame_number >= NUMSTATES)
- {
- DEH_Warning(context, "Invalid frame number: %i", frame_number);
- return NULL;
- }
-
- if (frame_number >= DEH_VANILLA_NUMSTATES)
- {
- DEH_Warning(context, "Attempt to modify frame %i: this will cause "
- "problems in Vanilla dehacked.", frame_number);
- }
-
- state = &states[frame_number];
-
- return state;
-}
-
-// Simulate a frame overflow: Doom has 967 frames in the states[] array, but
-// DOS dehacked internally only allocates memory for 966. As a result,
-// attempts to set frame 966 (the last frame) will overflow the dehacked
-// array and overwrite the weaponinfo[] array instead.
-//
-// This is noticable in Batman Doom where it is impossible to switch weapons
-// away from the fist once selected.
-
-static void DEH_FrameOverflow(deh_context_t *context, char *varname, int value)
-{
- if (!strcasecmp(varname, "Duration"))
- {
- weaponinfo[0].ammo = value;
- }
- else if (!strcasecmp(varname, "Codep frame"))
- {
- weaponinfo[0].upstate = value;
- }
- else if (!strcasecmp(varname, "Next frame"))
- {
- weaponinfo[0].downstate = value;
- }
- else if (!strcasecmp(varname, "Unknown 1"))
- {
- weaponinfo[0].readystate = value;
- }
- else if (!strcasecmp(varname, "Unknown 2"))
- {
- weaponinfo[0].atkstate = value;
- }
- else
- {
- DEH_Error(context, "Unable to simulate frame overflow: field '%s'",
- varname);
- }
-}
-
-static void DEH_FrameParseLine(deh_context_t *context, char *line, void *tag)
-{
- state_t *state;
- char *variable_name, *value;
- int ivalue;
-
- if (tag == NULL)
- return;
-
- state = (state_t *) tag;
-
- // Parse the assignment
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
-
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
- // all values are integers
-
- ivalue = atoi(value);
-
- if (state == &states[NUMSTATES - 1])
- {
- DEH_FrameOverflow(context, variable_name, ivalue);
- }
- else
- {
- // set the appropriate field
-
- DEH_SetMapping(context, &state_mapping, state, variable_name, ivalue);
- }
-}
-
-static void DEH_FrameMD5Sum(md5_context_t *context)
-{
- int i;
-
- for (i=0; i<NUMSTATES; ++i)
- {
- DEH_StructMD5Sum(context, &state_mapping, &states[i]);
- }
-}
-
-deh_section_t deh_section_frame =
-{
- "Frame",
- NULL,
- DEH_FrameStart,
- DEH_FrameParseLine,
- NULL,
- DEH_FrameMD5Sum,
-};
-
--- a/src/deh_io.c
+++ /dev/null
@@ -1,212 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Dehacked I/O code (does all reads from dehacked files)
-//
-//-----------------------------------------------------------------------------
-
-#include <stdarg.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "i_system.h"
-#include "z_zone.h"
-
-#include "deh_defs.h"
-#include "deh_io.h"
-
-struct deh_context_s
-{
- FILE *stream;
- char *filename;
- int linenum;
- boolean last_was_newline;
- char *readbuffer;
- int readbuffer_size;
-};
-
-// Open a dehacked file for reading
-// Returns NULL if open failed
-
-deh_context_t *DEH_OpenFile(char *filename)
-{
- FILE *fstream;
- deh_context_t *context;
-
- fstream = fopen(filename, "r");
-
- if (fstream == NULL)
- return NULL;
-
- context = Z_Malloc(sizeof(*context), PU_STATIC, NULL);
- context->stream = fstream;
-
- // Initial read buffer size of 128 bytes
-
- context->readbuffer_size = 128;
- context->readbuffer = Z_Malloc(context->readbuffer_size, PU_STATIC, NULL);
- context->filename = filename;
- context->linenum = 0;
- context->last_was_newline = true;
-
- return context;
-}
-
-// Close dehacked file
-
-void DEH_CloseFile(deh_context_t *context)
-{
- fclose(context->stream);
- Z_Free(context->readbuffer);
- Z_Free(context);
-}
-
-// Reads a single character from a dehacked file
-
-int DEH_GetChar(deh_context_t *context)
-{
- int result;
-
- // Read characters, but ignore carriage returns
- // Essentially this is a DOS->Unix conversion
-
- do
- {
- if (feof(context->stream))
- {
- // end of file
-
- result = -1;
- }
- else
- {
- result = fgetc(context->stream);
- }
-
- } while (result == '\r');
-
- // Track the current line number
-
- if (context->last_was_newline)
- {
- ++context->linenum;
- }
-
- context->last_was_newline = result == '\n';
-
- return result;
-}
-
-// Increase the read buffer size
-
-static void IncreaseReadBuffer(deh_context_t *context)
-{
- char *newbuffer;
- int newbuffer_size;
-
- newbuffer_size = context->readbuffer_size * 2;
- newbuffer = Z_Malloc(newbuffer_size, PU_STATIC, NULL);
-
- memcpy(newbuffer, context->readbuffer, context->readbuffer_size);
-
- Z_Free(context->readbuffer);
-
- context->readbuffer = newbuffer;
- context->readbuffer_size = newbuffer_size;
-}
-
-// Read a whole line
-
-char *DEH_ReadLine(deh_context_t *context)
-{
- int c;
- int pos;
-
- for (pos=0; ; ++pos)
- {
- c = DEH_GetChar(context);
-
- if (c < 0)
- {
- // end of file
-
- return NULL;
- }
-
- if (c == '\0')
- {
- return NULL;
- }
-
- // cope with lines of any length: increase the buffer size
-
- if (pos >= context->readbuffer_size)
- {
- IncreaseReadBuffer(context);
- }
-
- if (c == '\n')
- {
- // end of line: a full line has been read
-
- context->readbuffer[pos] = '\0';
- break;
- }
- else
- {
- context->readbuffer[pos] = (char) c;
- }
- }
-
- return context->readbuffer;
-}
-
-void DEH_Warning(deh_context_t *context, char *msg, ...)
-{
- va_list args;
-
- va_start(args, msg);
-
- fprintf(stderr, "%s:%i: warning: ", context->filename, context->linenum);
- vfprintf(stderr, msg, args);
- fprintf(stderr, "\n");
-
- va_end(args);
-}
-
-void DEH_Error(deh_context_t *context, char *msg, ...)
-{
- va_list args;
-
- va_start(args, msg);
-
- fprintf(stderr, "%s:%i: ", context->filename, context->linenum);
- vfprintf(stderr, msg, args);
- fprintf(stderr, "\n");
-
- va_end(args);
-
- I_Error("Error parsing dehacked file");
-}
-
-
--- a/src/deh_io.h
+++ /dev/null
@@ -1,40 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Dehacked I/O code (does all reads from dehacked files)
-//
-//-----------------------------------------------------------------------------
-
-#ifndef DEH_IO_H
-#define DEH_IO_H
-
-#include "deh_defs.h"
-
-deh_context_t *DEH_OpenFile(char *filename);
-void DEH_CloseFile(deh_context_t *context);
-int DEH_GetChar(deh_context_t *context);
-char *DEH_ReadLine(deh_context_t *context);
-void DEH_Error(deh_context_t *context, char *msg, ...);
-void DEH_Warning(deh_context_t *context, char *msg, ...);
-
-#endif /* #ifndef DEH_IO_H */
-
--- a/src/deh_main.c
+++ /dev/null
@@ -1,408 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Main dehacked code
-//
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <ctype.h>
-
-#include "doomtype.h"
-#include "d_iwad.h"
-#include "m_argv.h"
-
-#include "deh_defs.h"
-#include "deh_io.h"
-
-static char *deh_signatures[] =
-{
- "Patch File for DeHackEd v2.3",
- "Patch File for DeHackEd v3.0",
-};
-
-// deh_ammo.c:
-extern deh_section_t deh_section_ammo;
-// deh_cheat.c:
-extern deh_section_t deh_section_cheat;
-// deh_frame.c:
-extern deh_section_t deh_section_frame;
-// deh_misc.c:
-extern deh_section_t deh_section_misc;
-// deh_ptr.c:
-extern deh_section_t deh_section_pointer;
-// deh_sound.c
-extern deh_section_t deh_section_sound;
-// deh_text.c:
-extern deh_section_t deh_section_text;
-// deh_thing.c:
-extern deh_section_t deh_section_thing;
-// deh_weapon.c:
-extern deh_section_t deh_section_weapon;
-
-// If true, we can do long string replacements.
-
-boolean deh_allow_long_strings = false;
-
-// If true, we can do cheat replacements longer than the originals.
-
-boolean deh_allow_long_cheats = false;
-
-//
-// List of section types:
-//
-
-static deh_section_t *section_types[] =
-{
- &deh_section_ammo,
- &deh_section_cheat,
- &deh_section_frame,
- &deh_section_misc,
- &deh_section_pointer,
- &deh_section_sound,
- &deh_section_text,
- &deh_section_thing,
- &deh_section_weapon,
-};
-
-void DEH_Checksum(md5_digest_t digest)
-{
- md5_context_t md5_context;
- unsigned int i;
-
- MD5_Init(&md5_context);
-
- for (i=0; i<arrlen(section_types); ++i)
- {
- if (section_types[i]->md5_hash != NULL)
- {
- section_types[i]->md5_hash(&md5_context);
- }
- }
-
- MD5_Final(digest, &md5_context);
-}
-
-// Called on startup to call the Init functions
-
-static void InitialiseSections(void)
-{
- unsigned int i;
-
- for (i=0; i<arrlen(section_types); ++i)
- {
- if (section_types[i]->init != NULL)
- {
- section_types[i]->init();
- }
- }
-}
-
-// Given a section name, get the section structure which corresponds
-
-static deh_section_t *GetSectionByName(char *name)
-{
- unsigned int i;
-
- for (i=0; i<arrlen(section_types); ++i)
- {
- if (!strcasecmp(section_types[i]->name, name))
- {
- return section_types[i];
- }
- }
-
- return NULL;
-}
-
-// Is the string passed just whitespace?
-
-static boolean IsWhitespace(char *s)
-{
- for (; *s; ++s)
- {
- if (!isspace(*s))
- return false;
- }
-
- return true;
-}
-
-// Strip whitespace from the start and end of a string
-
-static char *CleanString(char *s)
-{
- char *strending;
-
- // Leading whitespace
-
- while (*s && isspace(*s))
- ++s;
-
- // Trailing whitespace
-
- strending = s + strlen(s) - 1;
-
- while (strlen(s) > 0 && isspace(*strending))
- {
- *strending = '\0';
- --strending;
- }
-
- return s;
-}
-
-// This pattern is used a lot of times in different sections,
-// an assignment is essentially just a statement of the form:
-//
-// Variable Name = Value
-//
-// The variable name can include spaces or any other characters.
-// The string is split on the '=', essentially.
-//
-// Returns true if read correctly
-
-boolean DEH_ParseAssignment(char *line, char **variable_name, char **value)
-{
- char *p;
-
- // find the equals
-
- p = strchr(line, '=');
-
- if (p == NULL && p-line > 2)
- {
- return false;
- }
-
- // variable name at the start
- // turn the '=' into a \0 to terminate the string here
-
- *p = '\0';
- *variable_name = CleanString(line);
-
- // value immediately follows the '='
-
- *value = CleanString(p+1);
-
- return true;
-}
-
-static boolean CheckSignatures(deh_context_t *context)
-{
- size_t i;
- char *line;
-
- // Read the first line
-
- line = DEH_ReadLine(context);
-
- if (line == NULL)
- {
- return false;
- }
-
- // Check all signatures to see if one matches
-
- for (i=0; i<arrlen(deh_signatures); ++i)
- {
- if (!strcmp(deh_signatures[i], line))
- {
- return true;
- }
- }
-
- return false;
-}
-
-// Parses a comment string in a dehacked file.
-
-static void DEH_ParseComment(char *comment)
-{
- // Allow comments containing this special value to allow string
- // replacements longer than those permitted by DOS dehacked.
- // This allows us to use a dehacked patch for doing string
- // replacements for emulating Chex Quest.
- //
- // If you use this, your dehacked patch may not work in Vanilla
- // Doom.
-
- if (strstr(comment, "*allow-long-strings*") != NULL)
- {
- deh_allow_long_strings = true;
- }
-
- // Allow magic comments to allow longer cheat replacements than
- // those permitted by DOS dehacked. This is also for Chex
- // Quest.
-
- if (strstr(comment, "*allow-long-cheats*") != NULL)
- {
- deh_allow_long_cheats = true;
- }
-}
-
-// Parses a dehacked file by reading from the context
-
-static void DEH_ParseContext(deh_context_t *context)
-{
- deh_section_t *current_section = NULL;
- char section_name[20];
- void *tag = NULL;
- char *line;
-
- // Read the header and check it matches the signature
-
- if (!CheckSignatures(context))
- {
- DEH_Error(context, "This is not a valid dehacked patch file!");
- }
-
- deh_allow_long_strings = false;
- deh_allow_long_cheats = false;
-
- // Read the file
-
- for (;;)
- {
- // read a new line
-
- line = DEH_ReadLine(context);
-
- // end of file?
-
- if (line == NULL)
- return;
-
- while (line[0] != '\0' && isspace(line[0]))
- ++line;
-
- if (line[0] == '#')
- {
- // comment
-
- DEH_ParseComment(line);
- continue;
- }
-
- if (IsWhitespace(line))
- {
- if (current_section != NULL)
- {
- // end of section
-
- if (current_section->end != NULL)
- {
- current_section->end(context, tag);
- }
-
- //printf("end %s tag\n", current_section->name);
- current_section = NULL;
- }
- }
- else
- {
- if (current_section != NULL)
- {
- // parse this line
-
- current_section->line_parser(context, line, tag);
- }
- else
- {
- // possibly the start of a new section
-
- sscanf(line, "%19s", section_name);
-
- current_section = GetSectionByName(section_name);
-
- if (current_section != NULL)
- {
- tag = current_section->start(context, line);
- //printf("started %s tag\n", section_name);
- }
- else
- {
- //printf("unknown section name %s\n", section_name);
- }
- }
- }
- }
-}
-
-// Parses a dehacked file
-
-int DEH_LoadFile(char *filename)
-{
- deh_context_t *context;
-
- printf(" loading %s\n", filename);
-
- context = DEH_OpenFile(filename);
-
- if (context == NULL)
- {
- fprintf(stderr, "DEH_LoadFile: Unable to open %s\n", filename);
- return 0;
- }
-
- DEH_ParseContext(context);
-
- DEH_CloseFile(context);
-
- return 1;
-}
-
-// Checks the command line for -deh argument
-
-void DEH_Init(void)
-{
- char *filename;
- int p;
-
- InitialiseSections();
-
- //!
- // @arg <files>
- // @category mod
- //
- // Load the given dehacked patch(es)
- //
-
- p = M_CheckParm("-deh");
-
- if (p > 0)
- {
- ++p;
-
- while (p < myargc && myargv[p][0] != '-')
- {
- filename = D_TryFindWADByName(myargv[p]);
- DEH_LoadFile(filename);
- ++p;
- }
- }
-}
-
-
--- a/src/deh_main.h
+++ /dev/null
@@ -1,66 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Dehacked entrypoint and common code
-//
-//-----------------------------------------------------------------------------
-
-#ifndef DEH_MAIN_H
-#define DEH_MAIN_H
-
-#include "doomtype.h"
-#include "doomfeatures.h"
-#include "md5.h"
-
-// These are the limits that dehacked uses (from dheinit.h in the dehacked
-// source). If these limits are exceeded, it does not generate an error, but
-// a warning is displayed.
-
-#define DEH_VANILLA_NUMSTATES 966
-#define DEH_VANILLA_NUMSFX 107
-
-void DEH_Init(void);
-int DEH_LoadFile(char *filename);
-
-boolean DEH_ParseAssignment(char *line, char **variable_name, char **value);
-
-void DEH_Checksum(md5_digest_t digest);
-
-// deh_text.c:
-//
-// Used to do dehacked text substitutions throughout the program
-
-#ifdef FEATURE_DEHACKED
-
-char *DEH_String(char *s);
-
-#else
-
-#define DEH_String(x) (x)
-
-#endif
-
-extern boolean deh_allow_long_strings;
-extern boolean deh_allow_long_cheats;
-
-#endif /* #ifndef DEH_MAIN_H */
-
--- a/src/deh_mapping.c
+++ /dev/null
@@ -1,133 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Dehacked "mapping" code
-// Allows the fields in structures to be mapped out and accessed by
-// name
-//
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "doomtype.h"
-#include "i_system.h"
-#include "deh_mapping.h"
-
-//
-// Set the value of a particular field in a structure by name
-//
-
-boolean DEH_SetMapping(deh_context_t *context, deh_mapping_t *mapping,
- void *structptr, char *name, int value)
-{
- int i;
-
- for (i=0; mapping->entries[i].name != NULL; ++i)
- {
- deh_mapping_entry_t *entry = &mapping->entries[i];
-
- if (!strcasecmp(entry->name, name))
- {
- void *location;
-
- if (entry->location == NULL)
- {
- DEH_Warning(context, "Field '%s' is unsupported", name);
- return false;
- }
-
- location = (uint8_t *)structptr + ((uint8_t *)entry->location - (uint8_t *)mapping->base);
-
- // printf("Setting %p::%s to %i (%i bytes)\n",
- // structptr, name, value, entry->size);
-
- switch (entry->size)
- {
- case 1:
- * ((uint8_t *) location) = value;
- break;
- case 2:
- * ((uint16_t *) location) = value;
- break;
- case 4:
- * ((uint32_t *) location) = value;
- break;
- default:
- DEH_Error(context, "Unknown field type for '%s' (BUG)", name);
- return false;
- }
-
- return true;
- }
- }
-
- // field with this name not found
-
- DEH_Warning(context, "Field named '%s' not found", name);
-
- return false;
-}
-
-void DEH_StructMD5Sum(md5_context_t *context, deh_mapping_t *mapping,
- void *structptr)
-{
- int i;
-
- // Go through each mapping
-
- for (i=0; mapping->entries[i].name != NULL; ++i)
- {
- deh_mapping_entry_t *entry = &mapping->entries[i];
- void *location;
-
- if (entry->location == NULL)
- {
- // Unsupported field
-
- continue;
- }
-
- // Add in data for this field
-
- location = (uint8_t *)structptr + ((uint8_t *)entry->location - (uint8_t *)mapping->base);
-
- switch (entry->size)
- {
- case 1:
- MD5_UpdateInt32(context, *((uint8_t *) location));
- break;
- case 2:
- MD5_UpdateInt32(context, *((uint16_t *) location));
- break;
- case 4:
- MD5_UpdateInt32(context, *((uint32_t *) location));
- break;
- default:
- I_Error("Unknown dehacked mapping field type for '%s' (BUG)",
- entry->name);
- break;
- }
- }
-}
-
--- a/src/deh_mapping.h
+++ /dev/null
@@ -1,90 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Dehacked "mapping" code
-// Allows the fields in structures to be mapped out and accessed by
-// name
-//
-//-----------------------------------------------------------------------------
-
-#ifndef DEH_MAPPING_H
-#define DEH_MAPPING_H
-
-#include "doomtype.h"
-#include "deh_io.h"
-#include "md5.h"
-
-#define DEH_BEGIN_MAPPING(mapping_name, structname) \
- static structname deh_mapping_base; \
- static deh_mapping_t mapping_name = \
- { \
- &deh_mapping_base, \
- {
-
-#define DEH_MAPPING(deh_name, fieldname) \
- {deh_name, &deh_mapping_base.fieldname, \
- sizeof(deh_mapping_base.fieldname)},
-
-#define DEH_UNSUPPORTED_MAPPING(deh_name) \
- {deh_name, NULL, -1},
-
-#define DEH_END_MAPPING \
- {NULL, NULL, -1} \
- } \
- };
-
-
-
-#define MAX_MAPPING_ENTRIES 32
-
-typedef struct deh_mapping_s deh_mapping_t;
-typedef struct deh_mapping_entry_s deh_mapping_entry_t;
-
-struct deh_mapping_entry_s
-{
- // field name
-
- char *name;
-
- // location relative to the base in the deh_mapping_t struct
- // If this is NULL, it is an unsupported mapping
-
- void *location;
-
- // field size
-
- int size;
-};
-
-struct deh_mapping_s
-{
- void *base;
- deh_mapping_entry_t entries[MAX_MAPPING_ENTRIES];
-};
-
-boolean DEH_SetMapping(deh_context_t *context, deh_mapping_t *mapping,
- void *structptr, char *name, int value);
-void DEH_StructMD5Sum(md5_context_t *context, deh_mapping_t *mapping,
- void *structptr);
-
-#endif /* #ifndef DEH_MAPPING_H */
-
--- a/src/deh_misc.c
+++ /dev/null
@@ -1,237 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Misc" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdlib.h>
-#include <string.h>
-
-#include "doomtype.h"
-#include "deh_defs.h"
-#include "deh_io.h"
-#include "deh_main.h"
-#include "deh_misc.h"
-
-// Dehacked: "Initial Health"
-// This is the initial health a player has when starting anew.
-// See G_PlayerReborn in g_game.c
-
-int deh_initial_health = DEH_DEFAULT_INITIAL_HEALTH;
-
-// Dehacked: "Initial bullets"
-// This is the number of bullets the player has when starting anew.
-// See G_PlayerReborn in g_game.c
-
-int deh_initial_bullets = DEH_DEFAULT_INITIAL_BULLETS;
-
-// Dehacked: "Max Health"
-// This is the maximum health that can be reached using medikits
-// alone. See P_TouchSpecialThing in p_inter.c
-
-int deh_max_health = DEH_DEFAULT_MAX_HEALTH;
-
-// Dehacked: "Max Armor"
-// This is the maximum armor which can be reached by picking up
-// armor helmets. See P_TouchSpecialThing in p_inter.c
-
-int deh_max_armor = DEH_DEFAULT_MAX_ARMOR;
-
-// Dehacked: "Green Armor Class"
-// This is the armor class that is given when picking up the green
-// armor or an armor helmet. See P_TouchSpecialThing in p_inter.c
-//
-// DOS dehacked only modifies the behavior of the green armor shirt,
-// the armor class set by armor helmets is not affected.
-
-int deh_green_armor_class = DEH_DEFAULT_GREEN_ARMOR_CLASS;
-
-// Dehacked: "Blue Armor Class"
-// This is the armor class that is given when picking up the blue
-// armor or a megasphere. See P_TouchSpecialThing in p_inter.c
-//
-// DOS dehacked only modifies the MegaArmor behavior and not
-// the MegaSphere, which always gives armor type 2.
-
-int deh_blue_armor_class = DEH_DEFAULT_BLUE_ARMOR_CLASS;
-
-// Dehacked: "Max soulsphere"
-// The maximum health which can be reached by picking up the
-// soulsphere. See P_TouchSpecialThing in p_inter.c
-
-int deh_max_soulsphere = DEH_DEFAULT_MAX_SOULSPHERE;
-
-// Dehacked: "Soulsphere health"
-// The amount of health bonus that picking up a soulsphere
-// gives. See P_TouchSpecialThing in p_inter.c
-
-int deh_soulsphere_health = DEH_DEFAULT_SOULSPHERE_HEALTH;
-
-// Dehacked: "Megasphere health"
-// This is what the health is set to after picking up a
-// megasphere. See P_TouchSpecialThing in p_inter.c
-
-int deh_megasphere_health = DEH_DEFAULT_MEGASPHERE_HEALTH;
-
-// Dehacked: "God mode health"
-// This is what the health value is set to when cheating using
-// the IDDQD god mode cheat. See ST_Responder in st_stuff.c
-
-int deh_god_mode_health = DEH_DEFAULT_GOD_MODE_HEALTH;
-
-// Dehacked: "IDFA Armor"
-// This is what the armor is set to when using the IDFA cheat.
-// See ST_Responder in st_stuff.c
-
-int deh_idfa_armor = DEH_DEFAULT_IDFA_ARMOR;
-
-// Dehacked: "IDFA Armor Class"
-// This is what the armor class is set to when using the IDFA cheat.
-// See ST_Responder in st_stuff.c
-
-int deh_idfa_armor_class = DEH_DEFAULT_IDFA_ARMOR_CLASS;
-
-// Dehacked: "IDKFA Armor"
-// This is what the armor is set to when using the IDKFA cheat.
-// See ST_Responder in st_stuff.c
-
-int deh_idkfa_armor = DEH_DEFAULT_IDKFA_ARMOR;
-
-// Dehacked: "IDKFA Armor Class"
-// This is what the armor class is set to when using the IDKFA cheat.
-// See ST_Responder in st_stuff.c
-
-int deh_idkfa_armor_class = DEH_DEFAULT_IDKFA_ARMOR_CLASS;
-
-// Dehacked: "BFG Cells/Shot"
-// This is the number of CELLs firing the BFG uses up.
-// See P_CheckAmmo and A_FireBFG in p_pspr.c
-
-int deh_bfg_cells_per_shot = DEH_DEFAULT_BFG_CELLS_PER_SHOT;
-
-// Dehacked: "Monsters infight"
-// This controls whether monsters can harm other monsters of the same
-// species. For example, whether an imp fireball will damage other
-// imps. The value of this in dehacked patches is weird - '202' means
-// off, while '221' means on.
-//
-// See PIT_CheckThing in p_map.c
-
-int deh_species_infighting = DEH_DEFAULT_SPECIES_INFIGHTING;
-
-static struct
-{
- char *deh_name;
- int *value;
-} misc_settings[] = {
- {"Initial Health", &deh_initial_health},
- {"Initial Bullets", &deh_initial_bullets},
- {"Max Health", &deh_max_health},
- {"Max Armor", &deh_max_armor},
- {"Green Armor Class", &deh_green_armor_class},
- {"Blue Armor Class", &deh_blue_armor_class},
- {"Max Soulsphere", &deh_max_soulsphere},
- {"Soulsphere Health", &deh_soulsphere_health},
- {"Megasphere Health", &deh_megasphere_health},
- {"God Mode Health", &deh_god_mode_health},
- {"IDFA Armor", &deh_idfa_armor},
- {"IDFA Armor Class", &deh_idfa_armor_class},
- {"IDKFA Armor", &deh_idkfa_armor},
- {"IDKFA Armor Class", &deh_idkfa_armor_class},
- {"BFG Cells/Shot", &deh_bfg_cells_per_shot},
-};
-
-static void *DEH_MiscStart(deh_context_t *context, char *line)
-{
- return NULL;
-}
-
-static void DEH_MiscParseLine(deh_context_t *context, char *line, void *tag)
-{
- char *variable_name, *value;
- int ivalue;
- size_t i;
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
-
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
- ivalue = atoi(value);
-
- if (!strcasecmp(variable_name, "Monsters Infight"))
- {
- // See notes above.
-
- if (ivalue == 202)
- {
- deh_species_infighting = 0;
- }
- else if (ivalue == 221)
- {
- deh_species_infighting = 1;
- }
- else
- {
- DEH_Warning(context,
- "Invalid value for 'Monsters Infight': %i", ivalue);
- }
-
- return;
- }
-
- for (i=0; i<arrlen(misc_settings); ++i)
- {
- if (!strcasecmp(variable_name, misc_settings[i].deh_name))
- {
- *misc_settings[i].value = ivalue;
- return;
- }
- }
-
- DEH_Warning(context, "Unknown Misc variable '%s'", variable_name);
-}
-
-static void DEH_MiscMD5Sum(md5_context_t *context)
-{
- unsigned int i;
-
- for (i=0; i<arrlen(misc_settings); ++i)
- {
- MD5_UpdateInt32(context, *misc_settings[i].value);
- }
-}
-
-deh_section_t deh_section_misc =
-{
- "Misc",
- NULL,
- DEH_MiscStart,
- DEH_MiscParseLine,
- NULL,
- DEH_MiscMD5Sum,
-};
-
--- a/src/deh_misc.h
+++ /dev/null
@@ -1,92 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Misc" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#ifndef DEH_MISC_H
-#define DEH_MISC_H
-
-#include "doomfeatures.h"
-
-#define DEH_DEFAULT_INITIAL_HEALTH 100
-#define DEH_DEFAULT_INITIAL_BULLETS 50
-#define DEH_DEFAULT_MAX_HEALTH 200
-#define DEH_DEFAULT_MAX_ARMOR 200
-#define DEH_DEFAULT_GREEN_ARMOR_CLASS 1
-#define DEH_DEFAULT_BLUE_ARMOR_CLASS 2
-#define DEH_DEFAULT_MAX_SOULSPHERE 200
-#define DEH_DEFAULT_SOULSPHERE_HEALTH 100
-#define DEH_DEFAULT_MEGASPHERE_HEALTH 200
-#define DEH_DEFAULT_GOD_MODE_HEALTH 100
-#define DEH_DEFAULT_IDFA_ARMOR 200
-#define DEH_DEFAULT_IDFA_ARMOR_CLASS 2
-#define DEH_DEFAULT_IDKFA_ARMOR 200
-#define DEH_DEFAULT_IDKFA_ARMOR_CLASS 2
-#define DEH_DEFAULT_BFG_CELLS_PER_SHOT 40
-#define DEH_DEFAULT_SPECIES_INFIGHTING 0
-
-#ifdef FEATURE_DEHACKED
-
-extern int deh_initial_health;
-extern int deh_initial_bullets;
-extern int deh_max_health;
-extern int deh_max_armor;
-extern int deh_green_armor_class;
-extern int deh_blue_armor_class;
-extern int deh_max_soulsphere;
-extern int deh_soulsphere_health;
-extern int deh_megasphere_health;
-extern int deh_god_mode_health;
-extern int deh_idfa_armor;
-extern int deh_idfa_armor_class;
-extern int deh_idkfa_armor;
-extern int deh_idkfa_armor_class;
-extern int deh_bfg_cells_per_shot;
-extern int deh_species_infighting;
-
-#else
-
-// If dehacked is disabled, hard coded values
-
-#define deh_initial_health DEH_DEFAULT_INITIAL_HEALTH
-#define deh_initial_bullets DEH_DEFAULT_INITIAL_BULLETS
-#define deh_max_health DEH_DEFAULT_MAX_HEALTH
-#define deh_max_armor DEH_DEFAULT_MAX_ARMOR
-#define deh_green_armor_class DEH_DEFAULT_GREEN_ARMOR_CLASS
-#define deh_blue_armor_class DEH_DEFAULT_BLUE_ARMOR_CLASS
-#define deh_max_soulsphere DEH_DEFAULT_MAX_SOULSPHERE
-#define deh_soulsphere_health DEH_DEFAULT_SOULSPHERE_HEALTH
-#define deh_megasphere_health DEH_DEFAULT_MEGASPHERE_HEALTH
-#define deh_god_mode_health DEH_DEFAULT_GOD_MODE_HEALTH
-#define deh_idfa_armor DEH_DEFAULT_IDFA_ARMOR
-#define deh_idfa_armor_class DEH_DEFAULT_IDFA_ARMOR_CLASS
-#define deh_idkfa_armor DEH_DEFAULT_IDKFA_ARMOR
-#define deh_idkfa_armor_class DEH_DEFAULT_IDKFA_ARMOR_CLASS
-#define deh_bfg_cells_per_shot DEH_DEFAULT_BFG_CELLS_PER_SHOT
-#define deh_species_infighting DEH_DEFAULT_SPECIES_INFIGHTING
-
-#endif
-
-#endif /* #ifndef DEH_MISC_H */
-
--- a/src/deh_ptr.c
+++ /dev/null
@@ -1,151 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses Action Pointer entries in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "doomtype.h"
-#include "info.h"
-
-#include "deh_defs.h"
-#include "deh_io.h"
-#include "deh_main.h"
-
-static actionf_t codeptrs[NUMSTATES];
-
-static int CodePointerIndex(actionf_t *ptr)
-{
- int i;
-
- for (i=0; i<NUMSTATES; ++i)
- {
- if (!memcmp(&codeptrs[i], ptr, sizeof(actionf_t)))
- {
- return i;
- }
- }
-
- return -1;
-}
-
-static void DEH_PointerInit(void)
-{
- int i;
-
- // Initialise list of dehacked pointers
-
- for (i=0; i<NUMSTATES; ++i)
- codeptrs[i] = states[i].action;
-}
-
-static void *DEH_PointerStart(deh_context_t *context, char *line)
-{
- int frame_number = 0;
-
- // FIXME: can the third argument here be something other than "Frame"
- // or are we ok?
-
- if (sscanf(line, "Pointer %*i (%*s %i)", &frame_number) != 1)
- {
- DEH_Warning(context, "Parse error on section start");
- return NULL;
- }
-
- if (frame_number < 0 || frame_number >= NUMSTATES)
- {
- DEH_Warning(context, "Invalid frame number: %i", frame_number);
- return NULL;
- }
-
- return &states[frame_number];
-}
-
-static void DEH_PointerParseLine(deh_context_t *context, char *line, void *tag)
-{
- state_t *state;
- char *variable_name, *value;
- int ivalue;
-
- if (tag == NULL)
- return;
-
- state = (state_t *) tag;
-
- // Parse the assignment
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
-// printf("Set %s to %s for state\n", variable_name, value);
-
- // all values are integers
-
- ivalue = atoi(value);
-
- // set the appropriate field
-
- if (!strcasecmp(variable_name, "Codep frame"))
- {
- if (ivalue < 0 || ivalue >= NUMSTATES)
- {
- DEH_Warning(context, "Invalid state '%i'", ivalue);
- }
- else
- {
- state->action = codeptrs[ivalue];
- }
- }
- else
- {
- DEH_Warning(context, "Unknown variable name '%s'", variable_name);
- }
-}
-
-static void DEH_PointerMD5Sum(md5_context_t *context)
-{
- int i;
-
- for (i=0; i<NUMSTATES; ++i)
- {
- MD5_UpdateInt32(context, CodePointerIndex(&states[i].action));
- }
-}
-
-deh_section_t deh_section_pointer =
-{
- "Pointer",
- DEH_PointerInit,
- DEH_PointerStart,
- DEH_PointerParseLine,
- NULL,
- DEH_PointerMD5Sum,
-};
-
--- a/src/deh_sound.c
+++ /dev/null
@@ -1,113 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Sound" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-#include <stdlib.h>
-
-#include "doomfeatures.h"
-#include "doomtype.h"
-#include "deh_defs.h"
-#include "deh_main.h"
-#include "deh_mapping.h"
-#include "sounds.h"
-
-DEH_BEGIN_MAPPING(sound_mapping, sfxinfo_t)
- DEH_UNSUPPORTED_MAPPING("Offset")
- DEH_MAPPING("Zero/One", singularity)
- DEH_MAPPING("Value", priority)
- DEH_MAPPING("Zero 1", link)
- DEH_MAPPING("Zero 2", pitch)
- DEH_MAPPING("Zero 3", volume)
- DEH_MAPPING("Zero 4", data)
- DEH_MAPPING("Neg. One 1", usefulness)
- DEH_MAPPING("Neg. One 2", lumpnum)
-DEH_END_MAPPING
-
-static void *DEH_SoundStart(deh_context_t *context, char *line)
-{
- int sound_number = 0;
-
- if (sscanf(line, "Sound %i", &sound_number) != 1)
- {
- DEH_Warning(context, "Parse error on section start");
- return NULL;
- }
-
- if (sound_number < 0 || sound_number >= NUMSFX)
- {
- DEH_Warning(context, "Invalid sound number: %i", sound_number);
- return NULL;
- }
-
- if (sound_number >= DEH_VANILLA_NUMSFX)
- {
- DEH_Warning(context, "Attempt to modify SFX %i. This will cause "
- "problems in Vanilla dehacked.", sound_number);
- }
-
- return &S_sfx[sound_number];
-}
-
-static void DEH_SoundParseLine(deh_context_t *context, char *line, void *tag)
-{
- sfxinfo_t *sfx;
- char *variable_name, *value;
- int ivalue;
-
- if (tag == NULL)
- return;
-
- sfx = (sfxinfo_t *) tag;
-
- // Parse the assignment
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
- // all values are integers
-
- ivalue = atoi(value);
-
- // Set the field value
-
- DEH_SetMapping(context, &sound_mapping, sfx, variable_name, ivalue);
-
-}
-
-deh_section_t deh_section_sound =
-{
- "Sound",
- NULL,
- DEH_SoundStart,
- DEH_SoundParseLine,
- NULL,
- NULL,
-};
-
--- /dev/null
+++ b/src/deh_str.c
@@ -1,0 +1,180 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses Text substitution sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "doomtype.h"
+#include "deh_str.h"
+
+#include "z_zone.h"
+
+typedef struct
+{
+ char *from_text;
+ char *to_text;
+} deh_substitution_t;
+
+static deh_substitution_t **hash_table = NULL;
+static int hash_table_entries;
+static int hash_table_length = -1;
+
+// This is the algorithm used by glib
+
+static unsigned int strhash(char *s)
+{
+ char *p = s;
+ unsigned int h = *p;
+
+ if (h)
+ {
+ for (p += 1; *p; p++)
+ h = (h << 5) - h + *p;
+ }
+
+ return h;
+}
+
+// Look up a string to see if it has been replaced with something else
+// This will be used throughout the program to substitute text
+
+char *DEH_String(char *s)
+{
+ int entry;
+
+ // Fallback if we have not initialised the hash table yet
+
+ if (hash_table_length < 0)
+ return s;
+
+ entry = strhash(s) % hash_table_length;
+
+ while (hash_table[entry] != NULL)
+ {
+ if (!strcmp(hash_table[entry]->from_text, s))
+ {
+ // substitution found!
+
+ return hash_table[entry]->to_text;
+ }
+
+ entry = (entry + 1) % hash_table_length;
+ }
+
+ // no substitution found
+
+ return s;
+}
+
+static void InitHashTable(void)
+{
+ // init hash table
+
+ hash_table_entries = 0;
+ hash_table_length = 16;
+ hash_table = Z_Malloc(sizeof(deh_substitution_t *) * hash_table_length,
+ PU_STATIC, NULL);
+ memset(hash_table, 0, sizeof(deh_substitution_t *) * hash_table_length);
+}
+
+static void DEH_AddToHashtable(deh_substitution_t *sub);
+
+static void IncreaseHashtable(void)
+{
+ deh_substitution_t **old_table;
+ int old_table_length;
+ int i;
+
+ // save the old table
+
+ old_table = hash_table;
+ old_table_length = hash_table_length;
+
+ // double the size
+
+ hash_table_length *= 2;
+ hash_table = Z_Malloc(sizeof(deh_substitution_t *) * hash_table_length,
+ PU_STATIC, NULL);
+ memset(hash_table, 0, sizeof(deh_substitution_t *) * hash_table_length);
+
+ // go through the old table and insert all the old entries
+
+ for (i=0; i<old_table_length; ++i)
+ {
+ if (old_table[i] != NULL)
+ {
+ DEH_AddToHashtable(old_table[i]);
+ }
+ }
+
+ // free the old table
+
+ Z_Free(old_table);
+}
+
+static void DEH_AddToHashtable(deh_substitution_t *sub)
+{
+ int entry;
+
+ // if the hash table is more than 60% full, increase its size
+
+ if ((hash_table_entries * 10) / hash_table_length > 6)
+ {
+ IncreaseHashtable();
+ }
+
+ // find where to insert it
+
+ entry = strhash(sub->from_text) % hash_table_length;
+
+ while (hash_table[entry] != NULL)
+ {
+ entry = (entry + 1) % hash_table_length;
+ }
+
+ hash_table[entry] = sub;
+ ++hash_table_entries;
+}
+
+void DEH_AddStringReplacement(char *from_text, char *to_text)
+{
+ deh_substitution_t *sub;
+
+ // Initialise the hash table if this is the first time
+
+ if (hash_table_length < 0)
+ {
+ InitHashTable();
+ }
+
+ sub = Z_Malloc(sizeof(*sub), PU_STATIC, 0);
+
+ sub->from_text = from_text;
+ sub->to_text = to_text;
+
+ DEH_AddToHashtable(sub);
+}
+
--- /dev/null
+++ b/src/deh_str.h
@@ -1,0 +1,46 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Dehacked string replacements
+//
+//-----------------------------------------------------------------------------
+
+#ifndef DEH_STR_H
+#define DEH_STR_H
+
+#include "doomfeatures.h"
+
+// Used to do dehacked text substitutions throughout the program
+
+#ifdef FEATURE_DEHACKED
+
+char *DEH_String(char *s);
+void DEH_AddStringReplacement(char *from_text, char *to_text);
+
+#else
+
+#define DEH_String(x) (x)
+
+#endif
+
+#endif /* #ifndef DEH_STR_H */
+
--- a/src/deh_text.c
+++ /dev/null
@@ -1,254 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses Text substitution sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <string.h>
-
-#include "doomtype.h"
-
-#include "z_zone.h"
-
-#include "deh_defs.h"
-#include "deh_io.h"
-#include "deh_main.h"
-
-typedef struct
-{
- char *from_text;
- char *to_text;
-} deh_substitution_t;
-
-static deh_substitution_t **hash_table;
-static int hash_table_entries;
-static int hash_table_length = -1;
-
-// This is the algorithm used by glib
-
-static unsigned int strhash(char *s)
-{
- char *p = s;
- unsigned int h = *p;
-
- if (h)
- {
- for (p += 1; *p; p++)
- h = (h << 5) - h + *p;
- }
-
- return h;
-}
-
-// Look up a string to see if it has been replaced with something else
-// This will be used throughout the program to substitute text
-
-char *DEH_String(char *s)
-{
- int entry;
-
- // Fallback if we have not initialised the hash table yet
-
- if (hash_table_length < 0)
- return s;
-
- entry = strhash(s) % hash_table_length;
-
- while (hash_table[entry] != NULL)
- {
- if (!strcmp(hash_table[entry]->from_text, s))
- {
- // substitution found!
-
- return hash_table[entry]->to_text;
- }
-
- entry = (entry + 1) % hash_table_length;
- }
-
- // no substitution found
-
- return s;
-}
-
-static void DEH_AddToHashtable(deh_substitution_t *sub);
-
-static void IncreaseHashtable(void)
-{
- deh_substitution_t **old_table;
- int old_table_length;
- int i;
-
- // save the old table
-
- old_table = hash_table;
- old_table_length = hash_table_length;
-
- // double the size
-
- hash_table_length *= 2;
- hash_table = Z_Malloc(sizeof(deh_substitution_t *) * hash_table_length,
- PU_STATIC, NULL);
- memset(hash_table, 0, sizeof(deh_substitution_t *) * hash_table_length);
-
- // go through the old table and insert all the old entries
-
- for (i=0; i<old_table_length; ++i)
- {
- if (old_table[i] != NULL)
- {
- DEH_AddToHashtable(old_table[i]);
- }
- }
-
- // free the old table
-
- Z_Free(old_table);
-}
-
-static void DEH_AddToHashtable(deh_substitution_t *sub)
-{
- int entry;
-
- // if the hash table is more than 60% full, increase its size
-
- if ((hash_table_entries * 10) / hash_table_length > 6)
- {
- IncreaseHashtable();
- }
-
- // find where to insert it
-
- entry = strhash(sub->from_text) % hash_table_length;
-
- while (hash_table[entry] != NULL)
- {
- entry = (entry + 1) % hash_table_length;
- }
-
- hash_table[entry] = sub;
- ++hash_table_entries;
-}
-
-// Given a string length, find the maximum length of a
-// string that can replace it.
-
-static int TXT_MaxStringLength(int len)
-{
- // Enough bytes for the string and the NUL terminator
-
- len += 1;
-
- // All strings in doom.exe are on 4-byte boundaries, so we may be able
- // to support a slightly longer string.
- // Extend up to the next 4-byte boundary
-
- len += (4 - (len % 4)) % 4;
-
- // Less one for the NUL terminator.
-
- return len - 1;
-}
-
-static void DEH_TextInit(void)
-{
- // init hash table
-
- hash_table_entries = 0;
- hash_table_length = 16;
- hash_table = Z_Malloc(sizeof(deh_substitution_t *) * hash_table_length,
- PU_STATIC, NULL);
- memset(hash_table, 0, sizeof(deh_substitution_t *) * hash_table_length);
-}
-
-static void *DEH_TextStart(deh_context_t *context, char *line)
-{
- deh_substitution_t *sub;
- int fromlen, tolen;
- int i;
-
- if (sscanf(line, "Text %i %i", &fromlen, &tolen) != 2)
- {
- DEH_Warning(context, "Parse error on section start");
- return NULL;
- }
-
- // Only allow string replacements that are possible in Vanilla Doom.
- // Chocolate Doom is unforgiving!
-
- if (!deh_allow_long_strings && tolen > TXT_MaxStringLength(fromlen))
- {
- DEH_Error(context, "Replacement string is longer than the maximum "
- "possible in doom.exe");
- return NULL;
- }
-
- sub = Z_Malloc(sizeof(deh_substitution_t), PU_STATIC, NULL);
- sub->from_text = Z_Malloc(fromlen + 1, PU_STATIC, NULL);
- sub->to_text = Z_Malloc(tolen + 1, PU_STATIC, NULL);
-
- // read in the "from" text
-
- for (i=0; i<fromlen; ++i)
- {
- int c;
-
- c = DEH_GetChar(context);
-
- sub->from_text[i] = c;
- }
-
- sub->from_text[fromlen] = '\0';
-
- // read in the "to" text
-
- for (i=0; i<tolen; ++i)
- {
- int c;
-
- c = DEH_GetChar(context);
-
- sub->to_text[i] = c;
- }
- sub->to_text[tolen] = '\0';
-
- DEH_AddToHashtable(sub);
-
- return NULL;
-}
-
-static void DEH_TextParseLine(deh_context_t *context, char *line, void *tag)
-{
- // not used
-}
-
-deh_section_t deh_section_text =
-{
- "Text",
- DEH_TextInit,
- DEH_TextStart,
- DEH_TextParseLine,
- NULL,
- NULL,
-};
-
--- a/src/deh_thing.c
+++ /dev/null
@@ -1,140 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Thing" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdio.h>
-#include <stdlib.h>
-
-#include "doomtype.h"
-
-#include "deh_defs.h"
-#include "deh_main.h"
-#include "deh_mapping.h"
-
-#include "info.h"
-
-DEH_BEGIN_MAPPING(thing_mapping, mobjinfo_t)
- DEH_MAPPING("ID #", doomednum)
- DEH_MAPPING("Initial frame", spawnstate)
- DEH_MAPPING("Hit points", spawnhealth)
- DEH_MAPPING("First moving frame", seestate)
- DEH_MAPPING("Alert sound", seesound)
- DEH_MAPPING("Reaction time", reactiontime)
- DEH_MAPPING("Attack sound", attacksound)
- DEH_MAPPING("Injury frame", painstate)
- DEH_MAPPING("Pain chance", painchance)
- DEH_MAPPING("Pain sound", painsound)
- DEH_MAPPING("Close attack frame", meleestate)
- DEH_MAPPING("Far attack frame", missilestate)
- DEH_MAPPING("Death frame", deathstate)
- DEH_MAPPING("Exploding frame", xdeathstate)
- DEH_MAPPING("Death sound", deathsound)
- DEH_MAPPING("Speed", speed)
- DEH_MAPPING("Width", radius)
- DEH_MAPPING("Height", height)
- DEH_MAPPING("Mass", mass)
- DEH_MAPPING("Missile damage", damage)
- DEH_MAPPING("Action sound", activesound)
- DEH_MAPPING("Bits", flags)
- DEH_MAPPING("Respawn frame", raisestate)
-DEH_END_MAPPING
-
-static void *DEH_ThingStart(deh_context_t *context, char *line)
-{
- int thing_number = 0;
- mobjinfo_t *mobj;
-
- if (sscanf(line, "Thing %i", &thing_number) != 1)
- {
- DEH_Warning(context, "Parse error on section start");
- return NULL;
- }
-
- // dehacked files are indexed from 1
- --thing_number;
-
- if (thing_number < 0 || thing_number >= NUMMOBJTYPES)
- {
- DEH_Warning(context, "Invalid thing number: %i", thing_number);
- return NULL;
- }
-
- mobj = &mobjinfo[thing_number];
-
- return mobj;
-}
-
-static void DEH_ThingParseLine(deh_context_t *context, char *line, void *tag)
-{
- mobjinfo_t *mobj;
- char *variable_name, *value;
- int ivalue;
-
- if (tag == NULL)
- return;
-
- mobj = (mobjinfo_t *) tag;
-
- // Parse the assignment
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
-
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
-// printf("Set %s to %s for mobj\n", variable_name, value);
-
- // all values are integers
-
- ivalue = atoi(value);
-
- // Set the field value
-
- DEH_SetMapping(context, &thing_mapping, mobj, variable_name, ivalue);
-}
-
-static void DEH_ThingMD5Sum(md5_context_t *context)
-{
- int i;
-
- for (i=0; i<NUMMOBJTYPES; ++i)
- {
- DEH_StructMD5Sum(context, &thing_mapping, &mobjinfo[i]);
- }
-}
-
-deh_section_t deh_section_thing =
-{
- "Thing",
- NULL,
- DEH_ThingStart,
- DEH_ThingParseLine,
- NULL,
- DEH_ThingMD5Sum,
-};
-
--- a/src/deh_weapon.c
+++ /dev/null
@@ -1,109 +1,0 @@
-// Emacs style mode select -*- C++ -*-
-//-----------------------------------------------------------------------------
-//
-// Copyright(C) 2005 Simon Howard
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License
-// as published by the Free Software Foundation; either version 2
-// 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. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with this program; if not, write to the Free Software
-// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-// 02111-1307, USA.
-//
-//-----------------------------------------------------------------------------
-//
-// Parses "Weapon" sections in dehacked files
-//
-//-----------------------------------------------------------------------------
-
-#include <stdlib.h>
-#include <string.h>
-
-#include "doomtype.h"
-
-#include "d_items.h"
-
-#include "deh_defs.h"
-#include "deh_main.h"
-#include "deh_mapping.h"
-
-DEH_BEGIN_MAPPING(weapon_mapping, weaponinfo_t)
- DEH_MAPPING("Ammo type", ammo)
- DEH_MAPPING("Deselect frame", upstate)
- DEH_MAPPING("Select frame", downstate)
- DEH_MAPPING("Bobbing frame", readystate)
- DEH_MAPPING("Shooting frame", atkstate)
- DEH_MAPPING("Firing frame", flashstate)
-DEH_END_MAPPING
-
-static void *DEH_WeaponStart(deh_context_t *context, char *line)
-{
- int weapon_number = 0;
-
- if (sscanf(line, "Weapon %i", &weapon_number) != 1)
- {
- DEH_Warning(context, "Parse error on section start");
- return NULL;
- }
-
- if (weapon_number < 0 || weapon_number >= NUMWEAPONS)
- {
- DEH_Warning(context, "Invalid weapon number: %i", weapon_number);
- return NULL;
- }
-
- return &weaponinfo[weapon_number];
-}
-
-static void DEH_WeaponParseLine(deh_context_t *context, char *line, void *tag)
-{
- char *variable_name, *value;
- weaponinfo_t *weapon;
- int ivalue;
-
- if (tag == NULL)
- return;
-
- weapon = (weaponinfo_t *) tag;
-
- if (!DEH_ParseAssignment(line, &variable_name, &value))
- {
- // Failed to parse
-
- DEH_Warning(context, "Failed to parse assignment");
- return;
- }
-
- ivalue = atoi(value);
-
- DEH_SetMapping(context, &weapon_mapping, weapon, variable_name, ivalue);
-}
-
-static void DEH_WeaponMD5Sum(md5_context_t *context)
-{
- int i;
-
- for (i=0; i<NUMWEAPONS ;++i)
- {
- DEH_StructMD5Sum(context, &weapon_mapping, &weaponinfo[i]);
- }
-}
-
-deh_section_t deh_section_weapon =
-{
- "Weapon",
- NULL,
- DEH_WeaponStart,
- DEH_WeaponParseLine,
- NULL,
- DEH_WeaponMD5Sum,
-};
-
--- a/src/doom/Makefile.am
+++ b/src/doom/Makefile.am
@@ -60,5 +60,21 @@
st_stuff.c st_stuff.h \
wi_stuff.c wi_stuff.h
-libdoom_a_SOURCES=$(SOURCE_FILES)
+FEATURE_DEHACKED_SOURCE_FILES = \
+deh_ammo.c \
+deh_cheat.c \
+deh_defs.h \
+deh_frame.c \
+deh_io.c deh_io.h \
+deh_main.c deh_main.h \
+deh_mapping.c deh_mapping.h \
+deh_misc.c deh_misc.h \
+deh_ptr.c \
+deh_sound.c \
+deh_text.c \
+deh_thing.c \
+deh_weapon.c
+
+libdoom_a_SOURCES = $(SOURCE_FILES) \
+ $(FEATURE_DEHACKED_SOURCE_FILES)
--- /dev/null
+++ b/src/doom/deh_ammo.c
@@ -1,0 +1,111 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Ammo" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "doomtype.h"
+#include "deh_defs.h"
+#include "deh_io.h"
+#include "deh_main.h"
+#include "p_local.h"
+
+static void *DEH_AmmoStart(deh_context_t *context, char *line)
+{
+ int ammo_number = 0;
+
+ if (sscanf(line, "Ammo %i", &ammo_number) != 1)
+ {
+ DEH_Warning(context, "Parse error on section start");
+ return NULL;
+ }
+
+ if (ammo_number < 0 || ammo_number >= NUMAMMO)
+ {
+ DEH_Warning(context, "Invalid ammo number: %i", ammo_number);
+ return NULL;
+ }
+
+ return &maxammo[ammo_number];
+}
+
+static void DEH_AmmoParseLine(deh_context_t *context, char *line, void *tag)
+{
+ char *variable_name, *value;
+ int ivalue;
+ int ammo_number;
+
+ if (tag == NULL)
+ return;
+
+ ammo_number = ((int *) tag) - maxammo;
+
+ // Parse the assignment
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+ ivalue = atoi(value);
+
+ // maxammo
+
+ if (!strcasecmp(variable_name, "Per ammo"))
+ clipammo[ammo_number] = ivalue;
+ else if (!strcasecmp(variable_name, "Max ammo"))
+ maxammo[ammo_number] = ivalue;
+ else
+ {
+ DEH_Warning(context, "Field named '%s' not found", variable_name);
+ }
+}
+
+static void DEH_AmmoMD5Hash(md5_context_t *context)
+{
+ int i;
+
+ for (i=0; i<NUMAMMO; ++i)
+ {
+ MD5_UpdateInt32(context, clipammo[i]);
+ MD5_UpdateInt32(context, maxammo[i]);
+ }
+}
+
+deh_section_t deh_section_ammo =
+{
+ "Ammo",
+ NULL,
+ DEH_AmmoStart,
+ DEH_AmmoParseLine,
+ NULL,
+ DEH_AmmoMD5Hash,
+};
+
--- /dev/null
+++ b/src/doom/deh_cheat.c
@@ -1,0 +1,148 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Cheat" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdlib.h>
+
+#include "doomtype.h"
+
+#include "deh_defs.h"
+#include "deh_io.h"
+#include "deh_main.h"
+#include "am_map.h"
+#include "st_stuff.h"
+
+typedef struct
+{
+ char *name;
+ cheatseq_t *seq;
+} deh_cheat_t;
+
+static deh_cheat_t allcheats[] =
+{
+ {"Change music", &cheat_mus },
+ {"Chainsaw", &cheat_choppers },
+ {"God mode", &cheat_god },
+ {"Ammo & Keys", &cheat_ammo },
+ {"Ammo", &cheat_ammonokey },
+ {"No Clipping 1", &cheat_noclip },
+ {"No Clipping 2", &cheat_commercial_noclip },
+ {"Invincibility", &cheat_powerup[0] },
+ {"Berserk", &cheat_powerup[1] },
+ {"Invisibility", &cheat_powerup[2] },
+ {"Radiation Suit", &cheat_powerup[3] },
+ {"Auto-map", &cheat_powerup[4] },
+ {"Lite-Amp Goggles", &cheat_powerup[5] },
+ {"BEHOLD menu", &cheat_powerup[6] },
+ {"Level Warp", &cheat_clev },
+ {"Player Position", &cheat_mypos },
+ {"Map cheat", &cheat_amap },
+};
+
+static deh_cheat_t *FindCheatByName(char *name)
+{
+ size_t i;
+
+ for (i=0; i<arrlen(allcheats); ++i)
+ {
+ if (!strcasecmp(allcheats[i].name, name))
+ return &allcheats[i];
+ }
+
+ return NULL;
+}
+
+static void *DEH_CheatStart(deh_context_t *context, char *line)
+{
+ return NULL;
+}
+
+static void DEH_CheatParseLine(deh_context_t *context, char *line, void *tag)
+{
+ deh_cheat_t *cheat;
+ char *variable_name;
+ char *value;
+ unsigned char *unsvalue;
+ unsigned int i;
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+ unsvalue = (unsigned char *) value;
+
+ cheat = FindCheatByName(variable_name);
+
+ if (cheat == NULL)
+ {
+ DEH_Warning(context, "Unknown cheat '%s'", variable_name);
+ return;
+ }
+
+ // write the value into the cheat sequence
+
+ i = 0;
+
+ while (unsvalue[i] != 0 && unsvalue[i] != 0xff)
+ {
+ // If the cheat length exceeds the Vanilla limit, stop. This
+ // does not apply if we have the limit turned off.
+
+ if (!deh_allow_long_cheats && i >= cheat->seq->sequence_len)
+ {
+ DEH_Warning(context, "Cheat sequence longer than supported by "
+ "Vanilla dehacked");
+ break;
+ }
+
+ cheat->seq->sequence[i] = unsvalue[i];
+ ++i;
+
+ // Absolute limit - don't exceed
+
+ if (i >= MAX_CHEAT_LEN - cheat->seq->parameter_chars)
+ {
+ DEH_Error(context, "Cheat sequence too long!");
+ return;
+ }
+ }
+
+ cheat->seq->sequence[i] = '\0';
+}
+
+deh_section_t deh_section_cheat =
+{
+ "Cheat",
+ NULL,
+ DEH_CheatStart,
+ DEH_CheatParseLine,
+ NULL,
+ NULL,
+};
+
--- /dev/null
+++ b/src/doom/deh_defs.h
@@ -1,0 +1,68 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Definitions for use in the dehacked code
+//
+//-----------------------------------------------------------------------------
+
+#ifndef DEH_DEFS_H
+#define DEH_DEFS_H
+
+#include "md5.h"
+
+typedef struct deh_context_s deh_context_t;
+typedef struct deh_section_s deh_section_t;
+typedef void (*deh_section_init_t)(void);
+typedef void *(*deh_section_start_t)(deh_context_t *context, char *line);
+typedef void (*deh_section_end_t)(deh_context_t *context, void *tag);
+typedef void (*deh_line_parser_t)(deh_context_t *context, char *line, void *tag);
+typedef void (*deh_md5_hash_t)(md5_context_t *context);
+
+struct deh_section_s
+{
+ char *name;
+
+ // Called on startup to initialise code
+
+ deh_section_init_t init;
+
+ // This is called when a new section is started. The pointer
+ // returned is used as a tag for the following calls.
+
+ deh_section_start_t start;
+
+ // This is called for each line in the section
+
+ deh_line_parser_t line_parser;
+
+ // This is called at the end of the section for any cleanup
+
+ deh_section_end_t end;
+
+ // Called when generating an MD5 sum of the dehacked state
+
+ deh_md5_hash_t md5_hash;
+};
+
+#endif /* #ifndef DEH_DEFS_H */
+
+
--- /dev/null
+++ b/src/doom/deh_frame.c
@@ -1,0 +1,169 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Frame" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdlib.h>
+
+#include "doomtype.h"
+#include "d_items.h"
+#include "info.h"
+
+#include "deh_defs.h"
+#include "deh_io.h"
+#include "deh_main.h"
+#include "deh_mapping.h"
+
+DEH_BEGIN_MAPPING(state_mapping, state_t)
+ DEH_MAPPING("Sprite number", sprite)
+ DEH_MAPPING("Sprite subnumber", frame)
+ DEH_MAPPING("Duration", tics)
+ DEH_MAPPING("Next frame", nextstate)
+ DEH_MAPPING("Unknown 1", misc1)
+ DEH_MAPPING("Unknown 2", misc2)
+ DEH_UNSUPPORTED_MAPPING("Codep frame")
+DEH_END_MAPPING
+
+static void *DEH_FrameStart(deh_context_t *context, char *line)
+{
+ int frame_number = 0;
+ state_t *state;
+
+ if (sscanf(line, "Frame %i", &frame_number) != 1)
+ {
+ DEH_Warning(context, "Parse error on section start");
+ return NULL;
+ }
+
+ if (frame_number < 0 || frame_number >= NUMSTATES)
+ {
+ DEH_Warning(context, "Invalid frame number: %i", frame_number);
+ return NULL;
+ }
+
+ if (frame_number >= DEH_VANILLA_NUMSTATES)
+ {
+ DEH_Warning(context, "Attempt to modify frame %i: this will cause "
+ "problems in Vanilla dehacked.", frame_number);
+ }
+
+ state = &states[frame_number];
+
+ return state;
+}
+
+// Simulate a frame overflow: Doom has 967 frames in the states[] array, but
+// DOS dehacked internally only allocates memory for 966. As a result,
+// attempts to set frame 966 (the last frame) will overflow the dehacked
+// array and overwrite the weaponinfo[] array instead.
+//
+// This is noticable in Batman Doom where it is impossible to switch weapons
+// away from the fist once selected.
+
+static void DEH_FrameOverflow(deh_context_t *context, char *varname, int value)
+{
+ if (!strcasecmp(varname, "Duration"))
+ {
+ weaponinfo[0].ammo = value;
+ }
+ else if (!strcasecmp(varname, "Codep frame"))
+ {
+ weaponinfo[0].upstate = value;
+ }
+ else if (!strcasecmp(varname, "Next frame"))
+ {
+ weaponinfo[0].downstate = value;
+ }
+ else if (!strcasecmp(varname, "Unknown 1"))
+ {
+ weaponinfo[0].readystate = value;
+ }
+ else if (!strcasecmp(varname, "Unknown 2"))
+ {
+ weaponinfo[0].atkstate = value;
+ }
+ else
+ {
+ DEH_Error(context, "Unable to simulate frame overflow: field '%s'",
+ varname);
+ }
+}
+
+static void DEH_FrameParseLine(deh_context_t *context, char *line, void *tag)
+{
+ state_t *state;
+ char *variable_name, *value;
+ int ivalue;
+
+ if (tag == NULL)
+ return;
+
+ state = (state_t *) tag;
+
+ // Parse the assignment
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+ // all values are integers
+
+ ivalue = atoi(value);
+
+ if (state == &states[NUMSTATES - 1])
+ {
+ DEH_FrameOverflow(context, variable_name, ivalue);
+ }
+ else
+ {
+ // set the appropriate field
+
+ DEH_SetMapping(context, &state_mapping, state, variable_name, ivalue);
+ }
+}
+
+static void DEH_FrameMD5Sum(md5_context_t *context)
+{
+ int i;
+
+ for (i=0; i<NUMSTATES; ++i)
+ {
+ DEH_StructMD5Sum(context, &state_mapping, &states[i]);
+ }
+}
+
+deh_section_t deh_section_frame =
+{
+ "Frame",
+ NULL,
+ DEH_FrameStart,
+ DEH_FrameParseLine,
+ NULL,
+ DEH_FrameMD5Sum,
+};
+
--- /dev/null
+++ b/src/doom/deh_io.c
@@ -1,0 +1,212 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Dehacked I/O code (does all reads from dehacked files)
+//
+//-----------------------------------------------------------------------------
+
+#include <stdarg.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "i_system.h"
+#include "z_zone.h"
+
+#include "deh_defs.h"
+#include "deh_io.h"
+
+struct deh_context_s
+{
+ FILE *stream;
+ char *filename;
+ int linenum;
+ boolean last_was_newline;
+ char *readbuffer;
+ int readbuffer_size;
+};
+
+// Open a dehacked file for reading
+// Returns NULL if open failed
+
+deh_context_t *DEH_OpenFile(char *filename)
+{
+ FILE *fstream;
+ deh_context_t *context;
+
+ fstream = fopen(filename, "r");
+
+ if (fstream == NULL)
+ return NULL;
+
+ context = Z_Malloc(sizeof(*context), PU_STATIC, NULL);
+ context->stream = fstream;
+
+ // Initial read buffer size of 128 bytes
+
+ context->readbuffer_size = 128;
+ context->readbuffer = Z_Malloc(context->readbuffer_size, PU_STATIC, NULL);
+ context->filename = filename;
+ context->linenum = 0;
+ context->last_was_newline = true;
+
+ return context;
+}
+
+// Close dehacked file
+
+void DEH_CloseFile(deh_context_t *context)
+{
+ fclose(context->stream);
+ Z_Free(context->readbuffer);
+ Z_Free(context);
+}
+
+// Reads a single character from a dehacked file
+
+int DEH_GetChar(deh_context_t *context)
+{
+ int result;
+
+ // Read characters, but ignore carriage returns
+ // Essentially this is a DOS->Unix conversion
+
+ do
+ {
+ if (feof(context->stream))
+ {
+ // end of file
+
+ result = -1;
+ }
+ else
+ {
+ result = fgetc(context->stream);
+ }
+
+ } while (result == '\r');
+
+ // Track the current line number
+
+ if (context->last_was_newline)
+ {
+ ++context->linenum;
+ }
+
+ context->last_was_newline = result == '\n';
+
+ return result;
+}
+
+// Increase the read buffer size
+
+static void IncreaseReadBuffer(deh_context_t *context)
+{
+ char *newbuffer;
+ int newbuffer_size;
+
+ newbuffer_size = context->readbuffer_size * 2;
+ newbuffer = Z_Malloc(newbuffer_size, PU_STATIC, NULL);
+
+ memcpy(newbuffer, context->readbuffer, context->readbuffer_size);
+
+ Z_Free(context->readbuffer);
+
+ context->readbuffer = newbuffer;
+ context->readbuffer_size = newbuffer_size;
+}
+
+// Read a whole line
+
+char *DEH_ReadLine(deh_context_t *context)
+{
+ int c;
+ int pos;
+
+ for (pos=0; ; ++pos)
+ {
+ c = DEH_GetChar(context);
+
+ if (c < 0)
+ {
+ // end of file
+
+ return NULL;
+ }
+
+ if (c == '\0')
+ {
+ return NULL;
+ }
+
+ // cope with lines of any length: increase the buffer size
+
+ if (pos >= context->readbuffer_size)
+ {
+ IncreaseReadBuffer(context);
+ }
+
+ if (c == '\n')
+ {
+ // end of line: a full line has been read
+
+ context->readbuffer[pos] = '\0';
+ break;
+ }
+ else
+ {
+ context->readbuffer[pos] = (char) c;
+ }
+ }
+
+ return context->readbuffer;
+}
+
+void DEH_Warning(deh_context_t *context, char *msg, ...)
+{
+ va_list args;
+
+ va_start(args, msg);
+
+ fprintf(stderr, "%s:%i: warning: ", context->filename, context->linenum);
+ vfprintf(stderr, msg, args);
+ fprintf(stderr, "\n");
+
+ va_end(args);
+}
+
+void DEH_Error(deh_context_t *context, char *msg, ...)
+{
+ va_list args;
+
+ va_start(args, msg);
+
+ fprintf(stderr, "%s:%i: ", context->filename, context->linenum);
+ vfprintf(stderr, msg, args);
+ fprintf(stderr, "\n");
+
+ va_end(args);
+
+ I_Error("Error parsing dehacked file");
+}
+
+
--- /dev/null
+++ b/src/doom/deh_io.h
@@ -1,0 +1,40 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Dehacked I/O code (does all reads from dehacked files)
+//
+//-----------------------------------------------------------------------------
+
+#ifndef DEH_IO_H
+#define DEH_IO_H
+
+#include "deh_defs.h"
+
+deh_context_t *DEH_OpenFile(char *filename);
+void DEH_CloseFile(deh_context_t *context);
+int DEH_GetChar(deh_context_t *context);
+char *DEH_ReadLine(deh_context_t *context);
+void DEH_Error(deh_context_t *context, char *msg, ...);
+void DEH_Warning(deh_context_t *context, char *msg, ...);
+
+#endif /* #ifndef DEH_IO_H */
+
--- /dev/null
+++ b/src/doom/deh_main.c
@@ -1,0 +1,408 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Main dehacked code
+//
+//-----------------------------------------------------------------------------
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <ctype.h>
+
+#include "doomtype.h"
+#include "d_iwad.h"
+#include "m_argv.h"
+
+#include "deh_defs.h"
+#include "deh_io.h"
+
+static char *deh_signatures[] =
+{
+ "Patch File for DeHackEd v2.3",
+ "Patch File for DeHackEd v3.0",
+};
+
+// deh_ammo.c:
+extern deh_section_t deh_section_ammo;
+// deh_cheat.c:
+extern deh_section_t deh_section_cheat;
+// deh_frame.c:
+extern deh_section_t deh_section_frame;
+// deh_misc.c:
+extern deh_section_t deh_section_misc;
+// deh_ptr.c:
+extern deh_section_t deh_section_pointer;
+// deh_sound.c
+extern deh_section_t deh_section_sound;
+// deh_text.c:
+extern deh_section_t deh_section_text;
+// deh_thing.c:
+extern deh_section_t deh_section_thing;
+// deh_weapon.c:
+extern deh_section_t deh_section_weapon;
+
+// If true, we can do long string replacements.
+
+boolean deh_allow_long_strings = false;
+
+// If true, we can do cheat replacements longer than the originals.
+
+boolean deh_allow_long_cheats = false;
+
+//
+// List of section types:
+//
+
+static deh_section_t *section_types[] =
+{
+ &deh_section_ammo,
+ &deh_section_cheat,
+ &deh_section_frame,
+ &deh_section_misc,
+ &deh_section_pointer,
+ &deh_section_sound,
+ &deh_section_text,
+ &deh_section_thing,
+ &deh_section_weapon,
+};
+
+void DEH_Checksum(md5_digest_t digest)
+{
+ md5_context_t md5_context;
+ unsigned int i;
+
+ MD5_Init(&md5_context);
+
+ for (i=0; i<arrlen(section_types); ++i)
+ {
+ if (section_types[i]->md5_hash != NULL)
+ {
+ section_types[i]->md5_hash(&md5_context);
+ }
+ }
+
+ MD5_Final(digest, &md5_context);
+}
+
+// Called on startup to call the Init functions
+
+static void InitialiseSections(void)
+{
+ unsigned int i;
+
+ for (i=0; i<arrlen(section_types); ++i)
+ {
+ if (section_types[i]->init != NULL)
+ {
+ section_types[i]->init();
+ }
+ }
+}
+
+// Given a section name, get the section structure which corresponds
+
+static deh_section_t *GetSectionByName(char *name)
+{
+ unsigned int i;
+
+ for (i=0; i<arrlen(section_types); ++i)
+ {
+ if (!strcasecmp(section_types[i]->name, name))
+ {
+ return section_types[i];
+ }
+ }
+
+ return NULL;
+}
+
+// Is the string passed just whitespace?
+
+static boolean IsWhitespace(char *s)
+{
+ for (; *s; ++s)
+ {
+ if (!isspace(*s))
+ return false;
+ }
+
+ return true;
+}
+
+// Strip whitespace from the start and end of a string
+
+static char *CleanString(char *s)
+{
+ char *strending;
+
+ // Leading whitespace
+
+ while (*s && isspace(*s))
+ ++s;
+
+ // Trailing whitespace
+
+ strending = s + strlen(s) - 1;
+
+ while (strlen(s) > 0 && isspace(*strending))
+ {
+ *strending = '\0';
+ --strending;
+ }
+
+ return s;
+}
+
+// This pattern is used a lot of times in different sections,
+// an assignment is essentially just a statement of the form:
+//
+// Variable Name = Value
+//
+// The variable name can include spaces or any other characters.
+// The string is split on the '=', essentially.
+//
+// Returns true if read correctly
+
+boolean DEH_ParseAssignment(char *line, char **variable_name, char **value)
+{
+ char *p;
+
+ // find the equals
+
+ p = strchr(line, '=');
+
+ if (p == NULL && p-line > 2)
+ {
+ return false;
+ }
+
+ // variable name at the start
+ // turn the '=' into a \0 to terminate the string here
+
+ *p = '\0';
+ *variable_name = CleanString(line);
+
+ // value immediately follows the '='
+
+ *value = CleanString(p+1);
+
+ return true;
+}
+
+static boolean CheckSignatures(deh_context_t *context)
+{
+ size_t i;
+ char *line;
+
+ // Read the first line
+
+ line = DEH_ReadLine(context);
+
+ if (line == NULL)
+ {
+ return false;
+ }
+
+ // Check all signatures to see if one matches
+
+ for (i=0; i<arrlen(deh_signatures); ++i)
+ {
+ if (!strcmp(deh_signatures[i], line))
+ {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+// Parses a comment string in a dehacked file.
+
+static void DEH_ParseComment(char *comment)
+{
+ // Allow comments containing this special value to allow string
+ // replacements longer than those permitted by DOS dehacked.
+ // This allows us to use a dehacked patch for doing string
+ // replacements for emulating Chex Quest.
+ //
+ // If you use this, your dehacked patch may not work in Vanilla
+ // Doom.
+
+ if (strstr(comment, "*allow-long-strings*") != NULL)
+ {
+ deh_allow_long_strings = true;
+ }
+
+ // Allow magic comments to allow longer cheat replacements than
+ // those permitted by DOS dehacked. This is also for Chex
+ // Quest.
+
+ if (strstr(comment, "*allow-long-cheats*") != NULL)
+ {
+ deh_allow_long_cheats = true;
+ }
+}
+
+// Parses a dehacked file by reading from the context
+
+static void DEH_ParseContext(deh_context_t *context)
+{
+ deh_section_t *current_section = NULL;
+ char section_name[20];
+ void *tag = NULL;
+ char *line;
+
+ // Read the header and check it matches the signature
+
+ if (!CheckSignatures(context))
+ {
+ DEH_Error(context, "This is not a valid dehacked patch file!");
+ }
+
+ deh_allow_long_strings = false;
+ deh_allow_long_cheats = false;
+
+ // Read the file
+
+ for (;;)
+ {
+ // read a new line
+
+ line = DEH_ReadLine(context);
+
+ // end of file?
+
+ if (line == NULL)
+ return;
+
+ while (line[0] != '\0' && isspace(line[0]))
+ ++line;
+
+ if (line[0] == '#')
+ {
+ // comment
+
+ DEH_ParseComment(line);
+ continue;
+ }
+
+ if (IsWhitespace(line))
+ {
+ if (current_section != NULL)
+ {
+ // end of section
+
+ if (current_section->end != NULL)
+ {
+ current_section->end(context, tag);
+ }
+
+ //printf("end %s tag\n", current_section->name);
+ current_section = NULL;
+ }
+ }
+ else
+ {
+ if (current_section != NULL)
+ {
+ // parse this line
+
+ current_section->line_parser(context, line, tag);
+ }
+ else
+ {
+ // possibly the start of a new section
+
+ sscanf(line, "%19s", section_name);
+
+ current_section = GetSectionByName(section_name);
+
+ if (current_section != NULL)
+ {
+ tag = current_section->start(context, line);
+ //printf("started %s tag\n", section_name);
+ }
+ else
+ {
+ //printf("unknown section name %s\n", section_name);
+ }
+ }
+ }
+ }
+}
+
+// Parses a dehacked file
+
+int DEH_LoadFile(char *filename)
+{
+ deh_context_t *context;
+
+ printf(" loading %s\n", filename);
+
+ context = DEH_OpenFile(filename);
+
+ if (context == NULL)
+ {
+ fprintf(stderr, "DEH_LoadFile: Unable to open %s\n", filename);
+ return 0;
+ }
+
+ DEH_ParseContext(context);
+
+ DEH_CloseFile(context);
+
+ return 1;
+}
+
+// Checks the command line for -deh argument
+
+void DEH_Init(void)
+{
+ char *filename;
+ int p;
+
+ InitialiseSections();
+
+ //!
+ // @arg <files>
+ // @category mod
+ //
+ // Load the given dehacked patch(es)
+ //
+
+ p = M_CheckParm("-deh");
+
+ if (p > 0)
+ {
+ ++p;
+
+ while (p < myargc && myargv[p][0] != '-')
+ {
+ filename = D_TryFindWADByName(myargv[p]);
+ DEH_LoadFile(filename);
+ ++p;
+ }
+ }
+}
+
+
--- /dev/null
+++ b/src/doom/deh_main.h
@@ -1,0 +1,53 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Dehacked entrypoint and common code
+//
+//-----------------------------------------------------------------------------
+
+#ifndef DEH_MAIN_H
+#define DEH_MAIN_H
+
+#include "doomtype.h"
+#include "doomfeatures.h"
+#include "md5.h"
+#include "deh_str.h"
+
+// These are the limits that dehacked uses (from dheinit.h in the dehacked
+// source). If these limits are exceeded, it does not generate an error, but
+// a warning is displayed.
+
+#define DEH_VANILLA_NUMSTATES 966
+#define DEH_VANILLA_NUMSFX 107
+
+void DEH_Init(void);
+int DEH_LoadFile(char *filename);
+
+boolean DEH_ParseAssignment(char *line, char **variable_name, char **value);
+
+void DEH_Checksum(md5_digest_t digest);
+
+extern boolean deh_allow_long_strings;
+extern boolean deh_allow_long_cheats;
+
+#endif /* #ifndef DEH_MAIN_H */
+
--- /dev/null
+++ b/src/doom/deh_mapping.c
@@ -1,0 +1,133 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Dehacked "mapping" code
+// Allows the fields in structures to be mapped out and accessed by
+// name
+//
+//-----------------------------------------------------------------------------
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "doomtype.h"
+#include "i_system.h"
+#include "deh_mapping.h"
+
+//
+// Set the value of a particular field in a structure by name
+//
+
+boolean DEH_SetMapping(deh_context_t *context, deh_mapping_t *mapping,
+ void *structptr, char *name, int value)
+{
+ int i;
+
+ for (i=0; mapping->entries[i].name != NULL; ++i)
+ {
+ deh_mapping_entry_t *entry = &mapping->entries[i];
+
+ if (!strcasecmp(entry->name, name))
+ {
+ void *location;
+
+ if (entry->location == NULL)
+ {
+ DEH_Warning(context, "Field '%s' is unsupported", name);
+ return false;
+ }
+
+ location = (uint8_t *)structptr + ((uint8_t *)entry->location - (uint8_t *)mapping->base);
+
+ // printf("Setting %p::%s to %i (%i bytes)\n",
+ // structptr, name, value, entry->size);
+
+ switch (entry->size)
+ {
+ case 1:
+ * ((uint8_t *) location) = value;
+ break;
+ case 2:
+ * ((uint16_t *) location) = value;
+ break;
+ case 4:
+ * ((uint32_t *) location) = value;
+ break;
+ default:
+ DEH_Error(context, "Unknown field type for '%s' (BUG)", name);
+ return false;
+ }
+
+ return true;
+ }
+ }
+
+ // field with this name not found
+
+ DEH_Warning(context, "Field named '%s' not found", name);
+
+ return false;
+}
+
+void DEH_StructMD5Sum(md5_context_t *context, deh_mapping_t *mapping,
+ void *structptr)
+{
+ int i;
+
+ // Go through each mapping
+
+ for (i=0; mapping->entries[i].name != NULL; ++i)
+ {
+ deh_mapping_entry_t *entry = &mapping->entries[i];
+ void *location;
+
+ if (entry->location == NULL)
+ {
+ // Unsupported field
+
+ continue;
+ }
+
+ // Add in data for this field
+
+ location = (uint8_t *)structptr + ((uint8_t *)entry->location - (uint8_t *)mapping->base);
+
+ switch (entry->size)
+ {
+ case 1:
+ MD5_UpdateInt32(context, *((uint8_t *) location));
+ break;
+ case 2:
+ MD5_UpdateInt32(context, *((uint16_t *) location));
+ break;
+ case 4:
+ MD5_UpdateInt32(context, *((uint32_t *) location));
+ break;
+ default:
+ I_Error("Unknown dehacked mapping field type for '%s' (BUG)",
+ entry->name);
+ break;
+ }
+ }
+}
+
--- /dev/null
+++ b/src/doom/deh_mapping.h
@@ -1,0 +1,90 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Dehacked "mapping" code
+// Allows the fields in structures to be mapped out and accessed by
+// name
+//
+//-----------------------------------------------------------------------------
+
+#ifndef DEH_MAPPING_H
+#define DEH_MAPPING_H
+
+#include "doomtype.h"
+#include "deh_io.h"
+#include "md5.h"
+
+#define DEH_BEGIN_MAPPING(mapping_name, structname) \
+ static structname deh_mapping_base; \
+ static deh_mapping_t mapping_name = \
+ { \
+ &deh_mapping_base, \
+ {
+
+#define DEH_MAPPING(deh_name, fieldname) \
+ {deh_name, &deh_mapping_base.fieldname, \
+ sizeof(deh_mapping_base.fieldname)},
+
+#define DEH_UNSUPPORTED_MAPPING(deh_name) \
+ {deh_name, NULL, -1},
+
+#define DEH_END_MAPPING \
+ {NULL, NULL, -1} \
+ } \
+ };
+
+
+
+#define MAX_MAPPING_ENTRIES 32
+
+typedef struct deh_mapping_s deh_mapping_t;
+typedef struct deh_mapping_entry_s deh_mapping_entry_t;
+
+struct deh_mapping_entry_s
+{
+ // field name
+
+ char *name;
+
+ // location relative to the base in the deh_mapping_t struct
+ // If this is NULL, it is an unsupported mapping
+
+ void *location;
+
+ // field size
+
+ int size;
+};
+
+struct deh_mapping_s
+{
+ void *base;
+ deh_mapping_entry_t entries[MAX_MAPPING_ENTRIES];
+};
+
+boolean DEH_SetMapping(deh_context_t *context, deh_mapping_t *mapping,
+ void *structptr, char *name, int value);
+void DEH_StructMD5Sum(md5_context_t *context, deh_mapping_t *mapping,
+ void *structptr);
+
+#endif /* #ifndef DEH_MAPPING_H */
+
--- /dev/null
+++ b/src/doom/deh_misc.c
@@ -1,0 +1,237 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Misc" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "doomtype.h"
+#include "deh_defs.h"
+#include "deh_io.h"
+#include "deh_main.h"
+#include "deh_misc.h"
+
+// Dehacked: "Initial Health"
+// This is the initial health a player has when starting anew.
+// See G_PlayerReborn in g_game.c
+
+int deh_initial_health = DEH_DEFAULT_INITIAL_HEALTH;
+
+// Dehacked: "Initial bullets"
+// This is the number of bullets the player has when starting anew.
+// See G_PlayerReborn in g_game.c
+
+int deh_initial_bullets = DEH_DEFAULT_INITIAL_BULLETS;
+
+// Dehacked: "Max Health"
+// This is the maximum health that can be reached using medikits
+// alone. See P_TouchSpecialThing in p_inter.c
+
+int deh_max_health = DEH_DEFAULT_MAX_HEALTH;
+
+// Dehacked: "Max Armor"
+// This is the maximum armor which can be reached by picking up
+// armor helmets. See P_TouchSpecialThing in p_inter.c
+
+int deh_max_armor = DEH_DEFAULT_MAX_ARMOR;
+
+// Dehacked: "Green Armor Class"
+// This is the armor class that is given when picking up the green
+// armor or an armor helmet. See P_TouchSpecialThing in p_inter.c
+//
+// DOS dehacked only modifies the behavior of the green armor shirt,
+// the armor class set by armor helmets is not affected.
+
+int deh_green_armor_class = DEH_DEFAULT_GREEN_ARMOR_CLASS;
+
+// Dehacked: "Blue Armor Class"
+// This is the armor class that is given when picking up the blue
+// armor or a megasphere. See P_TouchSpecialThing in p_inter.c
+//
+// DOS dehacked only modifies the MegaArmor behavior and not
+// the MegaSphere, which always gives armor type 2.
+
+int deh_blue_armor_class = DEH_DEFAULT_BLUE_ARMOR_CLASS;
+
+// Dehacked: "Max soulsphere"
+// The maximum health which can be reached by picking up the
+// soulsphere. See P_TouchSpecialThing in p_inter.c
+
+int deh_max_soulsphere = DEH_DEFAULT_MAX_SOULSPHERE;
+
+// Dehacked: "Soulsphere health"
+// The amount of health bonus that picking up a soulsphere
+// gives. See P_TouchSpecialThing in p_inter.c
+
+int deh_soulsphere_health = DEH_DEFAULT_SOULSPHERE_HEALTH;
+
+// Dehacked: "Megasphere health"
+// This is what the health is set to after picking up a
+// megasphere. See P_TouchSpecialThing in p_inter.c
+
+int deh_megasphere_health = DEH_DEFAULT_MEGASPHERE_HEALTH;
+
+// Dehacked: "God mode health"
+// This is what the health value is set to when cheating using
+// the IDDQD god mode cheat. See ST_Responder in st_stuff.c
+
+int deh_god_mode_health = DEH_DEFAULT_GOD_MODE_HEALTH;
+
+// Dehacked: "IDFA Armor"
+// This is what the armor is set to when using the IDFA cheat.
+// See ST_Responder in st_stuff.c
+
+int deh_idfa_armor = DEH_DEFAULT_IDFA_ARMOR;
+
+// Dehacked: "IDFA Armor Class"
+// This is what the armor class is set to when using the IDFA cheat.
+// See ST_Responder in st_stuff.c
+
+int deh_idfa_armor_class = DEH_DEFAULT_IDFA_ARMOR_CLASS;
+
+// Dehacked: "IDKFA Armor"
+// This is what the armor is set to when using the IDKFA cheat.
+// See ST_Responder in st_stuff.c
+
+int deh_idkfa_armor = DEH_DEFAULT_IDKFA_ARMOR;
+
+// Dehacked: "IDKFA Armor Class"
+// This is what the armor class is set to when using the IDKFA cheat.
+// See ST_Responder in st_stuff.c
+
+int deh_idkfa_armor_class = DEH_DEFAULT_IDKFA_ARMOR_CLASS;
+
+// Dehacked: "BFG Cells/Shot"
+// This is the number of CELLs firing the BFG uses up.
+// See P_CheckAmmo and A_FireBFG in p_pspr.c
+
+int deh_bfg_cells_per_shot = DEH_DEFAULT_BFG_CELLS_PER_SHOT;
+
+// Dehacked: "Monsters infight"
+// This controls whether monsters can harm other monsters of the same
+// species. For example, whether an imp fireball will damage other
+// imps. The value of this in dehacked patches is weird - '202' means
+// off, while '221' means on.
+//
+// See PIT_CheckThing in p_map.c
+
+int deh_species_infighting = DEH_DEFAULT_SPECIES_INFIGHTING;
+
+static struct
+{
+ char *deh_name;
+ int *value;
+} misc_settings[] = {
+ {"Initial Health", &deh_initial_health},
+ {"Initial Bullets", &deh_initial_bullets},
+ {"Max Health", &deh_max_health},
+ {"Max Armor", &deh_max_armor},
+ {"Green Armor Class", &deh_green_armor_class},
+ {"Blue Armor Class", &deh_blue_armor_class},
+ {"Max Soulsphere", &deh_max_soulsphere},
+ {"Soulsphere Health", &deh_soulsphere_health},
+ {"Megasphere Health", &deh_megasphere_health},
+ {"God Mode Health", &deh_god_mode_health},
+ {"IDFA Armor", &deh_idfa_armor},
+ {"IDFA Armor Class", &deh_idfa_armor_class},
+ {"IDKFA Armor", &deh_idkfa_armor},
+ {"IDKFA Armor Class", &deh_idkfa_armor_class},
+ {"BFG Cells/Shot", &deh_bfg_cells_per_shot},
+};
+
+static void *DEH_MiscStart(deh_context_t *context, char *line)
+{
+ return NULL;
+}
+
+static void DEH_MiscParseLine(deh_context_t *context, char *line, void *tag)
+{
+ char *variable_name, *value;
+ int ivalue;
+ size_t i;
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+ ivalue = atoi(value);
+
+ if (!strcasecmp(variable_name, "Monsters Infight"))
+ {
+ // See notes above.
+
+ if (ivalue == 202)
+ {
+ deh_species_infighting = 0;
+ }
+ else if (ivalue == 221)
+ {
+ deh_species_infighting = 1;
+ }
+ else
+ {
+ DEH_Warning(context,
+ "Invalid value for 'Monsters Infight': %i", ivalue);
+ }
+
+ return;
+ }
+
+ for (i=0; i<arrlen(misc_settings); ++i)
+ {
+ if (!strcasecmp(variable_name, misc_settings[i].deh_name))
+ {
+ *misc_settings[i].value = ivalue;
+ return;
+ }
+ }
+
+ DEH_Warning(context, "Unknown Misc variable '%s'", variable_name);
+}
+
+static void DEH_MiscMD5Sum(md5_context_t *context)
+{
+ unsigned int i;
+
+ for (i=0; i<arrlen(misc_settings); ++i)
+ {
+ MD5_UpdateInt32(context, *misc_settings[i].value);
+ }
+}
+
+deh_section_t deh_section_misc =
+{
+ "Misc",
+ NULL,
+ DEH_MiscStart,
+ DEH_MiscParseLine,
+ NULL,
+ DEH_MiscMD5Sum,
+};
+
--- /dev/null
+++ b/src/doom/deh_misc.h
@@ -1,0 +1,92 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Misc" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#ifndef DEH_MISC_H
+#define DEH_MISC_H
+
+#include "doomfeatures.h"
+
+#define DEH_DEFAULT_INITIAL_HEALTH 100
+#define DEH_DEFAULT_INITIAL_BULLETS 50
+#define DEH_DEFAULT_MAX_HEALTH 200
+#define DEH_DEFAULT_MAX_ARMOR 200
+#define DEH_DEFAULT_GREEN_ARMOR_CLASS 1
+#define DEH_DEFAULT_BLUE_ARMOR_CLASS 2
+#define DEH_DEFAULT_MAX_SOULSPHERE 200
+#define DEH_DEFAULT_SOULSPHERE_HEALTH 100
+#define DEH_DEFAULT_MEGASPHERE_HEALTH 200
+#define DEH_DEFAULT_GOD_MODE_HEALTH 100
+#define DEH_DEFAULT_IDFA_ARMOR 200
+#define DEH_DEFAULT_IDFA_ARMOR_CLASS 2
+#define DEH_DEFAULT_IDKFA_ARMOR 200
+#define DEH_DEFAULT_IDKFA_ARMOR_CLASS 2
+#define DEH_DEFAULT_BFG_CELLS_PER_SHOT 40
+#define DEH_DEFAULT_SPECIES_INFIGHTING 0
+
+#ifdef FEATURE_DEHACKED
+
+extern int deh_initial_health;
+extern int deh_initial_bullets;
+extern int deh_max_health;
+extern int deh_max_armor;
+extern int deh_green_armor_class;
+extern int deh_blue_armor_class;
+extern int deh_max_soulsphere;
+extern int deh_soulsphere_health;
+extern int deh_megasphere_health;
+extern int deh_god_mode_health;
+extern int deh_idfa_armor;
+extern int deh_idfa_armor_class;
+extern int deh_idkfa_armor;
+extern int deh_idkfa_armor_class;
+extern int deh_bfg_cells_per_shot;
+extern int deh_species_infighting;
+
+#else
+
+// If dehacked is disabled, hard coded values
+
+#define deh_initial_health DEH_DEFAULT_INITIAL_HEALTH
+#define deh_initial_bullets DEH_DEFAULT_INITIAL_BULLETS
+#define deh_max_health DEH_DEFAULT_MAX_HEALTH
+#define deh_max_armor DEH_DEFAULT_MAX_ARMOR
+#define deh_green_armor_class DEH_DEFAULT_GREEN_ARMOR_CLASS
+#define deh_blue_armor_class DEH_DEFAULT_BLUE_ARMOR_CLASS
+#define deh_max_soulsphere DEH_DEFAULT_MAX_SOULSPHERE
+#define deh_soulsphere_health DEH_DEFAULT_SOULSPHERE_HEALTH
+#define deh_megasphere_health DEH_DEFAULT_MEGASPHERE_HEALTH
+#define deh_god_mode_health DEH_DEFAULT_GOD_MODE_HEALTH
+#define deh_idfa_armor DEH_DEFAULT_IDFA_ARMOR
+#define deh_idfa_armor_class DEH_DEFAULT_IDFA_ARMOR_CLASS
+#define deh_idkfa_armor DEH_DEFAULT_IDKFA_ARMOR
+#define deh_idkfa_armor_class DEH_DEFAULT_IDKFA_ARMOR_CLASS
+#define deh_bfg_cells_per_shot DEH_DEFAULT_BFG_CELLS_PER_SHOT
+#define deh_species_infighting DEH_DEFAULT_SPECIES_INFIGHTING
+
+#endif
+
+#endif /* #ifndef DEH_MISC_H */
+
--- /dev/null
+++ b/src/doom/deh_ptr.c
@@ -1,0 +1,151 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses Action Pointer entries in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "doomtype.h"
+#include "info.h"
+
+#include "deh_defs.h"
+#include "deh_io.h"
+#include "deh_main.h"
+
+static actionf_t codeptrs[NUMSTATES];
+
+static int CodePointerIndex(actionf_t *ptr)
+{
+ int i;
+
+ for (i=0; i<NUMSTATES; ++i)
+ {
+ if (!memcmp(&codeptrs[i], ptr, sizeof(actionf_t)))
+ {
+ return i;
+ }
+ }
+
+ return -1;
+}
+
+static void DEH_PointerInit(void)
+{
+ int i;
+
+ // Initialise list of dehacked pointers
+
+ for (i=0; i<NUMSTATES; ++i)
+ codeptrs[i] = states[i].action;
+}
+
+static void *DEH_PointerStart(deh_context_t *context, char *line)
+{
+ int frame_number = 0;
+
+ // FIXME: can the third argument here be something other than "Frame"
+ // or are we ok?
+
+ if (sscanf(line, "Pointer %*i (%*s %i)", &frame_number) != 1)
+ {
+ DEH_Warning(context, "Parse error on section start");
+ return NULL;
+ }
+
+ if (frame_number < 0 || frame_number >= NUMSTATES)
+ {
+ DEH_Warning(context, "Invalid frame number: %i", frame_number);
+ return NULL;
+ }
+
+ return &states[frame_number];
+}
+
+static void DEH_PointerParseLine(deh_context_t *context, char *line, void *tag)
+{
+ state_t *state;
+ char *variable_name, *value;
+ int ivalue;
+
+ if (tag == NULL)
+ return;
+
+ state = (state_t *) tag;
+
+ // Parse the assignment
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+// printf("Set %s to %s for state\n", variable_name, value);
+
+ // all values are integers
+
+ ivalue = atoi(value);
+
+ // set the appropriate field
+
+ if (!strcasecmp(variable_name, "Codep frame"))
+ {
+ if (ivalue < 0 || ivalue >= NUMSTATES)
+ {
+ DEH_Warning(context, "Invalid state '%i'", ivalue);
+ }
+ else
+ {
+ state->action = codeptrs[ivalue];
+ }
+ }
+ else
+ {
+ DEH_Warning(context, "Unknown variable name '%s'", variable_name);
+ }
+}
+
+static void DEH_PointerMD5Sum(md5_context_t *context)
+{
+ int i;
+
+ for (i=0; i<NUMSTATES; ++i)
+ {
+ MD5_UpdateInt32(context, CodePointerIndex(&states[i].action));
+ }
+}
+
+deh_section_t deh_section_pointer =
+{
+ "Pointer",
+ DEH_PointerInit,
+ DEH_PointerStart,
+ DEH_PointerParseLine,
+ NULL,
+ DEH_PointerMD5Sum,
+};
+
--- /dev/null
+++ b/src/doom/deh_sound.c
@@ -1,0 +1,113 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Sound" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "doomfeatures.h"
+#include "doomtype.h"
+#include "deh_defs.h"
+#include "deh_main.h"
+#include "deh_mapping.h"
+#include "sounds.h"
+
+DEH_BEGIN_MAPPING(sound_mapping, sfxinfo_t)
+ DEH_UNSUPPORTED_MAPPING("Offset")
+ DEH_MAPPING("Zero/One", singularity)
+ DEH_MAPPING("Value", priority)
+ DEH_MAPPING("Zero 1", link)
+ DEH_MAPPING("Zero 2", pitch)
+ DEH_MAPPING("Zero 3", volume)
+ DEH_MAPPING("Zero 4", data)
+ DEH_MAPPING("Neg. One 1", usefulness)
+ DEH_MAPPING("Neg. One 2", lumpnum)
+DEH_END_MAPPING
+
+static void *DEH_SoundStart(deh_context_t *context, char *line)
+{
+ int sound_number = 0;
+
+ if (sscanf(line, "Sound %i", &sound_number) != 1)
+ {
+ DEH_Warning(context, "Parse error on section start");
+ return NULL;
+ }
+
+ if (sound_number < 0 || sound_number >= NUMSFX)
+ {
+ DEH_Warning(context, "Invalid sound number: %i", sound_number);
+ return NULL;
+ }
+
+ if (sound_number >= DEH_VANILLA_NUMSFX)
+ {
+ DEH_Warning(context, "Attempt to modify SFX %i. This will cause "
+ "problems in Vanilla dehacked.", sound_number);
+ }
+
+ return &S_sfx[sound_number];
+}
+
+static void DEH_SoundParseLine(deh_context_t *context, char *line, void *tag)
+{
+ sfxinfo_t *sfx;
+ char *variable_name, *value;
+ int ivalue;
+
+ if (tag == NULL)
+ return;
+
+ sfx = (sfxinfo_t *) tag;
+
+ // Parse the assignment
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+ // all values are integers
+
+ ivalue = atoi(value);
+
+ // Set the field value
+
+ DEH_SetMapping(context, &sound_mapping, sfx, variable_name, ivalue);
+
+}
+
+deh_section_t deh_section_sound =
+{
+ "Sound",
+ NULL,
+ DEH_SoundStart,
+ DEH_SoundParseLine,
+ NULL,
+ NULL,
+};
+
--- /dev/null
+++ b/src/doom/deh_text.c
@@ -1,0 +1,126 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses Text substitution sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <string.h>
+
+#include "doomtype.h"
+
+#include "z_zone.h"
+
+#include "deh_defs.h"
+#include "deh_io.h"
+#include "deh_main.h"
+
+// Given a string length, find the maximum length of a
+// string that can replace it.
+
+static int TXT_MaxStringLength(int len)
+{
+ // Enough bytes for the string and the NUL terminator
+
+ len += 1;
+
+ // All strings in doom.exe are on 4-byte boundaries, so we may be able
+ // to support a slightly longer string.
+ // Extend up to the next 4-byte boundary
+
+ len += (4 - (len % 4)) % 4;
+
+ // Less one for the NUL terminator.
+
+ return len - 1;
+}
+
+static void *DEH_TextStart(deh_context_t *context, char *line)
+{
+ char *from_text, *to_text;
+ int fromlen, tolen;
+ int i;
+
+ if (sscanf(line, "Text %i %i", &fromlen, &tolen) != 2)
+ {
+ DEH_Warning(context, "Parse error on section start");
+ return NULL;
+ }
+
+ // Only allow string replacements that are possible in Vanilla Doom.
+ // Chocolate Doom is unforgiving!
+
+ if (!deh_allow_long_strings && tolen > TXT_MaxStringLength(fromlen))
+ {
+ DEH_Error(context, "Replacement string is longer than the maximum "
+ "possible in doom.exe");
+ return NULL;
+ }
+
+ from_text = Z_Malloc(fromlen + 1, PU_STATIC, NULL);
+ to_text = Z_Malloc(tolen + 1, PU_STATIC, NULL);
+
+ // read in the "from" text
+
+ for (i=0; i<fromlen; ++i)
+ {
+ int c;
+
+ c = DEH_GetChar(context);
+
+ from_text[i] = c;
+ }
+
+ from_text[fromlen] = '\0';
+
+ // read in the "to" text
+
+ for (i=0; i<tolen; ++i)
+ {
+ int c;
+
+ c = DEH_GetChar(context);
+
+ to_text[i] = c;
+ }
+ to_text[tolen] = '\0';
+
+ DEH_AddStringReplacement(from_text, to_text);
+
+ return NULL;
+}
+
+static void DEH_TextParseLine(deh_context_t *context, char *line, void *tag)
+{
+ // not used
+}
+
+deh_section_t deh_section_text =
+{
+ "Text",
+ NULL,
+ DEH_TextStart,
+ DEH_TextParseLine,
+ NULL,
+ NULL,
+};
+
--- /dev/null
+++ b/src/doom/deh_thing.c
@@ -1,0 +1,140 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Thing" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "doomtype.h"
+
+#include "deh_defs.h"
+#include "deh_main.h"
+#include "deh_mapping.h"
+
+#include "info.h"
+
+DEH_BEGIN_MAPPING(thing_mapping, mobjinfo_t)
+ DEH_MAPPING("ID #", doomednum)
+ DEH_MAPPING("Initial frame", spawnstate)
+ DEH_MAPPING("Hit points", spawnhealth)
+ DEH_MAPPING("First moving frame", seestate)
+ DEH_MAPPING("Alert sound", seesound)
+ DEH_MAPPING("Reaction time", reactiontime)
+ DEH_MAPPING("Attack sound", attacksound)
+ DEH_MAPPING("Injury frame", painstate)
+ DEH_MAPPING("Pain chance", painchance)
+ DEH_MAPPING("Pain sound", painsound)
+ DEH_MAPPING("Close attack frame", meleestate)
+ DEH_MAPPING("Far attack frame", missilestate)
+ DEH_MAPPING("Death frame", deathstate)
+ DEH_MAPPING("Exploding frame", xdeathstate)
+ DEH_MAPPING("Death sound", deathsound)
+ DEH_MAPPING("Speed", speed)
+ DEH_MAPPING("Width", radius)
+ DEH_MAPPING("Height", height)
+ DEH_MAPPING("Mass", mass)
+ DEH_MAPPING("Missile damage", damage)
+ DEH_MAPPING("Action sound", activesound)
+ DEH_MAPPING("Bits", flags)
+ DEH_MAPPING("Respawn frame", raisestate)
+DEH_END_MAPPING
+
+static void *DEH_ThingStart(deh_context_t *context, char *line)
+{
+ int thing_number = 0;
+ mobjinfo_t *mobj;
+
+ if (sscanf(line, "Thing %i", &thing_number) != 1)
+ {
+ DEH_Warning(context, "Parse error on section start");
+ return NULL;
+ }
+
+ // dehacked files are indexed from 1
+ --thing_number;
+
+ if (thing_number < 0 || thing_number >= NUMMOBJTYPES)
+ {
+ DEH_Warning(context, "Invalid thing number: %i", thing_number);
+ return NULL;
+ }
+
+ mobj = &mobjinfo[thing_number];
+
+ return mobj;
+}
+
+static void DEH_ThingParseLine(deh_context_t *context, char *line, void *tag)
+{
+ mobjinfo_t *mobj;
+ char *variable_name, *value;
+ int ivalue;
+
+ if (tag == NULL)
+ return;
+
+ mobj = (mobjinfo_t *) tag;
+
+ // Parse the assignment
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+// printf("Set %s to %s for mobj\n", variable_name, value);
+
+ // all values are integers
+
+ ivalue = atoi(value);
+
+ // Set the field value
+
+ DEH_SetMapping(context, &thing_mapping, mobj, variable_name, ivalue);
+}
+
+static void DEH_ThingMD5Sum(md5_context_t *context)
+{
+ int i;
+
+ for (i=0; i<NUMMOBJTYPES; ++i)
+ {
+ DEH_StructMD5Sum(context, &thing_mapping, &mobjinfo[i]);
+ }
+}
+
+deh_section_t deh_section_thing =
+{
+ "Thing",
+ NULL,
+ DEH_ThingStart,
+ DEH_ThingParseLine,
+ NULL,
+ DEH_ThingMD5Sum,
+};
+
--- /dev/null
+++ b/src/doom/deh_weapon.c
@@ -1,0 +1,109 @@
+// Emacs style mode select -*- C++ -*-
+//-----------------------------------------------------------------------------
+//
+// Copyright(C) 2005 Simon Howard
+//
+// This program is free software; you can redistribute it and/or
+// modify it under the terms of the GNU General Public License
+// as published by the Free Software Foundation; either version 2
+// 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. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+// 02111-1307, USA.
+//
+//-----------------------------------------------------------------------------
+//
+// Parses "Weapon" sections in dehacked files
+//
+//-----------------------------------------------------------------------------
+
+#include <stdlib.h>
+#include <string.h>
+
+#include "doomtype.h"
+
+#include "d_items.h"
+
+#include "deh_defs.h"
+#include "deh_main.h"
+#include "deh_mapping.h"
+
+DEH_BEGIN_MAPPING(weapon_mapping, weaponinfo_t)
+ DEH_MAPPING("Ammo type", ammo)
+ DEH_MAPPING("Deselect frame", upstate)
+ DEH_MAPPING("Select frame", downstate)
+ DEH_MAPPING("Bobbing frame", readystate)
+ DEH_MAPPING("Shooting frame", atkstate)
+ DEH_MAPPING("Firing frame", flashstate)
+DEH_END_MAPPING
+
+static void *DEH_WeaponStart(deh_context_t *context, char *line)
+{
+ int weapon_number = 0;
+
+ if (sscanf(line, "Weapon %i", &weapon_number) != 1)
+ {
+ DEH_Warning(context, "Parse error on section start");
+ return NULL;
+ }
+
+ if (weapon_number < 0 || weapon_number >= NUMWEAPONS)
+ {
+ DEH_Warning(context, "Invalid weapon number: %i", weapon_number);
+ return NULL;
+ }
+
+ return &weaponinfo[weapon_number];
+}
+
+static void DEH_WeaponParseLine(deh_context_t *context, char *line, void *tag)
+{
+ char *variable_name, *value;
+ weaponinfo_t *weapon;
+ int ivalue;
+
+ if (tag == NULL)
+ return;
+
+ weapon = (weaponinfo_t *) tag;
+
+ if (!DEH_ParseAssignment(line, &variable_name, &value))
+ {
+ // Failed to parse
+
+ DEH_Warning(context, "Failed to parse assignment");
+ return;
+ }
+
+ ivalue = atoi(value);
+
+ DEH_SetMapping(context, &weapon_mapping, weapon, variable_name, ivalue);
+}
+
+static void DEH_WeaponMD5Sum(md5_context_t *context)
+{
+ int i;
+
+ for (i=0; i<NUMWEAPONS ;++i)
+ {
+ DEH_StructMD5Sum(context, &weapon_mapping, &weaponinfo[i]);
+ }
+}
+
+deh_section_t deh_section_weapon =
+{
+ "Weapon",
+ NULL,
+ DEH_WeaponStart,
+ DEH_WeaponParseLine,
+ NULL,
+ DEH_WeaponMD5Sum,
+};
+
--- a/src/i_pcsound.c
+++ b/src/i_pcsound.c
@@ -27,7 +27,7 @@
#include "doomtype.h"
-#include "deh_main.h"
+#include "deh_str.h"
#include "s_sound.h"
#include "sounds.h"
--- a/src/i_sdlmusic.c
+++ b/src/i_sdlmusic.c
@@ -34,7 +34,7 @@
#include "memio.h"
#include "mus2mid.h"
-#include "deh_main.h"
+#include "deh_str.h"
#include "m_misc.h"
#include "s_sound.h"
#include "w_wad.h"
--- a/src/i_sdlsound.c
+++ b/src/i_sdlsound.c
@@ -38,7 +38,7 @@
#include <samplerate.h>
#endif
-#include "deh_main.h"
+#include "deh_str.h"
#include "i_system.h"
#include "s_sound.h"
#include "m_argv.h"
--- a/src/i_system.c
+++ b/src/i_system.c
@@ -38,7 +38,7 @@
#include <unistd.h>
#endif
-#include "deh_main.h"
+#include "deh_str.h"
#include "doomtype.h"
#include "doomstat.h"
#include "m_argv.h"
--- a/src/i_video.c
+++ b/src/i_video.c
@@ -33,7 +33,7 @@
#include "icon.c"
#include "config.h"
-#include "deh_main.h"
+#include "deh_str.h"
#include "doomtype.h"
#include "doomkeys.h"
#include "i_joystick.h"
--- a/src/m_config.c
+++ b/src/m_config.c
@@ -32,7 +32,7 @@
#include <errno.h>
#include "config.h"
-#include "deh_main.h"
+#include "deh_str.h"
#include "doomtype.h"
#include "doomkeys.h"
#include "doomfeatures.h"
--- a/src/m_misc.c
+++ b/src/m_misc.c
@@ -45,7 +45,7 @@
#include "doomtype.h"
#include "doomstat.h"
-#include "deh_main.h"
+#include "deh_str.h"
#include "i_swap.h"
#include "i_system.h"
--- a/src/net_client.c
+++ b/src/net_client.c
@@ -29,6 +29,7 @@
#include "doomtype.h"
#include "doomstat.h"
#include "deh_main.h"
+#include "deh_str.h"
#include "g_game.h"
#include "i_system.h"
#include "i_timer.h"
--- a/src/s_sound.c
+++ b/src/s_sound.c
@@ -29,7 +29,7 @@
#include "i_system.h"
#include "doomfeatures.h"
-#include "deh_main.h"
+#include "deh_str.h"
#include "doomstat.h"
#include "doomtype.h"
--- a/src/v_video.c
+++ b/src/v_video.c
@@ -34,7 +34,7 @@
#include "doomtype.h"
#include "doomdata.h"
-#include "deh_main.h"
+#include "deh_str.h"
#include "m_bbox.h"
#include "i_swap.h"
#include "i_video.h"