From 5f00cd2e538e02c7662aea25ffd8a3cb17ce924b Mon Sep 17 00:00:00 2001 From: Manoel Trapier Date: Wed, 27 Mar 2013 15:49:29 +0100 Subject: [PATCH] Make a brk/sbrk emulation. Mac OS X seems to have some difficulties with brk/sbrk (maybe with the 4MB heap limit), and replace all the allocation logic will be prone to errors, I'll add a new define and lib to emulate brk/sbrk using more standard allocation methods. By default the heap is 64MB, it should be enough. --- h/missing_proto.h | 16 +++++++ modules/src/sbrk/pmfile | 20 +++++++++ modules/src/sbrk/sbrk_emu.c | 83 +++++++++++++++++++++++++++++++++++++ modules/src/system/break.c | 1 + pmfile | 11 +++-- util/LLgen/pmfile-ack | 2 + util/led/pmfile | 3 +- util/ncgg/pmfile | 3 +- 8 files changed, 134 insertions(+), 5 deletions(-) create mode 100644 modules/src/sbrk/pmfile create mode 100644 modules/src/sbrk/sbrk_emu.c diff --git a/h/missing_proto.h b/h/missing_proto.h index 0f62d5454..3294d989f 100644 --- a/h/missing_proto.h +++ b/h/missing_proto.h @@ -10,4 +10,20 @@ int brk(void * addr); char *mktemp(char *template); #endif +#ifdef EMULATE_BRK +void *sbrk_emu(int increment); +int brk_emu(void * addr); + +#ifdef sbrk +#undef sbrk +#endif +#ifdef brk +#undef brk +#endif + +#define sbrk sbrk_emu +#define brk brk_emu + +#endif + #endif /* H_MISSING_H */ \ No newline at end of file diff --git a/modules/src/sbrk/pmfile b/modules/src/sbrk/pmfile new file mode 100644 index 000000000..8492a1cab --- /dev/null +++ b/modules/src/sbrk/pmfile @@ -0,0 +1,20 @@ +-- $Source$ +-- $State$ + +local d = "modules/src/sbrk/" +lib_sbrk = file (LIBDIR.."libsbrk.a") + +module_sbrk = clibrary { + cfile (d.."sbrk_emu.c"), + + outputs = {"%U%/libsbrk.a"}, + install = { + pm.install(LIBDIR.."libsbrk.a"), + } +} + +-- Revision history +-- $Log$ +-- Revision 1.1 2013/03/27 godzil +-- First version. +-- diff --git a/modules/src/sbrk/sbrk_emu.c b/modules/src/sbrk/sbrk_emu.c new file mode 100644 index 000000000..f70d1fc36 --- /dev/null +++ b/modules/src/sbrk/sbrk_emu.c @@ -0,0 +1,83 @@ +/* + * The Amsterdam Compiler Kit + * See the copyright notice in the ACK home directory, in the file "Copyright". + */ +/* + * sbrk(), brk() emulation based on calloc() + * Based on version from D A Gwyn + * 02-Mar-1990 D A Gwyn + * http://www.linuxmisc.com/10-unix-questions/0875f91c36e18724.htm + */ +#include +#include /* for errno, ENOMEM */ +#if __STDC__ +#include /* for calloc */ +#else +extern char *calloc(); +#endif + +/* Allocate 64MB to brk/sbrk should be enough for such application */ +#ifndef HEAP_SIZE /* with 32-bit ints, 0x200000 is recommended */ +#define HEAP_SIZE 0x4000000 /* size of simulated heap, in bytes */ +#endif +#define BRK_OK 0 +#define BRK_ERR (-1) +#define SBRK_ERR ((void *)-1) /* horrible interface design */ + +static void *bottom = NULL; /* bottom of calloc()ed pseudo-heap */ +static void *brkval = NULL; /* current value of simulated break */ + +int brk_emu( void *endds ) +{ + int offset; + if ( bottom == NULL ) + { + if ( (bottom = calloc( HEAP_SIZE, 1 )) == 0 ) + { + return BRK_ERR; /* unable to set up pseudo-heap */ + } + else + { + brkval = bottom; + } + } + + if ( (offset = endds - bottom) < 0 || offset > HEAP_SIZE ) + { + errno = ENOMEM; + return BRK_ERR; /* attempt to set break out of heap */ + } + else + { + brkval = endds; + return BRK_OK; + } +} + +void *sbrk_emu(int incr) +{ + int offset; + if ( bottom == 0 ) + { + if ( (bottom = (char *)calloc( HEAP_SIZE, 1 )) == 0 ) + { + return SBRK_ERR; /* unable to set up heap */ + } + else + { + brkval = bottom; + } + } + + if ( (offset = (brkval - bottom) + incr) < 0 || offset > HEAP_SIZE ) + { + errno = ENOMEM; + return SBRK_ERR; /* attempt to set break out of heap */ + } + else + { + char *oldbrk = brkval; + brkval += incr; + return oldbrk; + } +} \ No newline at end of file diff --git a/modules/src/system/break.c b/modules/src/system/break.c index 321675496..3ba192e03 100644 --- a/modules/src/system/break.c +++ b/modules/src/system/break.c @@ -6,6 +6,7 @@ #include "system.h" #include +#include char *sys_break(int incr) { diff --git a/pmfile b/pmfile index afba88dd0..6be98e387 100644 --- a/pmfile +++ b/pmfile @@ -19,6 +19,8 @@ CINCLUDES = { include "util/data/pmfile" +include "modules/src/sbrk/pmfile" + include "util/LLgen/pmfile-ack" include "modules/src/alloc/pmfile" @@ -103,7 +105,10 @@ include "plat/nes/pmfile" -- NES default = group { -- Lots of things use LLgen, so we need to build it first. - + + -- Need it before anything else! (even LLgen depends on it) + module_sbrk, + tool_LLgen, -- Some of the dependency management across modules isn't entirely @@ -181,8 +186,8 @@ default = group { -- Build the platforms. platform_pc86, - platform_linux386, - platform_cpm, +-- platform_linux386, +-- platform_cpm, -- platform_nes, } diff --git a/util/LLgen/pmfile-ack b/util/LLgen/pmfile-ack index 7785418ac..481c49f34 100644 --- a/util/LLgen/pmfile-ack +++ b/util/LLgen/pmfile-ack @@ -26,6 +26,8 @@ tool_LLgen = cprogram { cfile (d.."src/Lpars.c"), cfile (d.."src/tokens.c"), + lib_sbrk, + outputs = {"%U%/LLgen"}, install = pm.install("%TOOLDIR%LLgen") } diff --git a/util/led/pmfile b/util/led/pmfile index 1704c077a..5ca7b02d8 100644 --- a/util/led/pmfile +++ b/util/led/pmfile @@ -20,7 +20,8 @@ tool_led = cprogram { lib_string, lib_object, - + lib_sbrk, + outputs = {"%U%/led"}, install = { -- FIXME lib.bin in next line needs removing --- pm bug? diff --git a/util/ncgg/pmfile b/util/ncgg/pmfile index 559c865f2..028a21a5b 100644 --- a/util/ncgg/pmfile +++ b/util/ncgg/pmfile @@ -51,7 +51,8 @@ tool_ncgg = cprogram { }, lib_em_data, - + lib_sbrk, + outputs = {"%U%-ncgg"}, install = pm.install(TOOLDIR.."ncgg") } -- 2.34.1