mirror of
https://github.com/Mercury-Language/mercury.git
synced 2026-04-17 10:23:46 +00:00
Estimated hours taken: 200
Major changes to bytecode interpreter.
Beginnings of native code integration
bytecode/bytecode.c:
bytecode/bytecode.h:
bytecode/dict.c:
bytecode/dict.h:
bytecode/disasm.c:
bytecode/disasm.h:
bytecode/machine.c:
bytecode/machine.h:
bytecode/mbi_main.c:
bytecode/mdb.m:
bytecode/mem.c:
bytecode/mem.h:
bytecode/slist.c:
bytecode/slist.h:
bytecode/template.c:
bytecode/template.h:
bytecode/util.c:
bytecode/util.h:
Removed. These are all the old bytecode files from
before I started. Any parts that were useful have already
been salvaged and used in the new interpreter.
bytecode/*:
Added MB_Bytecode_Addr and MB_Native_Addr types to remove abiguity
as to what type of code an instruction pointer points to, and
provide compiler help for erroneously mixing pointer types.
bytecode/Mmakefile:
bytecode/Mmake.params:
Makefile for test bytecode program. Note that any library
functions that are called from bytecode must be compiled
with trace information. (So their entry labels can be
looked up)
bytecode/mb_basetypes.h:
Added. Contains basic type definitions.
bytecode/mb_bytecode.c:
bytecode/mb_bytecode.h:
Better error messages.
Changed var_lists to direct pointers rather than
lookups through data stacks (much simpler but stop you
using realloc() on the bytecode argument data)
Label addresses are computed at module load time rather
than being looked up each jump
Added endof_negation_goal
Temporary stack slot numbers are translated to variable
numbers (now there is no distinction between temps & vars)
MB_read_cstring return value convention changed (see comments
for how to now free the returned memory)
Added distinction between functions and predicates
Added enter_else
Code addresses are all pointers rather than simple ints
Added MB_Code_Addr type for pred_const and call instructions
bytecode/mb_disasm.c:
bytecode/mb_disasm.h:
Added endof_negation_goal & enter_else
Output strings are now easier to read
MB_listing does not display anything for invalid addresses
MB_listing takes line length argument
bytecode/mb_interface.c:
bytecode/mb_interface.h:
bytecode/mb_interface_stub.m:
Interfacing between native/bytecode
bytecode/mb_machine.c:
bytecode/mb_machine.h:
bytecode/mb_machine_def.h:
Large sections of code branched off into mb_module.?
Most instructions completed, but not integrated with native
code.
Most of mb_machine_def has been removed as the native
code functions provide the same functionality.
bytecode/mb_machine_show.c:
bytecode/mb_machine_show.h:
Completely changed. Less information now as a lot of what
was being displayed before cannot be determined as easily
now that it is stored in the mercury runtime.
bytecode/mb_mem.c:
bytecode/mb_mem.h:
Added routines for garbage collected memory
bytecode/mb_module.c:
bytecode/mb_module.h:
Loading & accessing bytecode. Argument data indexes & id are now
stored in a single word. (see MB_BCID_xxx macros).
Call & label addresses are now calculated at load time.
bytecode/mb_stack.c:
bytecode/mb_stack.h:
Added options for garbage collection of MB_Stack memory
bytecode/mb_util.c:
bytecode/mb_util.h:
Miscellaneous string functions added and SAY() for debugging
bytecode/simple01.m:
Added. Simple test program. (replace with whatever
program is being tested at the time).
190 lines
4.3 KiB
C
190 lines
4.3 KiB
C
|
|
/*
|
|
** Copyright (C) 2000-2001 The University of Melbourne.
|
|
** This file may only be copied under the terms of the GNU Library General
|
|
** Public License - see the file COPYING.LIB in the Mercury distribution.
|
|
**
|
|
*/
|
|
|
|
|
|
#include "mercury_imp.h"
|
|
#include "mercury_regs.h"
|
|
#include "mercury_trace.h"
|
|
#include "mercury_trace_tables.h"
|
|
|
|
#include "mb_interface.h"
|
|
#include "mb_module.h"
|
|
#include "mb_machine.h"
|
|
|
|
/* Exported definitions */
|
|
|
|
/* Local declarations */
|
|
|
|
/* Implementation */
|
|
|
|
MR_declare_entry(MB_native_return_det_stub);
|
|
|
|
MB_Native_Addr
|
|
MB_native_get_return_det(void)
|
|
{
|
|
return (MB_Native_Addr) MR_ENTRY(MB_native_return_det_stub);
|
|
}
|
|
|
|
|
|
/* Search for the native code address of a procedure */
|
|
MB_Native_Addr
|
|
MB_code_find_proc_native(MB_CString_Const module, MB_CString_Const pred,
|
|
MB_Word proc, MB_Word arity, MB_Bool is_func)
|
|
{
|
|
MR_Matches_Info matches;
|
|
MR_Proc_Spec spec;
|
|
|
|
MR_register_all_modules_and_procs(stderr, TRUE);
|
|
MB_SAY("\n");
|
|
|
|
spec.MR_proc_module = module;
|
|
spec.MR_proc_name = pred;
|
|
spec.MR_proc_arity = arity;
|
|
spec.MR_proc_mode = proc;
|
|
spec.MR_proc_pf = (is_func) ? MR_FUNCTION : MR_PREDICATE;
|
|
|
|
MB_SAY("Looking for procedures .... ");
|
|
matches = MR_search_for_matching_procedures(&spec);
|
|
|
|
{
|
|
MB_Word i;
|
|
for (i = 0; i < matches.match_proc_next; i++) {
|
|
MB_SAY("Match %d: %s %s__%s/%d (%d)",
|
|
i,
|
|
(matches.match_procs[i]
|
|
->MR_sle_proc_id.MR_proc_user
|
|
.MR_user_pred_or_func == MR_PREDICATE) ?
|
|
"pred" : "func",
|
|
matches.match_procs[i]
|
|
->MR_sle_proc_id.MR_proc_user
|
|
.MR_user_def_module,
|
|
matches.match_procs[i]
|
|
->MR_sle_proc_id.MR_proc_user
|
|
.MR_user_name,
|
|
matches.match_procs[i]
|
|
->MR_sle_proc_id.MR_proc_user
|
|
.MR_user_arity,
|
|
matches.match_procs[i]
|
|
->MR_sle_proc_id.MR_proc_user
|
|
.MR_user_mode
|
|
);
|
|
}
|
|
}
|
|
|
|
switch (matches.match_proc_next) {
|
|
case 0:
|
|
return NULL;
|
|
case 1:
|
|
{
|
|
MB_Native_Addr addr = (MB_Native_Addr)
|
|
matches.match_procs[0]->
|
|
MR_sle_traversal.MR_trav_code_addr;
|
|
MB_SAY("Adr %08x", addr);
|
|
}
|
|
return (MB_Native_Addr)matches.match_procs[0]->
|
|
MR_sle_traversal.MR_trav_code_addr;
|
|
default:
|
|
MB_fatal("More than one native code entry found!");
|
|
return NULL;
|
|
}
|
|
}
|
|
|
|
/*
|
|
** A native code procedure wishes to call a deterministic bytecode procedure
|
|
*/
|
|
|
|
/*
|
|
** Needed to instantiate MB_Machine_State. Not #included above because nothing
|
|
** else in this module should need to know what is inside an MB_Machine_State
|
|
*/
|
|
#include "mb_machine_def.h"
|
|
|
|
MB_Native_Addr
|
|
MB_bytecode_call_entry(MB_Call *bytecode_call)
|
|
{
|
|
|
|
MB_Native_Addr native_ip;
|
|
MB_Bytecode_Addr bc_ip;
|
|
MB_SAY("Det stack is at %08x", MB_sp);
|
|
|
|
MB_SAY("\n\nHello from bytecode_entry_det");
|
|
|
|
if ((void *) bytecode_call->cached_ip == NULL) {
|
|
bc_ip = MB_code_find_proc(bytecode_call->module_name,
|
|
bytecode_call->pred_name,
|
|
bytecode_call->proc_num,
|
|
bytecode_call->arity,
|
|
bytecode_call->is_func);
|
|
} else {
|
|
bc_ip = bytecode_call->cached_ip;
|
|
}
|
|
if (bc_ip == MB_CODE_INVALID_ADR) {
|
|
MB_util_error("Attempting to call bytecode %s %s__%s/%d (%d):",
|
|
bytecode_call->is_func ? "func" : "pred",
|
|
bytecode_call->module_name,
|
|
bytecode_call->pred_name,
|
|
bytecode_call->arity,
|
|
bytecode_call->proc_num);
|
|
MB_fatal("Unable to find procedure\n"
|
|
"(Is the native code and the bytecode consistent?)");
|
|
}
|
|
|
|
MB_SAY(" bytecode addr %08x", bc_ip);
|
|
|
|
{
|
|
/* Create a new machine and start executing */
|
|
MB_Machine_State ms;
|
|
MB_machine_create(&ms, bc_ip, NULL);
|
|
|
|
MB_SAY("ZZZ ENTERING BYTECODE");
|
|
MB_show_state(&ms, stderr);
|
|
|
|
native_ip = MB_machine_exec(&ms);
|
|
|
|
MB_SAY("ZZZ RETURNING TO NATIVE1");
|
|
MB_show_state(&ms, stderr);
|
|
}
|
|
|
|
return native_ip;
|
|
}
|
|
|
|
/*
|
|
** This is the reentry point after a det bytecode procedure has called
|
|
** native code. See mb_interface.h for a description of how this occurs
|
|
*/
|
|
MB_Native_Addr
|
|
MB_bytecode_return_det(void)
|
|
{
|
|
/* Get the bytecode reentry address */
|
|
MB_Bytecode_Addr ip = (MB_Bytecode_Addr)
|
|
MB_stackitem(MB_DETFRAME_INTERFACE_BC_SUCCIP);
|
|
/* Get the initial stack frame */
|
|
MB_Word *initial_frame = (MB_Word *)
|
|
MB_stackitem(MB_DETFRAME_INTERFACE_INITIAL_FRAME);
|
|
|
|
MB_Native_Addr ret_ip;
|
|
|
|
MB_Machine_State ms;
|
|
|
|
MB_decr_sp(MB_DETFRAME_INTERFACE_SIZE);
|
|
|
|
MB_machine_create(&ms, ip, initial_frame);
|
|
|
|
MB_SAY("ZZZ RETURNING TO BYTECODE");
|
|
MB_show_state(&ms, stderr);
|
|
|
|
ret_ip = MB_machine_exec(&ms);
|
|
|
|
MB_SAY("ZZZ RETURNING TO NATIVE2");
|
|
MB_show_state(&ms, stderr);
|
|
|
|
return ret_ip;
|
|
|
|
}
|
|
|