Browse code

Started moving PPU into its own file

neauoire authored on 08/04/2021 00:32:18
Showing 5 changed files
... ...
@@ -6,6 +6,7 @@ clang-format -i src/uxn.h
6 6
 clang-format -i src/uxn.c
7 7
 clang-format -i src/emulator.c
8 8
 clang-format -i src/debugger.c
9
+clang-format -i src/ppu.c
9 10
 clang-format -i src/apu.c
10 11
 
11 12
 echo "Cleaning.."
... ...
@@ -20,12 +21,12 @@ if [ "${1}" = '--debug' ];
20 21
 then
21 22
 	echo "[debug]"
22 23
     cc -std=c89 -DDEBUG -Wall -Wno-unknown-pragmas -Wpedantic -Wshadow -Wextra -Werror=implicit-int -Werror=incompatible-pointer-types -Werror=int-conversion -Wvla -g -Og -fsanitize=address -fsanitize=undefined src/assembler.c -o bin/assembler
23
-	cc -std=c89 -DDEBUG -Wall -Wno-unknown-pragmas -Wpedantic -Wshadow -Wextra -Werror=implicit-int -Werror=incompatible-pointer-types -Werror=int-conversion -Wvla -g -Og -fsanitize=address -fsanitize=undefined src/uxn.c src/emulator.c src/apu.c -L/usr/local/lib -lSDL2 -o bin/emulator
24
+	cc -std=c89 -DDEBUG -Wall -Wno-unknown-pragmas -Wpedantic -Wshadow -Wextra -Werror=implicit-int -Werror=incompatible-pointer-types -Werror=int-conversion -Wvla -g -Og -fsanitize=address -fsanitize=undefined src/uxn.c src/ppu.c src/emulator.c src/apu.c -L/usr/local/lib -lSDL2 -o bin/emulator
24 25
     cc -std=c89 -DDEBUG -Wall -Wno-unknown-pragmas -Wpedantic -Wshadow -Wextra -Werror=implicit-int -Werror=incompatible-pointer-types -Werror=int-conversion -Wvla -g -Og -fsanitize=address -fsanitize=undefined src/uxn.c src/debugger.c -o bin/debugger
25 26
 else
26 27
 	cc src/assembler.c -std=c89 -Os -DNDEBUG -g0 -s -Wall -Wno-unknown-pragmas -o bin/assembler
27 28
 	cc src/uxn.c src/debugger.c -std=c89 -Os -DNDEBUG -g0 -s -Wall -Wno-unknown-pragmas -o bin/debugger
28
-	cc src/uxn.c src/emulator.c src/apu.c -std=c89 -Os -DNDEBUG -g0 -s -Wall -Wno-unknown-pragmas -L/usr/local/lib -lSDL2 -o bin/emulator
29
+	cc src/uxn.c src/ppu.c src/emulator.c src/apu.c -std=c89 -Os -DNDEBUG -g0 -s -Wall -Wno-unknown-pragmas -L/usr/local/lib -lSDL2 -o bin/emulator
29 30
 fi
30 31
 
31 32
 echo "Assembling.."
... ...
@@ -1,5 +1,4 @@
1 1
 #include <SDL2/SDL.h>
2
-#include <stdlib.h>
3 2
 
4 3
 /*
5 4
 Copyright (c) 2021 Devine Lu Linvega
... ...
@@ -14,25 +14,11 @@ WITH REGARD TO THIS SOFTWARE.
14 14
 */
15 15
 
16 16
 #include "uxn.h"
17
+#include "ppu.h"
17 18
 
18 19
 int initapu(Uxn *u, Uint8 id);
19
-void stepapu(Uxn *u);
20 20
 
