diff --git a/.gitignore b/.gitignore
index eee8ad32a2b446a572a0e7c898dbbed4956f3711..f51a4403e65c3790dea17ef5ee633394f6acdfc7 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,3 +1,4 @@
 *~
 data/
 out/
+*.mk
\ No newline at end of file
diff --git a/Makefile b/Makefile
index 76f0c6076f4442fcdd6b3d11aad177b273ff0e96..fb8afbc9912f50b124550545bf89c4736a114c8c 100644
--- a/Makefile
+++ b/Makefile
@@ -3,30 +3,25 @@ BRANCH := database/sp
 OUT    := out
 REMOTE := uni:.www/sp/quiz/
 
-QFILES  = $(shell find $(DATA) -name '[ws]s[[:digit:]][[:digit:]].q' -type f 2>/dev/null)
-JFILES  = $(QFILES:$(DATA)/%.q=$(OUT)/%.json)
-
-# We use a recursive make invocation here, to ensure that $(DATA) is
-# first checked out before we proceed to use it.  FIXME: It seems that
-# the combination of order-only dependencies and static patterns
-# doesn't work as expected.
 .PHONY: all
-all: $(DATA)
-	$(MAKE) $(OUT)/quiz.json $(OUT)/quiz.html $(OUT)/quiz.js $(OUT)/quiz.css $(OUT)/katalog.html $(OUT)/conf.js
+all: $(OUT)/quiz.json $(OUT)/quiz.html $(OUT)/quiz.js $(OUT)/quiz.css $(OUT)/katalog.html $(OUT)/conf.js
 
 $(DATA):
 	git fetch --all
 	git worktree add $@ $(BRANCH)
+GENMK := .q.mk
+
+$(GENMK): $(DATA) src/gen-mk.awk
+	find $< -name '[ws]s[[:digit:]][[:digit:]].q' -type f    | \
+	     xargs basename -s .q                                | \
+	     awk -v OUT=$(OUT) -v DATA=$< -f src/gen-mk.awk > $@
+
+-include $(GENMK)
 
-$(JFILES): $(OUT)/%.json: $(DATA)/%.q src/gen.pl src/mark.lua | $(OUT)
-	./src/gen.pl $< > $@
 
 $(OUT):
 	mkdir -p $(OUT)
 
-$(OUT)/quiz.json: $(JFILES) | $(OUT)
-	jq -cs '[.[][]]' $^ > $@
-
 $(OUT)/katalog.html: $(OUT)/quiz.json src/gen-katalog.py | $(OUT)
 	./src/gen-katalog.py "$(TITLE)" < $< > $@
 
@@ -47,4 +42,5 @@ sync: all
 clean:
 	rm -rf $(OUT)
 	rm -rf $(DATA)
+	rm -f $(GENMK)
 	git worktree prune
diff --git a/src/gen-mk.awk b/src/gen-mk.awk
new file mode 100644
index 0000000000000000000000000000000000000000..b86c5a94ec2224b6eeff35404909bd2374f76275
--- /dev/null
+++ b/src/gen-mk.awk
@@ -0,0 +1,14 @@
+BEGIN { deps = "" }
+
+{
+    print OUT "/" $1 ".json: " DATA "/" $1 ".q"
+    print "\t./src/gen.pl $< > $@"
+
+    deps = deps " " OUT "/" $1 ".json"
+}
+
+END {
+    print deps ": src/gen.pl src/mark.lua | "  OUT
+    print OUT "/quiz.json:" deps
+    print"\tjq -cs '[.[][]]' $^ > $@"
+}