tunnel
authorJohn Tsiombikas <nuclear@member.fsf.org>
Sat, 10 Apr 2021 06:42:27 +0000 (09:42 +0300)
committerJohn Tsiombikas <nuclear@member.fsf.org>
Sat, 10 Apr 2021 06:42:27 +0000 (09:42 +0300)
12 files changed:
.gdbinit [new file with mode: 0644]
.gitignore
Makefile
libs/aas/AAS_ASM.s
src/data.h
src/data.s [new file with mode: 0644]
src/dma.c
src/game.h [new file with mode: 0644]
src/gamescr.c [new file with mode: 0644]
src/main.c
src/menuscr.c [new file with mode: 0644]
tools/tungen.c [new file with mode: 0644]

diff --git a/.gdbinit b/.gdbinit
new file mode 100644 (file)
index 0000000..f4d7543
--- /dev/null
+++ b/.gdbinit
@@ -0,0 +1 @@
+target remote localhost:2345
index d7a3666..20f6b68 100644 (file)
@@ -7,3 +7,6 @@ cfg.mk
 *.a
 pngdump
 conv2aas
+tungen
+*.ppm
+*.png
index a0281a9..bf91267 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -6,6 +6,9 @@ name = gbajam21
 elf = $(name).elf
 bin = $(name).gba
 
+data = data/tuncross.raw data/tuncross.pal \
+          data/tun.map
+
 audata = data/audio/popcorn.mod
 dataobj = data/aas_data.o
 
@@ -21,7 +24,7 @@ OBJDUMP = $(TCPREFIX)objdump
 EMU = vbam
 
 opt = -O3 -fomit-frame-pointer -mcpu=arm7tdmi -mtune=arm7tdmi -mthumb -mthumb-interwork
-#dbg = -g
+dbg = -g
 inc = -I. -Ilibs/aas
 
 CFLAGS = $(opt) $(dbg) -pedantic -Wall -MMD $(def) $(inc)
@@ -43,12 +46,17 @@ $(elf): data/aas_data.h $(obj) $(libs)
 
 -include $(dep)
 
+src/data.o: src/data.s $(data)
+
 tools/pngdump/pngdump:
        $(MAKE) -C tools/pngdump
 
 tools/conv2aas/conv2aas:
        $(MAKE) -C tools/conv2aas
 
+tools/tungen: tools/tungen.c
+       cc -o $@ $< -lm
+
 #data/sprites.raw: data/sprites1.png data/sprites2.png data/sprites3.png data/sprites4.png data/sprites5.png data/sprites6.png
 #      tools/pngdump/pngdump -o $@ -n $^
 
@@ -58,6 +66,9 @@ tools/conv2aas/conv2aas:
 %.pal: %.png tools/pngdump/pngdump
        tools/pngdump/pngdump -o $@ -c $<
 
+data/tun.map: tools/tungen
+       tools/tungen -s 240x160 >$@
+
 data/aas_data.h: data/aas_data.s
 
 data/aas_data.s: $(audata) tools/conv2aas/conv2aas
@@ -85,7 +96,12 @@ run: $(bin_mb)
 
 .PHONY: simrun
 simrun: $(bin)
-       $(EMU) $(EMUFLAGS) $(bin)
+       mgba -2 $(bin)
+
+.PHONY: debug
+debug: $(elf)
+       mgba -2 -g $(bin) &
+       $(TCPREFIX)gdb $<
 
 .PHONY: disasm
 disasm: $(elf)
index bf99d4a..684f71f 100644 (file)
@@ -294,6 +294,6 @@ AAS_MixAudio_SetMaxChans_2:
 
 AAS_DoDMA3:
        mov r3,#0x04000000
-       add r3,r3,#0xd4
+       orr r3,r3,#0xd4
        stmia r3,{r0-r2}
        bx lr
index 3f92927..aa604be 100644 (file)
@@ -1,6 +1,15 @@
 #ifndef DATA_H_
 #define DATA_H_
 
+#include <stdint.h>
 #include "data/aas_data.h"
 