21
-#define HOR 48
22
-#define VER 32
23
-#define PAD 2
24
-#define RES (HOR * VER * 16)
25
-
26
-typedef struct {
27
-	Uint8 reqdraw, bg[RES], fg[RES];
28
-	Uint16 x1, y1, x2, y2;
29
-} Screen;
30
-
31
-int WIDTH = 8 * HOR + 8 * PAD * 2;
32
-int HEIGHT = 8 * VER + 8 * PAD * 2;
33
-int FPS = 30, GUIDES = 0, ZOOM = 2;
34
-
35
-Uint32 *pixels, theme[4];
21
+static Ppu screen;
36 22
 
37 23
 Uint8 font[][8] = {
38 24
 	{0x00, 0x3c, 0x46, 0x4a, 0x52, 0x62, 0x3c, 0x00},
... ...
@@ -56,7 +42,6 @@ static SDL_Window *gWindow;
56 42
 static SDL_Renderer *gRenderer;
57 43
 static SDL_Texture *gTexture;
58 44
 SDL_AudioDeviceID audio_id;
59
-static Screen screen;
60 45
 static Device *devsystem, *devscreen, *devmouse, *devkey, *devctrl;
61 46
 
62 47
 #pragma mark - Helpers
... ...
@@ -82,66 +67,8 @@ getflag(Uint8 *a, char flag)
82 67
 	return *a & flag;
83 68
 }
84 69
 
85
-#pragma mark - Paint
86
-
87
-void
88
-paintpixel(Uint8 *dst, Uint16 x, Uint16 y, Uint8 color)
89
-{
90
-	Uint16 row = (y % 8) + ((x / 8 + y / 8 * HOR) * 16), col = 7 - (x % 8);
91
-	if(x >= HOR * 8 || y >= VER * 8 || row > RES - 8)
92
-		return;
93
-	if(color == 0 || color == 2)
94
-		dst[row] &= ~(1UL << col);
95
-	else
96
-		dst[row] |= 1UL << col;
97
-	if(color == 0 || color == 1)
98
-		dst[row + 8] &= ~(1UL << col);
99
-	else
100
-		dst[row + 8] |= 1UL << col;
101
-}
102
-
103 70
 #pragma mark - Helpers
104 71
 
105
-void
106
-clear(Uint32 *dst)
107
-{
108
-	int v, h;
109
-	for(v = 0; v < HEIGHT; v++)
110
-		for(h = 0; h < WIDTH; h++)
111
-			dst[v * WIDTH + h] = theme[0];
112
-}
113
-
114
-void
115
-drawpixel(Uint32 *dst, Uint16 x, Uint16 y, Uint8 color)
116
-{
117
-	if(x >= screen.x1 && x <= screen.x2 && y >= screen.x1 && y <= screen.y2)
118
-		dst[y * WIDTH + x] = theme[color];
119
-}
120
-
121
-void
122
-drawchr(Uint32 *dst, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 alpha)
123
-{
124
-	Uint8 v, h;
125
-	for(v = 0; v < 8; v++)
126
-		for(h = 0; h < 8; h++) {
127
-			Uint8 ch1 = ((sprite[v] >> h) & 0x1);
128
-			Uint8 ch2 = (((sprite[v + 8] >> h) & 0x1) << 1);
129
-			if(!alpha || (alpha && ch1 + ch2 != 0))
130
-				drawpixel(dst, x + 7 - h, y + v, ch1 + ch2);
131
-		}
132
-}
133
-
134
-void
135
-drawicn(Uint32 *dst, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 fg, Uint8 bg)
136
-{
137
-	Uint8 v, h;
138
-	for(v = 0; v < 8; v++)
139
-		for(h = 0; h < 8; h++) {
140
-			Uint8 ch1 = (sprite[v] >> (7 - h)) & 0x1;
141
-			drawpixel(dst, x + h, y + v, ch1 ? fg : bg);
142
-		}
143
-}
144
-
145 72
 #pragma mark - Core
146 73
 
147 74
 int
... ...
@@ -151,36 +78,22 @@ error(char *msg, const char *err)
151 78
 	return 0;
