Browse code

Make system device able to load a rom from memory

Dario Rodriguez authored on 11/01/2024 18:00:13
Showing 3 changed files
... ...
@@ -1,11 +1,13 @@
1 1
 #include <stdio.h>
2 2
 #include <stdlib.h>
3
+#include <string.h>
3 4
 
4 5
 #include "../uxn.h"
5 6
 #include "system.h"
6 7
 
7 8
 /*
8 9
 Copyright (c) 2022-2023 Devine Lu Linvega, Andrew Alderwick
10
+Copyright (c) 2024 Dario Rodriguez
9 11
 
10 12
 Permission to use, copy, modify, and distribute this software for any
11 13
 purpose with or without fee is hereby granted, provided that the above
... ...
@@ -19,86 +21,98 @@ char *boot_rom;
19 21
 Uint16 dev_vers[0x10];
20 22
 
21 23
 static int
22
-system_load(Uxn *u, char *filename)
24
+system_load(Uxn *u, char *filename, char *romdata, int sizeromdata)
23 25
 {
24
-	int l, i = 0;
25
-	FILE *f = fopen(filename, "rb");
26
-	if(!f)
27
-		return 0;
28
-	l = fread(&u->ram[PAGE_PROGRAM], 0x10000 - PAGE_PROGRAM, 1, f);
29
-	while(l && ++i < RAM_PAGES)
30
-		l = fread(u->ram + 0x10000 * i, 0x10000, 1, f);
31
-	fclose(f);
32
-	return 1;
26
+        int l, i = 0;
27
+        if(romdata==NULL) {
28
+                FILE *f = fopen(filename, "rb");
29
+                if(!f)
30
+                        return 0;
31
+                l = fread(&u->ram[PAGE_PROGRAM], 0x10000 - PAGE_PROGRAM, 1, f);
32
+                while(l && ++i < RAM_PAGES)
33
+                        l = fread(u->ram + 0x10000 * i, 0x10000, 1, f);
34
+                fclose(f);
35
+        } else {
36
+                if(sizeromdata<0)
37
+                        return 0;
38
+                l=sizeromdata;
39
+                l=(sizeromdata>(RAM_PAGES*0x10000-PAGE_PROGRAM))
40
+                  ?(RAM_PAGES*0x10000-PAGE_PROGRAM)
41
+                  :l;
42
+                memcpy(u->ram+PAGE_PROGRAM,romdata,l);
43
+        }
44
+        return 1;
33 45
 }
34 46
 
35 47
 static void
36 48
 system_print(Stack *s, char *name)
37 49
 {
38
-	Uint8 i;
39
-	fprintf(stderr, "%s ", name);
40
-	for(i = 0; i < 9; i++) {
41
-		Uint8 pos = s->ptr - 4 + i;
42
-		fprintf(stderr, !pos ? "[%02x]" : i == 4 ? "<%02x>"
43
-												 : " %02x ",
44
-			s->dat[pos]);
45
-	}
46
-	fprintf(stderr, "\n");
50
+        Uint8 i;
51
+        fprintf(stderr, "%s ", name);
52
+        for(i = 0; i < 9; i++) {
53
+                Uint8 pos = s->ptr - 4 + i;
54
+                fprintf(stderr, !pos ? "[%02x]" : i == 4 ? "<%02x>"
55
+                                                                                                 : " %02x ",
56
+                        s->dat[pos]);
57
+        }
58
+        fprintf(stderr, "\n");
47 59
 }
48 60
 
49 61
 int
50 62
 system_error(char *msg, const char *err)
51 63
 {
52
-	fprintf(stderr, "%s: %s\n", msg, err);
53
-	fflush(stderr);
54
-	return 0;
64
+        fprintf(stderr, "%s: %s\n", msg, err);
65
+        fflush(stderr);
66
+        return 0;
55 67
 }
56 68
 
57 69
 void
58 70
 system_inspect(Uxn *u)
59 71
 {
60
-	system_print(&u->wst, "wst");
61
-	system_print(&u->rst, "rst");
72
+        system_print(&u->wst, "wst");
73
+        system_print(&u->rst, "rst");
62 74
 }
63 75
 
64 76
 int
65 77
 system_version(char *name, char *date)
66 78
 {
67
-	printf("%s, %s.\n", name, date);
68
-	return 0;
79
+        printf("%s, %s.\n", name, date);
80
+        return 0;
69 81
 }
70 82
 
71 83
 void
72 84
 system_boot(Uxn *u, int soft)
73 85
 {
74
-	int i;
75
-	for(i = 0x100 * soft; i < 0x10000; i++)
76
-		u->ram[i] = 0;
77
-	for(i = 0x0; i < 0x100; i++)
78
-		u->dev[i] = 0;
79
-	u->wst.ptr = 0;
80
-	u->rst.ptr = 0;
86
+        int i;
87
+        for(i = 0x100 * soft; i < 0x10000; i++)
88
+                u->ram[i] = 0;
89
+        for(i = 0x0; i < 0x100; i++)
90
+                u->dev[i] = 0;
91
+        u->wst.ptr = 0;
92
+        u->rst.ptr = 0;
81 93
 }
82 94
 
83 95
 void
84
-system_reboot(Uxn *u, char *rom, int soft)
96
+system_reboot(Uxn *u, char *rom, int soft, char *romdata, int sizeromdata)
85 97
 {
86
-	system_boot(u, soft);
87
-	if(system_load(u, boot_rom))
88
-		if(uxn_eval(u, PAGE_PROGRAM))
89
-			boot_rom = rom;
98
+        system_boot(u, soft);
99
+        if(system_load(u, boot_rom, romdata, sizeromdata)) {
100
+                if(uxn_eval(u, PAGE_PROGRAM))
101
+                        boot_rom = rom;
102
+        }
90 103
 }
91 104
 
92 105
 int
93
-system_init(Uxn *u, Uint8 *ram, char *rom)
106
+system_init(Uxn *u, Uint8 *ram, char *rom, char *romdata, int sizeromdata)
94 107
 {
95
-	u->ram = ram;
96
-	system_boot(u, 0);
97
-	if(!system_load(u, rom))
98
-		if(!system_load(u, "boot.rom"))
99
-			return system_error("Init", "Failed to load rom.");
100
-	boot_rom = rom;
101
-	return 1;
108
+        u->ram = ram;
109
+        system_boot(u, 0);
110
+        if(!system_load(u, rom, romdata, sizeromdata)
111
+          && !system_load(u, "boot.rom", romdata, sizeromdata)) {
112
+                return system_error("Init", "Failed to load rom.");
113
+        }
114
+        boot_rom = rom;
115
+        return 1;
102 116
 }
103 117
 
104 118
 /* IO */