+#define CONV_RGB24_RGB15(r, g, b) \
+       (((r) >> 3) | (((uint16_t)(g) & 0xf8) << 2) | (((uint16_t)(b) & 0xf8) << 7))
+
+extern unsigned char tuncross_pixels[];
+extern unsigned char tuncross_cmap[];
+
+extern uint32_t tunmap[];
+
 #endif /* DATA_H_ */
diff --git a/src/data.s b/src/data.s
new file mode 100644 (file)
index 0000000..7a74252
--- /dev/null
@@ -0,0 +1,15 @@
+       .section .rodata
+
+       .globl tuncross_pixels
+       .globl tuncross_cmap
+       .globl tunmap
+
+       .align 1
+tuncross_pixels:
+       .incbin "data/tuncross.raw"
+       .align 1
+tuncross_cmap:
+       .incbin "data/tuncross.pal"
+
+       .align 2
+tunmap: .incbin "data/tun.map"
index ba23ab7..9efade4 100644 (file)
--- a/src/dma.c
+++ b/src/dma.c
 
 static volatile uint32_t *reg_dma[4] = {(void*)0x040000b0, (void*)0x040000bc, (void*)0x040000c8, (void*)0x040000d4 };
 
+void AAS_DoDMA3(void*, void*, uint32_t);
+
 /* --- perform a copy of words or halfwords using DMA --- */
 
 void dma_copy32(int channel, void *dst, void *src, int words, unsigned int flags)
 {
-       reg_dma[channel][DMA_SRC] = (uint32_t)src;
-       reg_dma[channel][DMA_DST] = (uint32_t)dst;
-       reg_dma[channel][DMA_CTRL] = words | flags | DMA_32 | DMA_ENABLE;
+       if(channel == 3) {
+               AAS_DoDMA3(src, dst, words | flags | DMA_32 | DMA_ENABLE);
+       } else {
+               reg_dma[channel][DMA_SRC] = (uint32_t)src;
+               reg_dma[channel][DMA_DST] = (uint32_t)dst;
+               reg_dma[channel][DMA_CTRL] = words | flags | DMA_32 | DMA_ENABLE;
+       }
 }
 
 void dma_copy16(int channel, void *dst, void *src, int halfwords, unsigned int flags)
 {
-       reg_dma[channel][DMA_SRC] = (uint32_t)src;
-       reg_dma[channel][DMA_DST] = (uint32_t)dst;
-       reg_dma[channel][DMA_CTRL] = halfwords | flags | DMA_16 | DMA_ENABLE;
+       if(channel == 3) {
+               AAS_DoDMA3(src, dst, halfwords | flags | DMA_16 | DMA_ENABLE);
+       } else {
+               reg_dma[channel][DMA_SRC] = (uint32_t)src;
+               reg_dma[channel][DMA_DST] = (uint32_t)dst;
+               reg_dma[channel][DMA_CTRL] = halfwords | flags | DMA_16 | DMA_ENABLE;
+       }
 }
 
 /* --- fill a buffer with an ammount of words and halfwords using DMA --- */
@@ -48,15 +58,23 @@ static uint32_t fill[4];
 void dma_fill32(int channel, void *dst, uint32_t val, int words)
 {
        fill[channel] = val;
-       reg_dma[channel][DMA_SRC] = (uint32_t)(fill + channel);
-       reg_dma[channel][DMA_DST] = (uint32_t)dst;
-       reg_dma[channel][DMA_CTRL] = words | DMA_SRC_FIX | DMA_TIMING_IMMED | DMA_32 | DMA_ENABLE;
+       if(channel == 3) {
+               AAS_DoDMA3(fill + channel, dst, words | DMA_SRC_FIX | DMA_TIMING_IMMED | DMA_32 | DMA_ENABLE);
+       } else {
+               reg_dma[channel][DMA_SRC] = (uint32_t)(fill + channel);
+               reg_dma[channel][DMA_DST] = (uint32_t)dst;
+               reg_dma[channel][DMA_CTRL] = words | DMA_SRC_FIX | DMA_TIMING_IMMED | DMA_32 | DMA_ENABLE;
+       }
 }
 
 void dma_fill16(int channel, void *dst, uint16_t val, int halfwords)
 {
        fill[channel] = val;
-       reg_dma[channel][DMA_SRC] = (uint32_t)(fill + channel);
-       reg_dma[channel][DMA_DST] = (uint32_t)dst;
-       reg_dma[channel][DMA_CTRL] = halfwords | DMA_SRC_FIX | DMA_TIMING_IMMED | DMA_16 | DMA_ENABLE;
+       if(channel == 3) {
+               AAS_DoDMA3(fill + channel, dst, halfwords | DMA_SRC_FIX | DMA_TIMING_IMMED | DMA_16 | DMA_ENABLE);
+       } else {
+               reg_dma[channel][DMA_SRC] = (uint32_t)(fill + channel);
+               reg_dma[channel][DMA_DST] = (uint32_t)dst;
+               reg_dma[channel][DMA_CTRL] = halfwords | DMA_SRC_FIX | DMA_TIMING_IMMED | DMA_16 | DMA_ENABLE;
+       }
 }