152 79
 }
153 80
 
154
-void
155
-loadtheme(Uint8 *addr)
156
-{
157
-	int i;
158
-	for(i = 0; i < 4; ++i) {
159
-		Uint8
160
-			r = (*(addr + i / 2) >> (!(i % 2) << 2)) & 0x0f,
161
-			g = (*(addr + 2 + i / 2) >> (!(i % 2) << 2)) & 0x0f,
162
-			b = (*(addr + 4 + i / 2) >> (!(i % 2) << 2)) & 0x0f;
163
-		theme[i] = (r << 20) + (r << 16) + (g << 12) + (g << 8) + (b << 4) + b;
164
-	}
165
-	screen.reqdraw = 1;
166
-}
167
-
168 81
 void
169 82
 drawdebugger(Uint32 *dst, Uxn *u)
170 83
 {
171 84
 	Uint8 i, x, y, b;
172 85
 	for(i = 0; i < 0x10; ++i) { /* memory */
173 86
 		x = ((i % 8) * 3 + 3) * 8, y = screen.x1 + 8 + i / 8 * 8, b = u->wst.dat[i];
174
-		drawicn(dst, x, y, font[(b >> 4) & 0xf], 1 + (u->wst.ptr == i), 0);
175
-		drawicn(dst, x + 8, y, font[b & 0xf], 1 + (u->wst.ptr == i), 0);
87
+		drawicn(&screen, x, y, font[(b >> 4) & 0xf], 1 + (u->wst.ptr == i), 0);
88
+		drawicn(&screen, x + 8, y, font[b & 0xf], 1 + (u->wst.ptr == i), 0);
176 89
 	}
177 90
 	for(x = 0; x < 32; ++x) {
178
-		drawpixel(dst, x, HEIGHT / 2, 2);
179
-		drawpixel(dst, WIDTH - x, HEIGHT / 2, 2);
180
-		drawpixel(dst, WIDTH / 2, HEIGHT - x, 2);
181
-		drawpixel(dst, WIDTH / 2, x, 2);
182
-		drawpixel(dst, WIDTH / 2 - 16 + x, HEIGHT / 2, 2);
183
-		drawpixel(dst, WIDTH / 2, HEIGHT / 2 - 16 + x, 2);
91
+		drawpixel(&screen, x, HEIGHT / 2, 2);
92
+		drawpixel(&screen, WIDTH - x, HEIGHT / 2, 2);
93
+		drawpixel(&screen, WIDTH / 2, HEIGHT - x, 2);
94
+		drawpixel(&screen, WIDTH / 2, x, 2);
95
+		drawpixel(&screen, WIDTH / 2 - 16 + x, HEIGHT / 2, 2);
96
+		drawpixel(&screen, WIDTH / 2, HEIGHT / 2 - 16 + x, 2);
184 97
 	}
185 98
 }
186 99
 
... ...
@@ -191,10 +104,10 @@ redraw(Uint32 *dst, Uxn *u)
191 104
 	for(y = 0; y < VER; ++y)
192 105
 		for(x = 0; x < HOR; ++x) {
193 106
 			Uint16 key = (y * HOR + x) * 16;
194
-			drawchr(dst, (x + PAD) * 8, (y + PAD) * 8, &screen.bg[key], 0);
195
-			drawchr(dst, (x + PAD) * 8, (y + PAD) * 8, &screen.fg[key], 1);
107
+			drawchr(&screen, (x + PAD) * 8, (y + PAD) * 8, &screen.bg[key], 0);
108
+			drawchr(&screen, (x + PAD) * 8, (y + PAD) * 8, &screen.fg[key], 1);
196 109
 		}
197
-	if(GUIDES)
110
+	if(screen.debugger)
198 111
 		drawdebugger(dst, u);
199 112
 	SDL_UpdateTexture(gTexture, NULL, dst, WIDTH * sizeof(Uint32));
