Compare commits

..
Author SHA1 Message Date
Alug bcc58f54e4 address some more software overflows 2026-02-02 20:03:33 +01:00
Alug 55203c8711 r_segs: use fixed point clamp in more places
replaces the old overflow clamping since we now have a function for this purpose
2026-02-02 16:12:30 +01:00
Alug 19d83f82e4 software renderer: "address" an absolute silly amount of overflowing fixed point maths
honestly be better to just completely switch over to 64bit maths, or even better floats....
this is mostly just bandaids but seems to make software more "visually stable"
2026-02-02 16:12:26 +01:00
48 changed files with 743 additions and 412 deletions

No files matched your search

-1
View File
@@ -191,7 +191,6 @@ set(SRB2_CORE_GAME_SOURCES
k_kart.c
k_stats.c
i_time.c
i_threads.c
p_local.h
p_maputl.h
+5
View File
@@ -8,6 +8,11 @@ ifdef MINGW
libs+=-mconsole
endif
ifndef NOTHREADS
opts+=-DHAVE_THREADS
sources+=dedicated/i_threads.c
endif
NOOPENMPT=1
NOLIBGME=1
NOHW=1
-5
View File
@@ -27,11 +27,6 @@ endif
sources+=$(call List,hardware/Sourcefile)
endif
ifndef NOTHREADS
opts+=-DHAVE_THREADS
sources+=i_threads.c
endif
ifndef NOMD5
sources+=md5.c
endif
+5
View File
@@ -40,6 +40,11 @@ sources+=sdl/mixer_sound.c
endif
endif
ifndef NOTHREADS
opts+=-DHAVE_THREADS
sources+=sdl/i_threads.c
endif
ifdef SDL_PKGCONFIG
$(eval $(call Use_pkg_config,SDL))
else
+3 -3
View File
@@ -44,14 +44,14 @@
#define MAXHUDLINES 20
#ifdef HAVE_THREADS
I_Mutex con_mutex;
I_mutex con_mutex;
// g_in_exiting_signal_handler is an evil hack
// to avoid infinite SIGABRT recursion in the signal handler
// due to poisoned locks or mach-o kernel not supporting locks in signals
// or something like that. idk
# define Lock_state() if (!g_in_exiting_signal_handler) { I_LockMutex(&con_mutex); }
# define Unlock_state() if (!g_in_exiting_signal_handler) { I_UnlockMutex(con_mutex); }
# define Lock_state() if (!g_in_exiting_signal_handler) { I_lock_mutex(&con_mutex); }
# define Unlock_state() if (!g_in_exiting_signal_handler) { I_unlock_mutex(con_mutex); }
#else/*HAVE_THREADS*/
# define Lock_state()
# define Unlock_state()
+1 -1
View File
@@ -22,7 +22,7 @@ void CON_Init(void);
boolean CON_Responder(event_t *ev);
#ifdef HAVE_THREADS
extern I_Mutex con_mutex;
extern I_mutex con_mutex;
#endif
// set true when screen size has changed, to adapt console
+4 -4
View File
@@ -2830,11 +2830,11 @@ static boolean CL_ServerConnectionTicker(const char *tmpsave, tic_t *oldtic, tic
F_TitleScreenDrawer();
CL_DrawConnectionStatus();
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
M_Drawer(); //Needed for drawing messageboxes on the connection screen
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
I_UpdateNoVsync(); // page flip or blit buffer
if (moviemode)
@@ -7187,12 +7187,12 @@ void NetUpdate(void)
{
resptime = nowtime;
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
M_Ticker();
refreshdirmenu = 0;
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
CON_Ticker();
}
+6 -6
View File
@@ -223,13 +223,13 @@ void D_ProcessEvents(void)
// Menu input
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
{
eaten = M_Responder(ev);
}
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
if (eaten)
@@ -244,13 +244,13 @@ void D_ProcessEvents(void)
// console input
#ifdef HAVE_THREADS
I_LockMutex(&con_mutex);
I_lock_mutex(&con_mutex);
#endif
{
eaten = CON_Responder(ev);
}
#ifdef HAVE_THREADS
I_UnlockMutex(con_mutex);
I_unlock_mutex(con_mutex);
#endif
if (eaten)
@@ -577,11 +577,11 @@ static boolean D_Display(void)
vid.recalc = false;
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
M_Drawer(); // menu is drawn even on top of everything...
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
// focus lost moved to M_Drawer
+6 -6
View File
@@ -112,7 +112,7 @@ static fileused_t transferFiles[UINT8_MAX + 1];
INT32 fileneedednum = 0; // Number of files needed to join the server
fileneeded_t fileneeded[MAX_WADFILES] = {}; // List of needed files
#ifdef HAVE_THREADS
static I_Mutex downloadmutex;
static I_mutex downloadmutex;
#endif
char downloaddir[512] = "DOWNLOAD";
@@ -1427,7 +1427,7 @@ void CURLPrepareFile(const char* url, int dfilenum)
filedownload.http_running = true;
#ifdef HAVE_THREADS
(void)!I_SpawnThread("http-download", (I_ThreadFn)CURLGetFile, NULL);
I_spawn_thread("http-download", (I_thread_fn)CURLGetFile, NULL);
#endif
}
else
@@ -1440,15 +1440,15 @@ void CURLAbortFile(void)
#ifdef HAVE_THREADS
// lock and unlock to wait for the download thread to exit
I_LockMutex(&downloadmutex);
I_UnlockMutex(downloadmutex);
I_lock_mutex(&downloadmutex);
I_unlock_mutex(downloadmutex);
#endif
}
static void CURLGetFile(void)
{
#ifdef HAVE_THREADS
I_LockMutex(&downloadmutex);
I_lock_mutex(&downloadmutex);
#endif
CURLMcode mc; /* return code used by curl_multi_wait() */
CURLcode easyres; /* Return from easy interface */
@@ -1549,7 +1549,7 @@ static void CURLGetFile(void)
filedownload.http_running = false;
#ifdef HAVE_THREADS
I_UnlockMutex(downloadmutex);
I_unlock_mutex(downloadmutex);
#endif
}
+1
View File
@@ -2,5 +2,6 @@ i_system.c
i_main.c
i_video.c
i_sound.c
i_threads.c
dosstr.c
endtxt.c
+2 -2
View File
@@ -1381,8 +1381,8 @@ INT32 I_StartupSystem(void)
I_Fork();
#endif
#ifdef HAVE_THREADS
I_StartThreads();
I_AddExitFunc(I_StopThreads);
I_start_threads();
I_AddExitFunc(I_stop_threads);
#endif
I_RegisterSignals();
#ifndef NOMUMBLE
+59 -87
View File
@@ -1,4 +1,4 @@
// SONIC ROBO BLAST 2 KART
// SONIC ROBO BLAST 2
//-----------------------------------------------------------------------------
// Copyright (C) 2020-2023 by James R.
//
@@ -9,14 +9,12 @@
/// \file i_threads.c
/// \brief Multithreading abstraction
#ifdef HAVE_THREADS
#if defined (__unix__) || defined(UNIXCOMMON)
#if defined (__unix__) || (!defined(__APPLE__) && defined (UNIXCOMMON))
#include <pthread.h>
#include "i_threads.h"
#include "doomdef.h"
#include "doomtype.h"
#include "../i_threads.h"
#include "../doomdef.h"
typedef struct thread_s thread_t;
@@ -24,7 +22,7 @@ struct thread_s
{
thread_t *next;
void *userdata;
I_ThreadFn func;
I_thread_fn func;
pthread_t thread;
};
@@ -43,8 +41,12 @@ static void *HandleThread(void *data)
return NULL;
}
FUNCWARNRV
int I_SpawnThread(const char *name, I_ThreadFn entry, void *userdata)
void
I_spawn_thread (
const char * name,
I_thread_fn entry,
void * userdata
)
{
thread_t *thread;
(void)name;
@@ -64,20 +66,17 @@ int I_SpawnThread(const char *name, I_ThreadFn entry, void *userdata)
if (thread == NULL)
{
thread = malloc(sizeof(thread_t));
if (thread == NULL)
return false;
thread->next = thread_list;
thread_list = thread;
}
thread->func = entry;
thread->userdata = userdata;
int err = pthread_create(&thread->thread, NULL, HandleThread, thread);
pthread_create(&thread->thread, NULL, HandleThread, thread);
pthread_mutex_unlock(&thread_lock);
return err == 0;
}
int I_ThreadIsStopped(void)
int I_thread_is_stopped(void)
{
thread_t *thread;
pthread_mutex_lock(&thread_lock);
@@ -95,11 +94,11 @@ int I_ThreadIsStopped(void)
return true;
}
void I_StartThreads(void)
void I_start_threads(void)
{
}
void I_StopThreads(void)
void I_stop_threads(void)
{
thread_t *thread = thread_list;
while (thread != NULL)
@@ -110,7 +109,7 @@ void I_StopThreads(void)
}
}
void I_LockMutex(I_Mutex *anchor)
void I_lock_mutex(I_mutex *anchor)
{
pthread_mutex_lock(&thread_lock);
if (*anchor == NULL)
@@ -128,25 +127,25 @@ void I_LockMutex(I_Mutex *anchor)
pthread_mutex_lock(*anchor);
}
void I_UnlockMutex(I_Mutex id)
void I_unlock_mutex(I_mutex id)
{
pthread_mutex_unlock(id);
}
void I_HoldCond(I_Cond *condAnchor, I_Mutex mutexId)
void I_hold_cond(I_cond *cond_anchor, I_mutex mutex_id)
{
I_Assert(mutexId != NULL);
I_Assert(mutex_id != NULL);
pthread_mutex_lock(&thread_lock);
if (*condAnchor == NULL)
if (*cond_anchor == NULL)
{
*condAnchor = malloc(sizeof(pthread_cond_t));
pthread_cond_init(*condAnchor, NULL);
*cond_anchor = malloc(sizeof(pthread_cond_t));
pthread_cond_init(*cond_anchor, NULL);
}
pthread_mutex_unlock(&thread_lock);
pthread_cond_wait(*condAnchor, mutexId);
pthread_cond_wait(*cond_anchor, mutex_id);
}
void I_WakeOneCond(I_Cond *anchor)
void I_wake_one_cond(I_cond *anchor)
{
pthread_mutex_lock(&thread_lock);
if (*anchor == NULL)
@@ -158,7 +157,7 @@ void I_WakeOneCond(I_Cond *anchor)
pthread_cond_signal(*anchor);
}
void I_WakeAllCond(I_Cond *anchor)
void I_wake_all_cond(I_cond *anchor)
{
pthread_mutex_lock(&thread_lock);
if (*anchor == NULL)
@@ -169,17 +168,12 @@ void I_WakeAllCond(I_Cond *anchor)
pthread_mutex_unlock(&thread_lock);
pthread_cond_broadcast(*anchor);
}
thread_handle_t I_GetCurrentThread(void)
{
return pthread_self();
}
#elif defined (_WIN32)
#include <windows.h>
#include "i_threads.h"
#include "doomdef.h"
#include "doomtype.h"
#include "../i_threads.h"
#include "../doomdef.h"
#include "../doomtype.h"
typedef struct thread_s thread_t;
@@ -187,9 +181,9 @@ struct thread_s
{
thread_t *next;
void *userdata;
I_ThreadFn func;
I_thread_fn func;
HANDLE thread;
DWORD threadId;
DWORD thread_id;
};
// we use a linked list to avoid moving memory blocks when allocating new threads.
@@ -207,8 +201,7 @@ static DWORD __stdcall HandleThread(void *data)
return 0;
}
FUNCWARNRV
int I_SpawnThread(const char *name, I_ThreadFn entry, void *userdata)
void I_spawn_thread(const char *name, I_thread_fn entry, void *userdata)
{
thread_t *thread;
(void)name;
@@ -226,20 +219,17 @@ int I_SpawnThread(const char *name, I_ThreadFn entry, void *userdata)
if (thread == NULL)
{
thread = malloc(sizeof(thread_t));
if (thread == NULL)
return false;
thread->next = thread_list;
thread_list = thread;
}
thread->func = entry;
thread->userdata = userdata;
thread->thread = CreateThread(NULL, 0, HandleThread, thread, 0, &thread->threadId);
thread->thread = CreateThread(NULL, 0, HandleThread, thread, 0, &thread->thread_id);
LeaveCriticalSection(&thread_lock);
return thread->thread != NULL;
}
int I_ThreadIsStopped(void)
int I_thread_is_stopped(void)
{
thread_t *thread;
EnterCriticalSection(&thread_lock);
@@ -257,12 +247,12 @@ int I_ThreadIsStopped(void)
return true;
}
void I_StartThreads(void)
void I_start_threads(void)
{
InitializeCriticalSection(&thread_lock);
}
void I_StopThreads(void)
void I_stop_threads(void)
{
thread_t *thread = thread_list;
while (thread != NULL)
@@ -274,7 +264,7 @@ void I_StopThreads(void)
DeleteCriticalSection(&thread_lock);
}
void I_LockMutex(I_Mutex *anchor)
void I_lock_mutex(I_mutex *anchor)
{
EnterCriticalSection(&thread_lock);
if (*anchor == NULL)
@@ -286,25 +276,25 @@ void I_LockMutex(I_Mutex *anchor)
EnterCriticalSection(*anchor);
}
void I_UnlockMutex(I_Mutex id)
void I_unlock_mutex(I_mutex id)
{
LeaveCriticalSection(id);
}
void I_HoldCond(I_Cond *condAnchor, I_Mutex mutexId)
void I_hold_cond(I_cond *cond_anchor, I_mutex mutex_id)
{
I_Assert(mutexId != NULL);
I_Assert(mutex_id != NULL);
EnterCriticalSection(&thread_lock);
if (*condAnchor == NULL)
if (*cond_anchor == NULL)
{
*condAnchor = malloc(sizeof(CONDITION_VARIABLE));
InitializeConditionVariable(*condAnchor);
*cond_anchor = malloc(sizeof(CONDITION_VARIABLE));
InitializeConditionVariable(*cond_anchor);
}
LeaveCriticalSection(&thread_lock);
SleepConditionVariableCS(*condAnchor, mutexId, INFINITE);
SleepConditionVariableCS(*cond_anchor, mutex_id, INFINITE);
}
void I_WakeOneCond(I_Cond *anchor)
void I_wake_one_cond(I_cond *anchor)
{
EnterCriticalSection(&thread_lock);
if (*anchor == NULL)
@@ -316,7 +306,7 @@ void I_WakeOneCond(I_Cond *anchor)
WakeConditionVariable(*anchor);
}
void I_WakeAllCond(I_Cond *anchor)
void I_wake_all_cond(I_cond *anchor)
{
EnterCriticalSection(&thread_lock);
if (*anchor == NULL)
@@ -327,66 +317,48 @@ void I_WakeAllCond(I_Cond *anchor)
LeaveCriticalSection(&thread_lock);
WakeAllConditionVariable(*anchor);
}
void *I_GetCurrentThread(void)
{
return GetCurrentThread();
}
#else
#include "i_threads.h"
FUNCWARNRV
int I_SpawnThread(const char *name, I_ThreadFn entry, void *userdata)
void I_spawn_thread(const char *name, I_thread_fn entry, void *userdata)
{
(void)name;
entry(userdata);
return true;
}
int I_ThreadIsStopped(void)
{
return true;
}
void I_StartThreads(void)
int I_thread_is_stopped(void)
{
}
void I_StopThreads(void)
void I_start_threads(void)
{
}
void I_LockMutex(I_Mutex *anchor)
void I_stop_threads(void)
{
}
void I_lock_mutex(I_mutex *anchor)
{
(void)anchor;
}
void I_UnlockMutex(I_Mutex id)
void I_unlock_mutex(I_mutex id)
{
(void)id;
}
void I_HoldCond(I_Cond *condAnchor, I_Mutex mutexId)
void I_hold_cond(I_cond *cond_anchor, I_mutex mutex_id)
{
(void)condAnchor;
(void)mutexId;
(void)cond_anchor;
(void)mutex_id;
}
void I_WakeOneCond(I_Cond *anchor)
void I_wake_one_cond(I_cond *anchor)
{
(void)anchor;
}
void I_WakeAllCond(I_Cond *anchor)
void I_wake_all_cond(I_cond *anchor)
{
(void)anchor;
}
void *I_GetCurrentThread(void)
{
return NULL;
}
#endif
#endif // HAVE_THREADS
-5
View File
@@ -223,8 +223,6 @@ typedef int32_t boolean;
#define FUNCNOINLINE __attribute__((noinline))
#define FUNCWARNRV __attribute__((warn_unused_result))
#if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 4) // >= GCC 4.4
#ifdef __i386__ // i386 only
#define FUNCTARGET(X) __attribute__ ((__target__ (X)))
@@ -270,9 +268,6 @@ typedef int32_t boolean;
#ifndef FUNCTARGET
#define FUNCTARGET(x)
#endif
#ifndef FUNCWARNRV
#define FUNCWARNRV
#endif
#ifndef ATTRPACK
#define ATTRPACK
#endif
+3 -1
View File
@@ -1172,7 +1172,9 @@ void F_StartWaitingPlayers(void)
randskin = M_RandomKey(numskins);
boolean waithires = skins[randskin].flags && SF_HIRES;
Z_Free(waitcolormap);
if (waitcolormap)
Z_Free(waitcolormap);
waitcolormap = R_GetTranslationColormap(randskin, skins[randskin].prefcolor, 0);
if (waithires)
+2 -2
View File
@@ -388,11 +388,11 @@ void F_RunWipe(UINT8 wipetype, boolean drawMenu)
if (rendermode != render_none && drawMenu)
{
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
M_Drawer(); // menu is drawn even on top of wipes
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
}
+8 -6
View File
@@ -317,7 +317,8 @@ void closefilemenu(boolean validsize)
coredirmenu = NULL;
}
Z_Free(refreshdirname);
if (refreshdirname)
Z_Free(refreshdirname);
refreshdirname = NULL;
}
@@ -345,7 +346,8 @@ void searchfilemenu(char *tempname)
if (!menusearch.length)
{
Z_Free(dirmenu);
if (dirmenu)
Z_Free(dirmenu);
dirmenu = coredirmenu;
sizedirmenu = sizecoredirmenu;
@@ -387,8 +389,8 @@ void searchfilemenu(char *tempname)
I_Error("searchfilemenu(): could not create \"No results...\".");
sizedirmenu = 1;
dir_on[menudepthleft] = 0;
Z_Free(tempname);
if (tempname)
Z_Free(tempname);
return;
}
@@ -503,8 +505,8 @@ boolean preparefilemenu(boolean samedepth, boolean replayhut)
{
closedir(dirhandle);
closefilemenu(false);
Z_Free(tempname);
if (tempname)
Z_Free(tempname);
return false;
}
+5 -2
View File
@@ -523,8 +523,11 @@ void G_ClearRecords(void)
INT16 i;
for (i = 0; i < NUMMAPS; ++i)
{
Z_Free(mainrecords[i]);
mainrecords[i] = NULL;
if (mainrecords[i])
{
Z_Free(mainrecords[i]);
mainrecords[i] = NULL;
}
}
}
+9 -9
View File
@@ -62,7 +62,7 @@ static int hms_started;
static char *hms_api;
#ifdef HAVE_THREADS
static I_Mutex hms_api_mutex;
static I_mutex hms_api_mutex;
#endif
static char *hms_server_token;
@@ -90,9 +90,9 @@ Printf_url (const char *url)
boolean startup;
#ifdef HAVE_THREADS
I_LockMutex(&con_mutex);
I_lock_mutex(&con_mutex);
startup = con_startup;
I_UnlockMutex(con_mutex);
I_unlock_mutex(con_mutex);
#else
startup = con_startup;
#endif
@@ -183,7 +183,7 @@ HMS_connect (const char *format, ...)
}
#ifdef HAVE_THREADS
I_LockMutex(&hms_api_mutex);
I_lock_mutex(&hms_api_mutex);
#endif
seek = strlen(hms_api) + 1;/* + '/' */
@@ -195,7 +195,7 @@ HMS_connect (const char *format, ...)
sprintf(url, "%s/", hms_api);
#ifdef HAVE_THREADS
I_UnlockMutex(hms_api_mutex);
I_unlock_mutex(hms_api_mutex);
#endif
va_start (ap, format);
@@ -477,12 +477,12 @@ HMS_fetch_servers (msg_server_t *list, int query_id)
if (address && port)
{
#ifdef HAVE_THREADS
I_LockMutex(&ms_QueryId_mutex);
I_lock_mutex(&ms_QueryId_mutex);
{
if (query_id != ms_QueryId)
doing_shit = 0;
}
I_UnlockMutex(ms_QueryId_mutex);
I_unlock_mutex(ms_QueryId_mutex);
if (! doing_shit)
break;
@@ -611,14 +611,14 @@ void
HMS_set_api (char *api)
{
#ifdef HAVE_THREADS
I_LockMutex(&hms_api_mutex);
I_lock_mutex(&hms_api_mutex);
#endif
{
free(hms_api);
hms_api = Strip_trailing_slashes(api);
}
#ifdef HAVE_THREADS
I_UnlockMutex(hms_api_mutex);
I_unlock_mutex(hms_api_mutex);
#endif
}
+8 -4
View File
@@ -1072,7 +1072,8 @@ static void Got_Saycmd(const UINT8 **p, INT32 playernum)
HU_AddChatText(va(fmt2, prefix, cstart, dispname, textcolor, msg), cv_chatnotifications.value); // add to chat
Z_Free(tempchar);
if (tempchar)
Z_Free(tempchar);
}
#ifdef _DEBUG
// I just want to point out while I'm here that because the data is still
@@ -1568,7 +1569,8 @@ static void HU_drawMiniChat(void)
dy = 0;
dx = 0;
msglines += linescount+1;
Z_Free(msg);
if (msg)
Z_Free(msg);
}
y = chaty - charheight*(msglines+1);
@@ -1655,7 +1657,8 @@ static void HU_drawMiniChat(void)
dy += charheight;
dx = 0;
Z_Free(msg);
if (msg)
Z_Free(msg);
}
// decrement addy and make that shit smooth:
@@ -1764,7 +1767,8 @@ static void HU_drawChatLog(INT32 offset)
dy += charheight;
dx = 0;
Z_Free(msg);
if (msg)
Z_Free(msg);
}
if (((chat_scroll >= chat_maxscroll) || (chat_scrollmedown)) && !(justscrolleddown || justscrolledup || chat_scrolltime)) // was already at the bottom of the page before new maxscroll calculation and was NOT scrolling.
+10 -4
View File
@@ -1510,8 +1510,11 @@ static boolean SOCK_SetBanUsername(const char *username)
username = "Direct IP ban";
}
Z_Free(banned[numbans - 1].username);
banned[numbans - 1].username = NULL;
if (banned[numbans - 1].username)
{
Z_Free(banned[numbans - 1].username);
banned[numbans - 1].username = NULL;
}
banned[numbans - 1].username = Z_StrDup(username);
@@ -1525,8 +1528,11 @@ static boolean SOCK_SetBanReason(const char *reason)
reason = "No reason given";
}
Z_Free(banned[numbans - 1].reason);
banned[numbans - 1].reason = NULL;
if (banned[numbans - 1].reason)
{
Z_Free(banned[numbans - 1].reason);
banned[numbans - 1].reason = NULL;
}
banned[numbans - 1].reason = Z_StrDup(reason);
+13 -25
View File
@@ -1,6 +1,6 @@
// SONIC ROBO BLAST 2 KART
//-----------------------------------------------------------------------------
// Copyright (C) 2020-2023 by James R.
// Copyright (C) 2020 by James R.
//
// This program is free software distributed under the
// terms of the GNU General Public License, version 2.
@@ -14,46 +14,34 @@
#ifndef I_THREADS_H
#define I_THREADS_H
#include "doomtype.h"
#ifdef __cplusplus
extern "C" {
#endif
typedef void (*I_ThreadFn)(void *userdata);
typedef void (*I_thread_fn)(void *userdata);
typedef void * I_Mutex;
typedef void * I_Cond;
typedef void * I_mutex;
typedef void * I_cond;
#ifdef __linux__
typedef long unsigned int thread_handle_t;
#else
typedef void *thread_handle_t;
#endif
void I_start_threads (void);
void I_stop_threads (void);
void I_StartThreads (void);
void I_StopThreads (void);
FUNCWARNRV
int I_SpawnThread (const char *name, I_ThreadFn, void *userdata);
void I_spawn_thread (const char *name, I_thread_fn, void *userdata);
/* check in your thread whether to return early */
int I_ThreadIsStopped (void);
int I_thread_is_stopped (void);
void I_LockMutex (I_Mutex *);
void I_UnlockMutex (I_Mutex);
void I_lock_mutex (I_mutex *);
void I_unlock_mutex (I_mutex);
void I_HoldCond (I_Cond *, I_Mutex);
void I_hold_cond (I_cond *, I_mutex);
void I_WakeOneCond (I_Cond *);
void I_WakeAllCond (I_Cond *);
thread_handle_t I_GetCurrentThread(void);
void I_wake_one_cond (I_cond *);
void I_wake_all_cond (I_cond *);
#ifdef __cplusplus
} // extern "C"
#endif
#endif/*I_THREADS_H*/
#endif/*HAVE_THREADS*/
+2 -1
View File
@@ -99,7 +99,8 @@ void K_EraseStats(void)
// The only field we want to remember
boolean vanilla = kartstats.vanilla;
Z_Free(kartstats.copy);
if (kartstats.copy)
Z_Free(kartstats.copy);
memset(&kartstats, 0, sizeof(kartstats_t));
+12 -3
View File
@@ -136,9 +136,18 @@ void LUA_HUD_DestroyDrawList(huddrawlist_h list)
{
if (list == NULL) return;
Z_Free(list->items);
Z_Free(list->olditems);
Z_Free(list->strbuf);
if (list->items)
{
Z_Free(list->items);
}
if (list->olditems)
{
Z_Free(list->olditems);
}
if (list->strbuf)
{
Z_Free(list->strbuf);
}
Z_Free(list);
}
+6 -3
View File
@@ -695,13 +695,16 @@ INT32 GIF_close(void)
fclose(gif_out);
gif_out = NULL;
Z_Free(gifbwr_buf);
if (gifbwr_buf)
Z_Free(gifbwr_buf);
gifbwr_buf = gifbwr_cur = NULL;
Z_Free(gifframe_data);
if (gifframe_data)
Z_Free(gifframe_data);
gifframe_data = NULL;
Z_Free(giflzw_hashTable);
if (giflzw_hashTable)
Z_Free(giflzw_hashTable);
giflzw_hashTable = NULL;
Z_Free(scrbuf_screens);
+6 -3
View File
@@ -248,9 +248,12 @@ void M_AddRawCondition(UINT8 set, UINT8 id, conditiontype_t c, INT32 r, INT16 x1
void M_ClearConditionSet(UINT8 set)
{
Z_Free(conditionSets[set - 1].condition);
conditionSets[set - 1].condition = NULL;
conditionSets[set - 1].numconditions = 0;
if (conditionSets[set - 1].numconditions)
{
Z_Free(conditionSets[set - 1].condition);
conditionSets[set - 1].condition = NULL;
conditionSets[set - 1].numconditions = 0;
}
conditionSets[set - 1].achieved = false;
}
+9
View File
@@ -20,6 +20,7 @@ extern "C" {
#endif
#include "doomtype.h"
#ifdef __GNUC__
#include <stdlib.h>
#endif
@@ -71,6 +72,14 @@ FUNCMATH FUNCINLINE static ATTRINLINE fixed_t DoubleToFixed(double f)
#define FIXED_TO_FLOAT(x) FixedToFloat(x) // (((float)(x)) / ((float)FRACUNIT))
#define FLOAT_TO_FIXED(f) FloatToFixed(f) // (fixed_t)((f) * ((float)FRACUNIT))
FUNCMATH FUNCINLINE static ATTRINLINE fixed_t FixedClamp(INT64 val)
{
// stoopid includes
#define FCLAMP(x, y, z) ((x) < (y) ? (y) : ((x) > (z) ? (z) : (x)))
return (fixed_t)(FCLAMP(val, (INT64)INT32_MIN, (INT64)INT32_MAX));
#undef FCLAMP
}
/** \brief The FixedMul function
\param a fixed_t number
+32 -42
View File
@@ -142,7 +142,7 @@ typedef enum
} text_enum;
#ifdef HAVE_THREADS
I_Mutex m_menu_mutex;
I_mutex m_menu_mutex;
#endif
M_waiting_mode_t m_waiting_mode = M_NOT_WAITING;
@@ -1967,7 +1967,7 @@ void M_Ticker(void)
}
#if defined (MASTERSERVER) && defined (HAVE_THREADS)
I_LockMutex(&ms_ServerList_mutex);
I_lock_mutex(&ms_ServerList_mutex);
{
if (ms_ServerList)
{
@@ -1976,7 +1976,7 @@ void M_Ticker(void)
ms_ServerList = NULL;
}
}
I_UnlockMutex(ms_ServerList_mutex);
I_unlock_mutex(ms_ServerList_mutex);
#endif
}
@@ -4014,14 +4014,14 @@ size_t demolist_all_size = 0;
boolean replaynamesloaded = false;
#ifdef HAVE_THREADS
I_Mutex replayquerymutex;
I_mutex replayquerymutex;
// g_in_exiting_signal_handler is an evil hack
// to avoid infinite SIGABRT recursion in the signal handler
// due to poisoned locks or mach-o kernel not supporting locks in signals
// or something like that. idk
# define Lock_search_state() if (!g_in_exiting_signal_handler) { I_LockMutex(&replayquerymutex); }
# define Unlock_search_state() if (!g_in_exiting_signal_handler) { I_UnlockMutex(replayquerymutex); }
# define Lock_search_state() if (!g_in_exiting_signal_handler) { I_lock_mutex(&replayquerymutex); }
# define Unlock_search_state() if (!g_in_exiting_signal_handler) { I_unlock_mutex(replayquerymutex); }
#else/*HAVE_THREADS*/
# define Lock_search_state()
# define Unlock_search_state()
@@ -4088,10 +4088,7 @@ static void LoadReplayNames(void)
Unlock_search_state();
#ifdef HAVE_THREADS
if (!I_SpawnThread("replay-names-load", ReplayNamesLoadThread, replaydirpath))
{
free(replaydirpath);
}
I_spawn_thread("replay-names-load", ReplayNamesLoadThread, replaydirpath);
#else
ReplayNamesLoadThread(replaydirpath);
#endif
@@ -5359,7 +5356,7 @@ void M_PopupMasterServerRules(void)
{
firstDismissedRulesThisBoot = false;
M_StartMessage(va("%s\n(press any key)", rules), NULL, MM_NOTHING);
free(rules);
Z_Free(rules);
}
}
#endif
@@ -6563,22 +6560,17 @@ static void M_EraseGuest(INT32 choice)
static void M_OverwriteGuest(const char *which)
{
char *rguest;
char *rguest = Z_StrDup(va("%s"PATHSEP"replay"PATHSEP"%s"PATHSEP"%s-guest.lmp", srb2home, timeattackfolder, G_BuildMapName(cv_nextmap.value)));
UINT8 *buf;
size_t len;
len = FIL_ReadFile(va("%s"PATHSEP"replay"PATHSEP"%s"PATHSEP"%s-%s-%s.lmp", srb2home, timeattackfolder, G_BuildMapName(cv_nextmap.value), cv_chooseskin.string, which), &buf);
if (!len)
if (!len) {
return;
rguest = Z_StrDup(va("%s"PATHSEP"replay"PATHSEP"%s"PATHSEP"%s-guest.lmp", srb2home, timeattackfolder, G_BuildMapName(cv_nextmap.value)));
if (FIL_FileExists(rguest))
{
}
if (FIL_FileExists(rguest)) {
M_StopMessage(0);
remove(rguest);
}
FIL_WriteFile(rguest, buf, len);
Z_Free(rguest);
@@ -6687,11 +6679,11 @@ static void M_EndGame(INT32 choice)
void M_SetWaitingMode(int mode)
{
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
m_waiting_mode = mode;
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
}
@@ -6700,11 +6692,11 @@ int M_GetWaitingMode(void)
int mode;
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
mode = m_waiting_mode;
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
return mode;
@@ -6716,23 +6708,20 @@ static void Spawn_masterserver_thread(const char *name, void (*thread)(int*))
{
int *id = malloc(sizeof *id);
I_LockMutex(&ms_QueryId_mutex);
I_lock_mutex(&ms_QueryId_mutex);
*id = ms_QueryId;
I_UnlockMutex(ms_QueryId_mutex);
I_unlock_mutex(ms_QueryId_mutex);
if (!I_SpawnThread(name, (I_ThreadFn)thread, id))
{
free(id);
}
I_spawn_thread(name, (I_thread_fn)thread, id);
}
static int Same_instance(int id)
{
int okay;
I_LockMutex(&ms_QueryId_mutex);
I_lock_mutex(&ms_QueryId_mutex);
okay = ( id == ms_QueryId );
I_UnlockMutex(ms_QueryId_mutex);
I_unlock_mutex(ms_QueryId_mutex);
return okay;
}
@@ -6761,9 +6750,9 @@ static void Fetch_servers_thread(int *id)
M_SetWaitingMode(M_NOT_WAITING);
#ifdef HAVE_THREADS
I_LockMutex(&ms_ServerList_mutex);
I_lock_mutex(&ms_ServerList_mutex);
ms_ServerList = server_list;
I_UnlockMutex(ms_ServerList_mutex);
I_unlock_mutex(ms_ServerList_mutex);
#else
CL_QueryServerList(server_list);
free(server_list);
@@ -6796,7 +6785,7 @@ static void M_SearchServerList(void)
serverlistsearchedcount = 0;
#ifdef HAVE_THREADS
I_LockMutex(&ms_ServerList_mutex);
I_lock_mutex(&ms_ServerList_mutex);
#endif
for (UINT32 i = 0; i < serverlistcount; ++i)
@@ -6807,7 +6796,7 @@ static void M_SearchServerList(void)
}
#ifdef HAVE_THREADS
I_UnlockMutex(ms_ServerList_mutex);
I_unlock_mutex(ms_ServerList_mutex);
#endif
if (menuinput.length > 0)
@@ -7173,11 +7162,11 @@ static void M_CheckMODVersion(int id)
{
sprintf(updatestring, UPDATE_ALERT_STRING, VERSIONSTRING, updatecheck);
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
M_StartMessage(updatestring, NULL, MM_NOTHING);
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
}
}
@@ -7223,13 +7212,13 @@ static void M_ConnectMenu(INT32 choice)
itemOn = 0;
#if defined (MASTERSERVER) && defined (HAVE_THREADS)
I_LockMutex(&ms_QueryId_mutex);
I_lock_mutex(&ms_QueryId_mutex);
{
ms_QueryId++;
}
I_UnlockMutex(ms_QueryId_mutex);
I_unlock_mutex(ms_QueryId_mutex);
I_LockMutex(&ms_ServerList_mutex);
I_lock_mutex(&ms_ServerList_mutex);
{
if (ms_ServerList)
{
@@ -7237,7 +7226,7 @@ static void M_ConnectMenu(INT32 choice)
ms_ServerList = NULL;
}
}
I_UnlockMutex(ms_ServerList_mutex);
I_unlock_mutex(ms_ServerList_mutex);
#ifdef UPDATE_ALERT
Spawn_masterserver_thread("check-new-version", Check_new_version_thread);
@@ -7598,6 +7587,7 @@ static void M_DrawLevelSelectOnly(boolean leftfade, boolean rightfade)
static void M_DrawServerMenu(void)
{
M_DrawLevelSelectOnly(false, false);
#ifdef MASTERSERVER
if (currentMenu == &MP_ServerDef && cv_advertise.value) // Remind players where they're hosting.
+1 -1
View File
@@ -215,7 +215,7 @@ void M_SetupNextMenu(menu_t *menudef);
void M_ClearMenus(boolean callexitmenufunc);
#ifdef HAVE_THREADS
extern I_Mutex m_menu_mutex;
extern I_mutex m_menu_mutex;
#endif
extern menu_t *currentMenu;
+32 -37
View File
@@ -41,11 +41,11 @@ static time_t MSLastPing;
static char *MSRules;
#ifdef HAVE_THREADS
static I_Mutex MSMutex;
static I_Cond MSCond;
static I_mutex MSMutex;
static I_cond MSCond;
# define Lock_state() I_LockMutex (&MSMutex)
# define Unlock_state() I_UnlockMutex (MSMutex)
# define Lock_state() I_lock_mutex (&MSMutex)
# define Unlock_state() I_unlock_mutex (MSMutex)
#else/*HAVE_THREADS*/
# define Lock_state()
# define Unlock_state()
@@ -90,10 +90,10 @@ consvar_t cv_masterserver_nagattempts = {"masterserver_nagattempts", "5", CV_SAV
#if defined (MASTERSERVER) && defined (HAVE_THREADS)
int ms_QueryId = 0;
I_Mutex ms_QueryId_mutex;
I_mutex ms_QueryId_mutex;
msg_server_t *ms_ServerList = NULL;
I_Mutex ms_ServerList_mutex;
I_mutex ms_ServerList_mutex;
#endif
UINT16 current_port = 0;
@@ -129,11 +129,11 @@ void AddMServCommands(void)
static void WarnGUI (void)
{
#ifdef HAVE_THREADS
I_LockMutex(&m_menu_mutex);
I_lock_mutex(&m_menu_mutex);
#endif
M_PopupMasterServerConnectError();
#ifdef HAVE_THREADS
I_UnlockMutex(m_menu_mutex);
I_unlock_mutex(m_menu_mutex);
#endif
}
@@ -168,12 +168,12 @@ char *GetMODVersion(int id)
c = HMS_compare_mod_version(buffer, 16);
#ifdef HAVE_THREADS
I_LockMutex(&ms_QueryId_mutex);
I_lock_mutex(&ms_QueryId_mutex);
{
if (id != ms_QueryId)
c = -1;
}
I_UnlockMutex(ms_QueryId_mutex);
I_unlock_mutex(ms_QueryId_mutex);
#endif
if (c > 0)
@@ -219,9 +219,8 @@ static void Get_masterserver_rules(boolean checkfirst)
if (HMS_fetch_rules(rules, sizeof rules))
{
Lock_state();
if (MSRules)
free(MSRules);
MSRules = strdup(rules);
Z_Free(MSRules);
MSRules = Z_StrDup(rules);
if (MSRegistered == true)
{
@@ -341,7 +340,7 @@ Finish_unlist (void)
Unlock_state();
#ifdef HAVE_THREADS
I_WakeAllCond(&MSCond);
I_wake_all_cond(&MSCond);
#endif
}
}
@@ -377,7 +376,7 @@ New_server_id (void)
Lock_state();
{
*id = ++MSId;
I_WakeAllCond(&MSCond);
I_wake_all_cond(&MSCond);
}
Unlock_state();
return id;
@@ -392,7 +391,7 @@ Register_server_thread (int *id)
{
/* wait for previous unlist to finish */
while (*id == MSId && MSRegistered)
I_HoldCond(&MSCond, MSMutex);
I_hold_cond(&MSCond, MSMutex);
same = ( *id == MSId );/* it could have been a while */
}
@@ -444,7 +443,7 @@ Change_masterserver_thread (char *api)
Lock_state();
{
while (MSRegistered)
I_HoldCond(&MSCond, MSMutex);
I_hold_cond(&MSCond, MSMutex);
}
Unlock_state();
@@ -464,9 +463,9 @@ void RegisterServer(void)
{
#ifdef MASTERSERVER
#ifdef HAVE_THREADS
(void)!I_SpawnThread(
I_spawn_thread(
"register-server",
(I_ThreadFn)Register_server_thread,
(I_thread_fn)Register_server_thread,
New_server_id()
);
#else
@@ -478,9 +477,9 @@ void RegisterServer(void)
static void UpdateServer(void)
{
#ifdef HAVE_THREADS
(void)!I_SpawnThread(
I_spawn_thread(
"update-server",
(I_ThreadFn)Update_server_thread,
(I_thread_fn)Update_server_thread,
Server_id()
);
#else
@@ -492,9 +491,9 @@ void UnregisterServer(void)
{
#ifdef MASTERSERVER
#ifdef HAVE_THREADS
(void)!I_SpawnThread(
I_spawn_thread(
"unlist-server",
(I_ThreadFn)Unlist_server_thread,
(I_thread_fn)Unlist_server_thread,
Server_id()
);
#else
@@ -508,7 +507,7 @@ char *GetMasterServerRules(void)
char *rules;
Lock_state();
rules = MSRules ? strdup(MSRules) : NULL;
rules = MSRules ? Z_StrDup(MSRules) : NULL;
Unlock_state();
return rules;
@@ -557,18 +556,14 @@ void MasterClient_Ticker(void)
static void
Set_api (const char *api)
{
char *dapi = strdup(api);
#ifdef HAVE_THREADS
if (!I_SpawnThread(
"change-masterserver",
(I_ThreadFn)Change_masterserver_thread,
dapi
))
{
free(dapi);
}
I_spawn_thread(
"change-masterserver",
(I_thread_fn)Change_masterserver_thread,
strdup(api)
);
#else
Finish_masterserver_change(dapi);
Finish_masterserver_change(strdup(api));
#endif
}
@@ -576,9 +571,9 @@ void
Get_rules (void)
{
#ifdef HAVE_THREADS
(void)!I_SpawnThread(
"get-masterserver-rules",
(I_ThreadFn)Get_masterserver_rules_thread,
I_spawn_thread(
"get-masterserver-rules",
(I_thread_fn)Get_masterserver_rules_thread,
NULL
);
#else
+2 -2
View File
@@ -69,10 +69,10 @@ extern consvar_t cv_rendezvousserver;
#ifdef HAVE_THREADS
extern int ms_QueryId;
extern I_Mutex ms_QueryId_mutex;
extern I_mutex ms_QueryId_mutex;
extern msg_server_t *ms_ServerList;
extern I_Mutex ms_ServerList_mutex;
extern I_mutex ms_ServerList_mutex;
#endif
#ifdef MASTERSERVER
void RegisterServer(void);
+3 -1
View File
@@ -320,7 +320,9 @@ void P_AddGradesForMare(INT16 i, UINT8 mare, char *gtext)
*/
void P_DeleteGrades(INT16 i)
{
Z_Free(mapheaderinfo[i]->grades);
if (mapheaderinfo[i]->grades)
Z_Free(mapheaderinfo[i]->grades);
mapheaderinfo[i]->grades = NULL;
mapheaderinfo[i]->numGradedMares = 0;
}
+2 -1
View File
@@ -6221,7 +6221,8 @@ void P_SpawnSpecials(INT32 fromnetsave, boolean reloadinggamestate)
// Allocate each list
for (i = 0; i < numsectors; i++)
Z_Free(secthinkers[i].thinkers);
if(secthinkers[i].thinkers)
Z_Free(secthinkers[i].thinkers);
Z_Free(secthinkers);
+2 -1
View File
@@ -1720,7 +1720,8 @@ void R_InitData(void)
void R_ClearTextureNumCache(boolean btell)
{
Z_Free(tidcache);
if (tidcache)
Z_Free(tidcache);
tidcache = NULL;
if (btell)
CONS_Debug(DBG_SETUP, "Fun Fact: There are %d textures used in this map.\n", tidcachelen);
+2 -8
View File
@@ -289,14 +289,8 @@ void R_GenerateBlendTables(void)
state->LocalPalette = static_cast<RGBA_t *>(memcpy(malloc(palsize), pLocalPalette, palsize));
state->gammaCorrectedPalette = static_cast<RGBA_t *>(memcpy(malloc(palsize), pGammaCorrectedPalette, palsize));
if (!I_SpawnThread("blend-tables",
R_GenerateBlendTables_Thread, state))
{
free(state->gammaCorrectedPalette);
free(state->LocalPalette);
free(state);
I_Error("R_GenerateBlendTables: Failed to generate BlendTables\n"); // should we just retry on main thread instead?
}
I_spawn_thread("blend-tables",
R_GenerateBlendTables_Thread, state);
#else
struct GenerateBlendTables_State state = {pLocalPalette, pGammaCorrectedPalette};
R_GenerateBlendTables_Core(&state);
+14 -10
View File
@@ -519,10 +519,10 @@ void R_GetRenderBlockMapDimensions(fixed_t drawdist, INT32 *xl, INT32 *xh, INT32
const fixed_t vyright = viewy + FixedMul(drawdist, FSIN(right));
// Try to narrow the search to within only the field of view
*xl = (unsigned)(std::min(viewx, std::min(vxleft, vxright)) - bmaporgx)>>MAPBLOCKSHIFT;
*xh = (unsigned)(std::max(viewx, std::max(vxleft, vxright)) - bmaporgx)>>MAPBLOCKSHIFT;
*yl = (unsigned)(std::min(viewy, std::min(vyleft, vyright)) - bmaporgy)>>MAPBLOCKSHIFT;
*yh = (unsigned)(std::max(viewy, std::max(vyleft, vyright)) - bmaporgy)>>MAPBLOCKSHIFT;
*xl = (unsigned)(FixedClamp((INT64)std::min(viewx, std::min(vxleft, vxright)) - bmaporgx))>>MAPBLOCKSHIFT;
*xh = (unsigned)(FixedClamp((INT64)std::max(viewx, std::max(vxleft, vxright)) - bmaporgx))>>MAPBLOCKSHIFT;
*yl = (unsigned)(FixedClamp((INT64)std::min(viewy, std::min(vyleft, vyright)) - bmaporgy))>>MAPBLOCKSHIFT;
*yh = (unsigned)(FixedClamp((INT64)std::max(viewy, std::max(vyleft, vyright)) - bmaporgy))>>MAPBLOCKSHIFT;
if (*xh >= bmapwidth)
*xh = bmapwidth - 1;
@@ -925,11 +925,11 @@ void R_ExecuteSetViewSize(void)
viewheight = vid.height;
if (splitscreen)
{
viewheight >>= 1;
if (splitscreen > 1)
viewwidth >>= 1;
if (splitscreen > 1)
{
viewwidth >>= 1;
}
centerx = viewwidth/2;
@@ -956,9 +956,13 @@ void R_ExecuteSetViewSize(void)
screenheightarray[i] = (INT16)viewheight;
}
Z_Free(ds_su);
Z_Free(ds_sv);
Z_Free(ds_sz);
if (ds_su)
Z_Free(ds_su);
if (ds_sv)
Z_Free(ds_sv);
if (ds_sz)
Z_Free(ds_sz);
ds_su = ds_sv = ds_sz = NULL;
memset(scalelight, 0xFF, sizeof(scalelight));
+2 -2
View File
@@ -152,8 +152,8 @@ subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y);
FUNCMATH FUNCINLINE static ATTRINLINE fixed_t R_QuickDist(fixed_t x1, fixed_t y1, fixed_t x, fixed_t y)
{
const fixed_t absx = abs(x - x1);
const fixed_t absy = abs(y - y1);
const fixed_t absx = FixedClamp(labs((INT64)x - (INT64)x1));
const fixed_t absy = FixedClamp(labs((INT64)y - (INT64)y1));
#ifdef __cplusplus
return std::max<fixed_t>(absx, absy);
#else
+4 -2
View File
@@ -405,8 +405,10 @@ static void Patch_FreeData(patch_t *patch)
}*/
#endif
Z_Free(patch->columnofs);
Z_Free(patch->columns);
if (patch->columnofs)
Z_Free(patch->columnofs);
if (patch->columns)
Z_Free(patch->columns);
}
void Patch_Free(patch_t *patch)
+3 -3
View File
@@ -228,8 +228,8 @@ static void R_MapPlane(drawspandata_t *ds, spandrawfunc_t *localspanfunc, INT32
// to step from those to the proper texture coordinate to start drawing at.
// That way, the texture coordinate is always calculated by its position
// on the screen and not by its position relative to the edge of the visplane.
ds->xfrac = ds->xoffs + FixedMul(planecos, distance) + (x1 - centerx) * ds->xstep;
ds->yfrac = ds->yoffs - FixedMul(planesin, distance) + (x1 - centerx) * ds->ystep;
ds->xfrac = FixedClamp((INT64)ds->xoffs + (INT64)FixedMul(planecos, distance) + ((INT64)x1 - (INT64)centerx) * (INT64)ds->xstep);
ds->yfrac = FixedClamp((INT64)ds->yoffs - (INT64)FixedMul(planesin, distance) + ((INT64)x1 - (INT64)centerx) * (INT64)ds->ystep);
if (ds->planeripple.active)
{
@@ -1012,7 +1012,7 @@ void R_DrawSinglePlane(drawspandata_t* ds, visplane_t *pl, boolean allow_paralle
levelflat_t *levelflat;
void (*mapfunc)(drawspandata_t*, void(*)(drawspandata_t*), INT32, INT32, INT32, boolean) = R_MapPlane;
if (pl->minx > pl->maxx)
if (!(pl->minx <= pl->maxx))
return;
// sky flat
+2 -2
View File
@@ -312,8 +312,8 @@ void Portal_AddSkybox(const visplane_t* plane)
y = (viewy - skyboxmo[1]->y) * -mh->skybox_scaley;
// Apply transform to account for the skybox viewport angle.
portal->viewx += FixedMul(x,FINECOSINE(ang)) - FixedMul(y, FINESINE(ang));
portal->viewy += FixedMul(x, FINESINE(ang)) + FixedMul(y,FINECOSINE(ang));
portal->viewx += FixedMul(x, FINECOSINE(ang)) - FixedMul(y, FINESINE(ang));
portal->viewy += FixedMul(x, FINESINE(ang)) + FixedMul(y, FINECOSINE(ang));
}
if (mh->skybox_scalez > 0)
+79 -90
View File
@@ -226,10 +226,11 @@ static void R_RenderMaskedSegLoop(drawcolumndata_t* dc, drawseg_t *drawseg, INT3
leftheight -= viewz;
rightheight -= viewz;
rlight->height = (centeryfrac) - FixedMul(leftheight, drawseg->scale1);
rlight->heightstep = (centeryfrac) - FixedMul(rightheight, drawseg->scale2);
rlight->heightstep = (rlight->heightstep-rlight->height)/(range);
rlight->startheight = rlight->height; // keep starting value here to reset for each repeat
rlight->height = FixedClamp((INT64)centeryfrac - FixedMul(leftheight, drawseg->scale1));
rlight->heightstep = FixedClamp((INT64)centeryfrac - FixedMul(rightheight, drawseg->scale2));
rlight->heightstep = FixedClamp((INT64)rlight->heightstep - rlight->height)/(range);
rlight->startheight = rlight->height; // keep starting value here to reset for each repeat
rlight->lightlevel = *light->lightlevel;
rlight->extra_colormap = light->extra_colormap;
rlight->flags = static_cast<ffloortype_e>(light->flags);
@@ -341,7 +342,7 @@ static void R_RenderMaskedSegLoop(drawcolumndata_t* dc, drawseg_t *drawseg, INT3
for (i = 0; i < dc->numlights; i++)
{
rlight = &dc->lightlist[i];
rlight->height += rlight->heightstep;
rlight->height = FixedClamp((INT64)rlight->height + rlight->heightstep);
}
}
@@ -355,9 +356,9 @@ static void R_RenderMaskedSegLoop(drawcolumndata_t* dc, drawseg_t *drawseg, INT3
lighttable_t **xwalllights;
sprbotscreen = INT32_MAX;
sprtopscreen = windowtop = (centeryfrac - FixedMul(dc->texturemid, spryscale));
sprtopscreen = windowtop = FixedClamp((INT64)centeryfrac - FixedMul(dc->texturemid, spryscale));
realbot = windowbottom = FixedMul(textureheight[texnum], spryscale) + sprtopscreen;
realbot = windowbottom = FixedClamp((INT64)FixedMul(textureheight[texnum], spryscale) + sprtopscreen);
dc->iscale = 0xffffffffu / (unsigned)spryscale;
// draw the texture
@@ -407,7 +408,8 @@ static void R_RenderMaskedSegLoop(drawcolumndata_t* dc, drawseg_t *drawseg, INT3
set_light_vars(i);
height = rlight->height;
rlight->height += rlight->heightstep;
rlight->height = FixedClamp((INT64)rlight->height + rlight->heightstep);
if (height <= windowtop)
{
@@ -423,7 +425,7 @@ static void R_RenderMaskedSegLoop(drawcolumndata_t* dc, drawseg_t *drawseg, INT3
for (i++; i < dc->numlights; i++)
{
rlight = &dc->lightlist[i];
rlight->height += rlight->heightstep;
rlight->height = FixedClamp((INT64)rlight->height + rlight->heightstep);
}
continue;
@@ -455,7 +457,7 @@ static void R_RenderMaskedSegLoop(drawcolumndata_t* dc, drawseg_t *drawseg, INT3
if (frontsector->extra_colormap)
dc->colormap = frontsector->extra_colormap->colormap + (dc->colormap - colormaps);
sprtopscreen = centeryfrac - FixedMul(dc->texturemid, spryscale);
sprtopscreen = FixedClamp((INT64)centeryfrac - FixedMul(dc->texturemid, spryscale));
dc->iscale = 0xffffffffu / (unsigned)spryscale;
// draw the texture
@@ -710,17 +712,6 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
rw_scalestep = drawseg->scalestep;
spryscale = drawseg->scale1 + (x1 - drawseg->x1)*rw_scalestep;
#define CLAMPMAX INT32_MAX
#define CLAMPMIN (-INT32_MAX) // This is not INT32_MIN on purpose! INT32_MIN makes the drawers freak out.
auto overflow_clamp = [&](INT64 overflow_test)
{
return (overflow_test > (INT64)CLAMPMAX) ? CLAMPMAX :
(overflow_test > (INT64)CLAMPMIN) ? (fixed_t)overflow_test :
CLAMPMIN;
};
#undef CLAMPMAX
#undef CLAMPMIN
dc->numlights = 0;
if (frontsector->numlights)
{
@@ -736,7 +727,6 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
{
fixed_t leftheight, rightheight;
fixed_t pfloorleft, pfloorright;
INT64 overflow_test;
light = &frontsector->lightlist[i];
rlight = &dc->lightlist[p];
@@ -760,17 +750,14 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
continue;
}
leftheight -= viewz;
leftheight -= viewz;
rightheight -= viewz;
// Monster Iestyn (25/03/18): do not skip these lights if they fail overflow test, just clamp them instead so they behave.
overflow_test = (INT64)centeryfrac - (((INT64)leftheight*drawseg->scale1)>>FRACBITS);
rlight->height = overflow_clamp(overflow_test);
rlight->height = FixedClamp((INT64)centeryfrac - (((INT64)leftheight * drawseg->scale1)>>FRACBITS));
rlight->heightstep = FixedClamp((INT64)centeryfrac - (((INT64)rightheight * drawseg->scale2)>>FRACBITS));
rlight->heightstep = FixedClamp((INT64)rlight->heightstep - rlight->height)/(range);
overflow_test = (INT64)centeryfrac - (((INT64)rightheight*drawseg->scale2)>>FRACBITS);
rlight->heightstep = overflow_clamp(overflow_test);
rlight->heightstep = (rlight->heightstep-rlight->height)/(range);
rlight->flags = static_cast<ffloortype_e>(light->flags);
if (light->flags & FF_CUTLEVEL)
@@ -781,13 +768,9 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
rightheight -= viewz;
// Monster Iestyn (25/03/18): do not skip these lights if they fail overflow test, just clamp them instead so they behave.
overflow_test = (INT64)centeryfrac - (((INT64)leftheight*drawseg->scale1)>>FRACBITS);
rlight->botheight = overflow_clamp(overflow_test);
overflow_test = (INT64)centeryfrac - (((INT64)rightheight*drawseg->scale2)>>FRACBITS);
rlight->botheightstep = overflow_clamp(overflow_test);
rlight->botheightstep = (rlight->botheightstep-rlight->botheight)/(range);
rlight->botheight = FixedClamp((INT64)centeryfrac - (((INT64)leftheight*drawseg->scale1)>>FRACBITS));
rlight->botheightstep = FixedClamp(((INT64)centeryfrac - (((INT64)rightheight*drawseg->scale2)>>FRACBITS)));
rlight->botheightstep = FixedClamp((INT64)rlight->botheightstep - rlight->botheight)/(range);
}
rlight->lightlevel = *light->lightlevel;
@@ -896,10 +879,10 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
right_bottom = P_GetFFloorBottomZAt(pfloor, drawseg->rightpos.x, drawseg->rightpos.y) - viewz;
// using INT64 to avoid 32bit overflow
top_frac = (INT64)centeryfrac - (((INT64)left_top * drawseg->scale1) >> FRACBITS);
bottom_frac = (INT64)centeryfrac - (((INT64)left_bottom * drawseg->scale1) >> FRACBITS);
top_step = (INT64)centeryfrac - (((INT64)right_top * drawseg->scale2) >> FRACBITS);
bottom_step = (INT64)centeryfrac - (((INT64)right_bottom * drawseg->scale2) >> FRACBITS);
top_frac = FixedClamp((INT64)centeryfrac - (((INT64)left_top * drawseg->scale1) >> FRACBITS));
top_step = FixedClamp((INT64)centeryfrac - (((INT64)right_top * drawseg->scale2) >> FRACBITS));
bottom_frac = FixedClamp((INT64)centeryfrac - (((INT64)left_bottom * drawseg->scale1) >> FRACBITS));
bottom_step = FixedClamp((INT64)centeryfrac - (((INT64)right_bottom * drawseg->scale2) >> FRACBITS));
top_step = (top_step-top_frac)/(range);
bottom_step = (bottom_step-bottom_frac)/(range);
@@ -921,8 +904,8 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
// Calculate bounds
// clamp the values if necessary to avoid overflows and rendering glitches caused by them
sprtopscreen = windowtop = overflow_clamp(top_frac);
sprbotscreen = windowbottom = overflow_clamp(bottom_frac);
sprtopscreen = windowtop = top_frac;
sprbotscreen = windowbottom = bottom_frac;
top_frac += top_step;
bottom_frac += bottom_step;
@@ -935,9 +918,11 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
for (i = 0; i < dc->numlights; i++)
{
rlight = &dc->lightlist[i];
rlight->height += rlight->heightstep;
rlight->height = FixedClamp((INT64)rlight->height + rlight->heightstep);
if (rlight->flags & FF_CUTLEVEL)
rlight->botheight += rlight->botheightstep;
rlight->botheight = FixedClamp((INT64)rlight->botheight + rlight->botheightstep);
}
}
@@ -1045,12 +1030,12 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
solid = 0;
height = rlight->height;
rlight->height += rlight->heightstep;
rlight->height = FixedClamp((INT64)rlight->height + rlight->heightstep);
if (solid)
{
bheight = rlight->botheight - (FRACUNIT >> 1);
rlight->botheight += rlight->botheightstep;
bheight = FixedClamp((INT64)rlight->botheight - (FRACUNIT >> 1));
rlight->botheight = FixedClamp((INT64)rlight->botheight + rlight->botheightstep);
}
if (height <= windowtop)
@@ -1078,7 +1063,7 @@ void R_RenderThickSideRange(drawseg_t *drawseg, INT32 x1, INT32 x2, ffloor_t *pf
for (i++; i < dc->numlights; i++)
{
rlight = &dc->lightlist[i];
rlight->height += rlight->heightstep;
rlight->height = FixedClamp((INT64)rlight->height + rlight->heightstep);
if (rlight->flags & FF_CUTLEVEL)
rlight->botheight += rlight->botheightstep;
@@ -1212,7 +1197,7 @@ static void R_RenderSegLoop(drawcolumndata_t* dc)
for (; rw_x < rw_stopx; rw_x++)
{
// mark floor / ceiling areas
yl = (topfrac+HEIGHTUNIT-1)>>HEIGHTBITS;
yl = FixedClamp((INT64)topfrac + HEIGHTUNIT-1)>>HEIGHTBITS;
yh = bottomfrac>>HEIGHTBITS;
// Mark ceiling
@@ -1363,15 +1348,17 @@ static void R_RenderSegLoop(drawcolumndata_t* dc)
//SoM: Calculate offsets for Thick fake floors.
// calculate texture offset
angle = (rw_centerangle + xtoviewangle[rw_x])>>ANGLETOFINESHIFT;
// Mask 4095 to guarantee this index is within bounds
texturecolumn = rw_offset-FixedMul(FINETANGENT(angle & 4095), rw_distance);
texturecolumn = FixedClamp((INT64)rw_offset - FixedMul(FINETANGENT(angle & 4095), rw_distance));
if (oldtexturecolumn != -1)
{
rw_bottomtexturemid += FixedMul(rw_bottomtextureslide, oldtexturecolumn-texturecolumn);
rw_midtexturemid += FixedMul(rw_midtextureslide, oldtexturecolumn-texturecolumn);
rw_toptexturemid += FixedMul(rw_toptextureslide, oldtexturecolumn-texturecolumn);
rw_midtextureback += FixedMul(rw_midtexturebackslide, oldtexturecolumn-texturecolumn);
const fixed_t coloff = FixedClamp((INT64)oldtexturecolumn - texturecolumn);
rw_bottomtexturemid += FixedMul(rw_bottomtextureslide, coloff);
rw_midtexturemid += FixedMul(rw_midtextureslide, coloff);
rw_toptexturemid += FixedMul(rw_toptextureslide, coloff);
rw_midtextureback += FixedMul(rw_midtexturebackslide, coloff);
}
oldtexturecolumn = texturecolumn;
@@ -1381,7 +1368,7 @@ static void R_RenderSegLoop(drawcolumndata_t* dc)
// calculate lighting
pindex = FixedMul(rw_scale, LIGHTRESOLUTIONFIX)>>LIGHTSCALESHIFT;
if (pindex >= MAXLIGHTSCALE)
if (pindex >= MAXLIGHTSCALE)
pindex = MAXLIGHTSCALE-1;
dc->colormap = walllights[pindex];
@@ -1463,8 +1450,8 @@ static void R_RenderSegLoop(drawcolumndata_t* dc)
if (toptexture)
{
// top wall
mid = pixhigh>>HEIGHTBITS;
pixhigh += pixhighstep;
mid = pixhigh >> HEIGHTBITS;
pixhigh = FixedClamp((INT64)pixhigh + pixhighstep);
if (mid >= floorclip[rw_x])
mid = floorclip[rw_x]-1;
@@ -1493,8 +1480,8 @@ static void R_RenderSegLoop(drawcolumndata_t* dc)
if (bottomtexture)
{
// bottom wall
mid = (pixlow+HEIGHTUNIT-1)>>HEIGHTBITS;
pixlow += pixlowstep;
mid = FixedClamp((INT64)pixlow+HEIGHTUNIT-1)>>HEIGHTBITS;
pixlow = FixedClamp((INT64)pixlow + pixlowstep);
// no space above wall?
if (mid <= ceilingclip[rw_x])
@@ -1545,10 +1532,10 @@ static void R_RenderSegLoop(drawcolumndata_t* dc)
{
for (i = 0; i < dc->numlights; i++)
{
dc->lightlist[i].height += dc->lightlist[i].heightstep;
dc->lightlist[i].height = FixedClamp((INT64)dc->lightlist[i].height + dc->lightlist[i].heightstep);
if (dc->lightlist[i].flags & FF_CUTSOLIDS)
dc->lightlist[i].botheight += dc->lightlist[i].botheightstep;
dc->lightlist[i].botheight = FixedClamp((INT64)dc->lightlist[i].botheight + dc->lightlist[i].botheightstep);;
}
}
@@ -1569,9 +1556,10 @@ static void R_RenderSegLoop(drawcolumndata_t* dc)
visffloor[i].b_frac += visffloor[i].b_step;
}
rw_scale += rw_scalestep;
topfrac += topstep;
bottomfrac += bottomstep;
rw_scale = FixedClamp((INT64)rw_scale + rw_scalestep);
topfrac = FixedClamp((INT64)topfrac + topstep);
bottomfrac = FixedClamp((INT64)bottomfrac + bottomstep);
}
}
@@ -1585,7 +1573,7 @@ static void R_MarkSegBounds(void)
for (; rw_x < rw_stopx; rw_x++)
{
// mark floor / ceiling areas
yl = (topfrac+HEIGHTUNIT-1)>>HEIGHTBITS;
yl = FixedClamp((INT64)topfrac + HEIGHTUNIT-1)>>HEIGHTBITS;
yh = bottomfrac>>HEIGHTBITS;
// Mark ceiling
@@ -1822,7 +1810,7 @@ void R_StoreWallRange(INT32 start, INT32 stop)
// big room fix
if (longboi)
rw_distance = (fixed_t)R_CalcSegDist(curline,viewx,viewy);
rw_distance = FixedClamp(R_CalcSegDist(curline, viewx, viewy));
ds_p->x1 = rw_x = start;
ds_p->x2 = stop;
@@ -2205,8 +2193,8 @@ void R_StoreWallRange(INT32 start, INT32 stop)
}
}
rw_toptexturemid += sidedef->rowoffset;
rw_bottomtexturemid += sidedef->rowoffset;
rw_toptexturemid = FixedClamp((INT64)rw_toptexturemid + sidedef->rowoffset);
rw_bottomtexturemid = FixedClamp((INT64)rw_bottomtexturemid + sidedef->rowoffset);
R_AllocTextureColumnTables(rw_stopx - start);
@@ -2491,8 +2479,9 @@ void R_StoreWallRange(INT32 start, INT32 stop)
rw_offset = -rw_offset;
/// don't use texture offset for splats
rw_offset2 = rw_offset + curline->offset;
rw_offset += sidedef->textureoffset + curline->offset;
rw_offset2 = FixedClamp((INT64)rw_offset + curline->offset);
rw_offset = FixedClamp((INT64)rw_offset + (INT64)sidedef->textureoffset + curline->offset);
rw_centerangle = ANGLE_90 + viewangle - rw_normalangle;
// calculate light table
@@ -2552,8 +2541,8 @@ void R_StoreWallRange(INT32 start, INT32 stop)
auto set_topstep_normal = [&]
{
topstep = -FixedMul (rw_scalestep, worldtop);
topfrac = (centeryfrac>>4) - FixedMul (worldtop, rw_scale);
topstep = -FixedMul(rw_scalestep, worldtop);
topfrac = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldtop, rw_scale));
};
// untextured seg
@@ -2574,14 +2563,14 @@ void R_StoreWallRange(INT32 start, INT32 stop)
// this is an attempt to fix issues with textureless single sided lines drawing nothing where they should just draw sky instead
if (tophigh && !backsector && frontsector->ceilingpic == skyflatnum)
{
topstep = -FixedMul (rw_scalestep, worldbottom);
topfrac = (centeryfrac>>4) - FixedMul (worldbottom, rw_scale);
topstep = -FixedMul(rw_scalestep, worldbottom);
topfrac = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldbottom, rw_scale));
// account for slopes to try and get rid of sharp edges from the black void
if (frontsector->f_slope || (backsector && backsector->f_slope))
{
topstep = -FixedMul (rw_scalestep, worldbottomslope);
topfrac = (centeryfrac>>4) - FixedMul (worldbottomslope, rw_scale);
topstep = -FixedMul(rw_scalestep, worldbottomslope);
topfrac = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldbottomslope, rw_scale));
}
}
else
@@ -2590,18 +2579,18 @@ void R_StoreWallRange(INT32 start, INT32 stop)
else
set_topstep_normal();
bottomstep = -FixedMul (rw_scalestep, worldbottom);
bottomfrac = (centeryfrac>>4) - FixedMul (worldbottom, rw_scale);
bottomstep = -FixedMul(rw_scalestep, worldbottom);
bottomfrac = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldbottom, rw_scale));
if (frontsector->c_slope)
{
fixed_t topfracend = (centeryfrac>>4) - FixedMul (worldtopslope, ds_p->scale2);
fixed_t topfracend = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldtopslope, ds_p->scale2));
topstep = (topfracend-topfrac)/(range);
}
if (frontsector->f_slope)
{
fixed_t bottomfracend = (centeryfrac>>4) - FixedMul (worldbottomslope, ds_p->scale2);
fixed_t bottomfracend = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldbottomslope, ds_p->scale2));
bottomstep = (bottomfracend-bottomfrac)/(range);
}
}
@@ -2643,9 +2632,9 @@ void R_StoreWallRange(INT32 start, INT32 stop)
continue;
}
rlight->height = (centeryfrac>>4) - FixedMul(leftheight, rw_scale);
rlight->heightstep = (centeryfrac>>4) - FixedMul(rightheight, ds_p->scale2);
rlight->heightstep = (rlight->heightstep-rlight->height)/(range);
rlight->height = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(leftheight, rw_scale));
rlight->heightstep = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(rightheight, ds_p->scale2));
rlight->heightstep = FixedClamp((INT64)rlight->heightstep - rlight->height)/(range);
rlight->flags = static_cast<ffloortype_e>(light->flags);
if (light->caster && light->caster->flags & FF_CUTSOLIDS)
@@ -2707,9 +2696,9 @@ void R_StoreWallRange(INT32 start, INT32 stop)
if (toptexture)
{
fixed_t topfracend = (centeryfrac>>4) - FixedMul(worldhighslope, ds_p->scale2);
fixed_t topfracend = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldhighslope, ds_p->scale2));
pixhigh = (centeryfrac>>4) - FixedMul (worldhigh, rw_scale);
pixhigh = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldhigh, rw_scale));
pixhighstep = (topfracend-pixhigh)/(range);
// If the lowest part of a ceiling stretching down covers the entire screen
@@ -2719,9 +2708,9 @@ void R_StoreWallRange(INT32 start, INT32 stop)
if (bottomtexture)
{
fixed_t bottomfracend = (centeryfrac>>4) - FixedMul (worldlowslope, ds_p->scale2);
fixed_t bottomfracend = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldlowslope, ds_p->scale2));
pixlow = (centeryfrac>>4) - FixedMul (worldlow, rw_scale);
pixlow = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(worldlow, rw_scale));
pixlowstep = (bottomfracend-pixlow)/(range);
// If the highest part of a floor stretching up covers the entire screen
@@ -2742,8 +2731,8 @@ void R_StoreWallRange(INT32 start, INT32 stop)
visffloor[i].b_pos_slope = roverright;
visffloor[i].b_pos >>= 4;
visffloor[i].b_pos_slope >>= 4;
visffloor[i].b_frac = (centeryfrac >> 4) - FixedMul(visffloor[i].b_pos, rw_scale);
visffloor[i].b_step = (centeryfrac >> 4) - FixedMul(visffloor[i].b_pos_slope, ds_p->scale2);
visffloor[i].b_frac = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(visffloor[i].b_pos, rw_scale));
visffloor[i].b_step = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(visffloor[i].b_pos_slope, ds_p->scale2));
visffloor[i].b_step = (visffloor[i].b_step-visffloor[i].b_frac)/(range);
};
@@ -2849,7 +2838,7 @@ void R_StoreWallRange(INT32 start, INT32 stop)
visffloor[i].b_pos = height;
visffloor[i].b_pos = (visffloor[i].b_pos - viewz) >> 4;
visffloor[i].b_step = FixedMul(-rw_scalestep, visffloor[i].b_pos);
visffloor[i].b_frac = (centeryfrac >> 4) - FixedMul(visffloor[i].b_pos, rw_scale);
visffloor[i].b_frac = FixedClamp((INT64)(centeryfrac>>4) - FixedMul(visffloor[i].b_pos, rw_scale));
};
while (i < numffloors && visffloor[i].polyobj != curline->polyseg)
+7 -5
View File
@@ -11,6 +11,7 @@
/// \file r_things.c
/// \brief Refresh of things, i.e. objects represented by sprites
#include "m_fixed.h"
#include "r_main.h" // stplyr
#include "r_fps.h"
#include "r_things.h"
@@ -391,7 +392,7 @@ boolean R_AddSingleSpriteDef(const char *sprname, spritedef_t *spritedef, UINT16
// allocate space for the frames present and copy sprtemp to it
if (spritedef->numframes && // has been allocated
spritedef->numframes < maxframe) // more frames are defined ?
spritedef->numframes < maxframe) // more frames are defined ?
{
Z_Free(spritedef->spriteframes);
@@ -616,10 +617,11 @@ void R_DrawMaskedColumn(drawcolumndata_t* dc, column_t *column)
if (topdelta <= prevdelta)
topdelta += prevdelta;
prevdelta = topdelta;
topscreen = sprtopscreen + spryscale*topdelta;
bottomscreen = topscreen + spryscale*column->length;
dc->yl = (topscreen+FRACUNIT-1)>>FRACBITS;
topscreen = FixedClamp((INT64)sprtopscreen + (INT64)spryscale * (INT64)topdelta);
bottomscreen = FixedClamp((INT64)topscreen + (INT64)spryscale * (INT64)column->length);
dc->yl = FixedClamp((INT64)topscreen + (FRACUNIT-1))>>FRACBITS;
dc->yh = (bottomscreen-1)>>FRACBITS;
if (windowtop != INT32_MAX && windowbottom != INT32_MAX)
@@ -885,7 +887,7 @@ static void R_DrawVisSprite(vissprite_t *vis)
for (dc.x = vis->x1; dc.x <= vis->x2; dc.x++, spryscale += scalestep)
{
angle_t angle = ((vis->centerangle + xtoviewangle[dc.x]) >> ANGLETOFINESHIFT) & 0xFFF;
texturecolumn = (vis->paperoffset - FixedMul(FINETANGENT(angle), vis->paperdistance)) / horzscale;
texturecolumn = FixedClamp((INT64)vis->paperoffset - FixedMul(FINETANGENT(angle), vis->paperdistance)) / horzscale;
if (texturecolumn < 0 || texturecolumn >= pwidth)
continue;
+1
View File
@@ -35,6 +35,7 @@ set(SRB2_SDL2_SOURCES
i_system.cpp
i_ttf.c
i_video.c
i_threads.c
#IMG_xpm.c
ogl_sdl.c
+2 -2
View File
@@ -1896,8 +1896,8 @@ INT32 I_StartupSystem(void)
I_Fork();
#endif
#ifdef HAVE_THREADS
I_StartThreads();
I_AddExitFunc(I_StopThreads);
I_start_threads();
I_AddExitFunc(I_stop_threads);
I_ThreadPoolInit();
I_AddExitFunc(I_ThreadPoolShutdown);
#endif
+360
View File
@@ -0,0 +1,360 @@
// SONIC ROBO BLAST 2 KART
//-----------------------------------------------------------------------------
// Copyright (C) 2020 by James R.
//
// This program is free software distributed under the
// terms of the GNU General Public License, version 2.
// See the 'LICENSE' file for more details.
//-----------------------------------------------------------------------------
/// \file i_threads.c
/// \brief Multithreading abstraction
#ifdef HAVE_THREADS
#include "../doomdef.h"
#include "../i_threads.h"
#include <SDL.h>
typedef void * (*Create_fn)(void);
struct Link;
struct Thread;
typedef struct Link * Link;
typedef struct Thread * Thread;
struct Link
{
void * data;
Link next;
Link prev;
};
struct Thread
{
I_thread_fn entry;
void * userdata;
SDL_Thread * thread;
};
static Link i_thread_pool;
static Link i_mutex_pool;
static Link i_cond_pool;
static I_mutex i_thread_pool_mutex;
static I_mutex i_mutex_pool_mutex;
static I_mutex i_cond_pool_mutex;
static SDL_atomic_t i_threads_running = {1};
static Link
Insert_link (
Link * head,
Link link
){
link->prev = NULL;
link->next = (*head);
if ((*head))
(*head)->prev = link;
(*head) = link;
return link;
}
static void
Free_link (
Link * head,
Link link
){
if (link->prev)
link->prev->next = link->next;
else
(*head) = link->next;
if (link->next)
link->next->prev = link->prev;
free(link->data);
free(link);
}
static Link
New_link (void *data)
{
Link link;
link = malloc(sizeof *link);
if (! link)
abort();
link->data = data;
return link;
}
static void *
Identity (
Link * pool_anchor,
I_mutex pool_mutex,
void ** anchor,
Create_fn create_fn
){
void * id;
id = SDL_AtomicGetPtr(anchor);
if (! id)
{
I_lock_mutex(&pool_mutex);
{
id = SDL_AtomicGetPtr(anchor);
if (! id)
{
id = (*create_fn)();
if (! id)
abort();
Insert_link(pool_anchor, New_link(id));
SDL_AtomicSetPtr(anchor, id);
}
}
I_unlock_mutex(pool_mutex);
}
return id;
}
static int
Worker (
Link link
){
Thread th;
th = link->data;
(*th->entry)(th->userdata);
if (SDL_AtomicGet(&i_threads_running))
{
I_lock_mutex(&i_thread_pool_mutex);
{
if (SDL_AtomicGet(&i_threads_running))
{
SDL_DetachThread(th->thread);
Free_link(&i_thread_pool, link);
}
}
I_unlock_mutex(i_thread_pool_mutex);
}
return 0;
}
void
I_spawn_thread (
const char * name,
I_thread_fn entry,
void * userdata
){
Link link;
Thread th;
th = malloc(sizeof *th);
if (! th)
abort();/* this is pretty GNU of me */
th->entry = entry;
th->userdata = userdata;
I_lock_mutex(&i_thread_pool_mutex);
{
link = Insert_link(&i_thread_pool, New_link(th));
if (SDL_AtomicGet(&i_threads_running))
{
th->thread = SDL_CreateThread(
(SDL_ThreadFunction)Worker,
name,
link
);
if (! th->thread)
abort();
}
}
I_unlock_mutex(i_thread_pool_mutex);
}
int
I_thread_is_stopped (void)
{
return ( ! SDL_AtomicGet(&i_threads_running) );
}
void
I_start_threads (void)
{
i_thread_pool_mutex = SDL_CreateMutex();
i_mutex_pool_mutex = SDL_CreateMutex();
i_cond_pool_mutex = SDL_CreateMutex();
if (!(
i_thread_pool_mutex &&
i_mutex_pool_mutex &&
i_cond_pool_mutex
)){
abort();
}
}
void
I_stop_threads (void)
{
Link link;
Link next;
Thread th;
SDL_mutex * mutex;
SDL_cond * cond;
if (i_threads_running.value)
{
/* rely on the good will of thread-san */
SDL_AtomicSet(&i_threads_running, 0);
I_lock_mutex(&i_thread_pool_mutex);
{
for (
link = i_thread_pool;
link;
link = next
){
next = link->next;
th = link->data;
SDL_WaitThread(th->thread, NULL);
free(th);
free(link);
}
}
I_unlock_mutex(i_thread_pool_mutex);
for (
link = i_mutex_pool;
link;
link = next
){
next = link->next;
mutex = link->data;
SDL_DestroyMutex(mutex);
free(link);
}
for (
link = i_cond_pool;
link;
link = next
){
next = link->next;
cond = link->data;
SDL_DestroyCond(cond);
free(link);
}
SDL_DestroyMutex(i_thread_pool_mutex);
SDL_DestroyMutex(i_mutex_pool_mutex);
SDL_DestroyMutex(i_cond_pool_mutex);
}
}
void
I_lock_mutex (
I_mutex * anchor
){
SDL_mutex * mutex;
mutex = Identity(
&i_mutex_pool,
i_mutex_pool_mutex,
anchor,
(Create_fn)SDL_CreateMutex
);
if (SDL_LockMutex(mutex) == -1)
abort();
}
void
I_unlock_mutex (
I_mutex id
){
if (SDL_UnlockMutex(id) == -1)
abort();
}
void
I_hold_cond (
I_cond * cond_anchor,
I_mutex mutex_id
){
SDL_cond * cond;
cond = Identity(
&i_cond_pool,
i_cond_pool_mutex,
cond_anchor,
(Create_fn)SDL_CreateCond
);
if (SDL_CondWait(cond, mutex_id) == -1)
abort();
}
void
I_wake_one_cond (
I_cond * anchor
){
SDL_cond * cond;
cond = Identity(
&i_cond_pool,
i_cond_pool_mutex,
anchor,
(Create_fn)SDL_CreateCond
);
if (SDL_CondSignal(cond) == -1)
abort();
}
void
I_wake_all_cond (
I_cond * anchor
){
SDL_cond * cond;
cond = Identity(
&i_cond_pool,
i_cond_pool_mutex,
anchor,
(Create_fn)SDL_CreateCond
);
if (SDL_CondBroadcast(cond) == -1)
abort();
}
#endif // HAVE_THREADS
+3 -1
View File
@@ -3716,7 +3716,9 @@ void V_DoPostProcessor(INT32 view, INT32 param)
// Make sure table is built
if (heatshifter == NULL || lastheight != viewheight)
{
Z_Free(heatshifter);
if (heatshifter)
Z_Free(heatshifter);
heatshifter = Z_Calloc(viewheight * sizeof(boolean), PU_STATIC, NULL);
for (y = 0; y < viewheight; y++)
+4 -3
View File
@@ -122,9 +122,7 @@ void W_Shutdown(void)
if (wad->handle)
fclose(wad->handle);
Z_Free(wad->filename);
while (wad->numlumps--)
{
Z_Free(wad->lumpinfo[wad->numlumps].longname);
@@ -2732,7 +2730,10 @@ void vres_Free(virtres_t* vres)
while (vres->numlumps--)
{
Z_Free(vres->vlumps[vres->numlumps].data);
if (vres->vlumps[vres->numlumps].data)
{
Z_Free(vres->vlumps[vres->numlumps].data);
}
}
Z_Free(vres->vlumps);
-15
View File
@@ -75,8 +75,6 @@ typedef struct memblock_s
#define MEMORY(x) (void *)((uintptr_t)(x) + sizeof(memblock_t) + ALIGNPAD)
#define MEMBLOCK(x) (memblock_t *)((uintptr_t)(x) - ALIGNPAD - sizeof(memblock_t))
static thread_handle_t main_thread;
// both the head and tail of the zone memory block list
static memblock_t head;
@@ -110,7 +108,6 @@ static void Command_Memdump_f(void);
void Z_Init(void)
{
size_t total, memfree;
main_thread = I_GetCurrentThread();
memset(&head, 0x00, sizeof(head));
@@ -146,8 +143,6 @@ void Z_Free(void *ptr)
{
memblock_t *block;
I_Assert(I_GetCurrentThread() == main_thread);
if (ptr == NULL)
return;
@@ -242,8 +237,6 @@ void *Z_Malloc(size_t size, INT32 tag, void *user)
memblock_t *block;
void *ptr;
I_Assert(I_GetCurrentThread() == main_thread);
#ifdef ZDEBUG2
CONS_Debug(DBG_MEMORY, "Z_Malloc %s:%d\n", file, line);
#endif
@@ -307,8 +300,6 @@ void *Z_Calloc2(size_t size, INT32 tag, void *user, const char *file, INT32 line
void *Z_Calloc(size_t size, INT32 tag, void *user)
#endif
{
I_Assert(I_GetCurrentThread() == main_thread);
#ifdef VALGRIND_MEMPOOL_ALLOC
Z_calloc = true;
#endif
@@ -344,8 +335,6 @@ void *Z_Realloc(void *ptr, size_t size, INT32 tag, void *user)
memblock_t *block;
size_t copysize;
I_Assert(I_GetCurrentThread() == main_thread);
#ifdef ZDEBUG2
CONS_Debug(DBG_MEMORY, "Z_Realloc %s:%d\n", file, line);
#endif
@@ -425,8 +414,6 @@ void Z_FreeTags(INT32 lowtag, INT32 hightag)
{
memblock_t *block, *next;
I_Assert(I_GetCurrentThread() == main_thread);
#ifdef ZDEBUG
Z_CheckHeap2(file, line);
#else
@@ -460,8 +447,6 @@ void Z_IterateTags(INT32 lowtag, INT32 hightag, boolean (*iterfunc)(void *))
{
memblock_t *block, *next;
I_Assert(I_GetCurrentThread() == main_thread);
if (!iterfunc)
I_Error("Z_IterateTags: no iterator function was given");
+1 -1
View File
@@ -91,7 +91,7 @@ void Z_Init(void);
// Z_Free and alloc with alignment
#ifdef ZDEBUG
#define Z_Free(p) Z_Free2(p, __FILE__, __LINE__)
#define Z_Free(p) Z_Free2(p, __FILE__, __LINE__)
#define Z_Malloc(s,t,u) Z_Malloc2(s, t, u, __FILE__, __LINE__)
#define Z_Calloc(s,t,u) Z_Calloc2(s, t, u, __FILE__, __LINE__)
#define Z_Realloc(p,s,t,u) Z_Realloc2(p,s, t, u, __FILE__, __LINE__)