File: gbs2gb.c

package info (click to toggle)
gbsplay 0.0.99-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 1,044 kB
  • sloc: ansic: 8,360; sh: 1,667; makefile: 534; perl: 99; python: 72; xml: 13
file content (127 lines) | stat: -rw-r--r-- 2,432 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
/*
 * gbsplay is a Gameboy sound player
 *
 * 2003-2025 (C) by Tobias Diedrich <ranma+gbsplay@tdiedrich.de>
 *                  Christian Garbs <mitch@cgarbs.de>
 *
 * Licensed under GNU GPL v1 or, at your option, any later version.
 */

#include <inttypes.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

#include "common.h"
#include "gbhw.h"
#include "gbcpu.h"
#include "libgbs.h"
#include "gbs_internal.h"

/* global variables */
uint8_t logo_data[0x30];

void usage(long exitcode)
{
	FILE *out = exitcode ? stderr : stdout;
	fputs(_("Usage: gbs2gb [OPTION]... [--] GBS-FILE OUT-FILE\n"
		"\n"
		"Available options are:\n"
		"  -t  rom template\n"
		"  -h  display this help and exit\n"
		"  -V  print version and exit\n"
		"  --  end options, next argument is GBS-FILE\n"),
	      out);
	exit(exitcode);
}

void version(void)
{
	(void)puts("gbs2gb " GBS_VERSION);
	exit(EXIT_SUCCESS);
}

void read_rom_template(const char* const name)
{
	FILE *f = fopen(name, "rb");
	uint8_t hdr[0x200];
	if (!f) {
		fprintf(stderr, _("Could not open ROM template: %s"), name);
		exit(EXIT_FAILURE);
	}
	if (fread(hdr, 1, sizeof(hdr), f) != sizeof(hdr)) {
		fclose(f);
		fprintf(stderr, _("Could not open ROM template: %s"), name);
		exit(EXIT_FAILURE);
	}
	memcpy(logo_data, &hdr[0x104], 0x30);
	fclose(f);
}

void parseopts(int *argc, char ***argv)
{
	long res;
	while ((res = getopt(*argc, *argv, "t:hV")) != -1) {
		switch (res) {
		default:
			usage(EXIT_FAILURE);
			break;
		case 't':
			read_rom_template(optarg);
			break;
		case 'h':
			usage(EXIT_SUCCESS);
			break;
		case 'V':
			version();
			break;
		}
	}
	*argc -= optind;
	*argv += optind;
}

void read_default_template()
{
	const uint8_t *bootrom = gbs_internal_api.get_bootrom();
	if (!bootrom) {
		return;
	}
	memcpy(logo_data, &bootrom[0xa8], 0x30);
}

int main(int argc, char **argv)
{
	struct gbs *gbs;
	FILE *out;

	assert_internal_api_valid();
	i18n_init();
	read_default_template();

	parseopts(&argc, &argv);
	
	if (argc < 2) {
		usage(EXIT_FAILURE);
	}

	if (logo_data[0] == 0) {
		fputs(_("ROM template data not found!\n"), stderr);
		usage(EXIT_FAILURE);
	}

	if ((gbs = gbs_open(argv[0])) == NULL)
		exit(EXIT_FAILURE);

	out = fopen(argv[1], "wb");
	if (!out) {
		fprintf(stderr, _("Could not open output file: %s"), argv[1]);
		exit(EXIT_FAILURE);
	}

	gbs_internal_api.write_rom(gbs, out, logo_data);
	gbs_close(gbs);
	fclose(out);

	return 0;
}