200 113
 	SDL_RenderClear(gRenderer);
... ...
@@ -206,22 +119,22 @@ redraw(Uint32 *dst, Uxn *u)
206 119
 void
207 120
 toggledebug(Uxn *u)
208 121
 {
209
-	GUIDES = !GUIDES;
210
-	redraw(pixels, u);
122
+	screen.debugger = !screen.debugger;
123
+	redraw(screen.output, u);
211 124
 }
212 125
 
213 126
 void
214 127
 togglezoom(Uxn *u)
215 128
 {
216
-	ZOOM = ZOOM == 3 ? 1 : ZOOM + 1;
217
-	SDL_SetWindowSize(gWindow, WIDTH * ZOOM, HEIGHT * ZOOM);
218
-	redraw(pixels, u);
129
+	screen.zoom = screen.zoom == 3 ? 1 : screen.zoom + 1;
130
+	SDL_SetWindowSize(gWindow, WIDTH * screen.zoom, HEIGHT * screen.zoom);
131
+	redraw(screen.output, u);
219 132
 }
220 133
 
221 134
 void
222 135
 quit(void)
223 136
 {
224
-	free(pixels);
137
+	free(screen.output);
225 138
 	SDL_DestroyTexture(gTexture);
226 139
 	gTexture = NULL;
227 140
 	SDL_DestroyRenderer(gRenderer);
... ...
@@ -237,7 +150,7 @@ init(void)
237 150
 {
238 151
 	if(SDL_Init(SDL_INIT_VIDEO | SDL_INIT_AUDIO) < 0)
239 152
 		return error("Init", SDL_GetError());
240
-	gWindow = SDL_CreateWindow("Uxn", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, WIDTH * ZOOM, HEIGHT * ZOOM, SDL_WINDOW_SHOWN);
153
+	gWindow = SDL_CreateWindow("Uxn", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, WIDTH * screen.zoom, HEIGHT * screen.zoom, SDL_WINDOW_SHOWN);
241 154
 	if(gWindow == NULL)
242 155
 		return error("Window", SDL_GetError());
243 156
 	gRenderer = SDL_CreateRenderer(gWindow, -1, 0);
... ...
@@ -246,9 +159,9 @@ init(void)
246 159
 	gTexture = SDL_CreateTexture(gRenderer, SDL_PIXELFORMAT_ARGB8888, SDL_TEXTUREACCESS_STATIC, WIDTH, HEIGHT);
247 160
 	if(gTexture == NULL)
248 161
 		return error("Texture", SDL_GetError());
249
-	if(!(pixels = (Uint32 *)malloc(WIDTH * HEIGHT * sizeof(Uint32))))
162
+	if(!(screen.output = (Uint32 *)malloc(WIDTH * HEIGHT * sizeof(Uint32))))
250 163
 		return error("Pixels", "Failed to allocate memory");
251
-	clear(pixels);
164
+	clear(&screen);
252 165
 	SDL_StartTextInput();
253 166
 	SDL_ShowCursor(SDL_DISABLE);
254 167
 	screen.x1 = PAD * 8;
... ...
@@ -263,8 +176,8 @@ domouse(Uxn *u, SDL_Event *event)
263 176
 {
264 177
 	Uint8 flag = 0x00;
265 178
 	Uint16 addr = devmouse->addr + 2;
266
-	Uint16 x = clamp(event->motion.x / ZOOM - PAD * 8, 0, HOR * 8 - 1);
267
-	Uint16 y = clamp(event->motion.y / ZOOM - PAD * 8, 0, VER * 8 - 1);
179
+	Uint16 x = clamp(event->motion.x / screen.zoom - PAD * 8, 0, HOR * 8 - 1);
180
+	Uint16 y = clamp(event->motion.y / screen.zoom - PAD * 8, 0, VER * 8 - 1);
268 181
 	u->ram.dat[addr + 0] = (x >> 8) & 0xff;
269 182
 	u->ram.dat[addr + 1] = x & 0xff;
270 183
 	u->ram.dat[addr + 2] = (y >> 8) & 0xff;
... ...
@@ -450,7 +363,7 @@ system_poke(Uxn *u, Uint16 ptr, Uint8 b0, Uint8 b1)
450 363
 {
451 364
 	Uint8 *m = u->ram.dat;
452 365
 	m[PAGE_DEVICE + b0] = b1;
453
-	loadtheme(&m[PAGE_DEVICE + 0x0008]);
366
+	loadtheme(&screen, &m[PAGE_DEVICE + 0x0008]);
454 367
 	(void)ptr;
455 368
 	return b1;
456 369
 }
... ...
@@ -470,7 +383,7 @@ int
470 383
 start(Uxn *u)
471 384
 {
472 385
 	inituxn(u, 0x0200);
473
-	redraw(pixels, u);
386
+	redraw(screen.output, u);
474 387
 	while(1) {
475 388
 		SDL_Event event;
476 389
 		double elapsed, start = SDL_GetPerformanceCounter();
... ...
@@ -498,14 +411,14 @@ start(Uxn *u)
498 411
 				break;
499 412
 			case SDL_WINDOWEVENT:
500 413
 				if(event.window.event == SDL_WINDOWEVENT_EXPOSED)
501
-					redraw(pixels, u);
414
+					redraw(screen.output, u);
502 415
 				break;
503 416
 			}
504 417
 		}
505 418
 		evaluxn(u, devscreen->vector);
506 419
 		SDL_UnlockAudioDevice(audio_id);
507 420
 		if(screen.reqdraw)
508
-			redraw(pixels, u);
421
+			redraw(screen.output, u);
509 422
 		elapsed = (SDL_GetPerformanceCounter() - start) / (double)SDL_GetPerformanceFrequency() * 1000.0f;
510 423
 		SDL_Delay(clamp(16.666f - elapsed, 0, 1000));
511 424
 	}
... ...
@@ -516,6 +429,7 @@ int
516 429
 main(int argc, char **argv)
517 430
 {
518 431
 	Uxn u;
432
+	screen.zoom = 2;
519 433
 
520 434
 	if(argc < 2)
521 435
 		return error("Input", "Missing");
522 436
new file mode 100644
... ...
@@ -0,0 +1,83 @@
1
+/*
2
+Copyright (c) 2021 Devine Lu Linvega
3
+Copyright (c) 2021 Andrew Alderwick
4
+
5
+Permission to use, copy, modify, and distribute this software for any
6
+purpose with or without fee is hereby granted, provided that the above
7
+copyright notice and this permission notice appear in all copies.
8
+
9
+THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10
+WITH REGARD TO THIS SOFTWARE.
11
+*/
12
+
13
+#include "ppu.h"
14
+
15
+void
16
+clear(Ppu *p)
17
+{
18
+	int v, h;
19
+	for(v = 0; v < HEIGHT; v++)
20
+		for(h = 0; h < WIDTH; h++)
21
+			p->output[v * WIDTH + h] = p->colors[0];
22
+}
23
+
24
+void
25
+drawpixel(Ppu *p, Uint16 x, Uint16 y, Uint8 color)
26
+{
27
+	if(x >= p->x1 && x <= p->x2 && y >= p->x1 && y <= p->y2)
28
+		p->output[y * WIDTH + x] = p->colors[color];
29
+}
30
+
31
+void
32
+drawchr(Ppu *p, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 alpha)
33
+{
34
+	Uint8 v, h;
35
+	for(v = 0; v < 8; v++)
36
+		for(h = 0; h < 8; h++) {
37
+			Uint8 ch1 = ((sprite[v] >> h) & 0x1);
38
+			Uint8 ch2 = (((sprite[v + 8] >> h) & 0x1) << 1);
39
+			if(!alpha || (alpha && ch1 + ch2 != 0))
40
+				drawpixel(p, x + 7 - h, y + v, ch1 + ch2);
41
+		}
42
+}
43
+
44
+void
45
+drawicn(Ppu *p, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 fg, Uint8 bg)
46
+{
47
+	Uint8 v, h;
48
+	for(v = 0; v < 8; v++)
49
+		for(h = 0; h < 8; h++) {
50
+			Uint8 ch1 = (sprite[v] >> (7 - h)) & 0x1;
51
+			drawpixel(p, x + h, y + v, ch1 ? fg : bg);
52
+		}
53
+}
54
+
55
+void
56
+paintpixel(Uint8 *dst, Uint16 x, Uint16 y, Uint8 color)
57
+{
58
+	Uint16 row = (y % 8) + ((x / 8 + y / 8 * HOR) * 16), col = 7 - (x % 8);
59
+	if(x >= HOR * 8 || y >= VER * 8 || row > RES - 8)
60
+		return;
61
+	if(color == 0 || color == 2)
62
+		dst[row] &= ~(1UL << col);
63
+	else
64
+		dst[row] |= 1UL << col;
65
+	if(color == 0 || color == 1)
66
+		dst[row + 8] &= ~(1UL << col);
67
+	else
68
+		dst[row + 8] |= 1UL << col;
69
+}
70
+
71
+void
72
+loadtheme(Ppu *p, Uint8 *addr)
73
+{
74
+	int i;
75
+	for(i = 0; i < 4; ++i) {
76
+		Uint8
77
+			r = (*(addr + i / 2) >> (!(i % 2) << 2)) & 0x0f,
78
+			g = (*(addr + 2 + i / 2) >> (!(i % 2) << 2)) & 0x0f,
79
+			b = (*(addr + 4 + i / 2) >> (!(i % 2) << 2)) & 0x0f;
80
+		p->colors[i] = (r << 20) + (r << 16) + (g << 12) + (g << 8) + (b << 4) + b;
81
+	}
82
+	p->reqdraw = 1;
83
+}
0 84
\ No newline at end of file
1 85
new file mode 100644
... ...
@@ -0,0 +1,44 @@
1
+#include <stdio.h>
2
+
3
+/*
4
+Copyright (c) 2021 Devine Lu Linvega
5
+
6
+Permission to use, copy, modify, and distribute this software for any
7
+purpose with or without fee is hereby granted, provided that the above
8
+copyright notice and this permission notice appear in all copies.
9
+
10
+THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11
+WITH REGARD TO THIS SOFTWARE.
12
+*/
13
+
14
+typedef unsigned char Uint8;
15
+typedef signed char Sint8;
16
+typedef unsigned short Uint16;
17
+typedef signed short Sint16;
18
+typedef unsigned int Uint32;
19
+
20
+#define HOR 48
21
+#define VER 32
22
+#define PAD 2
23
+#define RES (HOR * VER * 16)
24
+
25
+#define WIDTH (8 * HOR + 8 * PAD * 2)
26
+#define HEIGHT (8 * VER + 8 * PAD * 2)
27
+
28
+typedef struct Ppu {
29
+	Uint8 reqdraw, zoom, debugger, bg[RES], fg[RES];
30
+	Uint16 x1, y1, x2, y2;
31
+	Uint32 *output, colors[4];
32
+} Ppu;
33
+
34
+void
35
+clear(Ppu *p);
36
+void
37
+drawpixel(Ppu *p, Uint16 x, Uint16 y, Uint8 color);
38
+void
39
+drawchr(Ppu *p, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 alpha);
40
+void
41
+drawicn(Ppu *p, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 fg, Uint8 bg);
42
+
43
+void paintpixel(Uint8 *dst, Uint16 x, Uint16 y, Uint8 color);
44
+void loadtheme(Ppu *p, Uint8 *addr);
0 45
\ No newline at end of file