mirror of
https://github.com/kanjitalk755/macemu.git
synced 2025-01-05 14:32:15 +00:00
Always use vm_acquire* to allocate frame buffers, so that cygwin/x86 version
can have a chance in case VOSF is not profitable (on video mode switches) Improve video mode switches in SheepShaver/SDL, aka avoid crashes on win32 as there is apparently no thread canceleation algorithm used in SDL/win32.
This commit is contained in:
parent
f8cd0231a0
commit
08a3e449d3
@ -56,6 +56,7 @@
|
||||
#include "video.h"
|
||||
#include "video_defs.h"
|
||||
#include "video_blit.h"
|
||||
#include "vm_alloc.h"
|
||||
|
||||
#define DEBUG 0
|
||||
#include "debug.h"
|
||||
@ -96,6 +97,8 @@ static uint32 the_buffer_size; // Size of allocated the_buffer
|
||||
static bool redraw_thread_active = false; // Flag: Redraw thread installed
|
||||
static volatile bool redraw_thread_cancel; // Flag: Cancel Redraw thread
|
||||
static SDL_Thread *redraw_thread = NULL; // Redraw thread
|
||||
static volatile bool thread_stop_req = false;
|
||||
static volatile bool thread_stop_ack = false; // Acknowledge for thread_stop_req
|
||||
|
||||
#ifdef ENABLE_VOSF
|
||||
static bool use_vosf = false; // Flag: VOSF enabled
|
||||
@ -144,6 +147,30 @@ static int redraw_func(void *arg);
|
||||
extern void SysMountFirstFloppy(void);
|
||||
|
||||
|
||||
/*
|
||||
* Framebuffer allocation routines
|
||||
*/
|
||||
|
||||
static void *vm_acquire_framebuffer(uint32 size)
|
||||
{
|
||||
#ifdef SHEEPSHAVER
|
||||
#ifdef DIRECT_ADDRESSING_HACK
|
||||
const uint32 FRAME_BUFFER_BASE = 0x61000000;
|
||||
uint8 *fb = Mac2HostAddr(FRAME_BUFFER_BASE);
|
||||
if (vm_acquire_fixed(fb, size) < 0)
|
||||
fb = VM_MAP_FAILED;
|
||||
return fb;
|
||||
#endif
|
||||
#endif
|
||||
return vm_acquire(size);
|
||||
}
|
||||
|
||||
static inline void vm_release_framebuffer(void *fb, uint32 size)
|
||||
{
|
||||
vm_release(fb, size);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* SheepShaver glue
|
||||
*/
|
||||
@ -554,12 +581,15 @@ driver_base::~driver_base()
|
||||
if (s)
|
||||
SDL_FreeSurface(s);
|
||||
|
||||
// the_buffer shall always be mapped through vm_acquire_framebuffer()
|
||||
if (the_buffer != VM_MAP_FAILED) {
|
||||
D(bug(" releasing the_buffer at %p (%d bytes)\n", the_buffer, the_buffer_size));
|
||||
vm_release_framebuffer(the_buffer, the_buffer_size);
|
||||
the_buffer = NULL;
|
||||
}
|
||||
|
||||
// Free frame buffer(s)
|
||||
if (!use_vosf) {
|
||||
if (the_buffer) {
|
||||
free(the_buffer);
|
||||
the_buffer = NULL;
|
||||
}
|
||||
if (the_buffer_copy) {
|
||||
free(the_buffer_copy);
|
||||
the_buffer_copy = NULL;
|
||||
@ -567,12 +597,6 @@ driver_base::~driver_base()
|
||||
}
|
||||
#ifdef ENABLE_VOSF
|
||||
else {
|
||||
// the_buffer shall always be mapped through vm_acquire() so that we can vm_protect() it at will
|
||||
if (the_buffer != VM_MAP_FAILED) {
|
||||
D(bug(" releasing the_buffer at %p (%d bytes)\n", the_buffer, the_buffer_size));
|
||||
vm_release(the_buffer, the_buffer_size);
|
||||
the_buffer = NULL;
|
||||
}
|
||||
if (the_host_buffer) {
|
||||
D(bug(" freeing the_host_buffer at %p\n", the_host_buffer));
|
||||
free(the_host_buffer);
|
||||
@ -583,6 +607,9 @@ driver_base::~driver_base()
|
||||
free(the_buffer_copy);
|
||||
the_buffer_copy = NULL;
|
||||
}
|
||||
|
||||
// Deinitialize VOSF
|
||||
video_vosf_exit();
|
||||
}
|
||||
#endif
|
||||
}
|
||||
@ -632,7 +659,7 @@ driver_window::driver_window(SDL_monitor_desc &m)
|
||||
// Allocate memory for frame buffer (SIZE is extended to page-boundary)
|
||||
the_host_buffer = (uint8 *)s->pixels;
|
||||
the_buffer_size = page_extend((aligned_height + 2) * s->pitch);
|
||||
the_buffer = (uint8 *)vm_acquire(the_buffer_size);
|
||||
the_buffer = (uint8 *)vm_acquire_framebuffer(the_buffer_size);
|
||||
the_buffer_copy = (uint8 *)malloc(the_buffer_size);
|
||||
D(bug("the_buffer = %p, the_buffer_copy = %p, the_host_buffer = %p\n", the_buffer, the_buffer_copy, the_host_buffer));
|
||||
|
||||
@ -656,7 +683,7 @@ driver_window::driver_window(SDL_monitor_desc &m)
|
||||
// Allocate memory for frame buffer
|
||||
the_buffer_size = (aligned_height + 2) * s->pitch;
|
||||
the_buffer_copy = (uint8 *)calloc(1, the_buffer_size);
|
||||
the_buffer = (uint8 *)calloc(1, the_buffer_size);
|
||||
the_buffer = (uint8 *)vm_acquire_framebuffer(the_buffer_size);
|
||||
D(bug("the_buffer = %p, the_buffer_copy = %p\n", the_buffer, the_buffer_copy));
|
||||
}
|
||||
|
||||
@ -1048,13 +1075,6 @@ void SDL_monitor_desc::video_close(void)
|
||||
UNLOCK_FRAME_BUFFER;
|
||||
D(bug(" frame buffer unlocked\n"));
|
||||
|
||||
#ifdef ENABLE_VOSF
|
||||
if (use_vosf) {
|
||||
// Deinitialize VOSF
|
||||
video_vosf_exit();
|
||||
}
|
||||
#endif
|
||||
|
||||
// Close display
|
||||
delete drv;
|
||||
drv = NULL;
|
||||
@ -1213,8 +1233,11 @@ int16 video_mode_change(VidLocals *csSave, uint32 ParamPtr)
|
||||
csSave->saveData = ReadMacInt32(ParamPtr + csData);
|
||||
csSave->savePage = ReadMacInt16(ParamPtr + csPage);
|
||||
|
||||
// Disable interrupts
|
||||
// Disable interrupts and pause redraw thread
|
||||
DisableInterrupt();
|
||||
thread_stop_ack = false;
|
||||
thread_stop_req = true;
|
||||
while (!thread_stop_ack) ;
|
||||
|
||||
cur_mode = i;
|
||||
monitor_desc *monitor = VideoMonitors[0];
|
||||
@ -1225,7 +1248,8 @@ int16 video_mode_change(VidLocals *csSave, uint32 ParamPtr)
|
||||
csSave->saveData=VModes[cur_mode].viAppleID;/* First mode ... */
|
||||
csSave->saveMode=VModes[cur_mode].viAppleMode;
|
||||
|
||||
// Enable interrupts
|
||||
// Enable interrupts and resume redraw thread
|
||||
thread_stop_req = false;
|
||||
EnableInterrupt();
|
||||
return noErr;
|
||||
}
|
||||
@ -1866,6 +1890,14 @@ static int redraw_func(void *arg)
|
||||
next = GetTicks_usec();
|
||||
ticks++;
|
||||
|
||||
#ifdef SHEEPSHAVER
|
||||
// Pause if requested (during video mode switches)
|
||||
if (thread_stop_req) {
|
||||
thread_stop_ack = true;
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
// Handle SDL events
|
||||
handle_events();
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user