... ...
@@ -106,39 +120,39 @@ system_init(Uxn *u, Uint8 *ram, char *rom)
106 120
 Uint8
107 121
 system_dei(Uxn *u, Uint8 addr)
108 122
 {
109
-	switch(addr) {
110
-	case 0x4: return u->wst.ptr;
111
-	case 0x5: return u->rst.ptr;
112
-	default: return u->dev[addr];
113
-	}
123
+        switch(addr) {
124
+        case 0x4: return u->wst.ptr;
125
+        case 0x5: return u->rst.ptr;
126
+        default: return u->dev[addr];
127
+        }
114 128
 }
115 129
 
116 130
 void
117 131
 system_deo(Uxn *u, Uint8 *d, Uint8 port)
118 132
 {
119
-	Uint8 *ram;
120
-	Uint16 addr;
121
-	switch(port) {
122
-	case 0x3:
123
-		ram = u->ram;
124
-		addr = PEEK2(d + 2);
125
-		if(ram[addr] == 0x1) {
126
-			Uint16 i, length = PEEK2(ram + addr + 1);
127
-			Uint16 a_page = PEEK2(ram + addr + 1 + 2), a_addr = PEEK2(ram + addr + 1 + 4);
128
-			Uint16 b_page = PEEK2(ram + addr + 1 + 6), b_addr = PEEK2(ram + addr + 1 + 8);
129
-			int src = (a_page % RAM_PAGES) * 0x10000, dst = (b_page % RAM_PAGES) * 0x10000;
130
-			for(i = 0; i < length; i++)
131
-				ram[dst + (Uint16)(b_addr + i)] = ram[src + (Uint16)(a_addr + i)];
132
-		}
133
-		break;
134
-	case 0x4:
135
-		u->wst.ptr = d[4];
136
-		break;
137
-	case 0x5:
138
-		u->rst.ptr = d[5];
139
-		break;
140
-	case 0xe:
141
-		system_inspect(u);
142
-		break;
143
-	}
133
+        Uint8 *ram;
134
+        Uint16 addr;
135
+        switch(port) {
136
+        case 0x3:
137
+                ram = u->ram;
138
+                addr = PEEK2(d + 2);
139
+                if(ram[addr] == 0x1) {
140
+                        Uint16 i, length = PEEK2(ram + addr + 1);
141
+                        Uint16 a_page = PEEK2(ram + addr + 1 + 2), a_addr = PEEK2(ram + addr + 1 + 4);
142
+                        Uint16 b_page = PEEK2(ram + addr + 1 + 6), b_addr = PEEK2(ram + addr + 1 + 8);
143
+                        int src = (a_page % RAM_PAGES) * 0x10000, dst = (b_page % RAM_PAGES) * 0x10000;
144
+                        for(i = 0; i < length; i++)
145
+                                ram[dst + (Uint16)(b_addr + i)] = ram[src + (Uint16)(a_addr + i)];
146
+                }
147
+                break;
148
+        case 0x4:
149
+                u->wst.ptr = d[4];
150
+                break;
151
+        case 0x5:
152
+                u->rst.ptr = d[5];
153
+                break;
154
+        case 0xe:
155
+                system_inspect(u);
156
+                break;
157
+        }
144 158
 }
