mirror of
https://github.com/kanjitalk755/macemu.git
synced 2025-01-21 00:31:50 +00:00
[Michael Schmitt]
SheepShaver includes the C errno string in many error messages. One case is when it calls the memory allocation routines in the Basilisk II vm_alloc.cpp program. This works when the memory allocation routine uses functions that set errno (such as mmap or malloc). For example, running SheepShaver on a Linux hosts produces meaningful error messages. The problem is that when run on an OS X host, the memory allocation uses Mach routines such as vm_allocate, which do not set errno. So when SheepShaver reported the error, it used a stale value of errno, which happened to be 17. The result was an extremely misleading error message: "Cannot map RAM: File already exists". The fix is to change vm_alloc so that it translates Mac return codes into POSIX errno values. It also initializes errno to 0 at the start of the memory allocation routine, so that no matter what path it takes, it won't return a stale value.
This commit is contained in:
parent
fbef7bcf22
commit
c6d88f213c
@ -32,6 +32,7 @@
|
||||
#include <windows.h>
|
||||
#endif
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
@ -151,6 +152,24 @@ static int translate_prot_flags(int prot_flags)
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Translate Mach return codes to POSIX errno values. */
|
||||
#ifdef HAVE_MACH_VM
|
||||
static int vm_error(kern_return_t ret_code)
|
||||
{
|
||||
switch (ret_code) {
|
||||
case KERN_SUCCESS:
|
||||
return 0;
|
||||
case KERN_INVALID_ADDRESS:
|
||||
case KERN_NO_SPACE:
|
||||
return ENOMEM;
|
||||
case KERN_PROTECTION_FAILURE:
|
||||
return EACCES;
|
||||
default:
|
||||
return EINVAL;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Initialize the VM system. Returns 0 if successful, -1 for errors. */
|
||||
|
||||
int vm_init(void)
|
||||
@ -186,6 +205,8 @@ void vm_exit(void)
|
||||
void * vm_acquire(size_t size, int options)
|
||||
{
|
||||
void * addr;
|
||||
|
||||
errno = 0;
|
||||
|
||||
// VM_MAP_FIXED are to be used with vm_acquire_fixed() only
|
||||
if (options & VM_MAP_FIXED)
|
||||
@ -198,8 +219,11 @@ void * vm_acquire(size_t size, int options)
|
||||
|
||||
#ifdef HAVE_MACH_VM
|
||||
// vm_allocate() returns a zero-filled memory region
|
||||
if (vm_allocate(mach_task_self(), (vm_address_t *)&addr, size, TRUE) != KERN_SUCCESS)
|
||||
kern_return_t ret_code = vm_allocate(mach_task_self(), (vm_address_t *)&addr, size, TRUE);
|
||||
if (ret_code != KERN_SUCCESS) {
|
||||
errno = vm_error(ret_code);
|
||||
return VM_MAP_FAILED;
|
||||
}
|
||||
#else
|
||||
#ifdef HAVE_MMAP_VM
|
||||
int fd = zero_fd;
|
||||
@ -244,6 +268,8 @@ void * vm_acquire(size_t size, int options)
|
||||
|
||||
int vm_acquire_fixed(void * addr, size_t size, int options)
|
||||
{
|
||||
errno = 0;
|
||||
|
||||
// Fixed mappings are required to be private
|
||||
if (options & VM_MAP_SHARED)
|
||||
return -1;
|
||||
@ -255,8 +281,11 @@ int vm_acquire_fixed(void * addr, size_t size, int options)
|
||||
|
||||
#ifdef HAVE_MACH_VM
|
||||
// vm_allocate() returns a zero-filled memory region
|
||||
if (vm_allocate(mach_task_self(), (vm_address_t *)&addr, size, 0) != KERN_SUCCESS)
|
||||
kern_return_t ret_code = vm_allocate(mach_task_self(), (vm_address_t *)&addr, size, 0);
|
||||
if (ret_code != KERN_SUCCESS) {
|
||||
errno = vm_error(ret_code);
|
||||
return -1;
|
||||
}
|
||||
#else
|
||||
#ifdef HAVE_MMAP_VM
|
||||
int fd = zero_fd;
|
||||
|
Loading…
x
Reference in New Issue
Block a user