# rspektrum - hand-written Makefile (GNU make + gcc, no premake/lua).
#
# Quick start:
#   make            # release build  -> bin/Release/rspektrum
#   make DEBUG=1    # debug build    -> bin/Debug/rspektrum
#   make run        # build + launch
#   make test       # build + run the DSP correctness tests
#   make bench      # build + run the FFT benchmark over mlnl_samples.wav
#   make clean      # remove build artifacts for the current config
#
# Override the toolchain or flags on the command line, e.g.
#   make CC=clang
#   make ARCH="-march=native"     # bleeding-edge tune for your own machine
#
# Pure C project (raylib is vendored as source and compiled in). Linux/X11.

# ---- toolchain ----------------------------------------------------------
CC      ?= gcc
AR      ?= ar

# ---- config: release (default) or DEBUG=1 -------------------------------
# ARCH is the portable baseline tune; override to -march=native for a local
# build. x86-64-v3 == AVX2 + FMA (~2013+), the sweet spot for the float FFT.
ARCH    ?= -march=x86-64-v3

ifdef DEBUG
  BUILD     := Debug
  OPT       := -g
  DEFCONFIG := -DDEBUG
else
  BUILD     := Release
  OPT       := -O3 -ffast-math $(ARCH)
  DEFCONFIG := -DNDEBUG
  STRIP     := -s
endif

BINDIR := bin/$(BUILD)
OBJDIR := obj/$(BUILD)
TARGET := $(BINDIR)/rspektrum
RAYLIB := $(BINDIR)/libraylib.a

# ---- shared flags -------------------------------------------------------
RAYLIB_SRC := build/external/raylib-master/src
DEFINES    := $(DEFCONFIG) -DPLATFORM_DESKTOP -DGRAPHICS_API_OPENGL_33 -D_GLFW_X11
INCLUDES   := -Isrc -Iinclude -I$(RAYLIB_SRC) -I$(RAYLIB_SRC)/external/glfw/include
CFLAGS     := -std=c17 -Wall -Wshadow $(OPT) $(DEFINES) $(INCLUDES)
DEPFLAGS    = -MMD -MP
LDLIBS     := -lpthread -lm -ldl -lrt -lX11
LDFLAGS    := $(STRIP)

# ---- sources ------------------------------------------------------------
# App: every src/*.c except the non-Linux platform backends.
APP_SRC := $(filter-out src/platform_win32.c src/platform_web.c,$(wildcard src/*.c))
APP_OBJ := $(patsubst src/%.c,$(OBJDIR)/app/%.o,$(APP_SRC))

# raylib: explicit list of the modules we link (matches the vendored tree).
RAY_MODULES := rcore rshapes rtextures rtext rmodels raudio rglfw
RAY_OBJ     := $(patsubst %,$(OBJDIR)/raylib/%.o,$(RAY_MODULES))

DEPS := $(APP_OBJ:.o=.d) $(RAY_OBJ:.o=.d)

# ---- top-level targets --------------------------------------------------
.PHONY: all run test bench clean help
.DEFAULT_GOAL := all

all: $(TARGET)

$(TARGET): $(APP_OBJ) $(RAYLIB) | $(BINDIR)
	@echo "Linking $@"
	$(CC) $(LDFLAGS) -o $@ $(APP_OBJ) $(RAYLIB) $(LDLIBS)

$(RAYLIB): $(RAY_OBJ) | $(BINDIR)
	@echo "Archiving $@"
	$(AR) rcs $@ $(RAY_OBJ)

# ---- compile rules ------------------------------------------------------
$(OBJDIR)/app/%.o: src/%.c | $(OBJDIR)/app
	@echo "  CC $<"
	$(CC) $(CFLAGS) $(DEPFLAGS) -c $< -o $@

$(OBJDIR)/raylib/%.o: $(RAYLIB_SRC)/%.c | $(OBJDIR)/raylib
	@echo "  CC $<"
	$(CC) $(CFLAGS) $(DEPFLAGS) -c $< -o $@

# ---- dirs ---------------------------------------------------------------
$(BINDIR) $(OBJDIR)/app $(OBJDIR)/raylib:
	@mkdir -p $@

# ---- convenience --------------------------------------------------------
run: $(TARGET)
	./$(TARGET)

# DSP tests/benchmarks (fft.c is standalone, so they link it directly with the
# same release flags this Makefile uses).
test:
	$(MAKE) -C bench test CC="$(CC)" CFLAGS="-O3 -ffast-math $(ARCH) -Wall"

bench:
	$(MAKE) -C bench bench CC="$(CC)" CFLAGS="-O3 -ffast-math $(ARCH) -Wall"

clean:
	rm -rf $(OBJDIR) $(TARGET) $(RAYLIB)
	$(MAKE) -C bench clean

help:
	@echo "Targets: all (default), run, test, bench, clean"
	@echo "Configs: release (default), or 'make DEBUG=1'"
	@echo "Vars:    CC, AR, ARCH (e.g. ARCH=-march=native)"

-include $(DEPS)