diff --git a/src/game.h b/src/game.h
new file mode 100644 (file)
index 0000000..376b26d
--- /dev/null
@@ -0,0 +1,7 @@
+#ifndef GAME_H_
+#define GAME_H_
+
+void menuscr(void);
+void gamescr(void);
+
+#endif /* GAME_H_ */
diff --git a/src/gamescr.c b/src/gamescr.c
new file mode 100644 (file)
index 0000000..330331e
--- /dev/null
@@ -0,0 +1,65 @@
+#include <string.h>
+#include "gbaregs.h"
+#include "dma.h"
+#include "data.h"
+#include "debug.h"
+
+#define present(x) \
+       do { \
+               REG_DISPCNT = DISPCNT_BG2 | 4 | ((x) << 4); \
+       } while(0)
+
+
+void gamescr(void)
+{
+       int i, j, tx, ty, angle, depth, nframes, backbuf, zoffs;
+       static uint16_t *vram[] = { (uint16_t*)VRAM_LFB_FB0_ADDR, (uint16_t*)VRAM_LFB_FB1_ADDR };
+       uint16_t *cdst;
+       unsigned char *csrc;
+       uint32_t tun, *tunptr;
+
+       REG_DISPCNT = 4 | DISPCNT_BG2 | DISPCNT_FB1;
+
+       cdst = (uint16_t*)CRAM_BG_ADDR;
+       csrc = tuncross_cmap;
+       for(i=0; i<256; i++) {
+               *cdst++ = CONV_RGB24_RGB15(csrc[0], csrc[1], csrc[2]);
+               csrc += 3;
+       }
+
+       nframes = 0;
+       for(;;) {
+               backbuf = ++nframes & 1;
+
+               zoffs = nframes << 1;
+
+               cdst = vram[backbuf];
+               tunptr = tunmap;
+               for(i=0; i<160; i++) {
+                       for(j=0; j<240/2; j++) {
+                               uint16_t pp;
+
+                               tun = *tunptr++;
+                               angle = tun & 0xffff;
+                               depth = tun >> 16;
+                               tx = (angle >> 6) & 0x7f;
+                               ty = ((depth >> 7) - zoffs) & 0x7f;
+                               pp = tuncross_pixels[(ty << 7) + tx];
+
+                               tun = *tunptr++;
+                               angle = tun & 0xffff;
+                               depth = tun >> 16;
+                               tx = (angle >> 6) & 0x7f;
+                               ty = ((depth >> 7) - zoffs) & 0x7f;
+                               pp |= (uint16_t)tuncross_pixels[(ty << 7) + tx] << 8;
+
+                               *cdst++ = pp;
+                       }
+               }
+
+               //while(!(REG_DISPSTAT & DISPSTAT_VBLANK));
+               while(REG_VCOUNT < 160);
+               //REG_DISPCNT ^= DISPCNT_FB1;
+               present(backbuf);
+       }
+}
index 03930b1..e358302 100644 (file)
@@ -2,6 +2,7 @@
 #include "gbaregs.h"
 #include "intr.h"
 #include "debug.h"
