Merge branch 'master' into JoyKit
This commit is contained in:
commit
0737655753
@ -1185,6 +1185,23 @@ static void rumbleCallback(GB_gameboy_t *gb, double amp)
|
||||
dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
|
||||
@try {
|
||||
if (!cameraSession) {
|
||||
if (@available(macOS 10.14, *)) {
|
||||
switch ([AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeVideo]) {
|
||||
case AVAuthorizationStatusAuthorized:
|
||||
break;
|
||||
case AVAuthorizationStatusNotDetermined: {
|
||||
[AVCaptureDevice requestAccessForMediaType:AVMediaTypeVideo completionHandler:^(BOOL granted) {
|
||||
[self cameraRequestUpdate];
|
||||
}];
|
||||
return;
|
||||
}
|
||||
case AVAuthorizationStatusDenied:
|
||||
case AVAuthorizationStatusRestricted:
|
||||
GB_camera_updated(&gb);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
NSError *error;
|
||||
AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType: AVMediaTypeVideo];
|
||||
AVCaptureDeviceInput *input = [AVCaptureDeviceInput deviceInputWithDevice: device error: &error];
|
||||
|
@ -2,6 +2,8 @@
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDisplayName</key>
|
||||
<string>SameBoy</string>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>en</string>
|
||||
<key>CFBundleDocumentTypes</key>
|
||||
@ -70,7 +72,7 @@
|
||||
<key>LSMinimumSystemVersion</key>
|
||||
<string>10.9</string>
|
||||
<key>NSHumanReadableCopyright</key>
|
||||
<string>Copyright © 2015-2019 Lior Halphon</string>
|
||||
<string>Copyright © 2015-2020 Lior Halphon</string>
|
||||
<key>NSMainNibFile</key>
|
||||
<string>MainMenu</string>
|
||||
<key>NSPrincipalClass</key>
|
||||
@ -116,6 +118,8 @@
|
||||
</dict>
|
||||
</dict>
|
||||
</array>
|
||||
<key>NSCameraUsageDescription</key>
|
||||
<string>SameBoy needs to access your camera to emulate the Game Boy Camera</string>
|
||||
<key>NSSupportsAutomaticGraphicsSwitching</key>
|
||||
<true/>
|
||||
</dict>
|
||||
|
@ -30,7 +30,7 @@
|
||||
|
||||
<h1>SameBoy</h1>
|
||||
<h2>MIT License</h2>
|
||||
<h3>Copyright © 2015-2019 Lior Halphon</h3>
|
||||
<h3>Copyright © 2015-2020 Lior Halphon</h3>
|
||||
|
||||
<p>Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
|
@ -1008,7 +1008,7 @@ void GB_set_sample_rate(GB_gameboy_t *gb, unsigned sample_rate)
|
||||
GB_apu_update_cycles_per_sample(gb);
|
||||
}
|
||||
|
||||
void GB_set_sample_rate_by_clocks(GB_gameboy_t *gb, unsigned cycles_per_sample)
|
||||
void GB_set_sample_rate_by_clocks(GB_gameboy_t *gb, double cycles_per_sample)
|
||||
{
|
||||
|
||||
if (cycles_per_sample == 0) {
|
||||
|
@ -148,7 +148,7 @@ typedef struct {
|
||||
} GB_apu_output_t;
|
||||
|
||||
void GB_set_sample_rate(GB_gameboy_t *gb, unsigned sample_rate);
|
||||
void GB_set_sample_rate_by_clocks(GB_gameboy_t *gb, unsigned cycles_per_sample); /* Cycles are in 8MHz units */
|
||||
void GB_set_sample_rate_by_clocks(GB_gameboy_t *gb, double cycles_per_sample); /* Cycles are in 8MHz units */
|
||||
void GB_set_highpass_filter_mode(GB_gameboy_t *gb, GB_highpass_mode_t mode);
|
||||
void GB_apu_set_sample_callback(GB_gameboy_t *gb, GB_sample_callback_t callback);
|
||||
#ifdef GB_INTERNAL
|
||||
|
@ -819,7 +819,7 @@ static bool registers(GB_gameboy_t *gb, char *arguments, char *modifiers, const
|
||||
GB_log(gb, "AF = $%04x (%c%c%c%c)\n", gb->registers[GB_REGISTER_AF], /* AF can't really be an address */
|
||||
(gb->f & GB_CARRY_FLAG)? 'C' : '-',
|
||||
(gb->f & GB_HALF_CARRY_FLAG)? 'H' : '-',
|
||||
(gb->f & GB_SUBSTRACT_FLAG)? 'N' : '-',
|
||||
(gb->f & GB_SUBTRACT_FLAG)? 'N' : '-',
|
||||
(gb->f & GB_ZERO_FLAG)? 'Z' : '-');
|
||||
GB_log(gb, "BC = %s\n", value_to_string(gb, gb->registers[GB_REGISTER_BC], false));
|
||||
GB_log(gb, "DE = %s\n", value_to_string(gb, gb->registers[GB_REGISTER_DE], false));
|
||||
|
11
Core/gb.c
11
Core/gb.c
@ -18,6 +18,13 @@
|
||||
#define GB_rewind_push(...)
|
||||
#endif
|
||||
|
||||
|
||||
static inline uint32_t state_magic(void)
|
||||
{
|
||||
if (sizeof(bool) == 1) return 'SAME';
|
||||
return 'S4ME';
|
||||
}
|
||||
|
||||
void GB_attributed_logv(GB_gameboy_t *gb, GB_log_attributes attributes, const char *fmt, va_list args)
|
||||
{
|
||||
char *string = NULL;
|
||||
@ -660,7 +667,7 @@ void GB_disconnect_serial(GB_gameboy_t *gb)
|
||||
|
||||
bool GB_is_inited(GB_gameboy_t *gb)
|
||||
{
|
||||
return gb->magic == 'SAME';
|
||||
return gb->magic == state_magic();
|
||||
}
|
||||
|
||||
bool GB_is_cgb(GB_gameboy_t *gb)
|
||||
@ -929,7 +936,7 @@ void GB_reset(GB_gameboy_t *gb)
|
||||
gb->nontrivial_jump_state = NULL;
|
||||
}
|
||||
|
||||
gb->magic = (uintptr_t)'SAME';
|
||||
gb->magic = state_magic();
|
||||
}
|
||||
|
||||
void GB_switch_model_and_reset(GB_gameboy_t *gb, GB_model_t model)
|
||||
|
@ -98,7 +98,7 @@ enum {
|
||||
enum {
|
||||
GB_CARRY_FLAG = 16,
|
||||
GB_HALF_CARRY_FLAG = 32,
|
||||
GB_SUBSTRACT_FLAG = 64,
|
||||
GB_SUBTRACT_FLAG = 64,
|
||||
GB_ZERO_FLAG = 128,
|
||||
};
|
||||
|
||||
@ -278,10 +278,6 @@ typedef struct {
|
||||
This struct is not packed, but dumped sections exclusively use types that have the same alignment in both 32 and 64
|
||||
bit platforms. */
|
||||
|
||||
/* We make sure bool is 1 for cross-platform save state compatibility. */
|
||||
/* Todo: We might want to typedef our own bool if this prevents SameBoy from working on specific platforms. */
|
||||
_Static_assert(sizeof(bool) == 1, "sizeof(bool) != 1");
|
||||
|
||||
#ifdef GB_INTERNAL
|
||||
struct GB_gameboy_s {
|
||||
#else
|
||||
|
@ -422,6 +422,11 @@ static GB_read_function_t * const read_map[] =
|
||||
read_ram, read_high_memory, /* EXXX FXXX */
|
||||
};
|
||||
|
||||
void GB_set_read_memory_callback(GB_gameboy_t *gb, GB_read_memory_callback_t callback)
|
||||
{
|
||||
gb->read_memory_callback = callback;
|
||||
}
|
||||
|
||||
uint8_t GB_read_memory(GB_gameboy_t *gb, uint16_t addr)
|
||||
{
|
||||
if (gb->n_watchpoints) {
|
||||
@ -745,7 +750,11 @@ static void write_high_memory(GB_gameboy_t *gb, uint16_t addr, uint8_t value)
|
||||
return;
|
||||
|
||||
case GB_IO_JOYP:
|
||||
if ((gb->io_registers[GB_IO_JOYP] & 0x30) != (value & 0x30)) {
|
||||
if (gb->joyp_write_callback) {
|
||||
gb->joyp_write_callback(gb, value);
|
||||
GB_update_joyp(gb);
|
||||
}
|
||||
else if ((gb->io_registers[GB_IO_JOYP] & 0x30) != (value & 0x30)) {
|
||||
GB_sgb_write(gb, value);
|
||||
gb->io_registers[GB_IO_JOYP] = value & 0xF0;
|
||||
GB_update_joyp(gb);
|
||||
|
@ -385,11 +385,7 @@ static void command_ready(GB_gameboy_t *gb)
|
||||
}
|
||||
|
||||
void GB_sgb_write(GB_gameboy_t *gb, uint8_t value)
|
||||
{
|
||||
if (gb->joyp_write_callback) {
|
||||
gb->joyp_write_callback(gb, value);
|
||||
}
|
||||
|
||||
{
|
||||
if (!GB_is_sgb(gb)) return;
|
||||
if (!GB_is_hle_sgb(gb)) {
|
||||
/* Notify via callback */
|
||||
|
@ -318,7 +318,7 @@ static void inc_hr(GB_gameboy_t *gb, uint8_t opcode)
|
||||
uint8_t register_id;
|
||||
register_id = ((opcode >> 4) + 1) & 0x03;
|
||||
gb->registers[register_id] += 0x100;
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBSTRACT_FLAG | GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBTRACT_FLAG | GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
|
||||
if ((gb->registers[register_id] & 0x0F00) == 0) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG;
|
||||
@ -334,7 +334,7 @@ static void dec_hr(GB_gameboy_t *gb, uint8_t opcode)
|
||||
register_id = ((opcode >> 4) + 1) & 0x03;
|
||||
gb->registers[register_id] -= 0x100;
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBTRACT_FLAG;
|
||||
|
||||
if ((gb->registers[register_id] & 0x0F00) == 0xF00) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG;
|
||||
@ -396,7 +396,7 @@ static void add_hl_rr(GB_gameboy_t *gb, uint8_t opcode)
|
||||
register_id = (opcode >> 4) + 1;
|
||||
rr = gb->registers[register_id];
|
||||
gb->registers[GB_REGISTER_HL] = hl + rr;
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBSTRACT_FLAG | GB_CARRY_FLAG | GB_HALF_CARRY_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBTRACT_FLAG | GB_CARRY_FLAG | GB_HALF_CARRY_FLAG);
|
||||
|
||||
/* The meaning of the Half Carry flag is really hard to track -_- */
|
||||
if (((hl & 0xFFF) + (rr & 0xFFF)) & 0x1000) {
|
||||
@ -432,7 +432,7 @@ static void inc_lr(GB_gameboy_t *gb, uint8_t opcode)
|
||||
value = (gb->registers[register_id] & 0xFF) + 1;
|
||||
gb->registers[register_id] = (gb->registers[register_id] & 0xFF00) | value;
|
||||
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBSTRACT_FLAG | GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBTRACT_FLAG | GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
|
||||
if ((gb->registers[register_id] & 0x0F) == 0) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG;
|
||||
@ -452,7 +452,7 @@ static void dec_lr(GB_gameboy_t *gb, uint8_t opcode)
|
||||
gb->registers[register_id] = (gb->registers[register_id] & 0xFF00) | value;
|
||||
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBTRACT_FLAG;
|
||||
|
||||
if ((gb->registers[register_id] & 0x0F) == 0xF) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG;
|
||||
@ -533,7 +533,7 @@ static void daa(GB_gameboy_t *gb, uint8_t opcode)
|
||||
|
||||
gb->registers[GB_REGISTER_AF] &= ~(0xFF00 | GB_ZERO_FLAG);
|
||||
|
||||
if (gb->registers[GB_REGISTER_AF] & GB_SUBSTRACT_FLAG) {
|
||||
if (gb->registers[GB_REGISTER_AF] & GB_SUBTRACT_FLAG) {
|
||||
if (gb->registers[GB_REGISTER_AF] & GB_HALF_CARRY_FLAG) {
|
||||
result = (result - 0x06) & 0xFF;
|
||||
}
|
||||
@ -567,19 +567,19 @@ static void daa(GB_gameboy_t *gb, uint8_t opcode)
|
||||
static void cpl(GB_gameboy_t *gb, uint8_t opcode)
|
||||
{
|
||||
gb->registers[GB_REGISTER_AF] ^= 0xFF00;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG | GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG | GB_SUBTRACT_FLAG;
|
||||
}
|
||||
|
||||
static void scf(GB_gameboy_t *gb, uint8_t opcode)
|
||||
{
|
||||
gb->registers[GB_REGISTER_AF] |= GB_CARRY_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_HALF_CARRY_FLAG | GB_SUBSTRACT_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_HALF_CARRY_FLAG | GB_SUBTRACT_FLAG);
|
||||
}
|
||||
|
||||
static void ccf(GB_gameboy_t *gb, uint8_t opcode)
|
||||
{
|
||||
gb->registers[GB_REGISTER_AF] ^= GB_CARRY_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_HALF_CARRY_FLAG | GB_SUBSTRACT_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_HALF_CARRY_FLAG | GB_SUBTRACT_FLAG);
|
||||
}
|
||||
|
||||
static void ld_dhli_a(GB_gameboy_t *gb, uint8_t opcode)
|
||||
@ -610,7 +610,7 @@ static void inc_dhl(GB_gameboy_t *gb, uint8_t opcode)
|
||||
value = cycle_read(gb, gb->registers[GB_REGISTER_HL]) + 1;
|
||||
cycle_write(gb, gb->registers[GB_REGISTER_HL], value);
|
||||
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBSTRACT_FLAG | GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] &= ~(GB_SUBTRACT_FLAG | GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
if ((value & 0x0F) == 0) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG;
|
||||
}
|
||||
@ -627,7 +627,7 @@ static void dec_dhl(GB_gameboy_t *gb, uint8_t opcode)
|
||||
cycle_write(gb, gb->registers[GB_REGISTER_HL], value);
|
||||
|
||||
gb->registers[GB_REGISTER_AF] &= ~( GB_ZERO_FLAG | GB_HALF_CARRY_FLAG);
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBTRACT_FLAG;
|
||||
if ((value & 0x0F) == 0x0F) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_HALF_CARRY_FLAG;
|
||||
}
|
||||
@ -763,7 +763,7 @@ static void sub_a_r(GB_gameboy_t *gb, uint8_t opcode)
|
||||
uint8_t value, a;
|
||||
value = get_src_value(gb, opcode);
|
||||
a = gb->registers[GB_REGISTER_AF] >> 8;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value) << 8) | GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value) << 8) | GB_SUBTRACT_FLAG;
|
||||
if (a == value) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_ZERO_FLAG;
|
||||
}
|
||||
@ -781,7 +781,7 @@ static void sbc_a_r(GB_gameboy_t *gb, uint8_t opcode)
|
||||
value = get_src_value(gb, opcode);
|
||||
a = gb->registers[GB_REGISTER_AF] >> 8;
|
||||
carry = (gb->registers[GB_REGISTER_AF] & GB_CARRY_FLAG) != 0;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value - carry) << 8) | GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value - carry) << 8) | GB_SUBTRACT_FLAG;
|
||||
|
||||
if ((uint8_t) (a - value - carry) == 0) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_ZERO_FLAG;
|
||||
@ -833,7 +833,7 @@ static void cp_a_r(GB_gameboy_t *gb, uint8_t opcode)
|
||||
value = get_src_value(gb, opcode);
|
||||
a = gb->registers[GB_REGISTER_AF] >> 8;
|
||||
gb->registers[GB_REGISTER_AF] &= 0xFF00;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBTRACT_FLAG;
|
||||
if (a == value) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_ZERO_FLAG;
|
||||
}
|
||||
@ -962,7 +962,7 @@ static void sub_a_d8(GB_gameboy_t *gb, uint8_t opcode)
|
||||
uint8_t value, a;
|
||||
value = cycle_read_inc_oam_bug(gb, gb->pc++);
|
||||
a = gb->registers[GB_REGISTER_AF] >> 8;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value) << 8) | GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value) << 8) | GB_SUBTRACT_FLAG;
|
||||
if (a == value) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_ZERO_FLAG;
|
||||
}
|
||||
@ -980,7 +980,7 @@ static void sbc_a_d8(GB_gameboy_t *gb, uint8_t opcode)
|
||||
value = cycle_read_inc_oam_bug(gb, gb->pc++);
|
||||
a = gb->registers[GB_REGISTER_AF] >> 8;
|
||||
carry = (gb->registers[GB_REGISTER_AF] & GB_CARRY_FLAG) != 0;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value - carry) << 8) | GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] = ((a - value - carry) << 8) | GB_SUBTRACT_FLAG;
|
||||
|
||||
if ((uint8_t) (a - value - carry) == 0) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_ZERO_FLAG;
|
||||
@ -1032,7 +1032,7 @@ static void cp_a_d8(GB_gameboy_t *gb, uint8_t opcode)
|
||||
value = cycle_read_inc_oam_bug(gb, gb->pc++);
|
||||
a = gb->registers[GB_REGISTER_AF] >> 8;
|
||||
gb->registers[GB_REGISTER_AF] &= 0xFF00;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBSTRACT_FLAG;
|
||||
gb->registers[GB_REGISTER_AF] |= GB_SUBTRACT_FLAG;
|
||||
if (a == value) {
|
||||
gb->registers[GB_REGISTER_AF] |= GB_ZERO_FLAG;
|
||||
}
|
||||
|
2
LICENSE
2
LICENSE
@ -1,6 +1,6 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2015-2019 Lior Halphon
|
||||
Copyright (c) 2015-2020 Lior Halphon
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
|
74
Makefile
74
Makefile
@ -34,7 +34,7 @@ ifeq ($(MAKECMDGOALS),)
|
||||
MAKECMDGOALS := $(DEFAULT)
|
||||
endif
|
||||
|
||||
VERSION := 0.12.2
|
||||
VERSION := 0.12.3
|
||||
export VERSION
|
||||
CONF ?= debug
|
||||
|
||||
@ -51,10 +51,15 @@ endif
|
||||
# Use clang if it's available.
|
||||
ifeq ($(origin CC),default)
|
||||
ifneq (, $(shell which clang))
|
||||
CC := clang
|
||||
CC := clang
|
||||
endif
|
||||
endif
|
||||
|
||||
# Find libraries with pkg-config if available.
|
||||
ifneq (, $(shell which pkg-config))
|
||||
PKG_CONFIG := pkg-config
|
||||
endif
|
||||
|
||||
ifeq ($(PLATFORM),windows32)
|
||||
# To force use of the Unix version instead of the Windows version
|
||||
MKDIR := $(shell which mkdir)
|
||||
@ -71,9 +76,11 @@ endif
|
||||
# Set compilation and linkage flags based on target, platform and configuration
|
||||
|
||||
OPEN_DIALOG = OpenDialog/gtk.c
|
||||
NULL := /dev/null
|
||||
|
||||
ifeq ($(PLATFORM),windows32)
|
||||
OPEN_DIALOG = OpenDialog/windows.c
|
||||
NULL := NUL
|
||||
endif
|
||||
|
||||
ifeq ($(PLATFORM),Darwin)
|
||||
@ -82,21 +89,35 @@ endif
|
||||
|
||||
|
||||
CFLAGS += -Werror -Wall -Wno-unused-result -Wno-strict-aliasing -Wno-unknown-warning -Wno-unknown-warning-option -Wno-multichar -Wno-int-in-bool-context -std=gnu11 -D_GNU_SOURCE -DVERSION="$(VERSION)" -I. -D_USE_MATH_DEFINES
|
||||
SDL_LDFLAGS := -lSDL2 -lGL
|
||||
ifeq (,$(PKG_CONFIG))
|
||||
SDL_CFLAGS := $(shell sdl2-config --cflags)
|
||||
SDL_LDFLAGS := $(shell sdl2-config --libs)
|
||||
else
|
||||
SDL_CFLAGS := $(shell $(PKG_CONFIG) --cflags sdl2)
|
||||
SDL_LDFLAGS := $(shell $(PKG_CONFIG) --libs sdl2)
|
||||
endif
|
||||
ifeq (,$(PKG_CONFIG))
|
||||
GL_LDFLAGS := -lGL
|
||||
else
|
||||
GL_CFLAGS := $(shell $(PKG_CONFIG) --cflags gl)
|
||||
GL_LDFLAGS := $(shell $(PKG_CONFIG) --libs gl || echo -lGL)
|
||||
endif
|
||||
ifeq ($(PLATFORM),windows32)
|
||||
CFLAGS += -IWindows -Drandom=rand
|
||||
LDFLAGS += -lmsvcrt -lcomdlg32 -lSDL2main -Wl,/MANIFESTFILE:NUL
|
||||
SDL_LDFLAGS := -lSDL2 -lopengl32
|
||||
LDFLAGS += -lmsvcrt -lcomdlg32 -luser32 -lSDL2main -Wl,/MANIFESTFILE:NUL
|
||||
SDL_LDFLAGS := -lSDL2
|
||||
GL_LDFLAGS := -lopengl32
|
||||
else
|
||||
LDFLAGS += -lc -lm -ldl
|
||||
endif
|
||||
|
||||
ifeq ($(PLATFORM),Darwin)
|
||||
SYSROOT := $(shell xcodebuild -sdk macosx -version Path 2> /dev/null)
|
||||
CFLAGS += -F/Library/Frameworks
|
||||
OCFLAGS += -x objective-c -fobjc-arc -Wno-deprecated-declarations -isysroot $(SYSROOT) -mmacosx-version-min=10.9
|
||||
LDFLAGS += -framework AppKit -framework PreferencePanes -framework Carbon -framework QuartzCore -weak_framework Metal -weak_framework MetalKit
|
||||
SDL_LDFLAGS := -F/Library/Frameworks -framework SDL2 -framework OpenGL
|
||||
SYSROOT := $(shell xcodebuild -sdk macosx -version Path 2> $(NULL))
|
||||
CFLAGS += -F/Library/Frameworks -mmacosx-version-min=10.9
|
||||
OCFLAGS += -x objective-c -fobjc-arc -Wno-deprecated-declarations -isysroot $(SYSROOT)
|
||||
LDFLAGS += -framework AppKit -framework PreferencePanes -framework Carbon -framework QuartzCore -weak_framework Metal -weak_framework MetalKit -mmacosx-version-min=10.9
|
||||
SDL_LDFLAGS := -F/Library/Frameworks -framework SDL2
|
||||
GL_LDFLAGS := -framework OpenGL
|
||||
endif
|
||||
CFLAGS += -Wno-deprecated-declarations
|
||||
ifeq ($(PLATFORM),windows32)
|
||||
@ -108,10 +129,16 @@ ifeq ($(CONF),debug)
|
||||
CFLAGS += -g
|
||||
else ifeq ($(CONF), release)
|
||||
CFLAGS += -O3 -DNDEBUG
|
||||
STRIP := strip
|
||||
ifeq ($(PLATFORM),Darwin)
|
||||
LDFLAGS += -Wl,-exported_symbols_list,$(NULL)
|
||||
STRIP := -@true
|
||||
endif
|
||||
ifneq ($(PLATFORM),windows32)
|
||||
LDFLAGS += -flto
|
||||
CFLAGS += -flto
|
||||
endif
|
||||
|
||||
else
|
||||
$(error Invalid value for CONF: $(CONF). Use "debug", "release" or "native_release")
|
||||
endif
|
||||
@ -169,6 +196,10 @@ ifneq ($(filter $(MAKECMDGOALS),cocoa),)
|
||||
endif
|
||||
endif
|
||||
|
||||
$(OBJ)/SDL/%.dep: SDL/%
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $(CFLAGS) $(SDL_CFLAGS) $(GL_CFLAGS) -MT $(OBJ)/$^.o -M $^ -c -o $@
|
||||
|
||||
$(OBJ)/%.dep: %
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $(CFLAGS) -MT $(OBJ)/$^.o -M $^ -c -o $@
|
||||
@ -179,6 +210,10 @@ $(OBJ)/Core/%.c.o: Core/%.c
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $(CFLAGS) -DGB_INTERNAL -c $< -o $@
|
||||
|
||||
$(OBJ)/SDL/%.c.o: SDL/%.c
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $(CFLAGS) $(SDL_CFLAGS) $(GL_CFLAGS) -c $< -o $@
|
||||
|
||||
$(OBJ)/%.c.o: %.c
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $(CFLAGS) -c $< -o $@
|
||||
@ -220,7 +255,7 @@ $(BIN)/SameBoy.app/Contents/MacOS/SameBoy: $(CORE_OBJECTS) $(COCOA_OBJECTS)
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $^ -o $@ $(LDFLAGS) -framework OpenGL -framework AudioUnit -framework AVFoundation -framework CoreVideo -framework CoreMedia -framework IOKit
|
||||
ifeq ($(CONF), release)
|
||||
strip $@
|
||||
$(STRIP) $@
|
||||
endif
|
||||
|
||||
$(BIN)/SameBoy.app/Contents/Resources/Base.lproj/%.nib: Cocoa/%.xib
|
||||
@ -240,10 +275,7 @@ $(BIN)/SameBoy.qlgenerator: $(BIN)/SameBoy.qlgenerator/Contents/MacOS/SameBoyQL
|
||||
# once in the QL Generator. It should probably become a dylib instead.
|
||||
$(BIN)/SameBoy.qlgenerator/Contents/MacOS/SameBoyQL: $(CORE_OBJECTS) $(QUICKLOOK_OBJECTS)
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $^ -o $@ $(LDFLAGS) -bundle -framework Cocoa -framework Quicklook
|
||||
ifeq ($(CONF), release)
|
||||
strip -u -r -s QuickLook/exports.sym $@
|
||||
endif
|
||||
$(CC) $^ -o $@ $(LDFLAGS) -Wl,-exported_symbols_list,QuickLook/exports.sym -bundle -framework Cocoa -framework Quicklook
|
||||
|
||||
# cgb_boot_fast.bin is not a standard boot ROM, we don't expect it to exist in the user-provided
|
||||
# boot ROM directory.
|
||||
@ -256,19 +288,19 @@ $(BIN)/SameBoy.qlgenerator/Contents/Resources/cgb_boot_fast.bin: $(BIN)/BootROMs
|
||||
# Unix versions build only one binary
|
||||
$(BIN)/SDL/sameboy: $(CORE_OBJECTS) $(SDL_OBJECTS)
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $^ -o $@ $(LDFLAGS) $(SDL_LDFLAGS)
|
||||
$(CC) $^ -o $@ $(LDFLAGS) $(SDL_LDFLAGS) $(GL_LDFLAGS)
|
||||
ifeq ($(CONF), release)
|
||||
strip $@
|
||||
$(STRIP) $@
|
||||
endif
|
||||
|
||||
# Windows version builds two, one with a conole and one without it
|
||||
$(BIN)/SDL/sameboy.exe: $(CORE_OBJECTS) $(SDL_OBJECTS) $(OBJ)/Windows/resources.o
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $^ -o $@ $(LDFLAGS) $(SDL_LDFLAGS) -Wl,/subsystem:windows
|
||||
$(CC) $^ -o $@ $(LDFLAGS) $(SDL_LDFLAGS) $(GL_LDFLAGS) -Wl,/subsystem:windows
|
||||
|
||||
$(BIN)/SDL/sameboy_debugger.exe: $(CORE_OBJECTS) $(SDL_OBJECTS) $(OBJ)/Windows/resources.o
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $^ -o $@ $(LDFLAGS) $(SDL_LDFLAGS) -Wl,/subsystem:console
|
||||
$(CC) $^ -o $@ $(LDFLAGS) $(SDL_LDFLAGS) $(GL_LDFLAGS) -Wl,/subsystem:console
|
||||
|
||||
ifneq ($(USE_WINDRES),)
|
||||
$(OBJ)/%.o: %.rc
|
||||
@ -294,7 +326,7 @@ $(BIN)/tester/sameboy_tester: $(CORE_OBJECTS) $(TESTER_OBJECTS)
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
$(CC) $^ -o $@ $(LDFLAGS)
|
||||
ifeq ($(CONF), release)
|
||||
strip $@
|
||||
$(STRIP) $@
|
||||
endif
|
||||
|
||||
$(BIN)/tester/sameboy_tester.exe: $(CORE_OBJECTS) $(SDL_OBJECTS)
|
||||
@ -345,7 +377,7 @@ $(BIN)/BootROMs/%.bin: BootROMs/%.asm $(OBJ)/BootROMs/SameBoyLogo.pb8
|
||||
-@$(MKDIR) -p $(dir $@)
|
||||
rgbasm -i $(OBJ)/BootROMs/ -i BootROMs/ -o $@.tmp $<
|
||||
rgblink -o $@.tmp2 $@.tmp
|
||||
dd if=$@.tmp2 of=$@ count=1 bs=$(if $(findstring dmg,$@)$(findstring sgb,$@),256,2304)
|
||||
dd if=$@.tmp2 of=$@ count=1 bs=$(if $(findstring dmg,$@)$(findstring sgb,$@),256,2304) 2> $(NULL)
|
||||
@rm $@.tmp $@.tmp2
|
||||
|
||||
# Libretro Core (uses its own build system)
|
||||
|
@ -47,7 +47,7 @@
|
||||
<key>CFPlugInUnloadFunction</key>
|
||||
<string></string>
|
||||
<key>NSHumanReadableCopyright</key>
|
||||
<string>Copyright © 2015-2019 Lior Halphon</string>
|
||||
<string>Copyright © 2015-2020 Lior Halphon</string>
|
||||
<key>QLNeedsToBeRunInMainThread</key>
|
||||
<false/>
|
||||
<key>QLPreviewHeight</key>
|
||||
|
@ -1,3 +1,3 @@
|
||||
_DeallocQuickLookGeneratorPluginType
|
||||
_QuickLookGeneratorQueryInterface
|
||||
_QuickLookGeneratorPluginFactory
|
||||
_QuickLookGeneratorPluginFactory
|
||||
|
12
SDL/gui.c
12
SDL/gui.c
@ -1,5 +1,5 @@
|
||||
#include <SDL2/SDL.h>
|
||||
#include <OpenDialog/open_dialog.h>
|
||||
#include <SDL.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdio.h>
|
||||
#include <stdint.h>
|
||||
@ -792,6 +792,7 @@ void connect_joypad(void)
|
||||
|
||||
void run_gui(bool is_running)
|
||||
{
|
||||
SDL_ShowCursor(SDL_ENABLE);
|
||||
connect_joypad();
|
||||
|
||||
/* Draw the background screen */
|
||||
@ -1011,6 +1012,15 @@ void run_gui(bool is_running)
|
||||
}
|
||||
|
||||
case SDL_KEYDOWN:
|
||||
if (event.key.keysym.scancode == SDL_SCANCODE_F && event.key.keysym.mod & MODIFIER) {
|
||||
if ((SDL_GetWindowFlags(window) & SDL_WINDOW_FULLSCREEN_DESKTOP) == false) {
|
||||
SDL_SetWindowFullscreen(window, SDL_WINDOW_FULLSCREEN_DESKTOP);
|
||||
}
|
||||
else {
|
||||
SDL_SetWindowFullscreen(window, 0);
|
||||
}
|
||||
update_viewport();
|
||||
}
|
||||
if (event.key.keysym.scancode == SDL_SCANCODE_O) {
|
||||
if (event.key.keysym.mod & MODIFIER) {
|
||||
char *filename = do_open_rom_dialog();
|
||||
|
@ -1,7 +1,7 @@
|
||||
#ifndef gui_h
|
||||
#define gui_h
|
||||
|
||||
#include <SDL2/SDL.h>
|
||||
#include <SDL.h>
|
||||
#include <Core/gb.h>
|
||||
#include <stdbool.h>
|
||||
#include "shader.h"
|
||||
|
17
SDL/main.c
Executable file → Normal file
17
SDL/main.c
Executable file → Normal file
@ -2,7 +2,7 @@
|
||||
#include <stdio.h>
|
||||
#include <signal.h>
|
||||
#include <OpenDialog/open_dialog.h>
|
||||
#include <SDL2/SDL.h>
|
||||
#include <SDL.h>
|
||||
#include <Core/gb.h>
|
||||
#include "utils.h"
|
||||
#include "gui.h"
|
||||
@ -12,6 +12,7 @@
|
||||
#ifndef _WIN32
|
||||
#define AUDIO_FREQUENCY 96000
|
||||
#else
|
||||
#include <Windows.h>
|
||||
/* Windows (well, at least my VM) can't handle 96KHz sound well :( */
|
||||
|
||||
/* felsqualle says: For SDL 2.0.6+ using the WASAPI driver, the highest freq.
|
||||
@ -98,6 +99,7 @@ static void open_menu(void)
|
||||
SDL_PauseAudioDevice(device_id, 1);
|
||||
}
|
||||
run_gui(true);
|
||||
SDL_ShowCursor(SDL_DISABLE);
|
||||
if (audio_playing) {
|
||||
SDL_ClearQueuedAudio(device_id);
|
||||
SDL_PauseAudioDevice(device_id, 0);
|
||||
@ -123,7 +125,7 @@ static void handle_events(GB_gameboy_t *gb)
|
||||
}
|
||||
|
||||
case SDL_WINDOWEVENT: {
|
||||
if (event.window.event == SDL_WINDOWEVENT_RESIZED) {
|
||||
if (event.window.event == SDL_WINDOWEVENT_SIZE_CHANGED) {
|
||||
update_viewport();
|
||||
}
|
||||
break;
|
||||
@ -273,6 +275,7 @@ static void handle_events(GB_gameboy_t *gb)
|
||||
else {
|
||||
SDL_SetWindowFullscreen(window, 0);
|
||||
}
|
||||
update_viewport();
|
||||
}
|
||||
break;
|
||||
|
||||
@ -406,14 +409,12 @@ static bool handle_pending_command(void)
|
||||
return false;
|
||||
}
|
||||
|
||||
case GB_SDL_RESET_COMMAND:
|
||||
GB_save_battery(&gb, battery_save_path_ptr);
|
||||
return true;
|
||||
|
||||
case GB_SDL_NO_COMMAND:
|
||||
return false;
|
||||
|
||||
case GB_SDL_RESET_COMMAND:
|
||||
case GB_SDL_NEW_FILE_COMMAND:
|
||||
GB_save_battery(&gb, battery_save_path_ptr);
|
||||
return true;
|
||||
|
||||
case GB_SDL_QUIT_COMMAND:
|
||||
@ -425,6 +426,7 @@ static bool handle_pending_command(void)
|
||||
|
||||
static void run(void)
|
||||
{
|
||||
SDL_ShowCursor(SDL_DISABLE);
|
||||
GB_model_t model;
|
||||
pending_command = GB_SDL_NO_COMMAND;
|
||||
restart:
|
||||
@ -550,6 +552,9 @@ static bool get_arg_flag(const char *flag, int *argc, char **argv)
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
SetProcessDPIAware();
|
||||
#endif
|
||||
#define str(x) #x
|
||||
#define xstr(x) str(x)
|
||||
fprintf(stderr, "SameBoy v" xstr(VERSION) "\n");
|
||||
|
@ -1,5 +1,5 @@
|
||||
#define GL_GLEXT_PROTOTYPES
|
||||
#include <SDL2/SDL_opengl.h>
|
||||
#include <SDL_opengl.h>
|
||||
|
||||
#ifndef __APPLE__
|
||||
#define GL_COMPAT_NAME(func) gl_compat_##func
|
||||
|
@ -2,8 +2,8 @@
|
||||
#define opengl_compat_h
|
||||
|
||||
#define GL_GLEXT_PROTOTYPES
|
||||
#include <SDL2/SDL_opengl.h>
|
||||
#include <SDL2/SDL_video.h>
|
||||
#include <SDL_opengl.h>
|
||||
#include <SDL_video.h>
|
||||
|
||||
#ifndef __APPLE__
|
||||
#define GL_COMPAT_NAME(func) gl_compat_##func
|
||||
|
@ -1,4 +1,4 @@
|
||||
#include <SDL2/SDL.h>
|
||||
#include <SDL.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include "utils.h"
|
||||
|
Binary file not shown.
@ -92,6 +92,7 @@ static unsigned emulated_devices = 1;
|
||||
static bool initialized = false;
|
||||
static unsigned screen_layout = 0;
|
||||
static unsigned audio_out = 0;
|
||||
static unsigned sgb_border = 1;
|
||||
|
||||
static bool geometry_updated = false;
|
||||
static bool link_cable_emulation = false;
|
||||
@ -209,6 +210,7 @@ static const struct retro_variable vars_single[] = {
|
||||
{ "sameboy_color_correction_mode", "Color correction; off|correct curves|emulate hardware|preserve brightness" },
|
||||
{ "sameboy_high_pass_filter_mode", "High-pass filter; off|accurate|remove dc offset" },
|
||||
{ "sameboy_model", "Emulated model; Auto|Game Boy|Game Boy Color|Game Boy Advance|Super Game Boy|Super Game Boy 2" },
|
||||
{ "sameboy_border", "Super Game Boy border; enabled|disabled" },
|
||||
{ NULL }
|
||||
};
|
||||
|
||||
@ -430,21 +432,20 @@ static void init_for_current_model(unsigned id)
|
||||
descs[7].len = 0x4000;
|
||||
descs[7].flags = RETRO_MEMDESC_CONST;
|
||||
|
||||
descs[8].ptr = GB_get_direct_access(&gameboy[i], GB_DIRECT_ACCESS_OAM, &size, &bank);
|
||||
descs[8].start = 0xFE00;
|
||||
descs[8].select = 0xFFFFFF00;
|
||||
descs[8].len = 0x00A0;
|
||||
descs[8].ptr = GB_get_direct_access(&gameboy[i], GB_DIRECT_ACCESS_OAM, &size, &bank);
|
||||
descs[8].start = 0xFE00;
|
||||
descs[8].len = 0x00A0;
|
||||
descs[8].select= 0xFFFFFF00;
|
||||
|
||||
descs[9].ptr = descs[2].ptr + 0x2000; /* GBC RAM bank 2 */
|
||||
descs[9].start = 0x10000;
|
||||
descs[9].select = 0xFFFF0000;
|
||||
descs[9].len = GB_is_cgb(&gameboy[i]) ? 0x6000 : 0; /* 0x1000 per bank (2-7), unmapped on GB */
|
||||
descs[9].ptr = descs[2].ptr + 0x2000; /* GBC RAM bank 2 */
|
||||
descs[9].start = 0x10000;
|
||||
descs[9].len = GB_is_cgb(&gameboy[i]) ? 0x6000 : 0; /* 0x1000 per bank (2-7), unmapped on GB */
|
||||
descs[9].select= 0xFFFF0000;
|
||||
|
||||
descs[10].ptr = descs[8].ptr;
|
||||
descs[10].offset = 0x100;
|
||||
descs[10].start = 0xFF00;
|
||||
descs[10].select = 0xFFFFFF00;
|
||||
descs[10].len = 0x0080;
|
||||
descs[10].ptr = GB_get_direct_access(&gameboy[i], GB_DIRECT_ACCESS_IO, &size, &bank);
|
||||
descs[10].start = 0xFF00;
|
||||
descs[10].len = 0x0080;
|
||||
descs[10].select= 0xFFFFFF00;
|
||||
|
||||
struct retro_memory_map mmaps;
|
||||
mmaps.descriptors = descs;
|
||||
@ -493,7 +494,7 @@ static void check_variables()
|
||||
{
|
||||
var.key = "sameboy_color_correction_mode";
|
||||
var.value = NULL;
|
||||
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value && GB_is_cgb(&gameboy[0]))
|
||||
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value)
|
||||
{
|
||||
if (strcmp(var.value, "off") == 0)
|
||||
GB_set_color_correction_mode(&gameboy[0], GB_COLOR_CORRECTION_DISABLED);
|
||||
@ -542,12 +543,22 @@ static void check_variables()
|
||||
init_for_current_model(0);
|
||||
}
|
||||
}
|
||||
|
||||
var.key = "sameboy_border";
|
||||
var.value = NULL;
|
||||
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value)
|
||||
{
|
||||
if (strcmp(var.value, "enabled") == 0)
|
||||
sgb_border = 1;
|
||||
else if (strcmp(var.value, "disabled") == 0)
|
||||
sgb_border = 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
var.key = "sameboy_color_correction_mode_1";
|
||||
var.value = NULL;
|
||||
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value && GB_is_cgb(&gameboy[0]))
|
||||
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value)
|
||||
{
|
||||
if (strcmp(var.value, "off") == 0)
|
||||
GB_set_color_correction_mode(&gameboy[0], GB_COLOR_CORRECTION_DISABLED);
|
||||
@ -561,7 +572,7 @@ static void check_variables()
|
||||
|
||||
var.key = "sameboy_color_correction_mode_2";
|
||||
var.value = NULL;
|
||||
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value && GB_is_cgb(&gameboy[1]))
|
||||
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value)
|
||||
{
|
||||
if (strcmp(var.value, "off") == 0)
|
||||
GB_set_color_correction_mode(&gameboy[1], GB_COLOR_CORRECTION_DISABLED);
|
||||
@ -887,8 +898,15 @@ void retro_run(void)
|
||||
}
|
||||
else
|
||||
{
|
||||
if (model[0] == MODEL_SGB || model[0] == MODEL_SGB2)
|
||||
video_cb(frame_buf, SGB_VIDEO_WIDTH, SGB_VIDEO_HEIGHT, SGB_VIDEO_WIDTH * sizeof(uint32_t));
|
||||
if (model[0] == MODEL_SGB || model[0] == MODEL_SGB2) {
|
||||
if (sgb_border == 1)
|
||||
video_cb(frame_buf, SGB_VIDEO_WIDTH, SGB_VIDEO_HEIGHT, SGB_VIDEO_WIDTH * sizeof(uint32_t));
|
||||
else {
|
||||
int crop = SGB_VIDEO_WIDTH * ((SGB_VIDEO_HEIGHT - VIDEO_HEIGHT) / 2) + ((SGB_VIDEO_WIDTH - VIDEO_WIDTH) / 2);
|
||||
|
||||
video_cb(frame_buf + crop, VIDEO_WIDTH, VIDEO_HEIGHT, SGB_VIDEO_WIDTH * sizeof(uint32_t));
|
||||
}
|
||||
}
|
||||
else
|
||||
video_cb(frame_buf, VIDEO_WIDTH, VIDEO_HEIGHT, VIDEO_WIDTH * sizeof(uint32_t));
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user