From 0bdf79cc51bf0ac1d06e77a643aac035e848a0b6 Mon Sep 17 00:00:00 2001 From: fgsfds Date: Tue, 12 Nov 2024 22:08:18 +0100 Subject: [PATCH 1/6] port: build: move to CMake god forgive me --- CMakeLists.txt | 292 ++++++++++++ Makefile | 812 ---------------------------------- Makefile.port | 358 --------------- cmake/AssetUtils.cmake | 27 ++ cmake/FindSDL2.cmake | 172 +++++++ cmake/TargetArch.cmake | 165 +++++++ port/include/versioninfo.h.in | 11 + tools/assetmgr/assetmgr.py | 10 +- tools/assetmgr/mkanims | 7 +- tools/assetmgr/mksequences | 7 +- tools/assetmgr/mktextures | 7 +- 11 files changed, 693 insertions(+), 1175 deletions(-) create mode 100644 CMakeLists.txt delete mode 100644 Makefile delete mode 100644 Makefile.port create mode 100644 cmake/AssetUtils.cmake create mode 100644 cmake/FindSDL2.cmake create mode 100644 cmake/TargetArch.cmake create mode 100644 port/include/versioninfo.h.in diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 000000000..36a368ea9 --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,292 @@ +cmake_minimum_required(VERSION 3.16) +list(APPEND CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake) + +project(pd C CXX) + +include(TargetArch) +include(FindPkgConfig) +include(AssetUtils) + +set(CMAKE_C_STANDARD 11) +set(CMAKE_CXX_STANDARD 20) + +# On first build set the build type to RelWithDebInfo if it's not already set +if (NOT EXISTS ${CMAKE_BINARY_DIR}/CMakeCache.txt) + if (NOT CMAKE_BUILD_TYPE) + set(CMAKE_BUILD_TYPE "RelWithDebInfo" CACHE STRING "" FORCE) + endif() +endif() + +# Options + +set(ROMID "ntsc-final" CACHE STRING "Which ROM to build an executable for: ntsc-final, pal-final or jpn-final") +option(FORCE_CROSSCOMPILE "Force cross compiling" NO) + +# Determine target arch + +target_architecture(TARGET_ARCH) + +# TODO +set(TARGET_IS_BIG_ENDIAN FALSE) + +if((TARGET_ARCH MATCHES "unknown") OR (TARGET_ARCH STREQUAL "")) + message(FATAL_ERROR "Unknown target arch") +elseif(TARGET_ARCH MATCHES "64") + set(TARGET_IS_64BIT TRUE) +else() + set(TARGET_IS_64BIT FALSE) +endif() + +message(STATUS "Target arch: ${TARGET_ARCH}") + +# Determine target OS and platform identifier ($arch-$os) + +if(WIN32) + # Windows + set(TARGET_OS "windows") +elseif(APPLE) + # OSX + set(TARGET_OS "osx") +elseif(UNIX) + # Generic *nix; assume Linux + set(TARGET_OS "linux") +else() + # ??? + message(FATAL_ERROR "Unknown target OS or compiler") +endif() + +set(TARGET_PLATFORM "${TARGET_ARCH}-${TARGET_OS}") + +message(STATUS "Target platform: ${TARGET_PLATFORM}") + +# Calculate version info and binary name + +set(VERSION_IS_PAL 0) + +if(ROMID STREQUAL "ntsc-final") + set(VERSION 2) + set(BIN_REGION "") +elseif(ROMID STREQUAL "pal-final") + set(VERSION 4) + set(BIN_REGION ".pal") + set(VERSION_IS_PAL 1) +elseif(ROMID STREQUAL "jpn-final") + set(VERSION 5) + set(BIN_REGION ".jpn") +else() + message(FATAL_ERROR "Unknown ROM ID: ${ROMID}") +endif() + +# git commit hash +execute_process( + COMMAND git rev-parse --short HEAD + WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} + OUTPUT_VARIABLE VERSION_HASH + OUTPUT_STRIP_TRAILING_WHITESPACE +) + +# git branch name +execute_process( + COMMAND git rev-parse --abbrev-ref HEAD + WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} + OUTPUT_VARIABLE VERSION_BRANCH + OUTPUT_STRIP_TRAILING_WHITESPACE +) + +set(VERSION_TARGET "${TARGET_PLATFORM}") +set(VERSION_ARCH "${TARGET_ARCH}") +set(VERSION_ROMID "${ROMID}") +set(VERSION_BUILD "${CMAKE_BUILD_TYPE}") + +if((VERSION_BRANCH STREQUAL "") OR (VERSION_BRANCH STREQUAL "HEAD")) + set(VERSION_BRANCH "port-custom") +endif() + +message(STATUS "Version: ${VERSION_ROMID}, hash ${VERSION_HASH}, branch ${VERSION_BRANCH}") + +configure_file("${CMAKE_SOURCE_DIR}/port/include/versioninfo.h.in" "${CMAKE_BINARY_DIR}/port/include/versioninfo.h" @ONLY) + +set(ASSET_DIR "src/assets/${ROMID}") +set(GENERATED_DIR "src/generated/${ROMID}") + +set(ENV{ROMID} ${ROMID}) + +# Build folder postfix + +set(BUILD_ID "${VERSION_ROMID}-${VERSION_TARGET}") + +# Compiler defs + +add_definitions( + -DMATCHING=0 + -DPIRACYCHECKS=0 + -DROM_SIZE=32 + -DAVOID_UB=1 + -D_LANGUAGE_C=1 + -DPAL=${VERSION_IS_PAL} + -DVERSION=${VERSION} +) + +if(TARGET_IS_64BIT) + add_definitions(-DPLATFORM_64BIT=1) +endif() + +# Compiler flags + +# Include directories +include_directories("${CMAKE_SOURCE_DIR}/include") +include_directories("${CMAKE_SOURCE_DIR}/include/PR") +include_directories("${CMAKE_SOURCE_DIR}/src/include") +include_directories("${CMAKE_BINARY_DIR}/src/generated/${ROMID}") +include_directories("${CMAKE_SOURCE_DIR}/src/lib/ultra/audio") +include_directories("${CMAKE_SOURCE_DIR}/port/include") +include_directories("${CMAKE_BINARY_DIR}/port/include") + +# Common CFLAGS +add_compile_options( + -fno-inline-functions + -fno-strict-aliasing + -funsigned-char + -fwrapv + -include "versioninfo.h" +) + +# Common warning flags +add_compile_options( + -Wall + -Wno-address + -Wno-int-in-bool-context + -Wno-misleading-indentation + -Wno-missing-braces + -Wno-multichar + -Wno-tautological-compare + -Wno-unused-but-set-variable + -Wno-unused-value + -Wno-unused-variable + -Wno-format-truncation +) + +# C specific flags +add_compile_options($<$:-Wno-pointer-sign>) + +# C++ specific flags +add_compile_options($<$:-Wno-unused-function>) + +# Dependencies + +set(LIBS ) + +# SDL2 +find_package(SDL2 REQUIRED) +include_directories(SYSTEM "${SDL2_INCLUDE_DIR}") +list(APPEND LIBS "${SDL2_LIBRARY}") + +# ZLib +find_package(ZLIB REQUIRED) +list(APPEND LIBS "${ZLIB_LIBRARY}") + +# GL +if(NOT GL_LIBRARY) + if(WIN32) + set(GL_LIBRARY "opengl32") + else() + set(GL_LIBRARY "GL") + endif() +endif() +list(APPEND LIBS "${GL_LIBRARY}") + +# Platform-specific extra libs +if(NOT EXTRA_LIBRARIES) + if(WIN32) + set(EXTRA_LIBRARIES dbghelp) + else() + set(EXTRA_LIBRARIES m dl) + endif() +endif() +list(APPEND LIBS "${EXTRA_LIBRARIES}") + +# Sources + +file(GLOB_RECURSE SRC_PORT "${CMAKE_SOURCE_DIR}/port/*.c") +file(GLOB_RECURSE SRC_PORT_CXX "${CMAKE_SOURCE_DIR}/port/*.cpp") + +file(GLOB_RECURSE SRC_GAME "${CMAKE_SOURCE_DIR}/src/game/*.c") + +file(GLOB SRC_LIB_MP3 "${CMAKE_SOURCE_DIR}/src/lib/mp3/*.c") +file(GLOB SRC_LIB_NAUDIO "${CMAKE_SOURCE_DIR}/src/lib/naudio/*.c") +file(GLOB SRC_LIB_ULTRA_AUDIO "${CMAKE_SOURCE_DIR}/src/lib/ultra/audio/*.c") +file(GLOB SRC_LIB_GU "${CMAKE_SOURCE_DIR}/src/lib/ultra/gu/*.c") +set(SRC_LIB + src/lib/ultra/io/vimodentsclan1.c + src/lib/ultra/io/vimodepallan1.c + src/lib/ultra/io/vimodempallan1.c + src/lib/ultra/io/vitbl.c + src/lib/ailist.c + src/lib/anim.c + src/lib/args.c + src/lib/audiodma.c + src/lib/audiomgr.c + src/lib/base.c + src/lib/collision.c + src/lib/debughud.c + src/lib/dma.c + src/lib/fault.c + src/lib/joy.c + src/lib/lib_2f490_c.c + src/lib/lib_2fc60.c + src/lib/lib_3e3e0.c + src/lib/lib_04f60nb.c + src/lib/lib_17ce0.c + src/lib/lib_034d0.c + src/lib/lib_39c80.c + src/lib/lib_15850.c + src/lib/mema.c + src/lib/memp.c + src/lib/model.c + src/lib/modelasm_c.c + src/lib/mp3.c + src/lib/mtx_c.c + src/lib/mtx.c + src/lib/music.c + src/lib/path.c + src/lib/profile.c + src/lib/rdp.c + src/lib/rmon.c + src/lib/rng_c.c + src/lib/rzip_c.c + src/lib/snd.c + src/lib/speaker.c + src/lib/varsinit.c + src/lib/vi.c + src/textureconfig.c +) +list(PREPEND SRC_LIB "${CMAKE_SOURCE_DIR}") + +set(SRC + ${SRC_GAME} + ${SRC_PORT} + ${SRC_PORT_CXX} + ${SRC_LIB_MP3} + ${SRC_LIB_NAUDIO} + ${SRC_LIB_ULTRA_AUDIO} + ${SRC_LIB_GU} + ${SRC_LIB} +) + +# Asset files + +generate_asset_headers("lang/" "${CMAKE_SOURCE_DIR}/tools/assetmgr/mklang" "en" JSON_HEADERS) +generate_asset_headers("pads/" "${CMAKE_SOURCE_DIR}/tools/assetmgr/mkpads" "" JSON_HEADERS) +generate_asset_headers("tiles/" "${CMAKE_SOURCE_DIR}/tools/assetmgr/mktiles" "" JSON_HEADERS) +generate_asset_headers("animations.json" "${CMAKE_SOURCE_DIR}/tools/assetmgr/mkanims" "" JSON_HEADERS) +generate_asset_headers("sequences.json" "${CMAKE_SOURCE_DIR}/tools/assetmgr/mksequences" "" JSON_HEADERS) +generate_asset_headers("textures.json" "${CMAKE_SOURCE_DIR}/tools/assetmgr/mktextures" "" JSON_HEADERS) + +add_custom_target(pd_headers ALL DEPENDS ${JSON_HEADERS}) + +# Game target + +add_executable(pd ${SRC}) +add_dependencies(pd pd_headers) +target_link_libraries(pd ${LIBS}) +set_target_properties(pd PROPERTIES OUTPUT_NAME "pd${BIN_REGION}.${TARGET_ARCH}") diff --git a/Makefile b/Makefile deleted file mode 100644 index aac5990eb..000000000 --- a/Makefile +++ /dev/null @@ -1,812 +0,0 @@ -################################################################################ -# Options - -# ROMID - The ROM version to build. -# -# Can be set in your environment using -# $ export ROMID=... -# -# Supported values: -# * ntsc-beta -# * ntsc-1.0 -# * ntsc-final -# * pal-beta -# * pal-final -# * jpn-final - -ROMID ?= ntsc-final - -# MATCHING - Whether to build a matching ROM (1) or a custom one (0). -# -# Build a matching ROM to prove that the decompilation is accurate. -# -# If enabled, all further options are ignored and are set automatically. - -MATCHING = 1 - -# COMPILER - Choose which compiler to use. -# -# A matching build uses ido. For non-matching builds, use gcc for performance. -# -# gcc is currently only supported when ROMID is ntsc-1.0 or ntsc-final. -# -# Supported values: ido, gcc - -COMPILER = gcc - -# GCC_OPT_LVL - the optimisation level if building with gcc. -# -# Supported values: -O0, -O1, -O2, -Os - -GCC_OPT_LVL = -Os - -# PAL - Whether to use the PAL television standard (1) or NTSC (0). -# -# PAL runs at 50Hz while NTSC is 60Hz, and PAL uses different screen dimensions. - -PAL = 0 - -# ROMALLOCATION -# -# The lib, data and game segments are compressed in the final ROM. -# -# These options define how much space is allocated for the compressed segments. -# -# If any value is not big enough, the build system will tell you which one needs -# to be changed and what to change it to. - -ROMALLOCATION_DATA = 0x015000 -ROMALLOCATION_LIB = 0x038800 -ROMALLOCATION_GAME = 0x144ee0 - -# ROM_SIZE - The desired ROM size in megabytes. -# -# All versions of the retail ROM are 32MB. -# -# If this is too low you might get this error from ld: -# "final link failed: memory exhausted" - -ROM_SIZE := 32 - -# DEBUG - Enable (1) or disable (0) the debug menu and crash screen. -# -# When enabled, press C-up and C-down simultaneously to toggle the debug menu. -# Note that some emulators have problems displaying the crash screen text. - -DEBUG = 0 - -################################################################################ - -# The VERSION constant is used in the source to handle version-specific code. -ifeq ($(ROMID), ntsc-beta) - VERSION = 0 -endif -ifeq ($(ROMID), ntsc-1.0) - VERSION = 1 -endif -ifeq ($(ROMID), ntsc-final) - VERSION = 2 -endif -ifeq ($(ROMID), pal-beta) - VERSION = 3 -endif -ifeq ($(ROMID), pal-final) - VERSION = 4 -endif -ifeq ($(ROMID), jpn-final) - VERSION = 5 -endif - -# Set runtime piracy checks off. We turn this on for matching builds if needed. -PIRACYCHECKS = 0 - -# A magic value that's only used to produce a matching ROM. -# It's required because old-school zlib was influenced by uninitialised data. -# ZIPMAGIC is the value of the uninitialised data. We set it per version for -# matching builds, otherwise 0 is fine. -ZIPMAGIC = 0x0000 - -# This is also a value that's only used to produce a matching ROM. -# The final ROM has some duplicate bytes, and there doesn't seem to be any logic -# for determining how many bytes are duplicated. -COPYLEN = 2 - -# If a matching build has been requested, override directives as needed. -ifeq ($(MATCHING), 1) -COMPILER = ido - -ROMALLOCATION_DATA = 0x015000 -ROMALLOCATION_LIB = 0x038800 - -ROM_SIZE = 32 -DEBUG = 0 - -ifeq ($(ROMID), ntsc-beta) - PAL = 0 - PIRACYCHECKS = 0 - ROMALLOCATION_DATA = 0x012000 - ROMALLOCATION_LIB = 0x02f800 - ROMALLOCATION_GAME = 0x105000 - DEBUG = 1 -endif -ifeq ($(ROMID), ntsc-1.0) - PAL = 0 - PIRACYCHECKS = 1 - ROMALLOCATION_GAME = 0x144ee0 - ZIPMAGIC = 0xffff -endif -ifeq ($(ROMID), ntsc-final) - PAL = 0 - PIRACYCHECKS = 1 - ROMALLOCATION_GAME = 0x144ee0 - ZIPMAGIC = 0xffff -endif -ifeq ($(ROMID), pal-beta) - PAL = 1 - PIRACYCHECKS = 1 - ROMALLOCATION_GAME = 0x1306f0 - ZIPMAGIC = 0x0c00 - COPYLEN = 6 - DEBUG = 1 -endif -ifeq ($(ROMID), pal-final) - PAL = 1 - PIRACYCHECKS = 1 - ROMALLOCATION_GAME = 0x1306f0 - ZIPMAGIC = 0xaf00 -endif -ifeq ($(ROMID), jpn-final) - PAL = 0 - PIRACYCHECKS = 1 - ROMALLOCATION_GAME = 0x1296f0 - ZIPMAGIC = 0x0002 - COPYLEN = 4 -endif -endif - -DEFINES := \ - VERSION=$(VERSION) \ - MATCHING=$(MATCHING) \ - PAL=$(PAL) \ - PIRACYCHECKS=$(PIRACYCHECKS) \ - ROM_SIZE=$(ROM_SIZE) \ - PLATFORM_N64=1 - -ifeq ($(DEBUG),1) - DEFINES := $(DEFINES) DEBUG=1 -endif - -C_DEFINES := $(foreach d,$(DEFINES),-D$(d)) -AS_DEFINES := $(foreach d,$(DEFINES),--defsym $(d)) --defsym _LANGUAGE_ASSEMBLY=1 - -A_DIR := src/assets/$(ROMID) -B_DIR := build/$(ROMID) -E_DIR := extracted/$(ROMID) - -ifneq ($(strip $(MIPS_BINUTILS_PREFIX)),) - TOOLCHAIN := $(MIPS_BINUTILS_PREFIX) -else ifeq ($(shell type mips-elf-ld >/dev/null 2>/dev/null; echo $$?), 0) - TOOLCHAIN := mips-elf -else ifeq ($(shell type mips-linux-gnu-ld >/dev/null 2>/dev/null; echo $$?), 0) - TOOLCHAIN := mips-linux-gnu -else ifeq ($(shell type mips64-elf-ld >/dev/null 2>/dev/null; echo $$?), 0) - TOOLCHAIN := mips64-elf -else ifeq ($(shell type mips64-linux-gnu-ld >/dev/null 2>/dev/null; echo $$?), 0) - TOOLCHAIN := mips64-linux-gnu -else - $(error You need to install a suitable MIPS binutils toolchain (eg. mips-elf-ld)) -endif - -# Asset files are files which are included in the "files" segment of the ROM. -# This excludes animations, fonts, SFX, MIDI and textures. -# And because setup files are part of the files segment they are included here, -# despite them being written in C. -# -# Create names such as $(B_DIR)/assets/files/PfooZ. -# These names (with .o added) will be dependenices for ld. -ASSET_FILES := \ - $(patsubst $(A_DIR)/files/audio/%.mp3, $(B_DIR)/assets/files/A%M, $(shell find $(A_DIR) -path '*/files/audio/*.mp3')) \ - $(patsubst $(A_DIR)/files/chrs/%.bin, $(B_DIR)/assets/files/C%Z, $(shell find $(A_DIR) -path '*/files/chrs/*.bin')) \ - $(patsubst $(A_DIR)/files/guns/%.bin, $(B_DIR)/assets/files/G%Z, $(shell find $(A_DIR) -path '*/files/guns/*.bin')) \ - $(patsubst $(A_DIR)/files/props/%.bin, $(B_DIR)/assets/files/P%Z, $(shell find $(A_DIR) -path '*/files/props/*.bin')) \ - $(patsubst src/setups/%.c, $(B_DIR)/assets/files/U%Z, $(shell find src/setups -name '*.c')) \ - $(patsubst $(A_DIR)/files/bgdata/%.seg, $(B_DIR)/assets/files/bgdata/%.seg, $(shell find $(A_DIR) -path '*/files/bgdata/*.seg')) \ - $(B_DIR)/assets/files/ob/ob_mid.seg.o - -LANG_JSON_FILES := $(shell find $(A_DIR) -path '*/lang/*.json') -PADS_JSON_FILES := $(shell find $(A_DIR) -path '*/pads/*.json') -TILES_JSON_FILES := $(shell find $(A_DIR) -path '*/tiles/*.json') - -LANG_O_FILES := \ - $(patsubst $(A_DIR)/lang/%.json, $(B_DIR)/assets/files/L%E.o, $(LANG_JSON_FILES)) \ - $(patsubst $(A_DIR)/lang/%.json, $(B_DIR)/assets/files/L%J.o, $(LANG_JSON_FILES)) \ - $(patsubst $(A_DIR)/lang/%.json, $(B_DIR)/assets/files/L%P.o, $(LANG_JSON_FILES)) \ - $(patsubst $(A_DIR)/lang/%.json, $(B_DIR)/assets/files/L%_str_f.o, $(LANG_JSON_FILES)) \ - $(patsubst $(A_DIR)/lang/%.json, $(B_DIR)/assets/files/L%_str_g.o, $(LANG_JSON_FILES)) \ - $(patsubst $(A_DIR)/lang/%.json, $(B_DIR)/assets/files/L%_str_i.o, $(LANG_JSON_FILES)) \ - $(patsubst $(A_DIR)/lang/%.json, $(B_DIR)/assets/files/L%_str_s.o, $(LANG_JSON_FILES)) - -PADS_O_FILES := $(patsubst $(A_DIR)/pads/%.json, $(B_DIR)/assets/files/bgdata/bg_%_padsZ.o, $(PADS_JSON_FILES)) -TILES_O_FILES := $(patsubst $(A_DIR)/tiles/%.json, $(B_DIR)/assets/files/bgdata/bg_%_tilesZ.o, $(TILES_JSON_FILES)) - -C_FILES := $(shell find src/lib src/game src/inflate -name '*.c') -S_FILES := $(shell find src/lib src/game src/preamble -name '*.s') - -C_O_FILES := $(patsubst src/%.c, $(B_DIR)/%.o, $(C_FILES)) -S_O_FILES := $(patsubst src/%.s, $(B_DIR)/%.o, $(S_FILES)) - -O_FILES := \ - $(C_O_FILES) \ - $(S_O_FILES) \ - $(patsubst %, %.o, $(ASSET_FILES)) \ - $(LANG_O_FILES) \ - $(PADS_O_FILES) \ - $(TILES_O_FILES) \ - $(B_DIR)/assets/animations.o \ - $(B_DIR)/assets/copyrightZ.o \ - $(B_DIR)/assets/files/list.o \ - $(B_DIR)/assets/fonts/bankgothic.o \ - $(B_DIR)/assets/fonts/handelgothiclg.o \ - $(B_DIR)/assets/fonts/handelgothicmd.o \ - $(B_DIR)/assets/fonts/handelgothicsm.o \ - $(B_DIR)/assets/fonts/handelgothicxs.o \ - $(B_DIR)/assets/fonts/numeric.o \ - $(B_DIR)/assets/fonts/ocralg.o \ - $(B_DIR)/assets/fonts/ocramd.o \ - $(B_DIR)/assets/fonts/tahoma.o \ - $(B_DIR)/assets/fonts/zurich.o \ - $(B_DIR)/assets/mpstrings/mpstringsE.o \ - $(B_DIR)/assets/mpstrings/mpstringsF.o \ - $(B_DIR)/assets/mpstrings/mpstringsG.o \ - $(B_DIR)/assets/mpstrings/mpstringsI.o \ - $(B_DIR)/assets/mpstrings/mpstringsJ.o \ - $(B_DIR)/assets/mpstrings/mpstringsP.o \ - $(B_DIR)/assets/mpstrings/mpstringsS.o \ - $(B_DIR)/assets/seq.ctl.o \ - $(B_DIR)/assets/seq.tbl.o \ - $(B_DIR)/assets/sequences.o \ - $(B_DIR)/assets/sfx.ctl.o \ - $(B_DIR)/assets/sfx.tbl.o \ - $(B_DIR)/assets/textureslist.o \ - $(B_DIR)/bootloader.o \ - $(B_DIR)/firingrange.o \ - $(B_DIR)/getitle.o \ - $(B_DIR)/mpconfigs.o \ - $(B_DIR)/romheader.o \ - $(B_DIR)/rsp/asp.data.o \ - $(B_DIR)/rsp/asp.text.o \ - $(B_DIR)/rsp/gsp.data.o \ - $(B_DIR)/rsp/gsp.text.o \ - $(B_DIR)/rsp/rspboot.text.o \ - $(B_DIR)/textureconfig.o - -# ntsc-beta doesn't have this segment -ifneq ($(ROMID), ntsc-beta) - O_FILES := $(O_FILES) $(B_DIR)/assets/accessingpakZ.o -endif - -ifeq ($(ROMID), jpn-final) - O_FILES := $(O_FILES) $(B_DIR)/assets/fonts/jpn.o -else - O_FILES := $(O_FILES) \ - $(B_DIR)/assets/fonts/jpnsingle.o \ - $(B_DIR)/assets/fonts/jpnmulti.o -endif - -INCLUDES = \ - -I include \ - -I include/PR \ - -I src/include \ - -I src/include/lib/libc \ - -I src/generated/$(ROMID) \ - -I src/lib/ultra/audio \ - -AS := $(TOOLCHAIN)-as -ASFLAGS = -march=vr4300 -mabi=32 $(INCLUDES) $(AS_DEFINES) - -ifeq ($(COMPILER), ido) - RECOMP_FILES := \ - build/recomp/5.3/as1 \ - build/recomp/5.3/cc \ - build/recomp/5.3/cfe \ - build/recomp/5.3/err.english.cc \ - build/recomp/5.3/ugen \ - build/recomp/5.3/ujoin \ - build/recomp/5.3/uld \ - build/recomp/5.3/umerge \ - build/recomp/5.3/uopt \ - build/recomp/5.3/usplit \ - build/recomp/7.1/as1 \ - build/recomp/7.1/cc \ - build/recomp/7.1/cfe \ - build/recomp/7.1/err.english.cc \ - build/recomp/7.1/ugen \ - build/recomp/7.1/uopt - - LOOPUNROLL_C_FILES := \ - src/lib/ultra/gu/frustum.c \ - src/lib/ultra/gu/mtxutil.c \ - src/lib/ultra/gu/ortho.c \ - src/lib/ultra/io/conteepread.c \ - src/lib/ultra/io/conteepwrite.c \ - src/lib/ultra/io/contpfs.c \ - src/lib/ultra/io/contramread.c \ - src/lib/ultra/io/contramwrite.c \ - src/lib/ultra/io/gbpakgetstatus.c \ - src/lib/ultra/io/gbpakreadid.c \ - src/lib/ultra/io/motor.c \ - src/lib/ultra/io/pfschecker.c \ - src/lib/ultra/io/pfsfreeblocks.c \ - src/lib/ultra/io/pfsgetstatus.c \ - src/lib/ultra/io/pfsinitpak2.c - - MIPS3_C_FILES := \ - src/lib/rng_c.c \ - src/lib/ultra/libc/ll.c \ - src/lib/ultra/libc/llcvt.c - - G_C_FILES := \ - $(shell find src/lib/ultra/audio -name '*.c') \ - $(shell find src/lib/naudio -name '*.c') \ - $(shell find src/lib/mp3 -name '*.c') \ - src/lib/lib_2fc60.c \ - src/lib/lib_317f0.c \ - src/lib/lib_39c80.c \ - src/lib/lib_3e3e0.c \ - src/lib/mp3.c \ - src/lib/speaker.c - - O1_C_FILES := \ - src/lib/lib_04f60nb.c \ - src/lib/ultra/io/ai.c \ - src/lib/ultra/io/aisetnextbuf.c \ - src/lib/ultra/io/conteeplongread.c \ - src/lib/ultra/io/contquery.c \ - src/lib/ultra/io/controller.c \ - src/lib/ultra/io/dpctr.c \ - src/lib/ultra/io/pigetcmdq.c \ - src/lib/ultra/io/pidma.c \ - src/lib/ultra/io/si.c \ - src/lib/ultra/io/sp.c \ - src/lib/ultra/io/spsetpc.c \ - src/lib/ultra/io/sptaskyielded.c \ - src/lib/ultra/io/vi.c \ - src/lib/ultra/io/viblack.c \ - src/lib/ultra/io/vigetcurrframebuf.c \ - src/lib/ultra/io/vigetnextframebuf.c \ - src/lib/ultra/io/visetevent.c \ - src/lib/ultra/io/visetmode.c \ - src/lib/ultra/io/visetxscale.c \ - src/lib/ultra/io/visetyscale.c \ - src/lib/ultra/io/viswapbuf.c \ - src/lib/ultra/libc/ll.c \ - src/lib/ultra/libc/llcvt.c \ - src/lib/ultra/os/atomic.c \ - src/lib/ultra/os/createmesgqueue.c \ - src/lib/ultra/os/destroythread.c \ - src/lib/ultra/os/getmemsize.c \ - src/lib/ultra/os/gettime.c \ - src/lib/ultra/os/initialize2.c \ - src/lib/ultra/os/jammesg.c \ - src/lib/ultra/os/recvmesg.c \ - src/lib/ultra/os/resetglobalintmask.c \ - src/lib/ultra/os/sendmesg.c \ - src/lib/ultra/os/seteventmesg.c \ - src/lib/ultra/os/setglobalintmask.c \ - src/lib/ultra/os/setthreadpri.c \ - src/lib/ultra/os/settimer.c \ - src/lib/ultra/os/startthread.c \ - src/lib/ultra/os/stopthread.c \ - src/lib/ultra/os/stoptimer.c \ - src/lib/ultra/os/thread.c \ - src/lib/ultra/os/timerintr.c \ - src/lib/ultra/os/virtualtophysical.c \ - src/lib/ultra/os/yieldthread.c - - ifeq ($(ROMID), ntsc-beta) - O1_C_FILES := $(O1_C_FILES) src/lib/ultra/io/pfsisplug.c - endif - - O3_C_FILES := \ - src/lib/ultra/gu/align.c \ - src/lib/ultra/gu/frustum.c \ - src/lib/ultra/gu/ortho.c \ - src/lib/ultra/gu/scale.c \ - src/lib/ultra/libc/xprintf.c - - IDO71_C_FILES := \ - $(shell find src/lib/ultra/audio -name '*.c') \ - $(shell find src/lib/naudio -name '*.c') \ - $(shell find src/lib/mp3 -name '*.c') \ - src/lib/lib_2fc60.c \ - src/lib/lib_39c80.c - - LOOPUNROLL_O_FILES = $(patsubst src/%.c, $(B_DIR)/%.o, $(LOOPUNROLL_C_FILES)) - MIPS3_O_FILES = $(patsubst src/%.c, $(B_DIR)/%.o, $(MIPS3_C_FILES)) - G_O_FILES = $(patsubst src/%.c, $(B_DIR)/%.o, $(G_C_FILES)) - O1_O_FILES = $(patsubst src/%.c, $(B_DIR)/%.o, $(O1_C_FILES)) - O3_O_FILES = $(patsubst src/%.c, $(B_DIR)/%.o, $(O3_C_FILES)) - IDO71_O_FILES = $(patsubst src/%.c, $(B_DIR)/%.o, $(IDO71_C_FILES)) - - LOOPUNROLL := -Wo,-loopunroll,0 - MIPSISET := -mips2 - OPT_LVL := -O2 - CC := build/recomp/5.3/cc - - $(LOOPUNROLL_O_FILES): LOOPUNROLL := - $(MIPS3_O_FILES): MIPSISET := -mips3 - $(G_O_FILES): OPT_LVL := -g - $(O1_O_FILES): OPT_LVL := -O1 - $(O3_O_FILES): OPT_LVL := -O3 - $(IDO71_O_FILES): CC := build/recomp/7.1/cc - - CFLAGS = $(C_DEFINES) $(INCLUDES) \ - $(LOOPUNROLL) \ - -Wab,-r4300_mul \ - -non_shared \ - -Olimit 2000 \ - -G 0 \ - -Xcpluscomm \ - -w2 \ - -Wab,-w \ - -woff 581,649,819,820,821,838,852 \ - $(MIPSISET) -32 - - # Files containing GLOBAL_ASM must be built with the asm_processor - ifeq ($(MATCHING), 1) - GLOBALASM_C_FILES != grep -rl 'GLOBAL_ASM(' $(C_FILES) - GLOBALASM_O_FILES = $(patsubst src/%.c, $(B_DIR)/%.o, $(GLOBALASM_C_FILES)) - $(GLOBALASM_O_FILES): CC := /usr/bin/env python3 tools/asm_processor/build.py $(CC) -- $(TOOLCHAIN)-as $(ASFLAGS) -- - endif -else ifeq ($(COMPILER), gcc) - CC := $(TOOLCHAIN)-gcc - - $(C_O_FILES): OPT_LVL := $(GCC_OPT_LVL) - - C_DEFINES += -DAVOID_UB - - CFLAGS := $(C_DEFINES) $(INCLUDES) \ - -EB \ - -march=vr4300 \ - -mabi=32 \ - -mfix4300 \ - -mdivide-breaks \ - -mno-abicalls \ - -ffreestanding \ - -fno-builtin \ - -fno-common \ - -fno-inline-functions \ - -fno-merge-constants \ - -fno-strict-aliasing \ - -fno-zero-initialized-in-bss \ - -funsigned-char \ - -fwrapv \ - -Wall \ - -Werror \ - -Wno-address \ - -Wno-aggressive-loop-optimizations \ - -Wno-array-bounds \ - -Wno-int-in-bool-context \ - -Wno-int-to-pointer-cast \ - -Wno-maybe-uninitialized \ - -Wno-misleading-indentation \ - -Wno-missing-braces \ - -Wno-multichar \ - -Wno-pointer-sign \ - -Wno-pointer-to-int-cast \ - -Wno-tautological-compare \ - -Wno-uninitialized \ - -Wno-unused-but-set-variable \ - -Wno-unused-value \ - -Wno-unused-variable \ - -G 0 - - $(B_DIR)/lib/ultra/libc/xldtob.o: CFLAGS += -ffast-math -fno-unsafe-math-optimizations -else - $(error The COMPILER option must be "ido" or "gcc") -endif - -# Make ROMID available as an environment variable to all tooling. -# (We use this a lot) -export ROMID - -default: rom - -################################################################################ -# Recomp -# ------------------------------------------------------------------------------ -# The ido-static-recomp project is installed as a git submodule at tools/recomp. -# The IRIX binaries are taken from that project and they are recompiled to -# build/recomp// - -tools/recomp/recomp.cpp: - @echo "Please install ido-static-recomp by running:" - @echo - @echo " git submodule update --init --recursive" - @echo - @exit 1 - -build/recomp/recomp: tools/recomp/recomp.cpp - @mkdir -p build/recomp/5.3 - @mkdir -p build/recomp/7.1 - g++ tools/recomp/recomp.cpp -o build/recomp/recomp -g -lcapstone - -build/recomp/5.3/ugen: - @mkdir -p build/recomp/5.3 - g++ tools/recomp/recomp.cpp -o build/recomp/recomp-ugen53 -g -lcapstone -Dugen53 - ./build/recomp/recomp-ugen53 tools/recomp/ido/5.3/usr/lib/ugen > build/recomp/5.3/ugen.c - gcc tools/recomp/libc_impl.c build/recomp/5.3/ugen.c -Itools/recomp -o build/recomp/5.3/ugen -O2 -fno-strict-aliasing -lm -no-pie -DIDO53 - -build/recomp/5.3/cc: build/recomp/recomp - ./build/recomp/recomp tools/recomp/ido/5.3/usr/bin/cc > build/recomp/5.3/cc.c - gcc tools/recomp/libc_impl.c build/recomp/5.3/cc.c -Itools/recomp -o build/recomp/5.3/cc -O2 -fno-strict-aliasing -lm -no-pie -DIDO53 - -build/recomp/5.3/%: build/recomp/recomp - ./build/recomp/recomp tools/recomp/ido/5.3/usr/lib/$* > build/recomp/5.3/$*.c - gcc tools/recomp/libc_impl.c build/recomp/5.3/$*.c -Itools/recomp -o build/recomp/5.3/$* -O2 -fno-strict-aliasing -lm -no-pie -DIDO53 - -build/recomp/7.1/cc: build/recomp/recomp - ./build/recomp/recomp tools/recomp/ido/7.1/usr/bin/cc > build/recomp/7.1/cc.c - gcc tools/recomp/libc_impl.c build/recomp/7.1/cc.c -Itools/recomp -o build/recomp/7.1/cc -O2 -fno-strict-aliasing -lm -no-pie -DIDO71 - -build/recomp/7.1/%: build/recomp/recomp - ./build/recomp/recomp tools/recomp/ido/7.1/usr/lib/$* > build/recomp/7.1/$*.c - gcc tools/recomp/libc_impl.c build/recomp/7.1/$*.c -Itools/recomp -o build/recomp/7.1/$* -O2 -fno-strict-aliasing -lm -no-pie -DIDO71 - -build/recomp/%/err.english.cc: - @mkdir -p build/recomp/$? - cp tools/err.english.cc build/recomp/$* - -################################################################################ -# ROM Finalisation Stages - -# Link all objects together with ld to make stage1.elf. In this stage, the game, -# lib and data segments are uncompressed and placed past the end of the ROM. -$(B_DIR)/stage1.elf: $(O_FILES) ld/pd.ld - cpp -DROMID=$(ROMID) -DVERSION=$(VERSION) -DROMALLOCATION_DATA=$(ROMALLOCATION_DATA) -DROMALLOCATION_LIB=$(ROMALLOCATION_LIB) -DROMALLOCATION_GAME=$(ROMALLOCATION_GAME) -DROM_SIZE=$(ROM_SIZE) -P ld/pd.ld -o $(B_DIR)/pd.ld - $(TOOLCHAIN)-ld --no-check-sections -z muldefs -T $(B_DIR)/pd.ld --print-map -o $@ > $(B_DIR)/pd.map - -$(B_DIR)/stage1.bin: $(B_DIR)/stage1.elf - $(TOOLCHAIN)-objcopy $< $@ -O binary - -# Build the final ROM from stage1.bin using mkrom -# mkrom handles calculating the piracy checksums, zipping segments and -# calculating the ROM checksum. -$(B_DIR)/pd.z64: $(B_DIR)/stage1.bin tools/mkrom/mkrom - tools/mkrom/mkrom $(B_DIR)/stage1.bin $(B_DIR)/pd.map $(PIRACYCHECKS) $(ZIPMAGIC) $(COPYLEN) $@ - @echo -e "\033[0;32mROM written to $@\033[0m" - -tools/mkrom/mkrom: - $(MAKE) -C tools/mkrom - -################################################################################ -# Testing Related -# --------------------- -# This works a little backwards, in that the ROM has to be built to at least -# stage 2, then extract-segment is used to slice out the segments. - -CHECK_FILES := $(shell awk '{print $$2}' checksums.$(ROMID).md5) - -test: $(CHECK_FILES) - @md5sum --quiet -c checksums.$(ROMID).md5 - -$(B_DIR)/segments/%.bin: $(B_DIR)/pd.z64 - @B_DIR=$(B_DIR) tools/extract-segment $* - -################################################################################ -# Raw data segments - -$(B_DIR)/assets/fonts/%.o: $(A_DIR)/fonts/%.bin - mkdir -p $(B_DIR)/assets/fonts - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/getitle.o: $(E_DIR)/getitle.bin - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/assets/seq.ctl.o: $(A_DIR)/seq.ctl - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/assets/seq.tbl.o: $(A_DIR)/seq.tbl - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/assets/sfx.ctl.o: $(A_DIR)/sfx.ctl - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/assets/sfx.tbl.o: $(A_DIR)/sfx.tbl - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -################################################################################ -# Asset Manager - -ASSETMGR_O_FILES := \ - $(B_DIR)/assets/animations.o \ - $(LANG_O_FILES) \ - $(PADS_O_FILES) \ - $(TILES_O_FILES) \ - $(B_DIR)/assets/sequences.o \ - $(B_DIR)/assets/textureslist.o \ - -# Anims -$(B_DIR)/assets/animations.o: $(A_DIR)/animations.json - tools/assetmgr/mkanims - -# Lang -$(B_DIR)/assets/files/L%E.o: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< en - -$(B_DIR)/assets/files/L%J.o: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< jp - -$(B_DIR)/assets/files/L%P.o: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< gb - -$(B_DIR)/assets/files/L%_str_f.o: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< fr - -$(B_DIR)/assets/files/L%_str_g.o: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< de - -$(B_DIR)/assets/files/L%_str_i.o: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< it - -$(B_DIR)/assets/files/L%_str_s.o: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< es - -# Pads -$(B_DIR)/assets/files/bgdata/bg_%_padsZ.o: $(A_DIR)/pads/%.json - tools/assetmgr/mkpads $< - -# Pads - but this is the zipped non-obj, for make test -$(B_DIR)/assets/files/bgdata/bg_%_padsZ: $(A_DIR)/pads/%.json - tools/assetmgr/mkpads $< - -# Sequences -$(B_DIR)/assets/sequences.o: $(A_DIR)/sequences.json - tools/assetmgr/mksequences - -# Textures -$(B_DIR)/assets/textureslist.o: $(A_DIR)/textures.json - tools/assetmgr/mktextures - -# Tiles -$(B_DIR)/assets/files/bgdata/bg_%_tilesZ.o: $(A_DIR)/tiles/%.json - tools/assetmgr/mktiles $< - -# Tiles - but this is the zipped non-obj, for make test -$(B_DIR)/assets/files/bgdata/bg_%_tilesZ: $(A_DIR)/tiles/%.json - tools/assetmgr/mktiles $< - -################################################################################ -# Files - -# Audio -$(B_DIR)/assets/files/A%M: $(A_DIR)/files/audio/%.mp3 - @mkdir -p $(B_DIR)/assets/files - cp $< $@ - -# BG segs -$(B_DIR)/assets/files/bgdata/bg_%.seg: $(A_DIR)/files/bgdata/bg_%.seg - @mkdir -p $(B_DIR)/assets/files/bgdata - cp $< $@ - -# Chrs -$(B_DIR)/assets/files/C%Z: $(A_DIR)/files/chrs/%.bin - @mkdir -p $(B_DIR)/assets/files - tools/rarezip $< > $@ - -# Guns -$(B_DIR)/assets/files/G%Z: $(A_DIR)/files/guns/%.bin - @mkdir -p $(B_DIR)/assets/files - tools/rarezip $< > $@ - -# OB seg -$(B_DIR)/assets/files/ob/ob_mid.seg.o: $(B_DIR)/assets/files/ob/ob_mid.seg - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/assets/files/ob/ob_mid.seg: - @mkdir -p $(B_DIR)/assets/files/ob - > $@ - -# Props -$(B_DIR)/assets/files/P%Z: $(A_DIR)/files/props/%.bin - tools/rarezip $< > $@ - -# Stage setups -# $(A_DIR)/files/setup/foo.c -# -> B_DIR/assets/files/setup/foo.o (done here) -# -> B_DIR/assets/files/setup/foo.elf (done here) -# -> B_DIR/assets/files/setup/foo.bin (done here) -# -> B_DIR/assets/files/UsetupfooZ (done here) -# -> B_DIR/assets/files/UsetupfooZ.o (done elsewhere) -$(B_DIR)/assets/files/setup/%.o: src/setups/%.c $(ASSETMGR_O_FILES) $(RECOMP_FILES) - @mkdir -p $(dir $@) - $(CC) -c $(CFLAGS) -o $@ $< - -$(B_DIR)/assets/files/setup/%.elf: $(B_DIR)/assets/files/setup/%.o - TOOLCHAIN=$(TOOLCHAIN) tools/mksimpleelf $< $@ - -$(B_DIR)/files/setup/%.bin: $(B_DIR)/assets/files/setup/%.elf - @mkdir -p $(dir $@) - $(TOOLCHAIN)-objcopy $< $@ -O binary - -$(B_DIR)/assets/files/U%Z: $(B_DIR)/files/setup/%.bin - tools/rarezip $< > $@ - -# General target to convert any finalised file into a raw object for ld -$(B_DIR)/assets/files/%.o: $(B_DIR)/assets/files/% - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/assets/files/%.bin: $(B_DIR)/assets/files/%.elf - $(TOOLCHAIN)-objcopy $< $@ -O binary - -################################################################################ -# Miscellaneous - -$(B_DIR)/bootloader.o: $(E_DIR)/bootloader.bin - @mkdir -p $(dir $@) - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/romheader.o: src/romheader/romheader.s - $(TOOLCHAIN)-as --defsym VERSION=$(VERSION) -march=vr4300 -mabi=32 -I src/include -EB -o $@ $< - -$(B_DIR)/assets/accessingpakZ: $(A_DIR)/accessingpak.bin - tools/rarezip $< > $@ - -$(B_DIR)/assets/copyrightZ: $(A_DIR)/copyright.bin - tools/rarezip $< > $@ - -$(B_DIR)/assets/accessingpakZ.o: $(B_DIR)/assets/accessingpakZ - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/assets/copyrightZ.o: $(B_DIR)/assets/copyrightZ - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -$(B_DIR)/rsp/%.text.bin $(B_DIR)/rsp/%.data.bin: src/rsp/%.s - @mkdir -p $(dir $@) - armips -strequ CODE_FILE $(B_DIR)/rsp/$*.text.bin -strequ DATA_FILE $(B_DIR)/rsp/$*.data.bin $< - -$(B_DIR)/rsp/%.o: $(B_DIR)/rsp/%.bin - TOOLCHAIN=$(TOOLCHAIN) ROMID=$(ROMID) tools/mkrawobject $< $@ - -ifeq ($(COMPILER), ido) -$(B_DIR)/lib/rng_c.o: src/lib/rng_c.c $(ASSETMGR_O_FILES) $(RECOMP_FILES) - @mkdir -p $(dir $@) - $(CC) -c $(CFLAGS) $(OPT_LVL) -o $@ $< - tools/patchmips3 $@ || rm $@ - -$(B_DIR)/lib/ultra/libc/llcvt.o: src/lib/ultra/libc/llcvt.c $(ASSETMGR_O_FILES) $(RECOMP_FILES) - @mkdir -p $(dir $@) - $(CC) -c $(CFLAGS) $(OPT_LVL) -o $@ $< - tools/patchmips3 $@ || rm $@ - -$(B_DIR)/lib/ultra/libc/ll.o: src/lib/ultra/libc/ll.c $(ASSETMGR_O_FILES) $(RECOMP_FILES) - @mkdir -p $(dir $@) - $(CC) -c $(CFLAGS) $(OPT_LVL) $< -o $@ - tools/patchmips3 $@ || rm $@ -endif - -$(B_DIR)/%.o: src/%.c $(ASSETMGR_O_FILES) $(RECOMP_FILES) - @mkdir -p $(dir $@) - $(CC) -c $(CFLAGS) $(OPT_LVL) -o $@ $< - -$(B_DIR)/%.o: src/%.s - @mkdir -p $(dir $@) - cpp -P -Wno-trigraphs -I include -I include/PR -I src/include $(C_DEFINES) -D_LANGUAGE_ASSEMBLY -D_MIPSEB $< | $(AS) $(ASFLAGS) -o $@ - -$(B_DIR)/assets/%.o: $(A_DIR)/%.c $(RECOMP_FILES) - @mkdir -p $(dir $@) - $(CC) -c $(CFLAGS) -o $@ $< - -extract: - ROMID=$(ROMID) tools/extract - -rom: $(B_DIR)/pd.z64 - -clean: - rm -rf build/$(ROMID) src/generated/$(ROMID) - -allclean: - rm -rf build/* src/generated - -codeclean: - find $(B_DIR)/game $(B_DIR)/inflate $(B_DIR)/lib -name '*.o' -delete diff --git a/Makefile.port b/Makefile.port deleted file mode 100644 index a9fea91bd..000000000 --- a/Makefile.port +++ /dev/null @@ -1,358 +0,0 @@ -# Options. - -# HOST_PLATFORM - Which platform we're building on. -# -# Determined automatically if not specified on command line. -# -# Supported values: -# * i686-windows -# * i686-linux - -HOST_PLATFORM ?= - -# TARGET_PLATFORM - Which platform to build for. -# -# Determined from HOST_PLATFORM if not specified on command line. -# -# Supported values: -# * i686-windows -# * i686-linux - -TARGET_PLATFORM ?= - -# ROMID - The ROM version to use. -# -# Can be set in your environment using -# $ export ROMID=... -# -# Supported values: -# * ntsc-final -# * pal-final -# * jpn-final - -ROMID ?= ntsc-final - -# GCC_OPT_LVL - the optimisation level if building with gcc. -# -# Supported values: -O0, -O1, -O2, -O3, -Os, -Og - -GCC_OPT_LVL = -Og - -# ROM_SIZE - The desired ROM size in megabytes. -# -# All versions of the retail ROM are 32MB. -# -# If this is too low you might get this error from ld: -# "final link failed: memory exhausted" - -ROM_SIZE := 32 - -# DEBUG - Enable (1) or disable (0) the debug menu and crash screen. -# -# When enabled, press C-up and C-down simultaneously to toggle the debug menu. -# Note that some emulators have problems displaying the crash screen text. - -DEBUG = 0 - -################################################################################ - -# Detect host platform if not specified. -ifeq ($(HOST_PLATFORM),) - ifeq ($(OS),Windows_NT) - # assume msys for now - UNAME_OS := $(shell uname -s) - ifneq (,$(findstring MINGW64,$(UNAME_OS))) - HOST_PLATFORM := x86_64-windows - else - HOST_PLATFORM := i686-windows - endif - else # TODO - UNAME_ARCH := $(shell uname -m) - UNAME_OS := $(shell uname -s) - UNAME_OS := $(shell echo $(UNAME_OS) | tr A-Z a-z) - HOST_PLATFORM := $(UNAME_ARCH)-$(UNAME_OS) - endif -endif - -# Set target platform to host platform if not specified. -ifeq ($(TARGET_PLATFORM),) - TARGET_PLATFORM := $(HOST_PLATFORM) -endif - -# Get the arch part from the platform designator. -HOST_ARCH := $(word 1,$(subst -, ,$(HOST_PLATFORM))) -TARGET_ARCH := $(word 1,$(subst -, ,$(TARGET_PLATFORM))) - -# Gather platform parameters. -# Whether the platform is 64 bit. -ifneq (,$(findstring 64,$(TARGET_PLATFORM))$(findstring armv8,$(TARGET_PLATFORM))) - TARGET_64BIT := 1 -else - TARGET_64BIT := 0 -endif -# Whether the target is big-endian or little-endian. -TARGET_BIG_ENDIAN = 0 # TODO -# Executable extension. -ifneq (,$(findstring windows,$(TARGET_PLATFORM))) - BIN_EXTENSION := .exe -else - BIN_EXTENSION := -endif - -ifeq (,$(findstring clean,$(MAKECMDGOALS))) - $(info Host platform: $(HOST_PLATFORM) (arch $(HOST_ARCH))) - $(info Target platform: $(TARGET_PLATFORM) (arch $(TARGET_ARCH))) -endif - -# The VERSION constant is used in the source to handle version-specific code. -ifeq ($(ROMID),ntsc-final) - BIN_NAME = pd.$(TARGET_ARCH)$(BIN_EXTENSION) - VERSION = 2 - IS_PAL = 0 -else ifeq ($(ROMID),pal-final) - BIN_NAME = pd.pal.$(TARGET_ARCH)$(BIN_EXTENSION) - VERSION = 4 - IS_PAL = 1 -else ifeq ($(ROMID),jpn-final) - BIN_NAME = pd.jpn.$(TARGET_ARCH)$(BIN_EXTENSION) - VERSION = 5 - IS_PAL = 0 -else - $(error ROM version $(VERSION) is not supported) -endif - -VERSION_HASH := $(shell git rev-parse --short HEAD) -VERSION_BRANCH := $(shell git rev-parse --abbrev-ref HEAD) -VERSION_TARGET := $(TARGET_PLATFORM) -VERSION_ARCH := $(TARGET_ARCH) -VERSION_ROMID := $(ROMID) - -ifeq ($(VERSION_BRANCH),) - VERSION_BRANCH := port-custom -endif -ifeq ($(VERSION_BRANCH),HEAD) - VERSION_BRANCH := port-custom -endif - -BUILDID := $(ROMID)-$(TARGET_PLATFORM) - -DEFINES := \ - VERSION=$(VERSION) \ - VERSION_HASH=\"$(VERSION_HASH)\" \ - VERSION_TARGET=\"$(VERSION_TARGET)\" \ - VERSION_ARCH=\"$(VERSION_ARCH)\" \ - VERSION_ROMID=\"$(VERSION_ROMID)\" \ - VERSION_BRANCH=\"$(VERSION_BRANCH)\" \ - MATCHING=0 \ - PAL=$(IS_PAL) \ - PIRACYCHECKS=0 \ - ROM_SIZE=$(ROM_SIZE) \ - _LANGUAGE_C=1 - -ifeq ($(DEBUG),1) - DEFINES := $(DEFINES) DEBUG=1 -endif - -ifeq (1,$(TARGET_64BIT)) - DEFINES += PLATFORM_64BIT=1 -endif - -C_DEFINES := $(foreach d,$(DEFINES),-D$(d)) - -A_DIR := src/assets/$(ROMID) -B_DIR := build/$(BUILDID) -G_DIR := src/generated/$(ROMID) - -ifneq (,$(findstring windows,$(TARGET_PLATFORM))) - TARGET_CFLAGS := $(shell pkg-config sdl2 --cflags-only-I) - TARGET_LDFLAGS := $(shell pkg-config sdl2 --libs) -lz -lopengl32 -ldbghelp -lws2_32 - # on windows/mingw we need this to be built with a 32-bit compiler so it finds the correct libs - TOOLCHAIN ?= i686-w64-mingw32- - # on GCC link libstdc++ statically - ifeq (,$(findstring clang,$(CC))$(findstring clang,$(CXX))) - TARGET_LDFLAGS += -static-libstdc++ - else - TARGET_LDFLAGS += -lstdc++ - endif -else # assume *nix - TARGET_CFLAGS := $(shell pkg-config sdl2 --cflags-only-I) - TARGET_LDFLAGS := $(shell pkg-config sdl2 --libs) -lGL -lz -ldl - ifneq (,$(findstring arm,$(TARGET_PLATFORM))$(findstring aarch,$(TARGET_PLATFORM))) - # linux on arm or aarch64 - # TODO: detect soft/hardfloat abi - TOOLCHAIN ?= arm-linux-gnueabihf- - endif -endif - -# On x86_64 gcc add -m32 to CFLAGS if building a 32-bit executable. -ifneq (,$(findstring x86_64,$(HOST_PLATFORM))$(findstring x86_64,$(TOOLCHAIN))) - ifneq (1,$(TARGET_64BIT)) - TARGET_CFLAGS += -m32 - endif -endif - -# These are still used in the port, but only to generate headers. -JSON_FILES := $(shell find $(A_DIR) -path '*/lang/*.json') -JSON_FILES += $(shell find $(A_DIR) -path '*/pads/*.json') -JSON_FILES += $(shell find $(A_DIR) -path '*/tiles/*.json') -JSON_FILES += $(wildcard $(A_DIR)/*.json) - -JSON_HEADERS := $(patsubst $(A_DIR)/%.json, $(G_DIR)/%.h, $(JSON_FILES)) - -C_FILES := $(shell find src/game port -name '*.c') -C_FILES := $(C_FILES) \ - $(wildcard src/lib/mp3/*.c) \ - $(wildcard src/lib/naudio/*.c) \ - $(wildcard src/lib/ultra/audio/*.c) \ - $(wildcard src/lib/ultra/gu/*.c) \ - src/lib/ultra/io/vimodentsclan1.c \ - src/lib/ultra/io/vimodepallan1.c \ - src/lib/ultra/io/vimodempallan1.c \ - src/lib/ultra/io/vitbl.c \ - $(wildcard src/lib/a*.c) \ - src/lib/base.c \ - src/lib/collision.c \ - src/lib/debughud.c \ - src/lib/dma.c \ - src/lib/fault.c \ - src/lib/joy.c \ - $(wildcard src/lib/lib_*.c) \ - src/lib/mema.c \ - src/lib/memp.c \ - src/lib/model.c \ - src/lib/modelasm_c.c \ - src/lib/mp3.c \ - src/lib/mtx_c.c \ - src/lib/mtx.c \ - src/lib/music.c \ - src/lib/path.c \ - src/lib/profile.c \ - src/lib/rdp.c \ - src/lib/rmon.c \ - src/lib/rng_c.c \ - src/lib/rzip_c.c \ - src/lib/snd.c \ - src/lib/speaker.c \ - src/lib/varsinit.c \ - src/lib/vi.c \ - src/textureconfig.c - -CXX_FILES :=$(shell find port -name '*.cpp') - -C_O_FILES := $(patsubst %.c, $(B_DIR)/%.o, $(C_FILES)) -CXX_O_FILES := $(patsubst %.cpp, $(B_DIR)/%.o, $(CXX_FILES)) - -O_FILES := $(C_O_FILES) $(CXX_O_FILES) - -ifneq (,$(findstring windows,$(TARGET_PLATFORM))) - O_FILES += $(B_DIR)/icon.res -endif - -INCLUDES = \ - -I include \ - -I include/PR \ - -I src/include \ - -I src/generated/$(ROMID) \ - -I src/lib/ultra/audio \ - -I port/include - -TOOLCHAIN ?= -CC ?= $(TOOLCHAIN)gcc -CXX ?= $(TOOLCHAIN)g++ -ifneq (,$(CXX_O_FILES)) - LD := $(CXX) -else - LD := $(CC) -endif - -$(O_FILES): OPT_LVL := $(GCC_OPT_LVL) - -COMMON_CFLAGS := $(C_DEFINES) -DAVOID_UB=1 $(INCLUDES) $(TARGET_CFLAGS) -g \ - -fno-inline-functions \ - -fno-strict-aliasing \ - -funsigned-char \ - -fwrapv \ - -Wall \ - -Wno-address \ - -Wno-int-in-bool-context \ - -Wno-misleading-indentation \ - -Wno-missing-braces \ - -Wno-multichar \ - -Wno-tautological-compare \ - -Wno-unused-but-set-variable \ - -Wno-unused-value \ - -Wno-unused-variable \ - -Wno-format-truncation - -CFLAGS := -std=c11 $(COMMON_CFLAGS) -Wno-pointer-sign -CXXFLAGS := -std=c++20 $(COMMON_CFLAGS) -Wno-unused-function -LDFLAGS := $(TARGET_LDFLAGS) - -# Make ROMID available as an environment variable to all tooling. -# (We use this a lot) -export ROMID -export BUILDID - -BIN := $(B_DIR)/$(BIN_NAME) - -default: $(BIN) - -################################################################################ -# Asset Manager header generation - -# Anims -$(G_DIR)/animations.h: $(A_DIR)/animations.json - tools/assetmgr/mkanims --headers-only - -# Lang -$(G_DIR)/lang/%.h: $(A_DIR)/lang/%.json - tools/assetmgr/mklang $< en --headers-only - -# Pads -$(G_DIR)/pads/%.h: $(A_DIR)/pads/%.json - tools/assetmgr/mkpads $< --headers-only - -# Sequences -$(G_DIR)/sequences.h: $(A_DIR)/sequences.json - tools/assetmgr/mksequences --headers-only - -# Textures -$(G_DIR)/textures.h: $(A_DIR)/textures.json - tools/assetmgr/mktextures --headers-only - -# Tiles -$(G_DIR)/tiles/%.h: $(A_DIR)/tiles/%.json - tools/assetmgr/mktiles $< --headers-only - -################################################################################ -# Generic compilation rules - -$(BIN): $(O_FILES) - $(LD) $(COMMON_CFLAGS) $(OPT_LVL) -o $(BIN) $^ $(LDFLAGS) -ifneq ($(CV2PDB),) - $(CV2PDB) $(BIN) -endif - -$(B_DIR)/%.o: %.c $(JSON_HEADERS) - @mkdir -p $(dir $@) - $(CC) -c $(CFLAGS) $(OPT_LVL) -o $@ $< - -$(B_DIR)/%.o: %.cpp $(JSON_HEADERS) - @mkdir -p $(dir $@) - $(CXX) -c $(CXXFLAGS) $(OPT_LVL) -o $@ $< - -$(B_DIR)/%.res: dist/windows/%.rc - windres $< -O coff -o $@ - -################################################################################ -# Clean rules - -clean: - rm -rf build/$(BUILDID) - -allclean: - rm -rf build/* - rm -rf src/generated - -codeclean: - find $(B_DIR)/ -name '*.o' -delete diff --git a/cmake/AssetUtils.cmake b/cmake/AssetUtils.cmake new file mode 100644 index 000000000..0a518b051 --- /dev/null +++ b/cmake/AssetUtils.cmake @@ -0,0 +1,27 @@ +# execute a header generator (execcmd) for every json file in jsonpath, collect headers in headerlist +# note that this reads ROMID +macro(generate_asset_headers jsonpath execcmd extraarg headerlist) + set(TMP_JSON "") + + if (${jsonpath} MATCHES "\.json") + # is a json file + list(APPEND TMP_JSON "${CMAKE_SOURCE_DIR}/${ASSET_DIR}/${jsonpath}") + else() + # is a directory + file(GLOB TMP_JSON "${CMAKE_SOURCE_DIR}/${ASSET_DIR}/${jsonpath}*.json") + endif() + + foreach(JSON ${TMP_JSON}) + unset(HEADERNAME) + string(REPLACE ".json" ".h" HEADERNAME ${JSON}) + string(REPLACE "${CMAKE_SOURCE_DIR}/${ASSET_DIR}" "${CMAKE_BINARY_DIR}/${GENERATED_DIR}" HEADERNAME ${HEADERNAME}) + add_custom_command( + OUTPUT ${HEADERNAME} + DEPENDS ${JSON} + COMMAND ${execcmd} ${JSON} ${extraarg} --headers-only --romid=${ROMID} + ) + list(APPEND ${headerlist} "${HEADERNAME}") + endforeach() + + unset(TMP_JSON) +endmacro() diff --git a/cmake/FindSDL2.cmake b/cmake/FindSDL2.cmake new file mode 100644 index 000000000..02c6bba06 --- /dev/null +++ b/cmake/FindSDL2.cmake @@ -0,0 +1,172 @@ +# Distributed under the OSI-approved BSD 3-Clause License. See accompanying +# file Copyright.txt or https://cmake.org/licensing for details. + +# Locate SDL2 library +# This module defines +# SDL2_LIBRARY, the name of the library to link against +# SDL2_FOUND, if false, do not try to link to SDL2 +# SDL2_INCLUDE_DIR, where to find SDL.h +# +# This module responds to the the flag: +# SDL2_BUILDING_LIBRARY +# If this is defined, then no SDL2_main will be linked in because +# only applications need main(). +# Otherwise, it is assumed you are building an application and this +# module will attempt to locate and set the the proper link flags +# as part of the returned SDL2_LIBRARY variable. +# +# Don't forget to include SDL2main.h and SDL2main.m your project for the +# OS X framework based version. (Other versions link to -lSDL2main which +# this module will try to find on your behalf.) Also for OS X, this +# module will automatically add the -framework Cocoa on your behalf. +# +# +# Additional Note: If you see an empty SDL2_LIBRARY_TEMP in your configuration +# and no SDL2_LIBRARY, it means CMake did not find your SDL2 library +# (SDL2.dll, libsdl2.so, SDL2.framework, etc). +# Set SDL2_LIBRARY_TEMP to point to your SDL2 library, and configure again. +# Similarly, if you see an empty SDL2MAIN_LIBRARY, you should set this value +# as appropriate. These values are used to generate the final SDL2_LIBRARY +# variable, but when these values are unset, SDL2_LIBRARY does not get created. +# +# +# $SDL2DIR is an environment variable that would +# correspond to the ./configure --prefix=$SDL2DIR +# used in building SDL2. +# l.e.galup 9-20-02 +# +# Modified by Eric Wing. +# Added code to assist with automated building by using environmental variables +# and providing a more controlled/consistent search behavior. +# Added new modifications to recognize OS X frameworks and +# additional Unix paths (FreeBSD, etc). +# Also corrected the header search path to follow "proper" SDL2 guidelines. +# Added a search for SDL2main which is needed by some platforms. +# Added a search for threads which is needed by some platforms. +# Added needed compile switches for MinGW. +# +# On OSX, this will prefer the Framework version (if found) over others. +# People will have to manually change the cache values of +# SDL2_LIBRARY to override this selection or set the CMake environment +# CMAKE_INCLUDE_PATH to modify the search paths. +# +# Note that the header path has changed from SDL2/SDL.h to just SDL.h +# This needed to change because "proper" SDL2 convention +# is #include "SDL.h", not . This is done for portability +# reasons because not all systems place things in SDL2/ (see FreeBSD). +# +# Ported by Johnny Patterson. This is a literal port for SDL2 of the FindSDL.cmake +# module with the minor edit of changing "SDL" to "SDL2" where necessary. This +# was not created for redistribution, and exists temporarily pending official +# SDL2 CMake modules. + +FIND_PATH(SDL2_INCLUDE_DIR SDL.h + HINTS + $ENV{SDL2DIR} + PATH_SUFFIXES include/SDL2 include + PATHS + ~/Library/Frameworks + /Library/Frameworks + /usr/local/include/SDL2 + /usr/include/SDL2 + /sw # Fink + /opt/local # DarwinPorts + /opt/csw # Blastwave + /opt + /boot/system/develop/headers/SDL2 #Hiaku OS +) +#MESSAGE("SDL2_INCLUDE_DIR is ${SDL2_INCLUDE_DIR}") + +FIND_LIBRARY(SDL2_LIBRARY_TEMP + NAMES SDL2 + HINTS + $ENV{SDL2DIR} + PATH_SUFFIXES lib64 lib + PATHS + /sw + /opt/local + /opt/csw + /opt + /system/lib #Hiaku OS +) + +#MESSAGE("SDL2_LIBRARY_TEMP is ${SDL2_LIBRARY_TEMP}") + +IF(NOT SDL2_BUILDING_LIBRARY) + IF(NOT ${SDL2_INCLUDE_DIR} MATCHES ".framework") + # Non-OS X framework versions expect you to also dynamically link to + # SDL2main. This is mainly for Windows and OS X. Other (Unix) platforms + # seem to provide SDL2main for compatibility even though they don't + # necessarily need it. + FIND_LIBRARY(SDL2MAIN_LIBRARY + NAMES SDL2main + HINTS + $ENV{SDL2DIR} + PATH_SUFFIXES lib64 lib + PATHS + /sw + /opt/local + /opt/csw + /opt + ) + ENDIF(NOT ${SDL2_INCLUDE_DIR} MATCHES ".framework") +ENDIF(NOT SDL2_BUILDING_LIBRARY) + +# SDL2 may require threads on your system. +# The Apple build may not need an explicit flag because one of the +# frameworks may already provide it. +# But for non-OSX systems, I will use the CMake Threads package. +IF(NOT APPLE) + FIND_PACKAGE(Threads) +ENDIF(NOT APPLE) + +# MinGW needs an additional library, mwindows +# It's total link flags should look like -lmingw32 -lSDL2main -lSDL2 -lmwindows +# (Actually on second look, I think it only needs one of the m* libraries.) +IF(MINGW) + SET(MINGW32_LIBRARY mingw32 CACHE STRING "mwindows for MinGW") +ENDIF(MINGW) + +SET(SDL2_FOUND "NO") +IF(SDL2_LIBRARY_TEMP) + # For SDL2main + IF(NOT SDL2_BUILDING_LIBRARY) + IF(SDL2MAIN_LIBRARY) + SET(SDL2_LIBRARY_TEMP ${SDL2MAIN_LIBRARY} ${SDL2_LIBRARY_TEMP}) + ENDIF(SDL2MAIN_LIBRARY) + ENDIF(NOT SDL2_BUILDING_LIBRARY) + + # For OS X, SDL2 uses Cocoa as a backend so it must link to Cocoa. + # CMake doesn't display the -framework Cocoa string in the UI even + # though it actually is there if I modify a pre-used variable. + # I think it has something to do with the CACHE STRING. + # So I use a temporary variable until the end so I can set the + # "real" variable in one-shot. + IF(APPLE) + SET(SDL2_LIBRARY_TEMP ${SDL2_LIBRARY_TEMP} "-framework Cocoa") + ENDIF(APPLE) + + # For threads, as mentioned Apple doesn't need this. + # In fact, there seems to be a problem if I used the Threads package + # and try using this line, so I'm just skipping it entirely for OS X. + IF(NOT APPLE) + SET(SDL2_LIBRARY_TEMP ${SDL2_LIBRARY_TEMP} ${CMAKE_THREAD_LIBS_INIT}) + ENDIF(NOT APPLE) + + # For MinGW library + IF(MINGW) + SET(SDL2_LIBRARY_TEMP ${MINGW32_LIBRARY} ${SDL2_LIBRARY_TEMP}) + ENDIF(MINGW) + + # Set the final string here so the GUI reflects the final state. + SET(SDL2_LIBRARY ${SDL2_LIBRARY_TEMP} CACHE STRING "Where the SDL2 Library can be found") + # Set the temp variable to INTERNAL so it is not seen in the CMake GUI + SET(SDL2_LIBRARY_TEMP "${SDL2_LIBRARY_TEMP}" CACHE INTERNAL "") + + SET(SDL2_FOUND "YES") +ENDIF(SDL2_LIBRARY_TEMP) + +INCLUDE(FindPackageHandleStandardArgs) + +FIND_PACKAGE_HANDLE_STANDARD_ARGS(SDL2 + REQUIRED_VARS SDL2_LIBRARY SDL2_INCLUDE_DIR) diff --git a/cmake/TargetArch.cmake b/cmake/TargetArch.cmake new file mode 100644 index 000000000..31e2e048d --- /dev/null +++ b/cmake/TargetArch.cmake @@ -0,0 +1,165 @@ + +# Copyright (c) 2012 Petroules Corporation. 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 COPYRIGHT HOLDERS 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 COPYRIGHT OWNER 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. + +# Based on the Qt 5 processor detection code, so should be very accurate +# https://qt.gitorious.org/qt/qtbase/blobs/master/src/corelib/global/qprocessordetection.h +# Currently handles arm (v5, v6, v7), x86 (32/64), ia64, and ppc (32/64) + +# Regarding POWER/PowerPC, just as is noted in the Qt source, +# "There are many more known variants/revisions that we do not handle/detect." + +set(archdetect_c_code " +#if defined(__arm__) || defined(__TARGET_ARCH_ARM) || defined(_M_ARM64) || defined (__aarch64__) + #if defined(__ARM_ARCH_7__) \\ + || defined(__ARM_ARCH_7A__) \\ + || defined(__ARM_ARCH_7R__) \\ + || defined(__ARM_ARCH_7M__) \\ + || (defined(__TARGET_ARCH_ARM) && __TARGET_ARCH_ARM-0 >= 7) + #error cmake_ARCH armv7 + #elif defined(__ARM_ARCH_6__) \\ + || defined(__ARM_ARCH_6J__) \\ + || defined(__ARM_ARCH_6T2__) \\ + || defined(__ARM_ARCH_6Z__) \\ + || defined(__ARM_ARCH_6K__) \\ + || defined(__ARM_ARCH_6ZK__) \\ + || defined(__ARM_ARCH_6M__) \\ + || (defined(__TARGET_ARCH_ARM) && __TARGET_ARCH_ARM-0 >= 6) + #error cmake_ARCH armv6 + #elif defined(__ARM_ARCH_5TEJ__) \\ + || (defined(__TARGET_ARCH_ARM) && __TARGET_ARCH_ARM-0 >= 5) + #error cmake_ARCH armv5 + #elif defined(_M_ARM64) || defined (__aarch64__) + #error cmake_ARCH arm64 + #else + #error cmake_ARCH arm + #endif +#elif defined(__i386) || defined(__i386__) || defined(_M_IX86) + #error cmake_ARCH i386 +#elif defined(__x86_64) || defined(__x86_64__) || defined(__amd64) || defined(_M_X64) + #error cmake_ARCH x86_64 +#elif defined(__ia64) || defined(__ia64__) || defined(_M_IA64) + #error cmake_ARCH ia64 +#elif defined(__ppc__) || defined(__ppc) || defined(__powerpc__) \\ + || defined(_ARCH_COM) || defined(_ARCH_PWR) || defined(_ARCH_PPC) \\ + || defined(_M_MPPC) || defined(_M_PPC) + #if defined(__ppc64__) || defined(__powerpc64__) || defined(__64BIT__) + #error cmake_ARCH ppc64 + #else + #error cmake_ARCH ppc + #endif +#endif + +#error cmake_ARCH unknown +") + +# Set ppc_support to TRUE before including this file or ppc and ppc64 +# will be treated as invalid architectures since they are no longer supported by Apple + +function(target_architecture output_var) + if(APPLE AND CMAKE_OSX_ARCHITECTURES) + # On OS X we use CMAKE_OSX_ARCHITECTURES *if* it was set + # First let's normalize the order of the values + + # Note that it's not possible to compile PowerPC applications if you are using + # the OS X SDK version 10.6 or later - you'll need 10.4/10.5 for that, so we + # disable it by default + # See this page for more information: + # http://stackoverflow.com/questions/5333490/how-can-we-restore-ppc-ppc64-as-well-as-full-10-4-10-5-sdk-support-to-xcode-4 + + # Architecture defaults to i386 or ppc on OS X 10.5 and earlier, depending on the CPU type detected at runtime. + # On OS X 10.6+ the default is x86_64 if the CPU supports it, i386 otherwise. + + foreach(osx_arch ${CMAKE_OSX_ARCHITECTURES}) + if("${osx_arch}" STREQUAL "ppc" AND ppc_support) + set(osx_arch_ppc TRUE) + elseif("${osx_arch}" STREQUAL "i386") + set(osx_arch_i386 TRUE) + elseif("${osx_arch}" STREQUAL "x86_64") + set(osx_arch_x86_64 TRUE) + elseif("${osx_arch}" STREQUAL "ppc64" AND ppc_support) + set(osx_arch_ppc64 TRUE) + elseif("${osx_arch}" STREQUAL "arm64") + set(osx_arch_arm64 TRUE) + else() + message(FATAL_ERROR "Invalid OS X arch name: ${osx_arch}") + endif() + endforeach() + + # Now add all the architectures in our normalized order + if(osx_arch_ppc) + list(APPEND ARCH ppc) + endif() + + if(osx_arch_i386) + list(APPEND ARCH i386) + endif() + + if(osx_arch_x86_64) + list(APPEND ARCH x86_64) + endif() + + if(osx_arch_ppc64) + list(APPEND ARCH ppc64) + endif() + + if(osx_arch_arm64) + list(APPEND ARCH arm64) + endif() + else() + file(WRITE "${CMAKE_BINARY_DIR}/arch.c" "${archdetect_c_code}") + + enable_language(C) + + # Detect the architecture in a rather creative way... + # This compiles a small C program which is a series of ifdefs that selects a + # particular #error preprocessor directive whose message string contains the + # target architecture. The program will always fail to compile (both because + # file is not a valid C program, and obviously because of the presence of the + # #error preprocessor directives... but by exploiting the preprocessor in this + # way, we can detect the correct target architecture even when cross-compiling, + # since the program itself never needs to be run (only the compiler/preprocessor) + try_run( + run_result_unused + compile_result_unused + "${CMAKE_BINARY_DIR}" + "${CMAKE_BINARY_DIR}/arch.c" + COMPILE_OUTPUT_VARIABLE ARCH + CMAKE_FLAGS CMAKE_OSX_ARCHITECTURES=${CMAKE_OSX_ARCHITECTURES} + ) + + # Parse the architecture name from the compiler output + string(REGEX MATCH "cmake_ARCH ([a-zA-Z0-9_]+)" ARCH "${ARCH}") + + # Get rid of the value marker leaving just the architecture name + string(REPLACE "cmake_ARCH " "" ARCH "${ARCH}") + + # If we are compiling with an unknown architecture this variable should + # already be set to "unknown" but in the case that it's empty (i.e. due + # to a typo in the code), then set it to unknown + if (NOT ARCH) + set(ARCH unknown) + endif() + endif() + + set(${output_var} "${ARCH}" PARENT_SCOPE) +endfunction() diff --git a/port/include/versioninfo.h.in b/port/include/versioninfo.h.in new file mode 100644 index 000000000..d152582d8 --- /dev/null +++ b/port/include/versioninfo.h.in @@ -0,0 +1,11 @@ +#ifndef _IN_VERSIONINFO_H +#define _IN_VERSIONINFO_H + +#define VERSION_TARGET "@VERSION_TARGET@" +#define VERSION_ARCH "@VERSION_ARCH@" +#define VERSION_ROMID "@VERSION_ROMID@" +#define VERSION_BUILD "@VERSION_BUILD@" +#define VERSION_HASH "@VERSION_HASH@" +#define VERSION_BRANCH "@VERSION_BRANCH@" + +#endif diff --git a/tools/assetmgr/assetmgr.py b/tools/assetmgr/assetmgr.py index bfc859057..81ecf4230 100644 --- a/tools/assetmgr/assetmgr.py +++ b/tools/assetmgr/assetmgr.py @@ -157,5 +157,11 @@ def writefile(filename, contents): fd.close() if 'ROMID' not in os.environ: - # default to ntsc-final - os.environ['ROMID'] = 'ntsc-final' + # check if it's in args + for arg in sys.argv: + if arg.startswith('--romid='): + os.environ['ROMID'] = arg.removeprefix('--romid=') + break + else: + # default to ntsc-final + os.environ['ROMID'] = 'ntsc-final' diff --git a/tools/assetmgr/mkanims b/tools/assetmgr/mkanims index bd5a9b4c8..550aa7068 100755 --- a/tools/assetmgr/mkanims +++ b/tools/assetmgr/mkanims @@ -6,7 +6,12 @@ import os import sys def main(): - fd = open('src/assets/%s/animations.json' % os.environ['ROMID'], 'r') + if (len(sys.argv) < 2) or (sys.argv[1].startswith('--')): + filename = 'src/assets/%s/sequences.json' % os.environ['ROMID'] + else: + filename = sys.argv[1] + + fd = open(filename, 'r') data = fd.read() fd.close() diff --git a/tools/assetmgr/mksequences b/tools/assetmgr/mksequences index ea30f84ea..b811f8097 100755 --- a/tools/assetmgr/mksequences +++ b/tools/assetmgr/mksequences @@ -6,7 +6,12 @@ import os import sys def main(): - fd = open('src/assets/%s/sequences.json' % os.environ['ROMID'], 'r') + if (len(sys.argv) < 2) or (sys.argv[1].startswith('--')): + filename = 'src/assets/%s/sequences.json' % os.environ['ROMID'] + else: + filename = sys.argv[1] + + fd = open(filename, 'r') data = fd.read() fd.close() diff --git a/tools/assetmgr/mktextures b/tools/assetmgr/mktextures index ca788dad8..c6373ed04 100755 --- a/tools/assetmgr/mktextures +++ b/tools/assetmgr/mktextures @@ -6,7 +6,12 @@ import os import sys def main(): - fd = open('src/assets/%s/textures.json' % os.environ['ROMID'], 'r') + if (len(sys.argv) < 2) or (sys.argv[1].startswith('--')): + filename = 'src/assets/%s/textures.json' % os.environ['ROMID'] + else: + filename = sys.argv[1] + + fd = open(filename, 'r') data = fd.read() fd.close() From 1a1accceca42ff16ad25156d28533937e9c9077b Mon Sep 17 00:00:00 2001 From: fgsfds Date: Tue, 12 Nov 2024 22:15:28 +0100 Subject: [PATCH 2/6] ci: update for cmake (i686-linux should be broken) --- .github/workflows/c-cpp.yml | 54 +++++++++++++++++++------------------ 1 file changed, 28 insertions(+), 26 deletions(-) diff --git a/.github/workflows/c-cpp.yml b/.github/workflows/c-cpp.yml index d9904c222..9ab70ba3a 100644 --- a/.github/workflows/c-cpp.yml +++ b/.github/workflows/c-cpp.yml @@ -25,20 +25,21 @@ jobs: mingw-w64-i686-toolchain mingw-w64-i686-SDL2 mingw-w64-i686-zlib + mingw-w64-i686-cmake - name: Checkout repository uses: actions/checkout@v4 - name: Build pd.i686.exe - run: make -f Makefile.port -j + run: cmake -G"Unix Makefiles" -Bbuild . && cmake --build build -j - name: Build pd.pal.i686.exe - run: make -f Makefile.port -j ROMID=pal-final + run: cmake -G"Unix Makefiles" -Bbuild_pal -DROMID=pal-final . && cmake --build build_pal -j - name: Build pd.jpn.i686.exe - run: make -f Makefile.port -j ROMID=jpn-final + run: cmake -G"Unix Makefiles" -Bbuild_jpn -DROMID=jpn-final . && cmake --build build_jpn -j - name: Prepare artifact for packaging run: | mkdir -p bin/data - cp build/ntsc-final-i686-windows/pd.i686.exe bin/ - cp build/pal-final-i686-windows/pd.pal.i686.exe bin/ - cp build/jpn-final-i686-windows/pd.jpn.i686.exe bin/ + cp build/pd.i686.exe bin/ + cp build_pal/pd.pal.i686.exe bin/ + cp build_jpn/pd.jpn.i686.exe bin/ cp /mingw32/bin/{SDL2.dll,zlib1.dll,libgcc_s_dw2-1.dll,libwinpthread-1.dll} bin/ touch bin/data/put_your_rom_here.txt - name: Upload artifact @@ -55,21 +56,21 @@ jobs: run: | sudo dpkg --add-architecture i386 sudo apt-get update - sudo apt-get install git gcc g++ gcc-multilib g++-multilib make libsdl2-dev zlib1g-dev libsdl2-dev:i386 zlib1g-dev:i386 + sudo apt-get install git gcc g++ gcc-multilib g++-multilib make libsdl2-dev zlib1g-dev libsdl2-dev:i386 zlib1g-dev:i386 cmake - name: Checkout repository uses: actions/checkout@v4 - name: Build pd.i686 - run: make -f Makefile.port TARGET_PLATFORM=i686-linux -j2 + run: cmake -G"Unix Makefiles" -Bbuild . && cmake --build build -j - name: Build pd.pal.i686 - run: make -f Makefile.port TARGET_PLATFORM=i686-linux -j2 ROMID=pal-final + run: cmake -G"Unix Makefiles" -Bbuild_pal -DROMID=pal-final . && cmake --build build_pal -j - name: Build pd.jpn.i686 - run: make -f Makefile.port TARGET_PLATFORM=i686-linux -j2 ROMID=jpn-final + run: cmake -G"Unix Makefiles" -Bbuild_jpn -DROMID=jpn-final . && cmake --build build_jpn -j - name: Prepare artifact for packaging run: | mkdir -p bin/data - cp build/ntsc-final-i686-linux/pd.i686 bin/pd - cp build/pal-final-i686-linux/pd.pal.i686 bin/pd.pal - cp build/jpn-final-i686-linux/pd.jpn.i686 bin/pd.jpn + cp build/pd.i686 bin/ + cp build_pal/pd.pal.i686 bin/ + cp build_jpn/pd.jpn.i686 bin/ touch bin/data/put_your_rom_here.txt - name: Upload artifact uses: actions/upload-artifact@v4 @@ -96,20 +97,21 @@ jobs: mingw-w64-x86_64-python mingw-w64-x86_64-SDL2 mingw-w64-x86_64-zlib + mingw-w64-x86_64-cmake - name: Checkout repository uses: actions/checkout@v4 - name: Build pd.x86_64.exe - run: make -f Makefile.port -j + run: cmake -G"Unix Makefiles" -Bbuild . && cmake --build build -j - name: Build pd.pal.x86_64.exe - run: make -f Makefile.port -j ROMID=pal-final + run: cmake -G"Unix Makefiles" -Bbuild_pal -DROMID=pal-final . && cmake --build build_pal -j - name: Build pd.jpn.x86_64.exe - run: make -f Makefile.port -j ROMID=jpn-final + run: cmake -G"Unix Makefiles" -Bbuild_jpn -DROMID=jpn-final . && cmake --build build_jpn -j - name: Prepare artifact for packaging run: | mkdir -p bin/data - cp build/ntsc-final-x86_64-windows/pd.x86_64.exe bin/ - cp build/pal-final-x86_64-windows/pd.pal.x86_64.exe bin/ - cp build/jpn-final-x86_64-windows/pd.jpn.x86_64.exe bin/ + cp build/pd.x86_64.exe bin/ + cp build_pal/pd.pal.x86_64.exe bin/ + cp build_jpn/pd.jpn.x86_64.exe bin/ cp /mingw64/bin/{SDL2.dll,zlib1.dll,libwinpthread-1.dll,libgcc_s_seh-1.dll} bin/ touch bin/data/put_your_rom_here.txt - name: Upload artifact @@ -126,21 +128,21 @@ jobs: run: | sudo dpkg --add-architecture amd64 sudo apt-get update - sudo apt-get install git gcc g++ gcc-multilib g++-multilib make libsdl2-dev zlib1g-dev libsdl2-2.0-0 + sudo apt-get install git gcc g++ gcc-multilib g++-multilib make libsdl2-dev zlib1g-dev libsdl2-2.0-0 cmake - name: Checkout repository uses: actions/checkout@v4 - name: Build pd.x86_64 - run: make -f Makefile.port TARGET_PLATFORM=x86_64-linux -j2 + run: cmake -G"Unix Makefiles" -Bbuild . && cmake --build build -j - name: Build pd.pal.x86_64 - run: make -f Makefile.port TARGET_PLATFORM=x86_64-linux -j2 ROMID=pal-final + run: cmake -G"Unix Makefiles" -Bbuild_pal -DROMID=pal-final . && cmake --build build_pal -j - name: Build pd.jpn.x86_64 - run: make -f Makefile.port TARGET_PLATFORM=x86_64-linux -j2 ROMID=jpn-final + run: cmake -G"Unix Makefiles" -Bbuild_jpn -DROMID=jpn-final . && cmake --build build_jpn -j - name: Prepare artifact for packaging run: | mkdir -p bin/data - cp build/ntsc-final-x86_64-linux/pd.x86_64 bin/pd - cp build/pal-final-x86_64-linux/pd.pal.x86_64 bin/pd.pal - cp build/jpn-final-x86_64-linux/pd.jpn.x86_64 bin/pd.jpn + cp build/pd.x86_64 bin/ + cp build_pal/pd.pal.x86_64 bin/ + cp build_jpn/pd.jpn.x86_64 bin/ touch bin/data/put_your_rom_here.txt - name: Upload artifact uses: actions/upload-artifact@v4 From ee7ce2d9880bae5e194d73113f88bbf40369e38f Mon Sep 17 00:00:00 2001 From: fgsfds Date: Tue, 12 Nov 2024 22:19:49 +0100 Subject: [PATCH 3/6] port: cmake: force disable gnu extensions --- CMakeLists.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 36a368ea9..9ac600dec 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -8,7 +8,9 @@ include(FindPkgConfig) include(AssetUtils) set(CMAKE_C_STANDARD 11) +set(CMAKE_C_EXTENSIONS OFF) set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_EXTENSIONS OFF) # On first build set the build type to RelWithDebInfo if it's not already set if (NOT EXISTS ${CMAKE_BINARY_DIR}/CMakeCache.txt) From fab41b6fcb826612836d0fab84ae65ac2f4c1b3d Mon Sep 17 00:00:00 2001 From: fgsfds Date: Tue, 12 Nov 2024 22:34:44 +0100 Subject: [PATCH 4/6] ci: probably fix i686-linux builds; rename i386 back to i686 --- .github/workflows/c-cpp.yml | 6 +++--- CMakeLists.txt | 4 ++++ 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/.github/workflows/c-cpp.yml b/.github/workflows/c-cpp.yml index 9ab70ba3a..888eb3626 100644 --- a/.github/workflows/c-cpp.yml +++ b/.github/workflows/c-cpp.yml @@ -60,11 +60,11 @@ jobs: - name: Checkout repository uses: actions/checkout@v4 - name: Build pd.i686 - run: cmake -G"Unix Makefiles" -Bbuild . && cmake --build build -j + run: cmake -G"Unix Makefiles" -Bbuild -DCMAKE_C_FLAGS=-m32 -DCMAKE_CXX_FLAGS=-m32 . && cmake --build build -j - name: Build pd.pal.i686 - run: cmake -G"Unix Makefiles" -Bbuild_pal -DROMID=pal-final . && cmake --build build_pal -j + run: cmake -G"Unix Makefiles" -Bbuild_pal -DCMAKE_C_FLAGS=-m32 -DCMAKE_CXX_FLAGS=-m32 -DROMID=pal-final . && cmake --build build_pal -j - name: Build pd.jpn.i686 - run: cmake -G"Unix Makefiles" -Bbuild_jpn -DROMID=jpn-final . && cmake --build build_jpn -j + run: cmake -G"Unix Makefiles" -Bbuild_jpn -DCMAKE_C_FLAGS=-m32 -DCMAKE_CXX_FLAGS=-m32 -DROMID=jpn-final . && cmake --build build_jpn -j - name: Prepare artifact for packaging run: | mkdir -p bin/data diff --git a/CMakeLists.txt b/CMakeLists.txt index 9ac600dec..4aecdeef4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -27,6 +27,10 @@ option(FORCE_CROSSCOMPILE "Force cross compiling" NO) # Determine target arch target_architecture(TARGET_ARCH) +if(TARGET_ARCH STREQUAL "i386") + # for historical reasons + set(TARGET_ARCH "i686") +endif() # TODO set(TARGET_IS_BIG_ENDIAN FALSE) From d37d9b7168f2a1fa051610603051d54729d828c8 Mon Sep 17 00:00:00 2001 From: fgsfds Date: Tue, 12 Nov 2024 22:50:36 +0100 Subject: [PATCH 5/6] ci: move flatpak back to i686 for now --- .github/workflows/c-cpp.yml | 2 +- dist/linux/io.github.fgsfdsfgs.perfect_dark.sh | 8 ++++---- dist/linux/io.github.fgsfdsfgs.perfect_dark.yaml | 8 +++----- 3 files changed, 8 insertions(+), 10 deletions(-) diff --git a/.github/workflows/c-cpp.yml b/.github/workflows/c-cpp.yml index 888eb3626..c4a7aa1a1 100644 --- a/.github/workflows/c-cpp.yml +++ b/.github/workflows/c-cpp.yml @@ -162,7 +162,7 @@ jobs: - uses: actions/checkout@v4 - uses: actions/download-artifact@v4 with: - name: pd-x86_64-linux + name: pd-i686-linux path: dist/linux/bin/ - uses: flatpak/flatpak-github-actions/flatpak-builder@v6 diff --git a/dist/linux/io.github.fgsfdsfgs.perfect_dark.sh b/dist/linux/io.github.fgsfdsfgs.perfect_dark.sh index 28ff8213b..9269fbd70 100644 --- a/dist/linux/io.github.fgsfdsfgs.perfect_dark.sh +++ b/dist/linux/io.github.fgsfdsfgs.perfect_dark.sh @@ -11,14 +11,14 @@ done # Default to pd as executable but switch to jpn/pal if the NTSC rom # is missing but JPN/PAL are present. # TODO: Other arch -executable="pd.x86_64" +executable="pd.i686" if [ -f ${XDG_DATA_HOME}/roms/pd.ntsc-final.z64 ] | \ [ -f ${XDG_DATA_HOME}/roms/pd.ntsc-1.0.z64 ]; then - executable="pd.x86_64" + executable="pd.i686" elif [ -f ${XDG_DATA_HOME}/roms/pd.jpn-final.z64 ]; then - executable="pd.jpn.x86_64" + executable="pd.jpn.i686" elif [ -f ${XDG_DATA_HOME}/roms/pd.pal-final.z64 ]; then - executable="pd.pal.x86_64" + executable="pd.pal.i686" fi # If first parameter passed to this script is one of the pd executables, diff --git a/dist/linux/io.github.fgsfdsfgs.perfect_dark.yaml b/dist/linux/io.github.fgsfdsfgs.perfect_dark.yaml index 7ef407946..c9d1d4f1d 100644 --- a/dist/linux/io.github.fgsfdsfgs.perfect_dark.yaml +++ b/dist/linux/io.github.fgsfdsfgs.perfect_dark.yaml @@ -5,8 +5,6 @@ sdk: org.freedesktop.Sdk command: io.github.fgsfdsfgs.perfect_dark.sh finish-args: - # multiarch is required for 32bit binaries - - --allow=multiarch # hardware 3D and controller access - --device=all # X11 + XShm access @@ -65,11 +63,11 @@ modules: buildsystem: simple sources: - type: file - path: bin/pd + path: bin/pd.i686 - type: file - path: bin/pd.jpn + path: bin/pd.jpn.i686 - type: file - path: bin/pd.pal + path: bin/pd.pal.i686 - type: file path: io.github.fgsfdsfgs.perfect_dark.sh - type: file From 6c8e5ee4dcb6e41b12cbb36642a36e8850e806fa Mon Sep 17 00:00:00 2001 From: fgsfds Date: Tue, 12 Nov 2024 23:05:04 +0100 Subject: [PATCH 6/6] update README.md --- README.md | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 8f3af136e..38aad50eb 100644 --- a/README.md +++ b/README.md @@ -105,29 +105,31 @@ Controls can be rebound in `pd.ini`. Default control scheme is as follows: 1. Install [MSYS2](https://www.msys2.org). 2. Open the `MINGW64` prompt if building for x86_64, or the `MINGW32` prompt if building for i686. (**NOTE:** _do not_ use the `MSYS` prompt) 3. Install dependencies: - `pacman -S mingw-w64-x86_64-toolchain mingw-w64-x86_64-SDL2 mingw-w64-x86_64-zlib mingw-w64-i686-toolchain mingw-w64-i686-SDL2 mingw-w64-i686-zlib make git` + `pacman -S mingw-w64-x86_64-toolchain mingw-w64-x86_64-SDL2 mingw-w64-x86_64-zlib mingw-w64-x86_64-cmake mingw-w64-i686-toolchain mingw-w64-i686-SDL2 mingw-w64-i686-zlib mingw-w64-i686-cmake make git` 4. Get the source code: `git clone --recursive https://github.com/fgsfdsfgs/perfect_dark.git && cd perfect_dark` -5. Run `make -f Makefile.port`. - * Add ` ROMID=pal-final` or ` ROMID=jpn-final` at the end of the command if you want to build a PAL or JPN executable respectively. -6. The resulting executable will be at `build/ntsc-final-x86_64-windows/pd.x86_64.exe` (or at `build/ntsc-final-i686-windows/pd.i686.exe` if building for i686). +5. Run `cmake -G"Unix Makefiles" -Bbuild .`. + * Add ` -DROMID=pal-final` or ` -DROMID=jpn-final` at the end of the command if you want to build a PAL or JPN executable respectively.\ +6. Run `cmake --build build -j4 -- -O`. +6. The resulting executable will be at `build/pd.x86_64.exe` (or at `build/pd.i686.exe` if building for i686). 7. If you don't know where you downloaded the source to, you can run `explorer .` to open the current directory. ### Linux -1. Ensure you have gcc, g++ (version 10.0+) and SDL2 (version 2.0.12+), libGL and ZLib installed on your system. +1. Ensure you have gcc, g++ (version 10.0+), make, cmake, git and SDL2 (version 2.0.12+), libGL and ZLib installed on your system. * If you wish to crosscompile, you will also need to have libraries and compilers for the target platform installed, e.g. `gcc-multilib` and `g++-multilib` for x86_64 -> i686 crosscompilation. 2. Get the source code: `git clone --recursive https://github.com/fgsfdsfgs/perfect_dark.git && cd perfect_dark` 3. Run the following command: - * ```make -f Makefile.port``` - * Add ` ROMID=pal-final` or ` ROMID=jpn-final` at the end of the command if you want to build a PAL or JPN executable respectively. - * Add ` TARGET_PLATFORM=your-target` at the end of the command if you want to crosscompile. -4. The resulting executable will be at `build/ntsc-final-/pd.` (for example `build/ntsc-final-x86_64-linux/pd.x86_64`). + * ```cmake -G"Unix Makefiles" -Bbuild .``` + * Add ` -DROMID=pal-final` or ` -DROMID=jpn-final` at the end of the command if you want to build a PAL or JPN executable respectively. + * Add ` -DCMAKE_C_FLAGS=-m32 -DCMAKE_CXX_FLAGS=-m32` at the end of the command if you want to crosscompile from x86_64 to x86. +4. Run `cmake --build build -j4`. +4. The resulting executable will be at `build/pd.` (for example `build/pd.x86_64`). ### Notes -Alternate compilers can be specified by passing `TOOLCHAIN=arch-whatever-` as a command line argument. +Alternate compilers or toolchains can be specified by passing `-DCMAKE_TOOLCHAIN_FILE=whatever` as normal. The port does not build with Visual Studio. You will need to provide a `jpn-final` or `pal-final` ROM to run executables built for those regions, named `pd.jpn-final.z64` or `pd.pal-final.z64`.