···11+22+.SUFFIXES: # Suppress a lot of useless default rules, which also provides a nice speedup.
33+44+# Recursive `wildcard` function.
55+rwildcard = $(foreach d,$(wildcard $(1:=/*)),$(call rwildcard,$d,$2) $(filter $(subst *,%,$2),$d))
66+77+# Program constants.
88+# POSIX OSes (the sane default).
99+RM_RF := rm -rf
1010+MKDIR_P := mkdir -p
1111+ifeq ($(strip $(shell which rm)),)
1212+ # Windows *really* tries its hardest to be Special™!
1313+ RM_RF := -rmdir /s /q
1414+ MKDIR_P := -mkdir
1515+endif
1616+1717+RGBDS ?= # Shortcut if you want to use a local copy of RGBDS.
1818+RGBASM := ${RGBDS}rgbasm
1919+RGBLINK := ${RGBDS}rgblink
2020+RGBFIX := ${RGBDS}rgbfix
2121+RGBGFX := ${RGBDS}rgbgfx
2222+2323+ROM = bin/${ROMNAME}.${ROMEXT}
2424+2525+# Argument constants
2626+INCDIRS = src/ include/
2727+WARNINGS = all extra
2828+ASFLAGS = -p ${PADVALUE} $(addprefix -I,${INCDIRS}) $(addprefix -W,${WARNINGS})
2929+LDFLAGS = -p ${PADVALUE}
3030+FIXFLAGS = -p ${PADVALUE} -i "${GAMEID}" -k "${LICENSEE}" -l ${OLDLIC} -m ${MBC} -n ${VERSION} -r ${SRAMSIZE} -t ${TITLE}
3131+3232+# The list of ASM files that RGBASM will be invoked on.
3333+SRCS = $(call rwildcard,src,*.asm)
3434+3535+## Project-specific configuration
3636+# Use this to override the above
3737+include project.mk
3838+3939+# `all` (Default target): build the ROM
4040+all: ${ROM}
4141+.PHONY: all
4242+4343+# `clean`: Clean temp and bin files
4444+clean:
4545+ ${RM_RF} bin obj assets
4646+.PHONY: clean
4747+4848+# `rebuild`: Build everything from scratch
4949+# It's important to do these two in order if we're using more than one job
5050+rebuild:
5151+ ${MAKE} clean
5252+ ${MAKE} all
5353+.PHONY: rebuild
5454+5555+# By default, asset recipes convert files in `assets/` into other files in `assets/`.
5656+# This line causes assets not found in `assets/` to be also looked for in `src/assets/`.
5757+# "Source" assets can thus be safely stored there without `make clean` removing them!
5858+VPATH := src
5959+6060+# Define how to compress files using the PackBits16 codec.
6161+# (The compressor script requires Python 3.)
6262+assets/%.pb16: src/tools/pb16.py assets/%
6363+ @${MKDIR_P} "${@D}"
6464+ $^ $@
6565+6666+# How to build a ROM.
6767+# Notice that the build date is always refreshed.
6868+bin/%.${ROMEXT}: $(patsubst src/%.asm,obj/%.o,${SRCS})
6969+ @${MKDIR_P} "${@D}"
7070+ ${RGBASM} ${ASFLAGS} -o obj/build_date.o src/assets/build_date.asm
7171+ ${RGBLINK} ${LDFLAGS} -m bin/$*.map -n bin/$*.sym -o $@ $^ \
7272+ && ${RGBFIX} -v ${FIXFLAGS} $@
7373+7474+# `.mk` files are auto-generated dependency lists of the source ASM files, to save a lot of hassle.
7575+# Also add all obj dependencies to the dep file too, so Make knows to remake it.
7676+# Caution: some of these flags were added in RGBDS 0.4.0, using an earlier version WILL NOT WORK
7777+# (and produce weird errors).
7878+obj/%.mk: src/%.asm
7979+ @${MKDIR_P} "${@D}"
8080+ ${RGBASM} ${ASFLAGS} -M $@ -MG -MP -MQ ${@:.mk=.o} -MQ $@ -o ${@:.mk=.o} $<
8181+# DO NOT merge this with the rule above, otherwise Make will assume that the `.o` file is generated,
8282+# even when it isn't!
8383+# This causes weird issues that depend, among other things, on the version of Make.
8484+obj/%.o: obj/%.mk
8585+ @touch $@
8686+8787+ifeq ($(filter clean,${MAKECMDGOALS}),)
8888+include $(patsubst src/%.asm,obj/%.mk,${SRCS})
8989+endif
-18
gb/main.asm
···11-INCLUDE "hardware.inc"
22-33-SECTION "Header", ROM0[$100]
44-55- jp EntryPoint
66-77- ds $150 - @, 0 ; Make room for the header
88-99-EntryPoint:
1010- ; Do not turn the LCD off outside of VBlank
1111-WaitVBlank:
1212- ld a, [rLY]
1313- cp 144
1414- jp c, WaitVBlank
1515-1616- ; Turn the LCD off
1717- ld a, 0
1818- ld [rLCDC], a
+67
gb/project.mk
···11+# This file contains project-specific configuration.
22+# You can override variables set in the Makefile here.
33+44+55+# Value that the ROM will be filled with.
66+PADVALUE := 0xFF
77+88+## Header constants (passed to RGBFIX).
99+1010+# ROM version (typically starting at 0 and incremented for each published version).
1111+VERSION := 0
1212+1313+# 4-ASCII letter game ID.
1414+GAMEID := DNGR
1515+1616+# Game title, up to 11 ASCII chars.
1717+TITLE := Dungeoner
1818+1919+# New licensee, 2 ASCII chars.
2020+# Homebrew games FTW!.
2121+LICENSEE := HB
2222+# Old licensee, please set to 0x33 (required to get SGB compatibility).
2323+OLDLIC := 0x33
2424+2525+# MBC type, tells which hardware is in the cart.
2626+# You can get a list of valid values by running `rgbfix -m help`.
2727+# See https://gbdev.io/pandocs/MBCs for more information, or consult any copy of Pan Docs.
2828+# If using no MBC, consider enabling `-t` below.
2929+MBC := 0x00
3030+3131+# ROM size is set automatically by RGBFIX.
3232+3333+# Size of the on-board SRAM; MBC type should indicate the presence of RAM.
3434+# See https://gbdev.io/pandocs/The_Cartridge_Header#0149--ram-size or consult any copy of Pan Docs.
3535+# Set this to 0 when using MBC2's built-in SRAM.
3636+SRAMSIZE := 0x00
3737+3838+# ROM name.
3939+ROMNAME := dungeoner
4040+ROMEXT := gb
4141+4242+4343+# Compilation parameters, uncomment to apply, comment to cancel.
4444+# "Sensible defaults" are included.
4545+# Please refer to RGBDS' documentation.
4646+# For example, offline: `man 1 rgbasm`; online: https://rgbds.gbdev.io/docs/rgbasm.1
4747+4848+# Export all labels.
4949+# This means they must all have unique names, but they will all show up in the .sym and .map files.
5050+# ASFLAGS += -E
5151+5252+# Game Boy Color compatible.
5353+# FIXFLAGS += -c
5454+# Game Boy Color required.
5555+# FIXFLAGS += -C
5656+5757+# Super Game Boy compatible.
5858+# FIXFLAGS += -s
5959+6060+# Game Boy mode.
6161+# LDFLAGS += -d
6262+6363+# No banked WRAM mode.
6464+# LDFLAGS += -w
6565+6666+# 32k mode.
6767+# LDFLAGS += -t
+6
gb/src/assets/build_date.asm
···11+SECTION "Build date", ROM0
22+33+ db "Built "
44+BuildDate::
55+ db __ISO_8601_UTC__
66+ db 0
+23
gb/src/main.asm
···11+INCLUDE "hardware.inc/hardware.inc"
22+ rev_Check_hardware_inc 4.0
33+44+SECTION "Header", ROM0[$100]
55+66+ ; This is your ROM's entry point
77+ ; You have 4 bytes of code to do... something
88+ di
99+ jp EntryPoint
1010+1111+ ; Make sure to allocate some space for the header, so no important
1212+ ; code gets put there and later overwritten by RGBFIX.
1313+ ; RGBFIX is designed to operate over a zero-filled header, so make
1414+ ; sure to put zeros regarless of the padding value. (This feature
1515+ ; was introduced in RGBDS 0.4.0, but the -MG etc flags were also
1616+ ; introduced in that version.)
1717+ ds $150 - @, 0
1818+1919+SECTION "Entry point", ROM0
2020+2121+EntryPoint:
2222+ ; Here is where the fun begins, happy coding :)
2323+ jr @