[Add] Automagically give backtraces in DEBUG mode.
This commit is contained in:
parent
39c7a4ecd5
commit
2a69789a24
38
bin/Makefile
38
bin/Makefile
@ -26,19 +26,6 @@ CXML = $(shell xml2-config --cflags)
|
|||||||
CTTF = $(shell freetype-config --cflags)
|
CTTF = $(shell freetype-config --cflags)
|
||||||
CGL =
|
CGL =
|
||||||
CFLAGS = $(CLUA) $(CSDL) $(CXML) $(CTTF) $(CGL) $(VERSION) -D$(OS)
|
CFLAGS = $(CLUA) $(CSDL) $(CXML) $(CTTF) $(CGL) $(VERSION) -D$(OS)
|
||||||
ifeq ($(OS),LINUX)
|
|
||||||
CFLAGS += -D_POSIX_SOURCE
|
|
||||||
endif
|
|
||||||
ifdef DEBUG
|
|
||||||
CFLAGS += -W -Wall -Wextra -Wunused -Wshadow -Wpointer-arith -Wmissing-prototypes \
|
|
||||||
-Winline -Wcast-align -Wmissing-declarations -fstack-protector \
|
|
||||||
-fstack-protector-all -g3 -DDEBUG -DLUA_USE_APICHECK -std=c99
|
|
||||||
ifdef DEBUG_PARANOID
|
|
||||||
CFLAGS += -DDEBUG_PARANOID
|
|
||||||
endif
|
|
||||||
else
|
|
||||||
CFLAGS += -O2 -funroll-loops -pipe -std=c99
|
|
||||||
endif
|
|
||||||
|
|
||||||
# LDFLAGS.
|
# LDFLAGS.
|
||||||
LDLUA = ../lib/lua/liblua.a
|
LDLUA = ../lib/lua/liblua.a
|
||||||
@ -49,6 +36,31 @@ LDGL = -lGL
|
|||||||
LDPNG = -lpng
|
LDPNG = -lpng
|
||||||
LDFLAGS = -lm $(LDLUA) $(LDSDL) $(LDXML) $(LDTTF) $(LDGL) $(LDPNG)
|
LDFLAGS = -lm $(LDLUA) $(LDSDL) $(LDXML) $(LDTTF) $(LDGL) $(LDPNG)
|
||||||
|
|
||||||
|
# OS Stuff.
|
||||||
|
ifeq ($(OS),LINUX)
|
||||||
|
CFLAGS += -D_POSIX_SOURCE
|
||||||
|
endif
|
||||||
|
|
||||||
|
# Debug stuff.
|
||||||
|
ifdef DEBUG
|
||||||
|
CFLAGS += -W -Wall -Wextra -Wunused -Wshadow -Wpointer-arith -Wmissing-prototypes \
|
||||||
|
-Winline -Wcast-align -Wmissing-declarations -fstack-protector \
|
||||||
|
-fstack-protector-all -g3 -DDEBUG -DLUA_USE_APICHECK -std=c99
|
||||||
|
|
||||||
|
ifdef DEBUG_PARANOID
|
||||||
|
CFLAGS += -DDEBUG_PARANOID
|
||||||
|
endif
|
||||||
|
|
||||||
|
# Handle OS Debug stuff here.
|
||||||
|
ifeq ($(OS), LINUX)
|
||||||
|
LDFLAGS += -rdynamic
|
||||||
|
endif # Linux.
|
||||||
|
|
||||||
|
else # DEBUG
|
||||||
|
CFLAGS += -O2 -funroll-loops -pipe -std=c99
|
||||||
|
endif
|
||||||
|
|
||||||
|
|
||||||
# This is just for gstat to run some analysis on performance.
|
# This is just for gstat to run some analysis on performance.
|
||||||
ifdef DEBUG
|
ifdef DEBUG
|
||||||
LDFLAGS += -pg
|
LDFLAGS += -pg
|
||||||
|
@ -10,8 +10,17 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include <SDL/SDL.h>
|
#include <SDL/SDL.h>
|
||||||
#include <string.h>
|
|
||||||
|
|
||||||
|
/* Global. */
|
||||||
|
#include <string.h>
|
||||||
|
#if defined(LINUX) && !defined(NODEBUG)
|
||||||
|
#include <signal.h>
|
||||||
|
#include <execinfo.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
#endif /* defined(LINUX) && !defined(NODEBUG) */
|
||||||
|
|
||||||
|
/* Local. */
|
||||||
#include "lephisto.h"
|
#include "lephisto.h"
|
||||||
#include "conf.h"
|
#include "conf.h"
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
@ -74,15 +83,17 @@ static void print_SDLversion(void);
|
|||||||
static void load_screen(void);
|
static void load_screen(void);
|
||||||
static void load_all(void);
|
static void load_all(void);
|
||||||
static void unload_all(void);
|
static void unload_all(void);
|
||||||
void main_loop(void);
|
|
||||||
static void display_fps(const double dt);
|
static void display_fps(const double dt);
|
||||||
static void window_caption(void);
|
static void window_caption(void);
|
||||||
static void data_name(void);
|
static void data_name(void);
|
||||||
|
static void debug_sigInit(void);
|
||||||
/* Update. */
|
/* Update. */
|
||||||
static void fps_control(void);
|
static void fps_control(void);
|
||||||
static void update_all(void);
|
static void update_all(void);
|
||||||
static void update_routine(double dt);
|
static void update_routine(double dt);
|
||||||
static void render_all(void);
|
static void render_all(void);
|
||||||
|
/* Misc. */
|
||||||
|
void main_loop(void); /* dialogue.c */
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -112,6 +123,9 @@ int main(int argc, char** argv) {
|
|||||||
/* Initialize SDL for possible warnings. */
|
/* Initialize SDL for possible warnings. */
|
||||||
SDL_Init(0);
|
SDL_Init(0);
|
||||||
|
|
||||||
|
/* Set up debug signal handlers. */
|
||||||
|
debug_sigInit();
|
||||||
|
|
||||||
/* Create the home directory if needed. */
|
/* Create the home directory if needed. */
|
||||||
if(lfile_dirMakeExist("."))
|
if(lfile_dirMakeExist("."))
|
||||||
WARN("Unable to create lephisto directory '%s'", lfile_basePath());
|
WARN("Unable to create lephisto directory '%s'", lfile_basePath());
|
||||||
@ -591,3 +605,82 @@ static void print_SDLversion(void) {
|
|||||||
WARN("SDL is older than compiled version.");
|
WARN("SDL is older than compiled version.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if defined(LINUX) && !defined(NODEBUG)
|
||||||
|
/**
|
||||||
|
* @brief Get the string related to the signal code.
|
||||||
|
* @param sig Signal to which code belongs.
|
||||||
|
* @param sig_code Signal code to get string of.
|
||||||
|
* @return String of signal code.
|
||||||
|
*/
|
||||||
|
static const char* debug_sigCodeToStr(int sig, int sig_code) {
|
||||||
|
if(sig == SIGFPE)
|
||||||
|
switch(sig_code) {
|
||||||
|
case FPE_INTDIV: return "SIGFPE (integer divide by zero)";
|
||||||
|
case FPE_INTOVF: return "SIGFPE (integer overflow)";
|
||||||
|
case FPE_FLTDIV: return "SIGFPE (floating-point divide by zero)";
|
||||||
|
case FPE_FLTOVF: return "SIGFPE (floating-point overflow)";
|
||||||
|
case FPE_FLTUND: return "SIGFPE (floating-point underflow)";
|
||||||
|
case FPE_FLTRES: return "SIGFPE (floating-point inexact result)";
|
||||||
|
case FPE_FLTINV: return "SIGFPE (floating-point invalid operation)";
|
||||||
|
case FPE_FLTSUB: return "SIGFPE (subscript out of range)";
|
||||||
|
default: return "SIGFPE";
|
||||||
|
}
|
||||||
|
else if(sig == SIGSEGV)
|
||||||
|
switch(sig_code) {
|
||||||
|
case SEGV_MAPERR: return "SIGEGV (address not mapped to object)";
|
||||||
|
case SEGV_ACCERR: return "SIGEGV (invalid permissions for mapped object)";
|
||||||
|
default: return "SIGSEGV";
|
||||||
|
}
|
||||||
|
/* No suitable code found. */
|
||||||
|
return strsignal(sig);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Backtrace signal handler for linux.
|
||||||
|
* @param sig Signal.
|
||||||
|
* @param info Signal information.
|
||||||
|
* @param unused Unused.
|
||||||
|
*/
|
||||||
|
static void debug_sigHandler(int sig, siginfo_t* info, void* unused) {
|
||||||
|
(void) sig;
|
||||||
|
(void) unused;
|
||||||
|
int i, num;
|
||||||
|
void* buf[64];
|
||||||
|
char** symbols;
|
||||||
|
|
||||||
|
num = backtrace(buf, 64);
|
||||||
|
symbols = backtrace_symbols(buf, num);
|
||||||
|
|
||||||
|
DEBUG("LEPHISTO recieved %s!",
|
||||||
|
debug_sigCodeToStr(info->si_signo, info->si_code));
|
||||||
|
for(i = 0; i < num; i++)
|
||||||
|
DEBUG(" %s", symbols[i]);
|
||||||
|
DEBUG("Report this to project maintainer with the backtrace.");
|
||||||
|
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
#endif /* defined(LINUX) && !defined(DEBUG) */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Set up the SignalHandler for Linux.
|
||||||
|
*/
|
||||||
|
static void debug_sigInit(void) {
|
||||||
|
#if defined(LINUX) && !defined(NODEBUG)
|
||||||
|
struct sigaction sa, so;
|
||||||
|
|
||||||
|
/* Set up handler. */
|
||||||
|
sa.sa_handler = NULL;
|
||||||
|
sa.sa_sigaction = debug_sigHandler;
|
||||||
|
sigemptyset(&sa.sa_mask);
|
||||||
|
sa.sa_flags = SA_SIGINFO;
|
||||||
|
|
||||||
|
/* Attach signals. */
|
||||||
|
sigaction(SIGSEGV, &sa, &so);
|
||||||
|
if(so.sa_handler == SIG_IGN)
|
||||||
|
DEBUG("Unable to set up SIGSEGV signal handler.");
|
||||||
|
sigaction(SIGFPE, &sa, &so);
|
||||||
|
if(so.sa_handler == SIG_IGN)
|
||||||
|
DEBUG("Unable to set up SIGFPE signal handler.");
|
||||||
|
#endif /* #if defined(LINUX) && !defined(NODEBUG) */
|
||||||
|
}
|
||||||
|
|
||||||
|
@ -5,7 +5,7 @@
|
|||||||
#include "lualib.h"
|
#include "lualib.h"
|
||||||
|
|
||||||
/* Debug stuff. */
|
/* Debug stuff. */
|
||||||
#ifdef DEBUG
|
#ifdef NODEBUG
|
||||||
#define LLUA_DEBUG(str, args...) \
|
#define LLUA_DEBUG(str, args...) \
|
||||||
(fprintf(stdout, "Lua: "str"\n", ## args))
|
(fprintf(stdout, "Lua: "str"\n", ## args))
|
||||||
|
|
||||||
@ -19,11 +19,11 @@
|
|||||||
LLUA_DEBUG("[%s] Too few arguments (%s:%d)", __func__, __FILE__, __LINE__); \
|
LLUA_DEBUG("[%s] Too few arguments (%s:%d)", __func__, __FILE__, __LINE__); \
|
||||||
return 0; \
|
return 0; \
|
||||||
}
|
}
|
||||||
#else /* DEBUG. */
|
#else /* NODEBUG. */
|
||||||
#define LLUA_DEBUG(str, args...) do {;} while(0)
|
#define LLUA_DEBUG(str, args...) do {;} while(0)
|
||||||
#define LLUA_MIN_ARGS(n) do {;} while(0)
|
#define LLUA_MIN_ARGS(n) do {;} while(0)
|
||||||
#define LLUA_INVALID_PARAMETER() do {;} while(0)
|
#define LLUA_INVALID_PARAMETER() do {;} while(0)
|
||||||
#endif /* DEBUG. */
|
#endif /* NODEBUG. */
|
||||||
|
|
||||||
/* Comfortability macros. */
|
/* Comfortability macros. */
|
||||||
#define luaL_dobuffer(L, b, n, s) \
|
#define luaL_dobuffer(L, b, n, s) \
|
||||||
|
@ -9,9 +9,9 @@
|
|||||||
|
|
||||||
#define LOG(str, args...)(fprintf(stdout, str"\n", ## args))
|
#define LOG(str, args...)(fprintf(stdout, str"\n", ## args))
|
||||||
#ifdef DEBUG_PARANOID /* Will cause WARN's to blow up. */
|
#ifdef DEBUG_PARANOID /* Will cause WARN's to blow up. */
|
||||||
#define WARN(str, args...)(fprintf(stderr, "Warning: "str"\n", ## args), assert(0))
|
#define WARN(str, args...)(fprintf(stderr, "Warning: [%s] "str"\n", __func__, ## args), assert(0))
|
||||||
#else
|
#else
|
||||||
#define WARN(str, args...)(fprintf(stderr, "Warning: "str"\n", ## args))
|
#define WARN(str, args...)(fprintf(stderr, "Warning: [%s] "str"\n", __func__, ## args))
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define ERR(str, args...) (fprintf(stderr, "ERROR %s:%d: [%s] "str"\n", \
|
#define ERR(str, args...) (fprintf(stderr, "ERROR %s:%d: [%s] "str"\n", \
|
||||||
|
Loading…
Reference in New Issue
Block a user