... ...
@@ -1,5 +1,6 @@
1 1
 /*
2 2
 Copyright (c) 2022 Devine Lu Linvega, Andrew Alderwick
3
+Copyright (c) 2024 Dario Rodriguez
3 4
 
4 5
 Permission to use, copy, modify, and distribute this software for any
5 6
 purpose with or without fee is hereby granted, provided that the above
... ...
@@ -17,11 +18,11 @@ WITH REGARD TO THIS SOFTWARE.
17 18
 
18 19
 extern char *boot_rom;
19 20
 
20
-void system_reboot(Uxn *u, char *rom, int soft);
21
+void system_reboot(Uxn *u, char *rom, int soft, char *romdata, int sizeromdata);
21 22
 void system_inspect(Uxn *u);
22 23
 int system_version(char *emulator, char *date);
23 24
 int system_error(char *msg, const char *err);
24
-int system_init(Uxn *u, Uint8 *ram, char *rom);
25
+int system_init(Uxn *u, Uint8 *ram, char *rom, char *romdata, int sizeromdata);
25 26
 
26 27
 Uint8 system_dei(Uxn *u, Uint8 addr);
27 28
 void system_deo(Uxn *u, Uint8 *d, Uint8 port);
... ...
@@ -154,8 +154,8 @@ varvara_init(char *romfilename, int flag_fullscreen, int zoom)
154 154
         if((varvara->instances[0]->ram=(Uint8 *)calloc(0x10000 * RAM_PAGES, sizeof(Uint8)))==NULL
155 155
           || (varvara->instances[0]->rom=(char *)malloc(strlen(romfilename)+1))==NULL
156 156
           || memcpy(varvara->instances[0]->rom,romfilename,strlen(romfilename)+1)==NULL
157
-          || !system_init(&(varvara->instances[0]->u), varvara->instances[0]->ram, varvara->instances[0]->rom)
158
-          || !system_init(&(varvara->instances[0]->u_audio), varvara->instances[0]->ram, varvara->instances[0]->rom)) {
157
+          || !system_init(&(varvara->instances[0]->u), varvara->instances[0]->ram, varvara->instances[0]->rom, NULL, 0)
158
+          || !system_init(&(varvara->instances[0]->u_audio), varvara->instances[0]->ram, varvara->instances[0]->rom, NULL, 0)) {
159 159
                 varvara_free(varvara),varvara=NULL;
160 160
                 system_error("Init", "Failed to initialize uxn.");
161 161
                 return(NULL);
... ...
@@ -442,7 +442,7 @@ emu_restart(Uxn *u, char *rom, int soft)
442 442
         screen_resize(u,WIDTH, HEIGHT);
443 443
         screen_fill(uxn_screen.bg, 0);
444 444
         screen_fill(uxn_screen.fg, 0);
445
-        system_reboot(u, rom, soft);
445
+        system_reboot(u, rom, soft, NULL, 0);
446 446
         SDL_SetWindowTitle(instance->video->emu_window, boot_rom);
447 447
 }
448 448