move #ifdefs to a JSON config

This commit is contained in:
rr- 2021-02-08 11:30:21 +01:00
parent 1b3bd187bc
commit 1eb83cd242
No known key found for this signature in database
GPG key ID: CC65E6FD28CAE42A
11 changed files with 1543 additions and 21 deletions

4
TR1Main.json Normal file
View file

@ -0,0 +1,4 @@
{
"keep_health_between_levels": false,
"disable_medpacks": false
}

View file

@ -1,2 +1,3 @@
#!/bin/sh
i686-w64-mingw32-gcc -shared src/*.c -ldbghelp -o build/TR1Main.dll
#!/bin/bash
shopt -s globstar
i686-w64-mingw32-gcc -W -static -shared src/**/*.c -ldbghelp -o build/TR1Main.dll

View file

@ -168,12 +168,9 @@ int LoadRooms(FILE *fp) {
void __cdecl LevelStats(int levelID) {
TRACE("");
#ifdef FEATURE_KEEP_HEALTH_BETWEEN_LEVELS
// store Lara health
TR1MStoredLaraHealth = LaraItem ? LaraItem->hitPoints : 1000;
TRACE("Lara pointers: %p/%d", LaraItem, Lara.itemNumber);
TRACE("Storing Lara health: %d", LaraItem ? LaraItem->hitPoints : -1);
#endif
if (TR1MConfig.keep_health_between_levels) {
TR1MData.stored_lara_health = LaraItem ? LaraItem->hitPoints : 1000;
}
static char buf[100];
@ -280,7 +277,7 @@ int __cdecl LoadLevelByID(int levelID) {
TRACE("%d", levelID);
int ret = LoadLevel(LevelNames[levelID], levelID);
#ifdef FEATURE_KEEP_HEALTH_BETWEEN_LEVELS
if (TR1MConfig.keep_health_between_levels) {
// check if we're in main menu by seeing if there is Lara item in the
// currently loaded level.
int laraFound = 0;
@ -292,9 +289,9 @@ int __cdecl LoadLevelByID(int levelID) {
if (!laraFound) {
TRACE("Resetting stored Lara health");
TR1MStoredLaraHealth = 1000;
TR1MData.stored_lara_health = 1000;
}
}
#endif
return ret;
}
@ -372,14 +369,14 @@ int __cdecl LoadItems(FILE *handle)
S_ExitSystem(StringToShow);
}
#ifdef FEATURE_DISABLE_MEDPACKS
if (TR1MConfig.disable_medpacks) {
if (objectID == ID_LARGE_MEDIPACK_ITEM || objectID == ID_SMALL_MEDIPACK_ITEM) {
currentItem->pos.x = -1;
currentItem->pos.y = -1;
currentItem->pos.z = -1;
currentItem->roomNumber = 0;
}
#endif
}
InitialiseItem(i);
}
@ -392,13 +389,13 @@ void __cdecl InitialiseLara(void) {
TRACE("");
LaraItem->moreFlags &= 0xFFDFu;
LaraItem->data = &Lara;
#ifdef FEATURE_KEEP_HEALTH_BETWEEN_LEVELS
TRACE("Restoring Lara health: %d", TR1MStoredLaraHealth);
LaraItem->hitPoints = TR1MStoredLaraHealth;
#else
if (TR1MConfig.keep_health_between_levels) {
TRACE("Restoring Lara health: %d", TR1MData.stored_lara_health);
LaraItem->hitPoints = TR1MData.stored_lara_health;
} else {
TRACE("Restoring Lara health: default");
LaraItem->hitPoints = 1000;
#endif
}
Lara.air = 1800;
Lara.field_8 = 0;

26
src/json-parser/LICENSE Normal file
View file

@ -0,0 +1,26 @@
Copyright (C) 2012, 2013 James McLaughlin et al. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
1. Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the distribution.
THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
SUCH DAMAGE.

97
src/json-parser/README.md Normal file
View file

@ -0,0 +1,97 @@
Very low footprint JSON parser written in portable ANSI C.
* BSD licensed with no dependencies (i.e. just drop the C file into your project)
* Never recurses or allocates more memory than it needs
* Very simple API with operator sugar for C++
[![Build Status](https://secure.travis-ci.org/udp/json-parser.png)](http://travis-ci.org/udp/json-parser)
_Want to serialize? Check out [json-builder](https://github.com/udp/json-builder)!_
Installing
----------
There is now a makefile which will produce a libjsonparser static and dynamic library. However, this
is _not_ required to build json-parser, and the source files (`json.c` and `json.h`) should be happy
in any build system you already have in place.
API
---
json_value * json_parse (const json_char * json,
size_t length);
json_value * json_parse_ex (json_settings * settings,
const json_char * json,
size_t length,
char * error);
void json_value_free (json_value *);
The `type` field of `json_value` is one of:
* `json_object` (see `u.object.length`, `u.object.values[x].name`, `u.object.values[x].value`)
* `json_array` (see `u.array.length`, `u.array.values`)
* `json_integer` (see `u.integer`)
* `json_double` (see `u.dbl`)
* `json_string` (see `u.string.ptr`, `u.string.length`)
* `json_boolean` (see `u.boolean`)
* `json_null`
Compile-Time Options
--------------------
-DJSON_TRACK_SOURCE
Stores the source location (line and column number) inside each `json_value`.
This is useful for application-level error reporting.
Runtime Options
---------------
settings |= json_enable_comments;
Enables C-style `// line` and `/* block */` comments.
size_t value_extra
The amount of space (if any) to allocate at the end of each `json_value`, in
order to give the application space to add metadata.
void * (* mem_alloc) (size_t, int zero, void * user_data);
void (* mem_free) (void *, void * user_data);
Custom allocator routines. If NULL, the default `malloc` and `free` will be used.
The `user_data` pointer will be forwarded from `json_settings` to allow application
context to be passed.
Changes in version 1.1.0
------------------------
* UTF-8 byte order marks are now skipped if present
* Allows cross-compilation by honoring --host if given (@wkz)
* Maximum size for error buffer is now exposed in header (@LB--)
* GCC warning for `static` after `const` fixed (@batrick)
* Optional support for C-style line and block comments added (@Jin-W-FS)
* `name_length` field added to object values
* It is now possible to retrieve the source line/column number of a parsed `json_value` when `JSON_TRACK_SOURCE` is enabled
* The application may now extend `json_value` using the `value_extra` setting
* Un-ambiguate pow call in the case of C++ overloaded pow (@fcartegnie)
* Fix null pointer de-reference when a non-existing array is closed and no root value is present

1040
src/json-parser/json.c Normal file

File diff suppressed because it is too large Load diff

283
src/json-parser/json.h Normal file
View file

@ -0,0 +1,283 @@
/* vim: set et ts=3 sw=3 sts=3 ft=c:
*
* Copyright (C) 2012, 2013, 2014 James McLaughlin et al. All rights reserved.
* https://github.com/udp/json-parser
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _JSON_H
#define _JSON_H
#ifndef json_char
#define json_char char
#endif
#ifndef json_int_t
#ifndef _MSC_VER
#include <inttypes.h>
#define json_int_t int64_t
#else
#define json_int_t __int64
#endif
#endif
#include <stdlib.h>
#ifdef __cplusplus
#include <string.h>
extern "C"
{
#endif
typedef struct
{
unsigned long max_memory;
int settings;
/* Custom allocator support (leave null to use malloc/free)
*/
void * (* mem_alloc) (size_t, int zero, void * user_data);
void (* mem_free) (void *, void * user_data);
void * user_data; /* will be passed to mem_alloc and mem_free */
size_t value_extra; /* how much extra space to allocate for values? */
} json_settings;
#define json_enable_comments 0x01
typedef enum
{
json_none,
json_object,
json_array,
json_integer,
json_double,
json_string,
json_boolean,
json_null
} json_type;
extern const struct _json_value json_value_none;
typedef struct _json_object_entry
{
json_char * name;
unsigned int name_length;
struct _json_value * value;
} json_object_entry;
typedef struct _json_value
{
struct _json_value * parent;
json_type type;
union
{
int boolean;
json_int_t integer;
double dbl;
struct
{
unsigned int length;
json_char * ptr; /* null terminated */
} string;
struct
{
unsigned int length;
json_object_entry * values;
#if defined(__cplusplus) && __cplusplus >= 201103L
decltype(values) begin () const
{ return values;
}
decltype(values) end () const
{ return values + length;
}
#endif
} object;
struct
{
unsigned int length;
struct _json_value ** values;
#if defined(__cplusplus) && __cplusplus >= 201103L
decltype(values) begin () const
{ return values;
}
decltype(values) end () const
{ return values + length;
}
#endif
} array;
} u;
union
{
struct _json_value * next_alloc;
void * object_mem;
} _reserved;
#ifdef JSON_TRACK_SOURCE
/* Location of the value in the source JSON
*/
unsigned int line, col;
#endif
/* Some C++ operator sugar */
#ifdef __cplusplus
public:
inline _json_value ()
{ memset (this, 0, sizeof (_json_value));
}
inline const struct _json_value &operator [] (int index) const
{
if (type != json_array || index < 0
|| ((unsigned int) index) >= u.array.length)
{
return json_value_none;
}
return *u.array.values [index];
}
inline const struct _json_value &operator [] (const char * index) const
{
if (type != json_object)
return json_value_none;
for (unsigned int i = 0; i < u.object.length; ++ i)
if (!strcmp (u.object.values [i].name, index))
return *u.object.values [i].value;
return json_value_none;
}
inline operator const char * () const
{
switch (type)
{
case json_string:
return u.string.ptr;
default:
return "";
};
}
inline operator json_int_t () const
{
switch (type)
{
case json_integer:
return u.integer;
case json_double:
return (json_int_t) u.dbl;
default:
return 0;
};
}
inline operator bool () const
{
if (type != json_boolean)
return false;
return u.boolean != 0;
}
inline operator double () const
{
switch (type)
{
case json_integer:
return (double) u.integer;
case json_double:
return u.dbl;
default:
return 0;
};
}
#endif
} json_value;
json_value * json_parse (const json_char * json,
size_t length);
#define json_error_max 128
json_value * json_parse_ex (json_settings * settings,
const json_char * json,
size_t length,
char * error);
void json_value_free (json_value *);
/* Not usually necessary, unless you used a custom mem_alloc and now want to
* use a custom mem_free.
*/
void json_value_free_ex (json_settings * settings,
json_value *);
#ifdef __cplusplus
} /* extern "C" */
#endif
#endif

34
src/json_utils.c Normal file
View file

@ -0,0 +1,34 @@
#include <string.h>
#include "json_utils.h"
json_value *get_json_field(json_value *root, json_type fieldType, const char *name, int *pIndex) {
if (root == NULL || root->type != json_object) {
return NULL;
}
json_value *result = NULL;
unsigned int len = name ? strlen(name) : 0;
unsigned int i = pIndex ? *pIndex : 0;
for (; i < root->u.object.length; ++i) {
if (root->u.object.values[i].value->type == fieldType) {
if (
!name
|| (
len == root->u.object.values[i].name_length
&& !strncmp(root->u.object.values[i].name, name, len)
)
) {
result = root->u.object.values[i].value;
break;
}
}
}
if (pIndex) {
*pIndex = i;
}
return result;
}
int get_json_boolean_field_value(json_value *root, const char *name) {
json_value *field = get_json_field(root, json_boolean, name, NULL);
return field ? field->u.boolean : 0;
}

9
src/json_utils.h Normal file
View file

@ -0,0 +1,9 @@
#ifndef TR1M_JSON_UTILS_H
#define TR1M_JSON_UTILS_H
#include "json-parser/json.h"
json_value *get_json_field(json_value *root, json_type fieldType, const char *name, int *pIndex);
int get_json_boolean_field_value(json_value *root, const char *name);
#endif

View file

@ -1,9 +1,11 @@
#include <windows.h>
#include <stdio.h>
#include "json_utils.h"
#include "struct.h"
#include "util.h"
#include "func.h"
#include "mod.h"
HINSTANCE hInstance = NULL;
@ -26,10 +28,34 @@ static void Inject() {
//INJECT(0x00430450, S_DrawAirBar);
}
static int ReadConfig() {
FILE *fp = fopen("TR1Main.json", "rb");
if (!fp) {
return 0;
}
fseek(fp, 0, SEEK_END);
int cfg_size = ftell(fp);
fseek(fp, 0, SEEK_SET);
char *cfg_data = malloc(cfg_size);
fread(cfg_data, 1, cfg_size, fp);
json_value *json = json_parse((const json_char*)cfg_data, cfg_size);
TR1MConfig.keep_health_between_levels = get_json_boolean_field_value(json, "keep_health_between_levels");
TR1MConfig.disable_medpacks = get_json_boolean_field_value(json, "disable_medpacks");
json_value_free(json);
free(cfg_data);
return 1;
}
BOOL APIENTRY DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved) {
switch (fdwReason) {
case DLL_PROCESS_ATTACH:
freopen("./TR1Main.log", "w", stdout);
ReadConfig();
TRACE("Attached");
hInstance = hinstDLL;
Inject();

View file

@ -3,8 +3,13 @@
#include "util.h"
#ifdef FEATURE_KEEP_HEALTH_BETWEEN_LEVELS
static int TR1MStoredLaraHealth = 1000;
#endif
struct {
int keep_health_between_levels;
int disable_medpacks;
} TR1MConfig;
struct {
int stored_lara_health;
} TR1MData;
#endif