uwx_env.c revision 256281
1264790Sbapt/* 2264790SbaptCopyright (c) 2003-2006 Hewlett-Packard Development Company, L.P. 3272955SrodrigcPermission is hereby granted, free of charge, to any person 4264790Sbaptobtaining a copy of this software and associated documentation 5264790Sbaptfiles (the "Software"), to deal in the Software without 6264790Sbaptrestriction, including without limitation the rights to use, 7264790Sbaptcopy, modify, merge, publish, distribute, sublicense, and/or sell 8264790Sbaptcopies of the Software, and to permit persons to whom the 9264790SbaptSoftware is furnished to do so, subject to the following 10264790Sbaptconditions: 11264790Sbapt 12264790SbaptThe above copyright notice and this permission notice shall be 13264790Sbaptincluded in all copies or substantial portions of the Software. 14264790Sbapt 15264790SbaptTHE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 16264790SbaptEXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES 17264790SbaptOF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 18264790SbaptNONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT 19264790SbaptHOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, 20264790SbaptWHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 21264790SbaptFROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 22264790SbaptOTHER DEALINGS IN THE SOFTWARE. 23264790Sbapt*/ 24264790Sbapt 25264790Sbapt#ifndef _KERNEL 26264790Sbapt#include <stdlib.h> 27264790Sbapt#endif 28264790Sbapt 29264790Sbapt#include "uwx_env.h" 30264790Sbapt#include "uwx_scoreboard.h" 31264790Sbapt#include "uwx_str.h" 32264790Sbapt#include "uwx_trace.h" 33264790Sbapt 34264790Sbapt#ifdef _KERNEL 35264790Sbaptstatic struct uwx_env uwx_env; 36264790Sbapt#define free(p) /* nullified */ 37264790Sbapt#define malloc(sz) ((sz == sizeof(uwx_env)) ? &uwx_env : NULL) 38264790Sbapt#endif 39264790Sbapt 40264790Sbaptalloc_cb uwx_allocate_cb = 0; 41264790Sbaptfree_cb uwx_free_cb = 0; 42264790Sbapt 43264790Sbaptint uwx_register_alloc_cb(alloc_cb alloc, free_cb free) 44264790Sbapt{ 45264790Sbapt uwx_allocate_cb = alloc; 46264790Sbapt uwx_free_cb = free; 47264790Sbapt return UWX_OK; 48264790Sbapt} 49264790Sbapt 50264790Sbaptint uwx_init_history(struct uwx_env *env) 51264790Sbapt{ 52264790Sbapt int i; 53264790Sbapt 54264790Sbapt if (env == 0) 55264790Sbapt return UWX_ERR_NOENV; 56264790Sbapt 57264790Sbapt for (i = 0; i < NSPECIALREG; i++) 58264790Sbapt env->history.special[i] = UWX_DISP_REG(i);; 59264790Sbapt for (i = 0; i < NPRESERVEDGR; i++) 60264790Sbapt env->history.gr[i] = UWX_DISP_REG(UWX_REG_GR(4+i)); 61264790Sbapt for (i = 0; i < NPRESERVEDBR; i++) 62264790Sbapt env->history.br[i] = UWX_DISP_REG(UWX_REG_BR(1+i)); 63264790Sbapt for (i = 0; i < 4; i++) 64264790Sbapt env->history.fr[i] = UWX_DISP_REG(UWX_REG_FR(2+i)); 65264790Sbapt for ( ; i < NPRESERVEDFR; i++) 66264790Sbapt env->history.fr[i] = UWX_DISP_REG(UWX_REG_FR(12+i)); 67264790Sbapt 68264790Sbapt return UWX_OK; 69264790Sbapt} 70264790Sbapt 71264790Sbaptint uwx_init_env(struct uwx_env *env, size_t total_size) 72264790Sbapt{ 73264790Sbapt int i; 74264790Sbapt struct uwx_str_pool *str_pool; 75264790Sbapt struct uwx_scoreboard *scoreboards; 76264790Sbapt 77264790Sbapt str_pool = (struct uwx_str_pool *)(env + 1); 78264790Sbapt scoreboards = (struct uwx_scoreboard *)(str_pool + 1); 79264790Sbapt 80264790Sbapt if (sizeof(struct uwx_env) + sizeof(struct uwx_str_pool) > total_size) 81264790Sbapt return UWX_ERR_NOMEM; 82264790Sbapt total_size -= sizeof(struct uwx_env) + sizeof(struct uwx_str_pool); 83264790Sbapt 84264790Sbapt env->context.valid_regs = 0; 85264790Sbapt env->context.valid_frs = 0; 86264790Sbapt for (i = 0; i < NSPECIALREG; i++) 87264790Sbapt env->context.special[i] = 0; 88264790Sbapt for (i = 0; i < NPRESERVEDGR; i++) 89264790Sbapt env->context.gr[i] = 0; 90264790Sbapt for (i = 0; i < NPRESERVEDBR; i++) 91264790Sbapt env->context.br[i] = 0; 92264790Sbapt for (i = 0; i < NPRESERVEDFR; i++) { 93264790Sbapt env->context.fr[i].part0 = 0; 94264790Sbapt env->context.fr[i].part1 = 0; 95264790Sbapt } 96264790Sbapt env->rstate = 0; 97264790Sbapt env->remapped_ip = 0; 98264790Sbapt env->function_offset = 0; 99264790Sbapt env->ptr_size = DWORDSZ; 100264790Sbapt env->uinfo_hdr = 0; 101264790Sbapt env->uinfo_end = 0; 102264790Sbapt env->code_start = 0; 103264790Sbapt env->text_base = 0; 104264790Sbapt (void)uwx_init_history(env); 105264790Sbapt if (uwx_allocate_cb != NULL) 106264790Sbapt env->allocate_cb = uwx_allocate_cb; 107264790Sbapt else 108264790Sbapt env->allocate_cb = NULL; 109264790Sbapt if (uwx_free_cb != NULL) 110264790Sbapt env->free_cb = uwx_free_cb; 111264790Sbapt else 112264790Sbapt env->free_cb = NULL; 113264790Sbapt env->free_scoreboards = 0; 114264790Sbapt env->used_scoreboards = 0; 115264790Sbapt env->labeled_scoreboards = 0; 116264790Sbapt (void)uwx_init_str_pool(env, str_pool); 117264790Sbapt env->module_name = 0; 118264790Sbapt env->function_name = 0; 119264790Sbapt env->cb_token = 0; 120264790Sbapt env->copyin = 0; 121264790Sbapt env->lookupip = 0; 122264790Sbapt env->remote = 0; 123264790Sbapt env->byte_swap = 0; 124264790Sbapt env->abi_context = 0; 125264790Sbapt env->nsbreg = NSBREG; 126264790Sbapt env->nscoreboards = 0; 127264790Sbapt env->on_heap = 0; 128264790Sbapt env->trace = 0; 129264790Sbapt TRACE_INIT 130264790Sbapt for (i = 0; total_size >= sizeof(struct uwx_scoreboard); i++) { 131264790Sbapt (void) uwx_prealloc_scoreboard(env, &scoreboards[i]); 132264790Sbapt total_size -= sizeof(struct uwx_scoreboard); 133264790Sbapt } 134264790Sbapt return UWX_OK; 135264790Sbapt} 136264790Sbapt 137264790Sbaptint uwx_set_nofr(struct uwx_env *env) 138264790Sbapt{ 139264790Sbapt if (env == 0) 140264790Sbapt return UWX_ERR_NOENV; 141264790Sbapt 142264790Sbapt env->nsbreg = NSBREG_NOFR; 143264790Sbapt return UWX_OK; 144264790Sbapt} 145264790Sbapt 146264790Sbaptstruct uwx_env *uwx_init() 147264790Sbapt{ 148264790Sbapt struct uwx_env *env; 149264790Sbapt size_t total_size; 150264790Sbapt 151264790Sbapt total_size = sizeof(struct uwx_env) + 152264790Sbapt sizeof(struct uwx_str_pool) + 153264790Sbapt NSCOREBOARDS * sizeof(struct uwx_scoreboard); 154264790Sbapt 155264790Sbapt if (uwx_allocate_cb == 0) 156264790Sbapt env = (struct uwx_env *) malloc(total_size); 157264790Sbapt else 158264790Sbapt env = (struct uwx_env *) (*uwx_allocate_cb)(total_size); 159264790Sbapt if (env != 0) { 160264790Sbapt uwx_init_env(env, total_size); 161264790Sbapt env->on_heap = 1; 162264790Sbapt } 163264790Sbapt return env; 164264790Sbapt} 165264790Sbapt 166264790Sbaptint uwx_set_remote(struct uwx_env *env, int is_big_endian_target) 167264790Sbapt{ 168264790Sbapt int is_big_endian_host; 169264790Sbapt char *p; 170264790Sbapt 171264790Sbapt if (env == 0) 172264790Sbapt return UWX_ERR_NOENV; 173264790Sbapt 174264790Sbapt env->remote = 1; 175264790Sbapt 176264790Sbapt is_big_endian_host = 1; 177264790Sbapt p = (char *)&is_big_endian_host; 178264790Sbapt *p = 0; 179264790Sbapt if (is_big_endian_target == is_big_endian_host) 180264790Sbapt env->byte_swap = 0; 181264790Sbapt else 182264790Sbapt env->byte_swap = 1; 183264790Sbapt 184264790Sbapt return UWX_OK; 185264790Sbapt} 186264790Sbapt 187264790Sbaptint uwx_register_callbacks( 188264790Sbapt struct uwx_env *env, 189264790Sbapt intptr_t tok, 190264790Sbapt copyin_cb copyin, 191264790Sbapt lookupip_cb lookupip) 192264790Sbapt{ 193264790Sbapt if (env == 0) 194264790Sbapt return UWX_ERR_NOENV; 195264790Sbapt env->cb_token = tok; 196264790Sbapt env->copyin = copyin; 197264790Sbapt env->lookupip = lookupip; 198272955Srodrigc return UWX_OK; 199272955Srodrigc} 200272955Srodrigc 201272955Srodrigcint uwx_get_abi_context_code(struct uwx_env *env) 202272955Srodrigc{ 203264790Sbapt if (env == 0) 204264790Sbapt return UWX_ERR_NOENV; 205264790Sbapt return env->abi_context; 206264790Sbapt} 207264790Sbapt 208264790Sbaptint uwx_free(struct uwx_env *env) 209264790Sbapt{ 210264790Sbapt if (env != 0) { 211264790Sbapt uwx_free_scoreboards(env); 212264790Sbapt uwx_free_str_pool(env); 213264790Sbapt if (env->on_heap) { 214264790Sbapt if (env->free_cb == 0) 215264790Sbapt free((void *)env); 216264790Sbapt else 217264790Sbapt (*env->free_cb)((void *)env); 218264790Sbapt } 219264790Sbapt } 220264790Sbapt return UWX_OK; 221264790Sbapt} 222264790Sbapt