+#include "game.h"
 
 #include "AAS.h"
 #include "data.h"
 
 int main(void)
 {
-       int i, j;
-       uint16_t *vptr;
-
        emuprint("\nStarting GBAJAM21\n-----------------\n");
 
        intr_init();
 
+#ifndef NOSOUND
        interrupt(INTR_TIMER1, AAS_Timer1InterruptHandler);
        AAS_SetConfig(AAS_CONFIG_MIX_24KHZ, AAS_CONFIG_CHANS_8, AAS_CONFIG_SPATIAL_STEREO, AAS_CONFIG_DYNAMIC_ON);
        unmask(INTR_TIMER1);
        intr_enable();
 
-
-       REG_DISPCNT = 3 | DISPCNT_BG2;
-
-       vptr = (uint16_t*)VRAM_START_ADDR;
-       for(i=0; i<160; i++) {
-               for(j=0; j<240; j++) {
-                       int xor = i ^ j;
-                       int r = xor >> 2;
-                       int g = xor >> 1;
-                       int b = xor;
-
-                       *vptr++ = RGB15(r, g, b);
-               }
-       }
-
        AAS_MOD_Play(AAS_DATA_MOD_popcorn);
+#else
+       intr_enable();
+#endif
+
+       gamescr();
 
        for(;;);
        return 0;
diff --git a/src/menuscr.c b/src/menuscr.c
new file mode 100644 (file)
index 0000000..dfbc8cb
--- /dev/null
@@ -0,0 +1,5 @@
+#include "gbaregs.h"
+
+void menuscr(void)
+{
+}
diff --git a/tools/tungen.c b/tools/tungen.c
new file mode 100644 (file)
index 0000000..4849ec3
--- /dev/null
@@ -0,0 +1,75 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <stdint.h>
+#include <math.h>
+
+int main(int argc, char **argv)
+{
+       int i, j, xsz = 240, ysz = 160, texsz = 128;
+       struct vec2 *tunbuf, *tun;
+       float aspect;
+
+       for(i=1; i<argc; i++) {
+               if(argv[i][0] == '-') {
+                       if(argv[i][2] != 0) goto invalopt;
+                       switch(argv[i][1]) {
+                       case 's':
+                               if(sscanf(argv[++i], "%dx%d", &xsz, &ysz) != 2 || xsz <= 1 || ysz <= 1) {
+                                       fprintf(stderr, "-s must be followed by WxH\n");
+                                       return 1;
+                               }
+                               break;
+
+                       case 't':
+                               if(!(texsz = atoi(argv[++i])) || texsz > 256) {
+                                       fprintf(stderr, "-t must be followed by the texture size (1-256)\n");
+                                       return 1;
+                               }
+                               break;
+
+                       default:
+                               goto invalopt;
+                       }
+               } else {
+invalopt:      fprintf(stderr, "invalid argument: %s\n", argv[i]);
+                       return 1;
+               }
+       }
+
+       FILE *fp = fopen("tun_preview.ppm", "wb");
+       if(fp) {
+               fprintf(fp, "P6\n%d %d\n255\n", xsz, ysz);
+       }
+
+       aspect = (float)xsz / (float)ysz;
+
+       tun = tunbuf;
+       for(i=0; i<ysz; i++) {
+               float y = 2.0f * (float)i / (float)(ysz - 1) - 1.0f;
+               for(j=0; j<xsz; j++) {
+                       float x = (2.0f * (float)j / (float)(xsz - 1) - 1.0f) * aspect;
+
+                       float r = sqrt(x * x + y * y);
+                       float theta = atan2(y, x);
+
+                       float u = 0.5f * theta / M_PI + 0.5f;
+                       float v = r;
+
+                       uint32_t out = ((uint32_t)(u * 65535.0f) & 0xffff) |
+                               (((uint32_t)(v * 65535.0f) & 0xffff) << 16);
+                       fwrite(&out, sizeof out, 1, stdout);
+
+                       if(fp) {
+                               int cr = (int)(u * 2048.0f) & 0xff;
+                               int cb = (int)(r * 2048.0f) & 0xff;
+                               fputc(cr, fp);
+                               fputc(0, fp);
+                               fputc(cb, fp);
+                       }
+               }
+       }
+       fflush(stdout);
+
+       if(fp) fclose(fp);
+       return 0;
+}